]> git.mdlowis.com Git - proto/rc.git/commitdiff
Initial commit
authorMichael D. Lowis <mike.lowis@gentex.com>
Mon, 13 Mar 2017 13:56:46 +0000 (09:56 -0400)
committerMichael D. Lowis <mike.lowis@gentex.com>
Mon, 13 Mar 2017 13:56:46 +0000 (09:56 -0400)
77 files changed:
AUTHORS [new file with mode: 0644]
COPYING [new file with mode: 0644]
ChangeLog [new file with mode: 0644]
EXAMPLES [new file with mode: 0644]
INSTALL [new file with mode: 0644]
Makefile.am [new file with mode: 0644]
Makefile.in [new file with mode: 0644]
MyMakefile [new file with mode: 0644]
NEWS [new file with mode: 0644]
README [new file with mode: 0644]
acinclude.m4 [new file with mode: 0644]
aclocal.m4 [new file with mode: 0644]
addon.c [new file with mode: 0644]
addon.h [new file with mode: 0644]
builtins.c [new file with mode: 0644]
compile [new file with mode: 0755]
config.h.in [new file with mode: 0644]
configure [new file with mode: 0755]
configure.ac [new file with mode: 0644]
depcomp [new file with mode: 0755]
edit-edit.c [new file with mode: 0644]
edit-editline.c [new file with mode: 0644]
edit-null.c [new file with mode: 0644]
edit-readline.c [new file with mode: 0644]
edit-vrl.c [new file with mode: 0644]
edit.h [new file with mode: 0644]
except.c [new file with mode: 0644]
exec.c [new file with mode: 0644]
execve.c [new file with mode: 0644]
fn.c [new file with mode: 0644]
footobar.c [new file with mode: 0644]
getgroups.h [new file with mode: 0644]
getopt.c [new file with mode: 0644]
glob.c [new file with mode: 0644]
glom.c [new file with mode: 0644]
hash.c [new file with mode: 0644]
heredoc.c [new file with mode: 0644]
history.1 [new file with mode: 0644]
history.c [new file with mode: 0644]
input.c [new file with mode: 0644]
input.h [new file with mode: 0644]
install-sh [new file with mode: 0755]
jbwrap.h [new file with mode: 0644]
lex.c [new file with mode: 0644]
list.c [new file with mode: 0644]
main.c [new file with mode: 0644]
make.log [new file with mode: 0644]
match.c [new file with mode: 0644]
missing [new file with mode: 0755]
mkinstalldirs [new file with mode: 0755]
mksignal.c [new file with mode: 0644]
mkstatval.c [new file with mode: 0644]
nalloc.c [new file with mode: 0644]
open.c [new file with mode: 0644]
parse.c [new file with mode: 0644]
parse.h [new file with mode: 0644]
parse.y [new file with mode: 0644]
print.c [new file with mode: 0644]
proto.h [new file with mode: 0644]
rc.1 [new file with mode: 0644]
rc.h [new file with mode: 0644]
redir.c [new file with mode: 0644]
rlimit.h [new file with mode: 0644]
signal.c [new file with mode: 0644]
stat.h [new file with mode: 0644]
status.c [new file with mode: 0644]
system-bsd.c [new file with mode: 0644]
system.c [new file with mode: 0644]
tree.c [new file with mode: 0644]
trip.rc [new file with mode: 0644]
tripping.c [new file with mode: 0644]
utils.c [new file with mode: 0644]
var.c [new file with mode: 0644]
wait.c [new file with mode: 0644]
wait.h [new file with mode: 0644]
walk.c [new file with mode: 0644]
which.c [new file with mode: 0644]

diff --git a/AUTHORS b/AUTHORS
new file mode 100644 (file)
index 0000000..d231e38
--- /dev/null
+++ b/AUTHORS
@@ -0,0 +1,40 @@
+The current maintainer of rc is Toby Goodwin <toby@paccrat.org>. Please
+send all bug reports to him, or via github:
+
+  https://github.com/rakitzis/rc/issues
+
+This shell was written by me, Byron Rakitzis, but kudos go to Paul Haahr
+for letting me know what a shell should do and for contributing certain
+bits and pieces to rc (notably the limits code, print.c, most of which.c
+and the backquote redirection code), and to Hugh Redelmeier for running
+rc through his fussy ANSI compiler and thereby provoking interesting
+discussions about portability, and also for providing many valuable
+suggestions for improving rc's code in general. Finally, many thanks go
+to David Sanderson, for reworking the man page to format well with
+troff, and for providing many suggestions both for rc and its man page.
+
+Thanks to Boyd Roberts for the original history.c, and to Hugh again for
+re-working parts of that code.
+
+Of course, without Tom Duff's design of the original rc, I could not
+have written this shell (though I probably would have written *a*
+shell). Almost all of the features, with minor exceptions, have been
+implemented as described in the Unix v10 manuals. Hats off to td for
+designing a C-like, minimal but very useful shell.
+
+Tom Duff has kindly given permission for the paper he wrote for UKUUG to
+be distributed with this version of rc (called "plan9.ps" in the same
+FTP or HTTP directory as the shell). Please read this paper bearing in
+mind that it describes a program that was written at AT&T and that the
+version of rc presented here differs in some respects.
+
+Toby would like to thank these people for their contributions since he
+took over maintenance of rc. Aharon Robbins, Arvid Requate, Bengt
+Kleberg, Brynjulv Hauksson, Byron Rakitzis, Callum Gibson, Chris
+Siebenmann, Christian Neukirchen, Dale Scheetz, Dan Moniz, David Luyer,
+David Swasey, Decklin Foster, Donn Cave, Erik Quanstrom, Gary Carvell,
+Gerry Tomlinson, Gert-Jan Vons, Ian Lance Taylor, Jakub Wilk, Jeremy
+Fitzhardinge, Marc Moorcroft, Mark H Wilkinson, Mark K Gardner, Raymond
+Venneker, Rich $alz, Rob Savoye, Scott Schwartz, Stefan Dalibor, Steve
+Simon, Thomas Nordin, Tom Culliton, Tom Tromey, Vincent Broman, Wolfgang
+Zekoll.
diff --git a/COPYING b/COPYING
new file mode 100644 (file)
index 0000000..8d93017
--- /dev/null
+++ b/COPYING
@@ -0,0 +1,22 @@
+/* rc -- the Plan 9 shell, reimplemented for Unix
+
+  Copyright (c) 1991, 1999, 2001-2003, 2014, 2015 Byron Rakitzis
+
+  This software is provided 'as-is', without any express or implied
+  warranty.  In no event will the authors be held liable for any damages
+  arising from the use of this software.
+
+  Permission is granted to anyone to use this software for any purpose,
+  including commercial applications, and to alter it and redistribute it
+  freely, subject to the following restrictions:
+
+  1. The origin of this software must not be misrepresented; you must not
+     claim that you wrote the original software. If you use this software
+     in a product, an acknowledgment in the product documentation would be
+     appreciated but is not required.
+  2. Altered source versions must be plainly marked as such, and must not be
+     misrepresented as being the original software.
+  3. This notice may not be removed or altered from any source distribution.
+
+  Byron Rakitzis <byron@rakitzis.com>
+*/
diff --git a/ChangeLog b/ChangeLog
new file mode 100644 (file)
index 0000000..5ba1cf3
--- /dev/null
+++ b/ChangeLog
@@ -0,0 +1,905 @@
+Changes since 1.2: (Too many to count!)
+
+A memory stomping bug was fixed (provoked by assigning a variable
+to its old value plus something else).
+
+Better signal handling; a real signal handler which manages a queue
+of pending signals was added.
+
+rc now ignores SIGQUIT and traps SIGINT even in non-interactive
+mode. Thus,
+
+       rc ed.sh
+
+will not do mysterious things if the shell script "ed.sh" calls a
+command like "ed" and then you hit ^C.
+
+rc now opens 0, 1, 2 on /dev/null if they are inherited closed.
+rc -o prevents this.
+
+A couple of stupid O(n^2) string appends were replaced with O(n)
+loops. This should make foo=`{cat /etc/termcap} bar=$^foo a little
+faster :-)
+
+Returning a list of signals from a function is now legal, so "return
+$status" should always work.
+
+The code has been revised, new printing routines have been added.
+
+rc no longer uses redundant braces when exporting functions.
+
+A first stab at a verification suite has been added (trip.rc).
+(someone, please help me make this comprehensive!)
+
+rc -p now does not initialize functions from the environment. This
+should make it easier to write shell scripts that don't need to
+assume anything about the environment.
+
+Inherited ignored signals are now ignored in the current shell and
+passed on ignored to the child processes. whatis -s also reflects
+this information.
+
+A file descriptor leak in the /dev/fd implementation of >{} was
+fixed.
+
+A variable set to '' was not imported from the environment; this
+has been fixed.
+
+Changes since 1.3beta:
+
+New Makefile/config.h setup.
+
+builtin echo may now be conditionally included out, to use a Goldwynism.
+
+builtin exit takes any legal exit status. If the status is not all zeros,
+rc exits with 1. (having "exit sigiot" produce a core dump would be going
+a little far, I think.)
+
+limit does not append a unit after a zero limit; 0g was too confusing.
+
+exec > /nonexistentfile does not cause rc to exit any more.
+
+If a noninteractive rc is started with sigint ignored, rc does not install
+its own signal handler.
+
+error messages produced by rc in a subshell were cleaned up. (rc erroneously
+reset the 'interactive' flag after a fork)
+
+print.c was cleaned up a little; no functionality was changed, but should
+be more portable now.
+
+a bug in rc-1.3beta (not previous versions) was fixed: setting the first
+element of $path to '' caused PATH to be exported as '':etc..
+
+getopt's "illegal option" message was gratuitously changed to something
+less abrupt.
+
+some dead code was removed from input.c
+
+%term was changed to %token in parse.y; apparently newer yacc's don't grok
+%term any more.
+
+a race condition in the signal handler was fixed.
+
+the variable in for() was getting evaluated each time through the loop
+(e.g., for (`{echo i;date>[1=2]} in 1 2 3)echo $i would print the date
+three times). This was cleaned up.
+
+a redundant fork() was removed from walk.c; this showed up when running
+a braced command with a redirection in the background. e.g., {a;b}>c&
+
+man pages for history and rc were cleaned up by david (thanks).
+
+rc set SIGQUIT and SIGTERM to SIG_DFL on background jobs---even when
+trying to do old-style backgrounding (i.e., don't use process groups,
+just ignore SIGINT & SIGQUIT & SIGTERM).
+
+$0 is now changed to the name of the signal when entering a signal
+handler. Thus it's possible to write code like
+
+       fn sigint sigterm sigquit {
+               switch ($0) {
+               case sigint
+                       ...
+               case sigterm
+                       ...
+
+wait with no arguments now prints the pid of any and all children
+that died with a signal. e.g.,
+
+       ; wait
+       25321: terminated
+       25325: terminated
+
+as opposed to
+
+       ; wait
+       terminated
+
+An error saving/restoring state in the input stream code would
+cause rc to exit with the (erroneous) command:
+
+       eval '|[a'
+
+FIFO's were not removed in a backgrounded command, e.g.,
+
+       cat <{echo hi}&
+
+Changes since rc-1.4beta:
+
+getopt was renamed to rc_getopt to avoid libc collisions.
+
+$cdpath with a / in it caused a cd to sometimes have two //'s at the
+front of the path. This is reserved by POSIX, so I changed it to skip
+one of the /'s.
+
+signal handling now emulates sh in the way I described in a previous
+message: the race condition present in older rc's whereby some SIGINTs
+got lost is now gone; any SIGINT received during a wait() is acted upon
+at the end of the wait(), unless of course SIGINT is being deliberately
+ignored.
+
+getopt was renamed to avoid naming conflicts with libc. Also a sound
+move since rc_getopt is no longer quite libc-getopt compatible; I had
+to add in a mechanism for resetting getopt.
+
+signal handler code in fn.c was cleaned up; there were several bugs
+in rc-1.4beta, notably the shell sometimes spawned background jobs
+with SIGTERM ignored. I took the opportunity to make things a little
+cleaner here.
+
+a quasi-memory leak in the code for while() was fixed: a long-running
+while that had rc commands allocating memory in it could cause the
+shell to grow without bounds. I fixed this by placing the while loop
+(*and* test!) inside a new allocation arena each time through the loop.
+
+A new configuration parameter, NOJOB, was added to allow you to force
+v7-style backgrounding (no setpgrp, ignore SIGINT and SIGTERM).
+
+The FIFO code was reworked a little. It should be more robust now---
+FIFOs get removed at the end of the command of the argument list
+that they were on:
+
+               fn foo {echo $*; cat $*}
+               foo<{echo hi}
+
+now works as expected. Also FIFO names are pushed onto the exception
+stack so that their removal occurs in the face of exceptions and so
+on.
+
+A memory leak in treefree() was plugged up --- the root node of a
+function was not getting freed.
+
+Changes since rc-1.4:
+
+General changes:
+
+        Some small memory leaks/uninit references revealed by Purify.
+
+        $bqstatus for querying the exit status of a backquote.
+
+        Globbing through unreadable directories.
+
+        More options to whatis.
+
+        History append which always re-opens the file (avoids
+        inconsistencies over multiple NFS-mounted accesses to
+        $history).
+
+        Support "rc -s".
+
+---------
+
+Makefile:      Added comment referring to README for yacc/malloc problem.
+
+uiltins.c:     Added more options to whatis, protected rlimit prototypes
+               with #ifndef SYSVR4, renamed SIGCHK to sigchk.
+
+except.c:      Patched nl_on_intr printing to happen only in interactive
+               shells.
+
+exec.c:                Added comment explaining nl_on_intr variable, renamed SIGCHK
+               to sigchk.
+
+fn.c:          Replaced by-hand consing of exception stack etc. for signal
+               handler execution with call to funcall(). Replaced fun2str
+               call with call on print routines.
+
+footobar.c:    Got rid of memory leak in get_name(), parenthesize count,
+               flat and var nodes for correctness in unparsing, removed
+               list2str, made get_name use nalloc space, merge in a
+               better parse_var from es.
+
+glob.c:                Split out a test so that closedir is called correctly, renamed
+               SIGCHK to sigchk.
+
+glom.c:                Added bqstatus, renamed SIGCHK to sigchk, removed spurious
+               setsigdefaults, patched uninit memory reference, rename
+               "clear" to "memzero", wait for bq subproc to finish on EINTR.
+
+hash.c:                Added options to function/variable print code.
+
+history/history.c: Added '@' to the list of chars which can precede an
+               ignored '-'.
+
+input.c:       Got rid of tiny memory leak in closefds, got rid of uninit
+               memory reference in popinput, moved nul ignored check into
+               realgchar(), changed history append to always reopen the
+               history file, replaced SIGCHK with sigchk. Freed memory
+               returned by call to readline().
+
+lex.c:         Corrected typo in comment, moved nul character ignore code
+               to input routines.
+
+main.c:                Added -s flag.
+
+nalloc.c:      Added convenience feature to erealloc. (Allow NULL parameter)
+
+print.c:       Changed use of va_start so broken compilers can compile
+               print code.
+
+proto.h:       Added fake memset.
+
+rc.h:          Replaced clear() function prototype with a macro call on
+               memset(), removed SIGCHK, fixed prototypes.
+
+signal.c:      Removed unconditional exit in catcher code, renamed SIGCHK
+               to sigchk.
+
+status.c:      Rewrite sgetstatus breaking out strstatus so that bqstatus
+               can be set from glom routines.
+
+utils.c:       Got rid of clear() (use memset from C library), rename SIGCHK
+               to sigchk.
+
+var.c:         Got rid of memory leak in listassign(), converted list2str()
+               call to something using the print routines.
+
+version.c:     New version string.
+
+wait.c:                Got rid of memory leak in rc_fork, renamed SIGCHK to sigchk.
+
+walk.c:                Fixed pre-redirection bug, removed spurious setsigdefaults(),
+               renamed SIGCHK to sigchk.
+
+
+Changes since rc-1.5beta1
+
+  Configuration: rc now uses GNU autoconf.
+
+  Portability: mksignal works on HPUX 10.
+
+  Portability: resources can be (quad_t).
+
+  Bug: if rc was started with SIGCLD == SIG_IGN (e.g. by Solaris's
+  rshd) it would loop.  Fixed by resetting SIGCLD to SIG_DFL if it
+  was SIG_IGN when rc was started.
+
+  Portability: POSIXish systems don't have NGROUPS.
+
+Changes since rc-1.5b2
+
+  Configuration: rc now uses GNU automake.
+
+  Portability: use sigsetjmp() when available.
+
+  Portability: improve tests for quad_t.
+
+  Configuration: don't leave FIFOs in /tmp when configuring.
+
+  Configuration: let configure find `-ltermcap' when using readline.
+
+  Configuration: pick up default path from config.cache.
+
+  Bug: sense of most HAVE_RESTARTABLE_SYSCALLS tests was wrong.
+
+  Bug: print prompts with `-i', even with editline / readline.
+
+  Testing: just say `false' (not `/bin/false').
+
+  Bug: confusion over gid_t versus GETGROUPS_T in which.c.
+
+  Feature: `-V' option added to report version number.
+
+  Configuration: remove version.c; `id' is defined in main.c now.
+
+  Bug: clear list of living children after fork(); `{ ls & wait } |cat'
+  no longer hangs or panics.
+
+  Testing: add regression test for above.
+
+  Tidiness: all the system call wrappers to prevent calls being
+  restarted now live in system-bsd.c.  The configure script decides
+  whether to build system.c or system-bsd.c.  Also, signal.c is more
+  careful to only declare slowbuf if it will be needed.
+
+  Tidiness: similarly, configure decides whether to build execve.c or
+  not.
+
+  Portability: test for ssize_t and use it where available; use long if
+  there's no ssize_t.
+
+  Portability: use sigsetjmp where it's available and appropriate.  If
+  no sigsetjmp, just use sigjmp; this probably fails in a traditional
+  SysV environment.
+
+  Portability: test explicitly for SysV SIGCLD semantics.  Main (and
+  dubious) benefit is that you can now define a function called `sigcld'
+  on systems where there is no signal called SIGCLD!
+
+  Bug: rc has its own memory allocator; don't use malloc directly.
+
+  Bug: the rc_wait() wrapper is only needed on systems which restart
+  system calls.  On Linux, in particular, the wrapper leads to a race
+  which causes rc to hang (or panic in later versions).  Other systems
+  apparently don't exercise this race.
+
+  Bug: waitforall() must return if rc_wait4() returns with errno ==
+  EINTR.  Otherwise, the rc builtin `wait' cannot be interrupted if
+  there are background processes (although apparently only if there is a
+  handler for SIGINT).
+
+  Portability: dreadful hack to track down the real locations of
+  signal.h to find signal names. rc now builds under CygWin32!
+
+  Portability: replace above dreadful hack with mksignal.c, contributed
+  by Vincent Broman.
+
+  Portability: use POSIX wait() macros (WIFEXITED and friends).
+  Unfortunately, POSIX omitted to supply WIFDUMPED, so this doesn't buy
+  a great deal.
+
+  Distribution: remove the dependencies of y.tab.[ch] on parse.y from
+  Makefile.am.  The justification for this is that, unless you're
+  hacking on rc's grammar, there's no reason to use anything other
+  than the distributed files (which were generated with byacc and very
+  lightly edited to silence a few gcc warnings).
+
+  Enhancement: the example in addon.c wasn't very useful, since it
+  depended on files which weren't included with the distribution.  There
+  is now a working, if trivial, example.
+
+  Tidiness: the code was compiled with as many gcc warnings enabled as
+  I could find.  Very few problems turned up.  Some unused function
+  arguments were removed.  Where unused arguments could not be removed
+  (because the function is one of a set that must all have the same
+  prototype), they were renamed to `ignore'.
+
+  Portability: some versions of readline define the name `Function',
+  which rc also uses.  Its use in rc has been renamed to `rc_Function'.
+
+  Documentation: the `history' man page didn't explain what end of line
+  does in editing mode.  It now does.
+
+  Bug: the interaction with readline was broken, particularly with
+  respect to signal handling.  I've incorporated some changes from Tom
+  Culliton which should sort this out.  Unfortunately, we now have 3
+  different code paths for readline 2.1, readline 2.2, and editline :-(.
+
+  Configuration: if you say `--with-readline' or `--with-editline' it is
+  now an error if the appropriate library is not found.
+
+  Bug: rc didn't work on RedHat 5 systems.  This is because of
+  peculiarities in the handling of signals and system calls on this
+  system (the C library attempts to fake restartable system calls).
+  The fix involves testing at configure time for sigaction() and
+  SA_INTERRUPT: if both exist, we set up sys_signal() to be an "always
+  interrupt" wrapper around sigaction().  (If we don't have sigaction(),
+  we use signal() and check for restartable system calls as usual.)
+
+  Portability: on AIX, lconv is defined by the system header files.
+  Rename lconv in print.c to avoid the clash.
+
+  Testing: add a test that `cd' prints the new directory if we are
+  interactive and the directory was found via $cdpath.
+
+1998-07-23
+
+  Testing: fix silly typo in above test.
+
+  Configuration: `--with-vrl' added to support Gert-Jan Vons's readline
+  library.
+
+1998-07-24
+
+  Portability: the autoconf macro AC_FUNC_SETPGRP doesn't work on OSF1: that
+  system supports arguments to setpgrp(), but also has a prototype in
+  <unistd.h> to say that it is void.  Fix this by defining our own
+  RC_FUNC_SETPGRP for now.
+
+  Bug: <sys/wait.h> was included twice in some source files.
+
+  Configuration: automake wants `make distclean' to remove *.tab.c.
+  Rename y.tab.[ch] to parse.[ch] to avoid this.
+
+1998-07-27
+
+  Portability: on Ultrix, `make trip' fails with `malloc: Invalid
+  argument'.  Problem is that getgroups(0, NULL) in which.c returns -1.
+  Add new configure test to check for POSIX getgroups() and fall back to
+  NGROUPS if it's not available.  The magic is done by "getgroups.h".
+
+  Tidiness: extract <sys/wait.h> magic into "wait.h".
+
+1998-10-20
+
+  Tidiness: include prototype for add_history() when doing editline.
+
+  Documentation: document the `-V' flag and mention Linux's
+  /proc/self/fd as alternative to /dev/fd.
+
+1998-10-21
+
+  Bug: shells need to be prepared for bogus applications to have set
+  their input file descriptor to non-blocking, and set it back.
+
+  Tidiness: <sys/types.h> is in "proto.h", so nothing else needs to
+  include it explicitly.
+
+  Documentation: document the ^A bug.
+
+1998-10-22
+
+  Tidiness: makenonblock() was a rather poor choice of name for
+  a function which makes a file descriptor *not* nonblocking :-).
+
+1998-10-26
+
+  Portability: apparently some systems declare `char *basename(const
+  char *)' in system header files.  Changing our basename() (in
+  history.c) to match this prototype allows it to be compiled on such
+  systems, and is harmless.  (Harmless, that is, if no system declares
+  `char *basename(char *)'.)
+
+1998-10-28
+
+  Bug: system-bsd.c needs to include "wait.h".
+
+  Warnings: some versions of gcc warn about "ambiguous" `else' clauses.
+
+  Portability: assigning va_list objects doesn't work everywhere (Linux
+  on the PowerPC, specifically).  Use the C 9x invention va_copy()
+  instead, if it exists, otherwise fall back to assignment.
+
+  Documentation: help HP-UX users by mentioning that you need `cc -Ae'.
+  Also, HP-UX make will build rc in a separate directory.
+
+  Tidiness: remove unused functions from print.c.  Anybody wanting to
+  use this library in another project should follow the pointer in the
+  documentation to an improved version.
+
+1998-10-29
+
+  Bug: the "null character ignored" warning was printed with the wrong
+  line number.  Fix by adding an offset argument to pr_error.
+
+  Portability: work around readline's broken treatment of a non-blocking
+  input file descriptor.
+
+  Testing: add `testing' auxiliary program; use `testing' to generate
+  null character on the fly (since it's a nuisance having a literal
+  null character in trip.rc); reset sigexit in `fn fail'; add test for
+  nonblocking input file descriptor; fix test for cdpath.
+
+  Portability: include <sys/types.h> before <sys/stat.h>.
+
+1998-10-30
+
+  Portability: rename basename() to rc_basename(), since the former is
+  quite widespread, and has a variety of different definitions (none of
+  them, of course, static).
+
+  Portability: work around i386 GCC 2.7.2.3 optimization bug triggered
+  by a (really quite simple) expression in history.c.
+
+1998-12-04
+
+  Bug: a debugging statement was left in history.c by mistake.
+
+  Bug: `history' needs to check for `me' character preceded by `/', as
+  well as all the other options.  An invocation like ../rc-1.5/- no
+  longer loops.
+
+  Documentation: it seems better to have but a single URL in the README
+  file, which indirects to the other places of interest.
+
+1998-12-08
+
+  Portability: use AM_PROG_CC_STDC.  This obviates the need for a
+  special hack on HP-UX.
+
+  Documentation: document all the flags to `whatis'.
+
+1998-12-09
+
+  Tidiness: latest autoconf version has fixed AC_FUNC_SETPGRP, so we
+  no longer need to supply our own.
+
+  Portability: test for va_copy() needs to include <stdarg.h>.
+
+1998-12-10
+
+  Tidiness: move most of the configure.in nastiness into acinclude.m4.
+
+1998-12-11
+
+  Tidiness: the release date now only needs to be changed in one place.
+
+1999-01-05
+
+  Documentation: the Bell Labs rc now has the list flattening operator,
+  but spelt $"foo.
+
+1999-01-11
+
+  Release: rc-1.5b4.
+
+1999-01-19
+
+  Documentation: document the `-s' option.  Also, arrange the option
+  documentation in alphabetical order.
+
+  Tidiness: just install `history' to `$(bindir)/-'; don't create an
+  extra link (which `make clean' failed to remove).
+
+1999-01-22
+
+  Bug: `-s' should not imply `-i'.
+
+  Testing: add regression test for `-s' behaviour.
+
+1999-01-27
+
+  Documentation: default path was out of date; minor consistency
+  improvements.
+
+  Release: rc-1.5b5.
+
+1999-02-15
+
+  Portability: AM_INIT_AUTOMAKE calls AC_ARG_PROGRAM and
+  AC_PROG_INSTALL.  Don't do it explicitly.  For once, the configure
+  script gets smaller!  Program name transformations work right now.
+
+  Documentation: note that rc has no `set' builtin; fix weird variable
+  name example; any character except `=' may be used in a variable name;
+  document bqstatus; document rc's exit status; other tidying.
+
+1999-03-01
+
+  Documentation: document the yacc-imposed limit on ; separated commands
+  in a line.
+
+1999-05-06
+
+  Portability: tgetent() might be in -lncurses instead of -ltermcap.
+
+1999-05-10
+
+  Portability: Linux *almost* has SysV SIGCLD semantics, and we need to
+  detect them.
+
+  Bug: if we reset SIGCLD to SIG_DFL, we need to record the fact in the
+  sighandlers[] array.
+
+1999-05-12
+
+  Documentation: note that `$(a.b)' syntax only mostly works, and that
+  list definitions in exported functions are noisier than they need to
+  be.
+
+  Release: rc-1.5b6.
+
+1999-05-19
+
+  Documentation: minor fixes to man page.
+
+1999-05-26
+
+  Tidiness: `make distclean' now removes sigmsgs.[ch].
+
+1999-05-28
+
+  Release: rc-1.6.
+
+1999-08-19
+
+  Portability: the proposed C 9x __va_copy() macro is called that, not
+  va_copy(), as I thought.  Furthermore, it is defined to be a macro, so
+  we don't need to use autoconf to check for it.
+
+1999-10-11
+
+  Bug: absolute globs don't need special case in doglob().  Avoids
+  creating path names like `//tmp', which is a UNC path under CygWin.
+
+1999-10-12
+
+  Portability: status.c assumes traditional Unix layout of 0 and 1 exit
+  statuses in the parent, which is not shared by BeOS.  Add mkstatval.c.
+
+1999-10-13
+
+  Bug: a read(2) error in fdgchar() should call rc_raise(), not
+  rc_exit().  This bug is easily tickled on systems (like Linux) which
+  allow you to open(2) but not read(2) directories: `. /tmp'.  In all
+  previous versions of rc, this caused the shell to exit.
+
+  Portability: use POSIX strerror() where it's available; fake it with
+  sys_errlist[] where not.
+
+  Feature: replace `-V' with `version' variable.
+
+1999-10-14
+
+  Portability: exporting `path' causes indigestion in CygWin.  Since
+  it's virtually impossible for a child `rc' process to inherit `path'
+  (which I consider a bug, but it's not going to be fixed now), simply
+  don't export `path'.
+
+  Portability: add /usr/bsd to default default path.
+
+  Documentation: failing to search $path for a `.' command is at least
+  an incompatibility with Tenth Edition rc, and probably a bug.
+
+1999-11-10
+
+  Feature: make `version' a list.
+
+1999-11-11
+
+  Documentation: when running configure, you need to set LDFLAGS for
+  `-L' options, not LIBS.
+
+  Release: rc-1.6b1.
+
+1999-12-10
+
+  Bug: absolute globs do still need a special case.  `/*' works again now, but
+  we still avoid creating names like `//tmp/foo'.
+
+  Bug: avoid a putative race condition in signal.c.
+
+  Documentation: extra parentheses around `~' and `!' expressions are
+  forbidden.  Tom Duff's paper is not distributed with rc, but is
+  available on the web.
+
+  Release: rc-1.6b2.
+
+2000-04-19
+
+  Bug: isatty() tests in input.c are relevant to any fd, not just 0.
+  Now `. -i /dev/tty' works right.
+
+  Bug: fn sigexit wasn't always cleared in child shells.
+
+  Bug: `~ () '*'' dumped core.
+
+2000-05-25
+
+  Portability: need special runes for read() returning EIO under job
+  control systems.
+
+2000-06-20
+
+  Feature: add `-I' flag (definitively not interactive) for
+  compatibility with Plan 9 rc.
+
+2000-11-27
+
+  Portability: configure fails to detect strerror() on NetBSD; we need
+  to include <string.h>.
+
+2001-06-18
+
+  Bug: you can't pass a short to a stdargs function!
+
+2001-09-27
+
+  Documentation: we don't consider that `.' failing to search path is
+  a bug.
+
+  Feature: ^A in lists is now handled transparently.
+
+2001-10-01
+
+  Bug: it's no longer possible to use parentheses to sneak a word that
+  needs quoting past the "quoting detector", so `fn x { echo $(x.y) }'
+  now works both in the current rc and its descendants.
+
+  Documentation: mention the catastrophic effects of a semantic error
+  in fn prompt.
+
+2001-10-03
+
+  Feature: exported lists no longer use redundant parentheses.
+
+2001-10-04
+
+  Bug: semantic errors in `fn prompt' no longer throw rc into a tailspin.
+
+  Feature: don't export $cdpath or $home (the lower-case versions).
+
+2001-10-12
+
+  Release: rc-1.6b3.
+
+2001-10-25
+
+  Feature: large file support (thanks Scott Schwartz, Chris
+  Siebenmann).
+
+2001-10-29
+
+  Bug: space vs tab confusion in commented out Makefile rules to
+  rebuild parser (thanks Gary Carvell).
+
+2001-10-31
+
+  Documentation: subscripted variables don't work in here documents.
+
+  Release: rc-1.6c4.
+
+2001-11-01
+
+  Bug: more wrongly ordered header file includes (thanks Callum
+  Gibson).
+
+2001-11-06
+
+  Portability: rename print.c::utoa() to rc_utoa() to avoid QNX name
+  clash; use "sh -c 'test ...'" in trip.rc for missing standalone
+  `test' on QNX (thanks Stefan Dalibor).
+
+2001-11-20
+
+  Documentation: tighten up various descriptions, and include some
+  more examples.
+
+  Release: rc-1.6c5.
+
+2001-11-23
+
+  Bug: parselimit() was broken in various ways (thanks Chris
+  Siebenmann).
+
+2002-02-08
+
+  Bug: yet more wrongly ordered header file includes.
+
+  Release: rc-1.6c6.
+
+2002-04-03
+
+  Feature: make $version less magical, and exportable if it's changed
+  from its default value.  Same for $prompt (thank Erik Quanstrom).
+
+  Bug: make $bqstatus and $status not exportable.
+
+  Feature: "stuttering" colons for multiple replacements in the
+  history programs (thanks Callum Gibson).
+
+2002-05-22
+
+  Documentation: possible warning in tripping.c (thanks Dan Moniz).
+
+  Release: rc-1.6c7.
+
+2002-06-18
+
+  Release: rc-1.7.
+
+2002-07-25
+
+  Bug: fix globbing of broken symlinks.
+
+2002-07-31
+
+  Bug: readline doesn't handle EIO either.
+
+2002-08-15
+
+  Bug: variables that are sometimes exported (i.e. $prompt and
+  $version) need to be made exportable if they are inherited from the
+  environment.
+
+  Portability: don't call sigaction() for SIGKILL or SIGSTOP; don't
+  hand a garbage signal mask to sigaction() (thanks Jeremy
+  Fitzhardinge).  Also, remove use of SA_INTERRUPT (SUSv3, BSD,
+  etc. have SA_RESTART with the inverted meaning).
+
+2002-08-20
+
+  Bug: don't call ealloc(0) on systems where getgroups() doesn't
+  return egid (thanks Chris Siebenmann).
+
+2002-11-27
+
+  Bug: history dumps core if more colons than substitutions (thanks
+  Callum Gibson); history fails to avoid itself if it's the only
+  command; history writes and reads outside allocated memory.
+
+  Configuration: upgrade to autoconf-2.56 and automake-1.7.1.
+
+2003-07-17
+
+  Testing: remove test for large file support, as it causes
+  indigestion on file systems that don't support sparse files (thanks
+  Scott Schwartz).
+
+2003-07-22
+
+  Release: rc-1.7.1.
+
+2003-09-24
+
+  Tidiness: minor improvements to input.c.
+
+2014-02-26
+
+  Bug: fix for CVE-2014-1936 from Jakub Wilk.
+
+2014-06-29
+
+  Documentation: update email and web addresses.
+
+2014-08-31
+
+  Feature: support quoting for filename completion in GNU readline.
+
+2014-09-01
+
+  Bug: quoting of glob characters was broken (thanks Christian
+  Neukirchen); fix the "sneaky parens" bug properly (thanks Wolfgang
+  Zekoll).
+
+  Feature: allow $"x as a synonym for $^x
+
+  Release: rc-1.7.2.
+
+2015-04-03
+
+  Packaging: the rc.spec file was very out-of-date.
+
+2015-04-04
+
+  Portability: the comment from 1999-08-19 may well have been true at
+  the time, but the final version of the C99 standard called varargs
+  copying macro va_copy().
+
+2015-04-07
+
+  Portability: look in -ltinfo for tgetent.
+
+  Packaging: various autoconf / automake updates and tweaks.
+
+2015-04-14
+
+  Bug: in initinput(), the call ugchar(EOF) used the ungetcount member
+  of the top Input structure without initializing it. Thanks to Jeff
+  Johnson for finding this, Robert Scheck for reporting it, and Uli
+  Drepper for implementing MALLOC_PERTURB_, a cheap way to find uses of
+  uninitialized memory.
+
+2015-04-18
+
+  Licensing: tweaked to match exactly the "zlib with acknowledgement"
+  license which is used by nunit and is already approved by various
+  distros.
+
+2015-04-20
+
+  Release: rc-1.7.3.
+
+2015-05-12
+
+  Licensing: due to GPL compatibility concerns, the license is changed
+  again to the "zlib" license. (N.B. This license change was agreed and
+  approved by Byron Rakitzis, who is the copyright holder.)
+
+  Testing: swap arguments to mktemp to be kinder to NetBSD (thanks Piotr
+  Meyer).
+
+2015-05-13
+
+  Release: rc-1.7.4.
diff --git a/EXAMPLES b/EXAMPLES
new file mode 100644 (file)
index 0000000..9f4b5c8
--- /dev/null
+++ b/EXAMPLES
@@ -0,0 +1,749 @@
+There is no repository for useful rc code snippets as yet, so
+I'm including a (short) file in the distribution with some
+helpful/intriguing pieces of rc code.
+
+A sample .rcrc
+--------------
+Here is the .rcrc I use on archone:
+
+umask 022 
+path=(/bin /usr/bin /usr/ucb)
+ht=`/usr/arch/bin/hosttype
+h=$home
+history=$h/.history
+bin=$h/bin/$ht
+lib=$h/lib/$ht
+sh=$h/bin/sh
+include=$h/lib/include
+
+switch ($ht) {
+case sun*
+       OBERON='. '$h/other/oberon
+       p=/usr/ucb
+       compiler='gcc -Wall -O -g'
+       MANPATH=$h/man:/usr/arch/man:/usr/man
+       if (! ~ $TERM ()) {
+               stty dec
+               /usr/arch/bin/msgs -q
+       }
+case next
+       p=(/usr/ucb /usr/bin /NextApps)
+       compiler='cc -Wall -O -g -DNODIRENT'
+       MANPATH=$h/man:/usr/arch/man:/usr/man
+       if (! ~ $TERM ())
+               stty dec
+case sgi
+       p=(/usr/ucb /usr/sbin /usr/bin)
+       compiler='gcc -Wall -O -g -DNOSIGCLD'
+       MANPATH=$h/man:/usr/arch/man:/usr/catman
+       if (!{~ $TERM () || ~ $TERM *iris*})
+               stty line 1 intr '\ 3' erase '\7f' kill '\15'
+case *
+       echo .rcrc not configured for this machine
+}
+
+path=(. $sh $bin /usr/arch/bin $p /bin /usr/bin/X11 /etc /usr/etc)
+cdpath=(. .. $h $h/src $h/misc $h/other $h/adm)
+RNINIT=-d$h' -t -M -2400-h -2400+hfrom'; DOTDIR=$h/misc/news
+PRINTER=lw
+
+fn s {
+       echo $status
+}
+fn cd {
+       builtin cd $1 && \
+       switch ($1) {
+       case ()
+               dir=$home
+       case *
+               dir=()
+       }
+}
+fn pwd {
+       if (~ $dir ())
+               dir=`/bin/pwd
+       echo $dir
+}
+fn x {
+       if (~ `tty /dev/console)
+               clear_colormap
+       clear
+       exit
+}
+fn p {
+       if (~ $history ()) {
+               echo '$history not set' >[1=2]
+               return 1
+       }
+
+       if (! ~ $#* 0 1 2) {
+               echo usage: $0 '[egrep pattern] [sed command]' >[1=2]
+               return 1
+       }
+
+       command=`{
+               egrep -v '^[    ]*p([    ]+|$)' $history | switch ($#*) {
+               case 0
+                       cat
+               case 1
+                       egrep $1
+               case 2
+                       egrep $1 | sed $2
+               } | tail -1
+       }
+
+       echo $command
+       eval $command
+}
+
+if (~ $TERM dialup network) {
+       TERM=vt100
+       biff y
+}
+
+A front-end to NeXT's "openfile"
+--------------------------------
+
+Named after the sam "B" command for opening a file, this script was written
+by Paul Haahr. (Assumes the "pick" command from Kernighan and Pike is also
+in your path.)
+
+#!/bin/rc
+if (~ $#* 0)
+        exec openfile
+create = ()
+files = ()
+for (i in $*)
+        if (test -f $i) {
+                files = ($files $i)
+        } else {
+                create = ($create $i)
+       }
+create = `{ pick $create }
+files = ($files $create)
+for (i in $create)
+        > $i
+if (! ~ $#files 0)
+       openfile $files
+
+A read function
+---------------
+
+Unlike sh, rc doesn't have a read. This clever alternative returns an
+exit status as well as fetch a variable. Use as
+
+       read foo
+
+to set $foo to a single line from the terminal.
+
+(due to John Mackin <john@syd.dit.csiro.au>)
+
+fn read {
+        x=() {
+                x = `` ($nl) { awk '{print; print 0; exit}' ^ $nl ^ \
+                                   'END {print 1; print 1}' }
+                $1 = $x(1)
+                return $x(2)
+        }
+}
+
+From cs.wisc.edu!dws Fri Aug  2 18:16:14 1991
+
+#-------
+# ls front end
+#-------
+fn ls  \
+{
+       test -t 1 && * = (-FCb $*)
+       builtin ls $*
+}
+#-------
+# nl - holds a newline, useful in certain command substitutions
+#-------
+nl='
+'
+#-------
+# show - tell me about a name
+#
+# Runs possibly dangerous things through cat -v in order to protect
+# me from the effects of control characters I might have in the
+# environment.
+#-------
+fn show        \
+{
+       * = `` $nl {whatis -- $*}
+       for(itis)
+       {
+               switch($^itis)
+               {
+               case 'fn '*     ; echo $itis | cat -v -t
+               case builtin*   ; echo $itis
+               case /*         ; file $itis; ls -ld $itis
+               case *'='*      ; echo $itis | cat -v -t
+               case *          ; echo $itis: UNKNOWN: update show
+               }
+       }
+       itis = ()
+}
+#-------
+# Tell me automatically when a command has a nonzero status.
+#-------
+fn prompt      \
+{
+       Status = $status
+       ~ $Status 0 || echo '[status '$Status']'
+}
+
+#-------
+# chop - echo the given list, less its final member
+#
+# e.g. chop (a b c) -> (a b)
+#-------
+fn chop {
+       ~ $#* 0 1 && return 0
+       ans = '' {      # local variable
+               ans = ()
+               while(! ~ $#* 1)
+               {
+                       ans = ($ans $1)
+                       shift
+               }
+               echo $ans
+       }
+}
+
+From arnold@audiofax.com Thu May 30 08:49:51 1991
+
+# cd.rc --- souped up version of cd
+
+# this is designed to emulate the fancy version of cd in ksh,
+# so if you're a purist, feel free to gag
+
+_cwd=$home
+_oldcwd=$home
+
+fn cd {
+       if (~ $#* 0) {
+               if (~ $_cwd $home) {    # do nothing
+               } else {
+                       builtin cd && { _oldcwd=$_cwd ; _cwd=$home }
+               }
+       } else if (~ $#* 1) {
+               if (~ $1 -) {
+                       _t=$_cwd
+                       builtin cd $_oldcwd && {
+                               _cwd=$_oldcwd
+                               _oldcwd=$_t
+                               echo $_cwd
+                       }
+                       _t=()
+               } else {
+                       # if a cd happens through the cdpath, rc echos
+                       # the directory on its own.  all we have to do
+                       # is track where we end up
+                       _dopwd = 1
+                       { ~ $1 /* } && _dopwd = 0       # absolute path
+                       builtin cd $1 && {
+                               _oldcwd=$_cwd
+                               _cwd=$1
+                               { ~ $_dopwd 1 } && _cwd=`/bin/pwd
+                       }
+                       _dopwd=()
+               }
+       } else if (~ $#* 2) {
+               _t=`{ echo $_cwd | sed 's<'$1'<'$2'<' }
+               builtin cd $_t && {
+                       _oldcwd=$_cwd
+                       _cwd=$_t
+                       echo $_cwd
+               }
+               _t=()
+       } else {
+               echo cd: takes 0, 1, or 2 arguments >[1=2]
+               builtin cd $1 && { _oldcwd=$_cwd ; _cwd=`/bin/pwd ; echo $_cwd }
+       }
+}
+
+fn pwd { echo $_cwd }
+
+From vlsi.cs.caltech.edu!drazen Tue Jan 21 16:03:14 1992
+
+# A kill builtin.
+
+#ifdef B_KILL
+#include <ctype.h>
+static void b_kill(char **av)
+{
+    int signal = SIGTERM;
+    int n = 1;
+    pid_t pid;
+    boolean res;
+
+    if (!av[1]) {
+        set(TRUE);
+        return;
+    }
+#undef  STRCMP
+#define STRCMP strcmp
+    if ( '-' == av[1][0]) {
+        char *p = 1+av[1];
+        if (0 == strcmp(av[1], "-l")){
+            int r; const int nsig = NUMOFSIGNALS;
+            const int C = 4, R = 1 + (int)((nsig-2)/C);
+            for (r=1; r<=R; r++){
+              int j;
+              for (j=r; j<nsig; j+=R){
+                fprint(1, "%s%d. %s\t", j<10?" ":"", j, signals[j][0]);
+              }
+              fprint(1,"\n");
+            }
+            set(TRUE);
+            return;
+        }
+        n++;
+        if ( (signal=a2u(p)) < 0){
+            int i;
+            for (i = 1; i < NUMOFSIGNALS; i++){
+                char UPPER[31], *u=UPPER, *q;
+                for (q=signals[i][0]; *q; q++, u++) *u = toupper(*q);
+                *u = '\0';
+
+                if (*signals[i][0] &&
+                  (!STRCMP(signals[i][0], p) || !STRCMP(3+signals[i][0],p)
+                   || !STRCMP(UPPER, p) || !STRCMP(3+UPPER, p) )  )
+                {
+                    signal = i;
+                    break;
+                }
+            }
+            if (signal < 0){
+                fprint(2,"kill: bad signal %s\n", av[1]);
+                set(FALSE);
+                return;
+            }
+        }
+    }
+#undef STRCMP
+
+    for (res=TRUE; av[n]; n++){
+        if( (pid = (pid_t) a2u(av[n])) < 0){
+            fprint(2, "kill: bad process number %s\n", av[n]);
+            res = FALSE;
+            continue;
+        }
+        if (kill(pid,signal)){
+            uerror("kill");
+            res = FALSE;
+            continue;
+        }
+    }
+    set(res);
+}
+#endif
+From acc.stolaf.edu!quanstro Thu Apr  2 02:51:10 1992
+Received: from thor.acc.stolaf.edu ([130.71.192.1]) by archone.tamu.edu with SMTP id <45339>; Thu, 2 Apr 1992 02:50:56 -0600
+Received: by thor.acc.stolaf.edu; Thu, 2 Apr 92 02:49:31 -0600
+Date: Thu, 2 Apr 1992 02:49:31 -0600
+From: quanstro@acc.stolaf.edu
+Message-Id: <9204020849.AA26566@thor.acc.stolaf.edu>
+To: byron@archone.tamu.edu
+Subject: EXAMPLES in 1.4beta
+Status: RO
+
+
+I have a little bit of code which might be a little more general than
+the souped-up version that is already there. Here it is, if you are
+interested. 
+
+# directory functions ###################################################
+fn pwd { echo $PWD; }
+
+fn pushd {
+  dirs = ($PWD $dirs);         
+  builtin cd $*;
+  PWD = `{builtin pwd};
+}
+
+fn popd {
+  switch ($#*)
+    {
+    case 0
+      ;
+    case 1
+      echo 'popd: argument '^$1^' ignored.' >[1=2];
+    case *
+      echo 'popd: usage: popd [n].';
+    }
+
+  if (! ~ $dirs ()) 
+    {
+      builtin cd $dirs(1);
+      PWD = $dirs(1);
+      echo $PWD;
+      * = $dirs;
+      shift
+      dirs = $*;
+    }
+}
+
+fn cd {
+  ~ $* () && * = $home;
+  !~ $#* 1 && echo 'cd: too many arguments' >[1=2] && return 1;
+
+  if (test -r $* ) {
+    pushd $*;
+  } else {
+    echo cd: $* does not exist. >[1=2]
+    return 1;
+  } 
+}
+
+fn back { popd $*; }
+
+fn Back { 
+  cd $home;
+  PWD = $home;
+  dirs = ();
+}
+
+fn dirs {
+  echo $dirs;
+}
+
+PWD = `{builtin pwd} ; dirs = $PWD             # kickstart
+
+
+
+
+
+From acc.stolaf.edu!quanstro Thu Apr  2 02:53:40 1992
+Received: from thor.acc.stolaf.edu ([130.71.192.1]) by archone.tamu.edu with SMTP id <45339>; Thu, 2 Apr 1992 02:53:38 -0600
+Received: by thor.acc.stolaf.edu; Thu, 2 Apr 92 02:51:46 -0600
+Date: Thu, 2 Apr 1992 02:51:46 -0600
+From: quanstro@acc.stolaf.edu
+Message-Id: <9204020851.AA26573@thor.acc.stolaf.edu>
+To: byron@archone.tamu.edu
+Subject: EXAMPLES
+Status: RO
+
+
+Little yp hack which act's like ~ w/o syntatic sugar (for those who do
+not have the luxury of seting up symbolic links to all user's homes
+
+# user function #########################################################
+fn u user {  
+  info = ()
+  info = `` (':') {ypmatch $1 passwd >[2] /dev/null }
+
+  if (~ $info ()) {
+    echo user $1 unknown >[1=2];
+    return 1;
+  } else {
+    echo $info(6)
+    if (~ $0 user) 
+      cd $info(6)
+  }
+}
+
+
+From stolaf.edu!quanstro Sun Apr  5 04:53:34 1992
+Date: Sun, 5 Apr 1992 04:53:08 -0500
+From: quanstro@stolaf.edu (Erik Quanstrom)
+To: byron@archone.tamu.edu
+Subject: man written in rc 
+Status: RO
+
+I whipped this up because the NeXTs here insist on using MANPAGER
+instead of PAGER and otherwise being obnoxious . . . 
+
+Anyway ... I hope you approve
+
+#!/bin/rc
+#########################################################################
+# file:                man                                                     #
+#                                                                      #
+# object:      display man pages                                       #
+#                                                                      #
+# bugs:                * slow                                                  #
+#              * does not know about fmt files                         #
+#                                                                      #
+# Erik Quanstrom                                                       #
+# 11. Februar 1992                                                     #
+#########################################################################
+PATH=/bin:/usr/bin:/usr/ucb:/usr/local/bin:$PATH ; 
+TROFF = (nroff -hq -Tcrt);
+macros=an;
+sections=(cat1 cat2 cat3 cat4 cat5 cat6 cat7 cat8 catl man1 man2 man3 man4 \
+         man5 man6 man7 man8 manl)
+$nl='
+'
+fn sigint sighup sigquit sigalrm sigterm { rm -f $Bat; exit 2;}
+  
+fn usage {
+  echo usage: $0 [-] [-t] [-M path] [-T macros] [[section] title] ...>[1=2];
+  exit 1;
+}
+
+n=();
+fn shiftn {
+  n=($n 1)
+}
+
+~ $PAGER () && test -t 1 && PAGER=more; #default pager
+     
+while (~ $1 -*)
+  { 
+    switch ($1)
+      {
+      case -
+       if (~ $PAGER troff)
+         echo bad combination of flags >[1=2] && usage;
+       PAGER=cat;
+      case -t
+       ~ TROFF () && TROFF = (troff -t);
+       ~ TCAT  () && PAGER=(lpr -t);
+      case -M
+       shift;
+       ~ $1 () && usage;
+       
+       MANPATH=$1;
+      case -T
+       shift;
+       ~ $1 () && usage;
+       macros=$1;
+      case -k
+       fflag=(); kflag=1;
+        shift;
+        break;
+      case -f
+       # locate related too filenames
+       kflag=(); fflag=1;
+        shift;
+        break;
+      case -*
+       echo bad flag '`'^$1^'''' >[1=2];
+       usage;
+      }
+    shift;
+  }
+
+if (!~ $#* 1) {
+  ~ $1 [l1-8] && { sname=$1 ; sections=(cat man)^$1 ; shift }
+  #hack for sun-style man pages
+  ~ $1 [l1-8]? && { sname=$1 ; sections=(cat man)^`{echo $1| cut -c1} ; shift }
+}
+
+if (~ 1 $fflag $kflag) {
+  dirlist=();
+  for (d in ``(:$nl) {echo $MANPATH})
+    test -s $d^/whatis && dirlist=($dirlist $d^/whatis);
+  
+  ~ $1 () && usage;
+  
+  if (~ $fflag 1) { 
+    while (!~ $1 ()) {
+      cmd=`{echo $1 | sed 's/^.*\///g'}
+      egrep -h '^'^$cmd' ' $dirlist;
+      shift;
+    }
+  } else {
+    while (!~ $1 ()) {
+      grep -h $1 $dirlist;
+      shift;
+    }
+  }
+ exit 0;
+}
+
+s=0;    
+while (!~ $1 ()) {
+  for (dir in ``(:$nl) {echo $MANPATH}) {
+    filelist=($filelist `{echo $dir/^$sections^/$1^.* |\
+                           tr ' ' '\12' | grep -v '*'})
+
+    # coment this out if you don't care about speed, but 
+    # would rather find all the pages.
+    ~ $filelist () || break;
+  }
+
+  if (~ $filelist ()) {
+    if (~ $#sections 2) {
+      echo no entry for $1 in section '`'$sname'''' of the manual >[1=2];
+    } else {
+      echo no entry for '`'$1'''' found. >[1=2];
+    }
+    s=1;
+  } else {
+
+    echo $filelist '(' $#filelist ')' >[1=2];
+
+    for (file in $filelist) {
+      if (~ $file */cat[1-8l]/*) {
+       Cat = ($Cat $file);
+      } else {
+       # search for dups
+       dont=()
+       for (x in $Cat) {
+         if (~ `{echo $x |  sed 's/\/[mc]a[nt][1-8l]//'} \
+               `{echo $file |  sed 's/\/[mc]a[nt][1-8l]//'}) {
+           dont=1;
+           break;
+         }
+       }
+
+       if (~ $dont ()) {
+         cd `{echo $file | sed 's/man[1-8].*//'}
+         echo -n Formatting ...
+         $TROFF -m^$macros $file > /tmp/man^$pid^$#n && \
+               Bat = ($Bat /tmp/man^$pid^$#n)
+
+         shiftn;
+         echo ' 'done.
+       }
+      }
+    }
+  } 
+  shift;
+}
+
+{ !~ () $Cat || !~ () $Bat } && $PAGER $Cat $Bat;
+
+rm -f $Bat;
+~ $s () || exit $s;
+     
+exit 0;
+
+
+
+From osf.org!rsalz Thu Apr 23 16:22:32 1992
+Date: Thu, 23 Apr 1992 16:22:07 -0500
+From: rsalz@osf.org
+To: byron@archone.tamu.edu
+Subject: One for your EXAMPLES file
+Status: RO
+
+Use
+       trimhist [-#lines]
+trims your history file back; useful for folks with disk quota's :-)
+fn trimhist { p1=-100 {
+    cp $history $history^'~'
+    ~ $#* 1 && p1=$1
+    tail $p1 <$history^'~' >$history
+    rm $history^'~'
+} }
+
+From Pa.dec.com!uucp Mon Apr 27 12:25:02 1992
+Date: Mon, 27 Apr 1992 12:15:18 -0500
+From: haahr@adobe.com
+To: Byron Rakitzis <byron@archone.tamu.edu>
+Subject: a neat little rc script
+
+what you have to know to understand this:
+       $md for me is usually obj.$machine
+       my mkfiles build *.o, *.a, and the a.outs in $md
+       this is my acc script, which i use for compiling adobe routines
+---
+#! /user/haahr/bin/next/rc
+
+cc = cc
+proto = '-DPROTOTYPES=1'
+
+switch ($md) {
+case noproto.$machine; proto = '-DPROTOTYPES=0'
+case gprof.$machine;   cc = ($cc -pg)
+case prof.$machine;    cc = ($cc -p)
+case lcomp.$machine;   cc = lcomp
+}
+exec $cc $proto '-DPACKAGE_SPECS="package.h"' '-DISP=isp_mc68020' '-DOS=os_mach' $*
+
+From rc-owner Tue May 12 14:54:10 1992
+Received: from postman.osf.org ([130.105.1.152]) by archone.tamu.edu with SMTP id <45337>; Tue, 12 May 1992 14:38:16 -0500
+Received: from earth.osf.org by postman.osf.org (5.64+/OSF 1.0)
+       id AA14480; Tue, 12 May 92 13:25:03 -0400
+Received: by earth.osf.org (5.64/4.7) id AA03499; Tue, 12 May 92 13:25:02 -0400
+Date: Tue, 12 May 1992 12:25:02 -0500
+From: rsalz@osf.org
+Message-Id: <9205121725.AA03499@earth.osf.org>
+To: rc@archone.tamu.edu
+Subject: Useful function
+Status: R
+
+It looks like line noise, but it turns things like
+       /home/rsalz/foo/bar
+into
+       ~/foo/bar
+
+Useful for when you put your current directory up in your icon title.
+By duplicating the $home section you can make things like
+       /project/dce/build/dce1.0.1/src/rpc
+become
+       $MYBT/src/rpc
+
+##  If a pathname starts with $home, turn $home into ~.  Uses all built-ins.
+fn tildepath { p1=() i=() {
+    p1=$1
+    switch ($p1) {
+    case $home $home/*
+       # Split arg into components
+       *=`` (/) { echo -n $p1 }
+       # Shift down by number of components in $home
+       for (i in `` (/) { echo -n $home } ) shift
+       # Glue back together
+       p1='~'
+       for (i) p1=$p1 ^ '/' ^ $i
+       echo $p1
+    case *
+       echo $p1
+    }
+    return 0
+} }
+
+From osf.org!rsalz Tue May 12 15:47:12 1992
+Received: from postman.osf.org ([130.105.1.152]) by archone.tamu.edu with SMTP id <45316>; Tue, 12 May 1992 15:47:06 -0500
+Received: from earth.osf.org by postman.osf.org (5.64+/OSF 1.0)
+       id AA21070; Tue, 12 May 92 16:46:58 -0400
+Received: by earth.osf.org (5.64/4.7) id AA09396; Tue, 12 May 92 16:46:56 -0400
+Date: Tue, 12 May 1992 15:46:56 -0500
+From: rsalz@osf.org
+Message-Id: <9205122046.AA09396@earth.osf.org>
+To: byron@archone.tamu.edu
+Subject: Re: Useful function
+Status: R
+
+>wow. thanks, i'll add it to EXAMPLES.
+Glad you like.  Getting something added to EXAMPLES has been a goal of mine...
+
+I've been thinking, a bit, about a more general way of doing it.  I want
+a "prefix-sub" function, like this
+       prefix $some_path var1 var2 var3 var4 var5
+That would take some_path and replace any leading $var1 (etc) values
+with the variable name.  Return on the first match.
+
+Hmm -- come to think of it, that's very easy to do:
+
+# Use pathprefix filename var1 var2 var3
+# returns filename, with leading prefixes (in $var1...) turned into the
+# string $var1...
+fn pathprefix { p1=() i=() j=() {
+    p1=$1 ; shift
+    for (i) {
+       ~ $p1 $$i $$i^/* && {
+           *=`` (/) { echo -n $p1 }
+           for (j in `` (/) { echo -n $$i } ) shift
+           p1='$'^$i
+           for (j) p1=$p1 ^ '/' ^ $j
+           echo $p1
+           return 0
+       }
+    }
+    echo $p1
+    return 0
+} }
+
+home=/user/users/rsalz
+z=/usr/users
+pathprefix /usr/users/rsalz home usr    # --> $home
+pathprefix /usr/users/rsalz z           # --> $z/rsalz
+pathprefix /usr/users/rsalz/foo z home  # --> $z/rsalz/foo
+pathprefix /usr/users/rsalz/foo home    # --> $home/foo
+
diff --git a/INSTALL b/INSTALL
new file mode 100644 (file)
index 0000000..007e939
--- /dev/null
+++ b/INSTALL
@@ -0,0 +1,370 @@
+Installation Instructions
+*************************
+
+Copyright (C) 1994-1996, 1999-2002, 2004-2013 Free Software Foundation,
+Inc.
+
+   Copying and distribution of this file, with or without modification,
+are permitted in any medium without royalty provided the copyright
+notice and this notice are preserved.  This file is offered as-is,
+without warranty of any kind.
+
+Basic Installation
+==================
+
+   Briefly, the shell commands `./configure; make; make install' should
+configure, build, and install this package.  The following
+more-detailed instructions are generic; see the `README' file for
+instructions specific to this package.  Some packages provide this
+`INSTALL' file but do not implement all of the features documented
+below.  The lack of an optional feature in a given package is not
+necessarily a bug.  More recommendations for GNU packages can be found
+in *note Makefile Conventions: (standards)Makefile Conventions.
+
+   The `configure' shell script attempts to guess correct values for
+various system-dependent variables used during compilation.  It uses
+those values to create a `Makefile' in each directory of the package.
+It may also create one or more `.h' files containing system-dependent
+definitions.  Finally, it creates a shell script `config.status' that
+you can run in the future to recreate the current configuration, and a
+file `config.log' containing compiler output (useful mainly for
+debugging `configure').
+
+   It can also use an optional file (typically called `config.cache'
+and enabled with `--cache-file=config.cache' or simply `-C') that saves
+the results of its tests to speed up reconfiguring.  Caching is
+disabled by default to prevent problems with accidental use of stale
+cache files.
+
+   If you need to do unusual things to compile the package, please try
+to figure out how `configure' could check whether to do them, and mail
+diffs or instructions to the address given in the `README' so they can
+be considered for the next release.  If you are using the cache, and at
+some point `config.cache' contains results you don't want to keep, you
+may remove or edit it.
+
+   The file `configure.ac' (or `configure.in') is used to create
+`configure' by a program called `autoconf'.  You need `configure.ac' if
+you want to change it or regenerate `configure' using a newer version
+of `autoconf'.
+
+   The simplest way to compile this package is:
+
+  1. `cd' to the directory containing the package's source code and type
+     `./configure' to configure the package for your system.
+
+     Running `configure' might take a while.  While running, it prints
+     some messages telling which features it is checking for.
+
+  2. Type `make' to compile the package.
+
+  3. Optionally, type `make check' to run any self-tests that come with
+     the package, generally using the just-built uninstalled binaries.
+
+  4. Type `make install' to install the programs and any data files and
+     documentation.  When installing into a prefix owned by root, it is
+     recommended that the package be configured and built as a regular
+     user, and only the `make install' phase executed with root
+     privileges.
+
+  5. Optionally, type `make installcheck' to repeat any self-tests, but
+     this time using the binaries in their final installed location.
+     This target does not install anything.  Running this target as a
+     regular user, particularly if the prior `make install' required
+     root privileges, verifies that the installation completed
+     correctly.
+
+  6. You can remove the program binaries and object files from the
+     source code directory by typing `make clean'.  To also remove the
+     files that `configure' created (so you can compile the package for
+     a different kind of computer), type `make distclean'.  There is
+     also a `make maintainer-clean' target, but that is intended mainly
+     for the package's developers.  If you use it, you may have to get
+     all sorts of other programs in order to regenerate files that came
+     with the distribution.
+
+  7. Often, you can also type `make uninstall' to remove the installed
+     files again.  In practice, not all packages have tested that
+     uninstallation works correctly, even though it is required by the
+     GNU Coding Standards.
+
+  8. Some packages, particularly those that use Automake, provide `make
+     distcheck', which can by used by developers to test that all other
+     targets like `make install' and `make uninstall' work correctly.
+     This target is generally not run by end users.
+
+Compilers and Options
+=====================
+
+   Some systems require unusual options for compilation or linking that
+the `configure' script does not know about.  Run `./configure --help'
+for details on some of the pertinent environment variables.
+
+   You can give `configure' initial values for configuration parameters
+by setting variables in the command line or in the environment.  Here
+is an example:
+
+     ./configure CC=c99 CFLAGS=-g LIBS=-lposix
+
+   *Note Defining Variables::, for more details.
+
+Compiling For Multiple Architectures
+====================================
+
+   You can compile the package for more than one kind of computer at the
+same time, by placing the object files for each architecture in their
+own directory.  To do this, you can use GNU `make'.  `cd' to the
+directory where you want the object files and executables to go and run
+the `configure' script.  `configure' automatically checks for the
+source code in the directory that `configure' is in and in `..'.  This
+is known as a "VPATH" build.
+
+   With a non-GNU `make', it is safer to compile the package for one
+architecture at a time in the source code directory.  After you have
+installed the package for one architecture, use `make distclean' before
+reconfiguring for another architecture.
+
+   On MacOS X 10.5 and later systems, you can create libraries and
+executables that work on multiple system types--known as "fat" or
+"universal" binaries--by specifying multiple `-arch' options to the
+compiler but only a single `-arch' option to the preprocessor.  Like
+this:
+
+     ./configure CC="gcc -arch i386 -arch x86_64 -arch ppc -arch ppc64" \
+                 CXX="g++ -arch i386 -arch x86_64 -arch ppc -arch ppc64" \
+                 CPP="gcc -E" CXXCPP="g++ -E"
+
+   This is not guaranteed to produce working output in all cases, you
+may have to build one architecture at a time and combine the results
+using the `lipo' tool if you have problems.
+
+Installation Names
+==================
+
+   By default, `make install' installs the package's commands under
+`/usr/local/bin', include files under `/usr/local/include', etc.  You
+can specify an installation prefix other than `/usr/local' by giving
+`configure' the option `--prefix=PREFIX', where PREFIX must be an
+absolute file name.
+
+   You can specify separate installation prefixes for
+architecture-specific files and architecture-independent files.  If you
+pass the option `--exec-prefix=PREFIX' to `configure', the package uses
+PREFIX as the prefix for installing programs and libraries.
+Documentation and other data files still use the regular prefix.
+
+   In addition, if you use an unusual directory layout you can give
+options like `--bindir=DIR' to specify different values for particular
+kinds of files.  Run `configure --help' for a list of the directories
+you can set and what kinds of files go in them.  In general, the
+default for these options is expressed in terms of `${prefix}', so that
+specifying just `--prefix' will affect all of the other directory
+specifications that were not explicitly provided.
+
+   The most portable way to affect installation locations is to pass the
+correct locations to `configure'; however, many packages provide one or
+both of the following shortcuts of passing variable assignments to the
+`make install' command line to change installation locations without
+having to reconfigure or recompile.
+
+   The first method involves providing an override variable for each
+affected directory.  For example, `make install
+prefix=/alternate/directory' will choose an alternate location for all
+directory configuration variables that were expressed in terms of
+`${prefix}'.  Any directories that were specified during `configure',
+but not in terms of `${prefix}', must each be overridden at install
+time for the entire installation to be relocated.  The approach of
+makefile variable overrides for each directory variable is required by
+the GNU Coding Standards, and ideally causes no recompilation.
+However, some platforms have known limitations with the semantics of
+shared libraries that end up requiring recompilation when using this
+method, particularly noticeable in packages that use GNU Libtool.
+
+   The second method involves providing the `DESTDIR' variable.  For
+example, `make install DESTDIR=/alternate/directory' will prepend
+`/alternate/directory' before all installation names.  The approach of
+`DESTDIR' overrides is not required by the GNU Coding Standards, and
+does not work on platforms that have drive letters.  On the other hand,
+it does better at avoiding recompilation issues, and works well even
+when some directory options were not specified in terms of `${prefix}'
+at `configure' time.
+
+Optional Features
+=================
+
+   If the package supports it, you can cause programs to be installed
+with an extra prefix or suffix on their names by giving `configure' the
+option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'.
+
+   Some packages pay attention to `--enable-FEATURE' options to
+`configure', where FEATURE indicates an optional part of the package.
+They may also pay attention to `--with-PACKAGE' options, where PACKAGE
+is something like `gnu-as' or `x' (for the X Window System).  The
+`README' should mention any `--enable-' and `--with-' options that the
+package recognizes.
+
+   For packages that use the X Window System, `configure' can usually
+find the X include and library files automatically, but if it doesn't,
+you can use the `configure' options `--x-includes=DIR' and
+`--x-libraries=DIR' to specify their locations.
+
+   Some packages offer the ability to configure how verbose the
+execution of `make' will be.  For these packages, running `./configure
+--enable-silent-rules' sets the default to minimal output, which can be
+overridden with `make V=1'; while running `./configure
+--disable-silent-rules' sets the default to verbose, which can be
+overridden with `make V=0'.
+
+Particular systems
+==================
+
+   On HP-UX, the default C compiler is not ANSI C compatible.  If GNU
+CC is not installed, it is recommended to use the following options in
+order to use an ANSI C compiler:
+
+     ./configure CC="cc -Ae -D_XOPEN_SOURCE=500"
+
+and if that doesn't work, install pre-built binaries of GCC for HP-UX.
+
+   HP-UX `make' updates targets which have the same time stamps as
+their prerequisites, which makes it generally unusable when shipped
+generated files such as `configure' are involved.  Use GNU `make'
+instead.
+
+   On OSF/1 a.k.a. Tru64, some versions of the default C compiler cannot
+parse its `<wchar.h>' header file.  The option `-nodtk' can be used as
+a workaround.  If GNU CC is not installed, it is therefore recommended
+to try
+
+     ./configure CC="cc"
+
+and if that doesn't work, try
+
+     ./configure CC="cc -nodtk"
+
+   On Solaris, don't put `/usr/ucb' early in your `PATH'.  This
+directory contains several dysfunctional programs; working variants of
+these programs are available in `/usr/bin'.  So, if you need `/usr/ucb'
+in your `PATH', put it _after_ `/usr/bin'.
+
+   On Haiku, software installed for all users goes in `/boot/common',
+not `/usr/local'.  It is recommended to use the following options:
+
+     ./configure --prefix=/boot/common
+
+Specifying the System Type
+==========================
+
+   There may be some features `configure' cannot figure out
+automatically, but needs to determine by the type of machine the package
+will run on.  Usually, assuming the package is built to be run on the
+_same_ architectures, `configure' can figure that out, but if it prints
+a message saying it cannot guess the machine type, give it the
+`--build=TYPE' option.  TYPE can either be a short name for the system
+type, such as `sun4', or a canonical name which has the form:
+
+     CPU-COMPANY-SYSTEM
+
+where SYSTEM can have one of these forms:
+
+     OS
+     KERNEL-OS
+
+   See the file `config.sub' for the possible values of each field.  If
+`config.sub' isn't included in this package, then this package doesn't
+need to know the machine type.
+
+   If you are _building_ compiler tools for cross-compiling, you should
+use the option `--target=TYPE' to select the type of system they will
+produce code for.
+
+   If you want to _use_ a cross compiler, that generates code for a
+platform different from the build platform, you should specify the
+"host" platform (i.e., that on which the generated programs will
+eventually be run) with `--host=TYPE'.
+
+Sharing Defaults
+================
+
+   If you want to set default values for `configure' scripts to share,
+you can create a site shell script called `config.site' that gives
+default values for variables like `CC', `cache_file', and `prefix'.
+`configure' looks for `PREFIX/share/config.site' if it exists, then
+`PREFIX/etc/config.site' if it exists.  Or, you can set the
+`CONFIG_SITE' environment variable to the location of the site script.
+A warning: not all `configure' scripts look for a site script.
+
+Defining Variables
+==================
+
+   Variables not defined in a site shell script can be set in the
+environment passed to `configure'.  However, some packages may run
+configure again during the build, and the customized values of these
+variables may be lost.  In order to avoid this problem, you should set
+them in the `configure' command line, using `VAR=value'.  For example:
+
+     ./configure CC=/usr/local2/bin/gcc
+
+causes the specified `gcc' to be used as the C compiler (unless it is
+overridden in the site shell script).
+
+Unfortunately, this technique does not work for `CONFIG_SHELL' due to
+an Autoconf limitation.  Until the limitation is lifted, you can use
+this workaround:
+
+     CONFIG_SHELL=/bin/bash ./configure CONFIG_SHELL=/bin/bash
+
+`configure' Invocation
+======================
+
+   `configure' recognizes the following options to control how it
+operates.
+
+`--help'
+`-h'
+     Print a summary of all of the options to `configure', and exit.
+
+`--help=short'
+`--help=recursive'
+     Print a summary of the options unique to this package's
+     `configure', and exit.  The `short' variant lists options used
+     only in the top level, while the `recursive' variant lists options
+     also present in any nested packages.
+
+`--version'
+`-V'
+     Print the version of Autoconf used to generate the `configure'
+     script, and exit.
+
+`--cache-file=FILE'
+     Enable the cache: use and save the results of the tests in FILE,
+     traditionally `config.cache'.  FILE defaults to `/dev/null' to
+     disable caching.
+
+`--config-cache'
+`-C'
+     Alias for `--cache-file=config.cache'.
+
+`--quiet'
+`--silent'
+`-q'
+     Do not print messages saying which checks are being made.  To
+     suppress all normal output, redirect it to `/dev/null' (any error
+     messages will still be shown).
+
+`--srcdir=DIR'
+     Look for the package's source code in directory DIR.  Usually
+     `configure' can determine that directory automatically.
+
+`--prefix=DIR'
+     Use DIR as the installation prefix.  *note Installation Names::
+     for more details, including other options available for fine-tuning
+     the installation locations.
+
+`--no-create'
+`-n'
+     Run the configure checks, but stop before creating any output
+     files.
+
+`configure' also accepts some other, not widely useful, options.  Run
+`configure --help' for more details.
diff --git a/Makefile.am b/Makefile.am
new file mode 100644 (file)
index 0000000..00c5dff
--- /dev/null
@@ -0,0 +1,71 @@
+## Process this file with automake to produce Makefile.in
+
+EDIT=@EDIT@
+
+if AMC_HISTORY
+man_MANS = rc.1 history.1
+HISTORY = history
+else
+man_MANS = rc.1
+endif
+
+if AMC_NO_HASHBANG
+EXECVE = execve.o
+endif
+
+if AMC_RESTART
+SYSTEM = system-bsd.o
+else
+SYSTEM = system.o
+endif
+
+bin_PROGRAMS = rc
+noinst_PROGRAMS = mksignal mkstatval tripping $(HISTORY)
+
+rc_SOURCES = builtins.c except.c exec.c fn.c footobar.c getopt.c glob.c glom.c hash.c heredoc.c input.c lex.c list.c main.c match.c nalloc.c open.c parse.c print.c redir.c signal.c status.c tree.c utils.c var.c wait.c walk.c which.c
+
+EXTRA_rc_SOURCES = addon.c edit-edit.c edit-editline.c edit-null.c edit-readline.c edit-vrl.c execve.c system.c system-bsd.c
+
+rc_DEPENDENCIES = sigmsgs.o $(ADDON) $(EDIT) $(EXECVE) $(SYSTEM)
+rc_LDADD = sigmsgs.o $(ADDON) $(EDIT) $(EXECVE) $(SYSTEM)
+
+noinst_HEADERS = edit.h getgroups.h input.h jbwrap.h parse.h proto.h rc.h rlimit.h stat.h wait.h
+
+BUILT_SOURCES = sigmsgs.c
+
+EXTRA_DIST = EXAMPLES addon.c addon.h history.1 parse.y rc.1 trip.rc
+
+sigmsgs.c sigmsgs.h: mksignal
+       ./mksignal
+
+# Newer automake's buildtime dependency tracking can't seem to figure
+# this one out.
+status.o: statval.h
+
+statval.h: mkstatval
+       ./mkstatval > statval.h
+
+DISTCLEANFILES = sigmsgs.c sigmsgs.h statval.h
+
+# Of course, parse.c and parse.h depend on parse.y.  However, unless
+# you're hacking on rc's grammar, it's not useful to have this
+# dependency expressed, since the distributed parse.[ch] (generated with
+# byacc, and lightly edited to remove a couple of gcc warnings) are
+# portable (I hope).
+#parse.c parse.h: $(srcdir)/parse.y
+#      $(YACC) -d $(srcdir)/parse.y
+#      mv y.tab.c parse.c
+#      mv y.tab.h parse.h
+
+check: trip
+
+trip: rc tripping
+       ./rc -p < $(srcdir)/trip.rc
+
+install-exec-hook:
+if AMC_HISTORY
+       $(INSTALL_PROGRAM) history $(bindir)/- ;\
+       rm -f $(bindir)/--;  $(LN) $(bindir)/- $(bindir)/-- ;\
+       rm -f $(bindir)/-p;  $(LN) $(bindir)/- $(bindir)/-p ;\
+       rm -f $(bindir)/--p; $(LN) $(bindir)/- $(bindir)/--p
+endif
diff --git a/Makefile.in b/Makefile.in
new file mode 100644 (file)
index 0000000..8838aae
--- /dev/null
@@ -0,0 +1,955 @@
+# Makefile.in generated by automake 1.14.1 from Makefile.am.
+# @configure_input@
+
+# Copyright (C) 1994-2013 Free Software Foundation, Inc.
+
+# This Makefile.in is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
+# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+# PARTICULAR PURPOSE.
+
+@SET_MAKE@
+
+
+VPATH = @srcdir@
+am__is_gnu_make = test -n '$(MAKEFILE_LIST)' && test -n '$(MAKELEVEL)'
+am__make_running_with_option = \
+  case $${target_option-} in \
+      ?) ;; \
+      *) echo "am__make_running_with_option: internal error: invalid" \
+              "target option '$${target_option-}' specified" >&2; \
+         exit 1;; \
+  esac; \
+  has_opt=no; \
+  sane_makeflags=$$MAKEFLAGS; \
+  if $(am__is_gnu_make); then \
+    sane_makeflags=$$MFLAGS; \
+  else \
+    case $$MAKEFLAGS in \
+      *\\[\ \  ]*) \
+        bs=\\; \
+        sane_makeflags=`printf '%s\n' "$$MAKEFLAGS" \
+          | sed "s/$$bs$$bs[$$bs $$bs  ]*//g"`;; \
+    esac; \
+  fi; \
+  skip_next=no; \
+  strip_trailopt () \
+  { \
+    flg=`printf '%s\n' "$$flg" | sed "s/$$1.*$$//"`; \
+  }; \
+  for flg in $$sane_makeflags; do \
+    test $$skip_next = yes && { skip_next=no; continue; }; \
+    case $$flg in \
+      *=*|--*) continue;; \
+        -*I) strip_trailopt 'I'; skip_next=yes;; \
+      -*I?*) strip_trailopt 'I';; \
+        -*O) strip_trailopt 'O'; skip_next=yes;; \
+      -*O?*) strip_trailopt 'O';; \
+        -*l) strip_trailopt 'l'; skip_next=yes;; \
+      -*l?*) strip_trailopt 'l';; \
+      -[dEDm]) skip_next=yes;; \
+      -[JT]) skip_next=yes;; \
+    esac; \
+    case $$flg in \
+      *$$target_option*) has_opt=yes; break;; \
+    esac; \
+  done; \
+  test $$has_opt = yes
+am__make_dryrun = (target_option=n; $(am__make_running_with_option))
+am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+pkgdatadir = $(datadir)/@PACKAGE@
+pkgincludedir = $(includedir)/@PACKAGE@
+pkglibdir = $(libdir)/@PACKAGE@
+pkglibexecdir = $(libexecdir)/@PACKAGE@
+am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
+install_sh_DATA = $(install_sh) -c -m 644
+install_sh_PROGRAM = $(install_sh) -c
+install_sh_SCRIPT = $(install_sh) -c
+INSTALL_HEADER = $(INSTALL_DATA)
+transform = $(program_transform_name)
+NORMAL_INSTALL = :
+PRE_INSTALL = :
+POST_INSTALL = :
+NORMAL_UNINSTALL = :
+PRE_UNINSTALL = :
+POST_UNINSTALL = :
+bin_PROGRAMS = rc$(EXEEXT)
+noinst_PROGRAMS = mksignal$(EXEEXT) mkstatval$(EXEEXT) \
+       tripping$(EXEEXT) $(am__EXEEXT_1)
+subdir = .
+DIST_COMMON = INSTALL NEWS README AUTHORS ChangeLog \
+       $(srcdir)/Makefile.in $(srcdir)/Makefile.am \
+       $(top_srcdir)/configure $(am__configure_deps) \
+       $(srcdir)/config.h.in mkinstalldirs depcomp $(noinst_HEADERS) \
+       COPYING compile install-sh missing
+ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
+am__aclocal_m4_deps = $(top_srcdir)/acinclude.m4 \
+       $(top_srcdir)/configure.ac
+am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
+       $(ACLOCAL_M4)
+am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \
+ configure.lineno config.status.lineno
+mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
+CONFIG_HEADER = config.h
+CONFIG_CLEAN_FILES =
+CONFIG_CLEAN_VPATH_FILES =
+am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(man1dir)"
+@AMC_HISTORY_TRUE@am__EXEEXT_1 = history$(EXEEXT)
+PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS)
+history_SOURCES = history.c
+history_OBJECTS = history.$(OBJEXT)
+history_LDADD = $(LDADD)
+mksignal_SOURCES = mksignal.c
+mksignal_OBJECTS = mksignal.$(OBJEXT)
+mksignal_LDADD = $(LDADD)
+mkstatval_SOURCES = mkstatval.c
+mkstatval_OBJECTS = mkstatval.$(OBJEXT)
+mkstatval_LDADD = $(LDADD)
+am_rc_OBJECTS = builtins.$(OBJEXT) except.$(OBJEXT) exec.$(OBJEXT) \
+       fn.$(OBJEXT) footobar.$(OBJEXT) getopt.$(OBJEXT) \
+       glob.$(OBJEXT) glom.$(OBJEXT) hash.$(OBJEXT) heredoc.$(OBJEXT) \
+       input.$(OBJEXT) lex.$(OBJEXT) list.$(OBJEXT) main.$(OBJEXT) \
+       match.$(OBJEXT) nalloc.$(OBJEXT) open.$(OBJEXT) \
+       parse.$(OBJEXT) print.$(OBJEXT) redir.$(OBJEXT) \
+       signal.$(OBJEXT) status.$(OBJEXT) tree.$(OBJEXT) \
+       utils.$(OBJEXT) var.$(OBJEXT) wait.$(OBJEXT) walk.$(OBJEXT) \
+       which.$(OBJEXT)
+rc_OBJECTS = $(am_rc_OBJECTS)
+am__DEPENDENCIES_1 =
+tripping_SOURCES = tripping.c
+tripping_OBJECTS = tripping.$(OBJEXT)
+tripping_LDADD = $(LDADD)
+AM_V_P = $(am__v_P_@AM_V@)
+am__v_P_ = $(am__v_P_@AM_DEFAULT_V@)
+am__v_P_0 = false
+am__v_P_1 = :
+AM_V_GEN = $(am__v_GEN_@AM_V@)
+am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@)
+am__v_GEN_0 = @echo "  GEN     " $@;
+am__v_GEN_1 = 
+AM_V_at = $(am__v_at_@AM_V@)
+am__v_at_ = $(am__v_at_@AM_DEFAULT_V@)
+am__v_at_0 = @
+am__v_at_1 = 
+DEFAULT_INCLUDES = -I.@am__isrc@
+depcomp = $(SHELL) $(top_srcdir)/depcomp
+am__depfiles_maybe = depfiles
+am__mv = mv -f
+COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
+       $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
+AM_V_CC = $(am__v_CC_@AM_V@)
+am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@)
+am__v_CC_0 = @echo "  CC      " $@;
+am__v_CC_1 = 
+CCLD = $(CC)
+LINK = $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@
+AM_V_CCLD = $(am__v_CCLD_@AM_V@)
+am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@)
+am__v_CCLD_0 = @echo "  CCLD    " $@;
+am__v_CCLD_1 = 
+SOURCES = history.c mksignal.c mkstatval.c $(rc_SOURCES) \
+       $(EXTRA_rc_SOURCES) tripping.c
+DIST_SOURCES = history.c mksignal.c mkstatval.c $(rc_SOURCES) \
+       $(EXTRA_rc_SOURCES) tripping.c
+am__can_run_installinfo = \
+  case $$AM_UPDATE_INFO_DIR in \
+    n|no|NO) false;; \
+    *) (install-info --version) >/dev/null 2>&1;; \
+  esac
+am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
+am__vpath_adj = case $$p in \
+    $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
+    *) f=$$p;; \
+  esac;
+am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`;
+am__install_max = 40
+am__nobase_strip_setup = \
+  srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'`
+am__nobase_strip = \
+  for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||"
+am__nobase_list = $(am__nobase_strip_setup); \
+  for p in $$list; do echo "$$p $$p"; done | \
+  sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \
+  $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \
+    if (++n[$$2] == $(am__install_max)) \
+      { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \
+    END { for (dir in files) print dir, files[dir] }'
+am__base_list = \
+  sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
+  sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
+am__uninstall_files_from_dir = { \
+  test -z "$$files" \
+    || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+    || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+         $(am__cd) "$$dir" && rm -f $$files; }; \
+  }
+man1dir = $(mandir)/man1
+NROFF = nroff
+MANS = $(man_MANS)
+HEADERS = $(noinst_HEADERS)
+am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) \
+       $(LISP)config.h.in
+# Read a list of newline-separated strings from the standard input,
+# and print each of them once, without duplicates.  Input order is
+# *not* preserved.
+am__uniquify_input = $(AWK) '\
+  BEGIN { nonempty = 0; } \
+  { items[$$0] = 1; nonempty = 1; } \
+  END { if (nonempty) { for (i in items) print i; }; } \
+'
+# Make sure the list of sources is unique.  This is necessary because,
+# e.g., the same source file might be shared among _SOURCES variables
+# for different programs/libraries.
+am__define_uniq_tagged_files = \
+  list='$(am__tagged_files)'; \
+  unique=`for i in $$list; do \
+    if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
+  done | $(am__uniquify_input)`
+ETAGS = etags
+CTAGS = ctags
+CSCOPE = cscope
+AM_RECURSIVE_TARGETS = cscope
+DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
+distdir = $(PACKAGE)-$(VERSION)
+top_distdir = $(distdir)
+am__remove_distdir = \
+  if test -d "$(distdir)"; then \
+    find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \
+      && rm -rf "$(distdir)" \
+      || { sleep 5 && rm -rf "$(distdir)"; }; \
+  else :; fi
+am__post_remove_distdir = $(am__remove_distdir)
+DIST_ARCHIVES = $(distdir).tar.gz
+GZIP_ENV = --best
+DIST_TARGETS = dist-gzip
+distuninstallcheck_listfiles = find . -type f -print
+am__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \
+  | sed 's|^\./|$(prefix)/|' | grep -v '$(infodir)/dir$$'
+distcleancheck_listfiles = find . -type f -print
+ACLOCAL = @ACLOCAL@
+ADDON = @ADDON@
+AMTAR = @AMTAR@
+AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@
+AUTOCONF = @AUTOCONF@
+AUTOHEADER = @AUTOHEADER@
+AUTOMAKE = @AUTOMAKE@
+AWK = @AWK@
+CC = @CC@
+CCDEPMODE = @CCDEPMODE@
+CFLAGS = @CFLAGS@
+CPP = @CPP@
+CPPFLAGS = @CPPFLAGS@
+CYGPATH_W = @CYGPATH_W@
+DEFS = @DEFS@
+DEPDIR = @DEPDIR@
+ECHO_C = @ECHO_C@
+ECHO_N = @ECHO_N@
+ECHO_T = @ECHO_T@
+EDIT = @EDIT@
+EGREP = @EGREP@
+EXEEXT = @EXEEXT@
+GREP = @GREP@
+INSTALL = @INSTALL@
+INSTALL_DATA = @INSTALL_DATA@
+INSTALL_PROGRAM = @INSTALL_PROGRAM@
+INSTALL_SCRIPT = @INSTALL_SCRIPT@
+INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
+LDFLAGS = @LDFLAGS@
+LIBOBJS = @LIBOBJS@
+LIBS = @LIBS@
+LN = @LN@
+LTLIBOBJS = @LTLIBOBJS@
+MAKEINFO = @MAKEINFO@
+MKDIR_P = @MKDIR_P@
+OBJEXT = @OBJEXT@
+PACKAGE = @PACKAGE@
+PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
+PACKAGE_NAME = @PACKAGE_NAME@
+PACKAGE_STRING = @PACKAGE_STRING@
+PACKAGE_TARNAME = @PACKAGE_TARNAME@
+PACKAGE_URL = @PACKAGE_URL@
+PACKAGE_VERSION = @PACKAGE_VERSION@
+PATH_SEPARATOR = @PATH_SEPARATOR@
+SET_MAKE = @SET_MAKE@
+SHELL = @SHELL@
+STRIP = @STRIP@
+VERSION = @VERSION@
+abs_builddir = @abs_builddir@
+abs_srcdir = @abs_srcdir@
+abs_top_builddir = @abs_top_builddir@
+abs_top_srcdir = @abs_top_srcdir@
+ac_ct_CC = @ac_ct_CC@
+am__include = @am__include@
+am__leading_dot = @am__leading_dot@
+am__quote = @am__quote@
+am__tar = @am__tar@
+am__untar = @am__untar@
+bindir = @bindir@
+build_alias = @build_alias@
+builddir = @builddir@
+datadir = @datadir@
+datarootdir = @datarootdir@
+docdir = @docdir@
+dvidir = @dvidir@
+exec_prefix = @exec_prefix@
+host_alias = @host_alias@
+htmldir = @htmldir@
+includedir = @includedir@
+infodir = @infodir@
+install_sh = @install_sh@
+libdir = @libdir@
+libexecdir = @libexecdir@
+localedir = @localedir@
+localstatedir = @localstatedir@
+mandir = @mandir@
+mkdir_p = @mkdir_p@
+oldincludedir = @oldincludedir@
+pdfdir = @pdfdir@
+prefix = @prefix@
+program_transform_name = @program_transform_name@
+psdir = @psdir@
+sbindir = @sbindir@
+sharedstatedir = @sharedstatedir@
+srcdir = @srcdir@
+sysconfdir = @sysconfdir@
+target_alias = @target_alias@
+top_build_prefix = @top_build_prefix@
+top_builddir = @top_builddir@
+top_srcdir = @top_srcdir@
+@AMC_HISTORY_FALSE@man_MANS = rc.1
+@AMC_HISTORY_TRUE@man_MANS = rc.1 history.1
+@AMC_HISTORY_TRUE@HISTORY = history
+@AMC_NO_HASHBANG_TRUE@EXECVE = execve.o
+@AMC_RESTART_FALSE@SYSTEM = system.o
+@AMC_RESTART_TRUE@SYSTEM = system-bsd.o
+rc_SOURCES = builtins.c except.c exec.c fn.c footobar.c getopt.c glob.c glom.c hash.c heredoc.c input.c lex.c list.c main.c match.c nalloc.c open.c parse.c print.c redir.c signal.c status.c tree.c utils.c var.c wait.c walk.c which.c
+EXTRA_rc_SOURCES = addon.c edit-edit.c edit-editline.c edit-null.c edit-readline.c edit-vrl.c execve.c system.c system-bsd.c
+rc_DEPENDENCIES = sigmsgs.o $(ADDON) $(EDIT) $(EXECVE) $(SYSTEM)
+rc_LDADD = sigmsgs.o $(ADDON) $(EDIT) $(EXECVE) $(SYSTEM)
+noinst_HEADERS = edit.h getgroups.h input.h jbwrap.h parse.h proto.h rc.h rlimit.h stat.h wait.h
+BUILT_SOURCES = sigmsgs.c
+EXTRA_DIST = EXAMPLES addon.c addon.h history.1 parse.y rc.1 trip.rc
+DISTCLEANFILES = sigmsgs.c sigmsgs.h statval.h
+all: $(BUILT_SOURCES) config.h
+       $(MAKE) $(AM_MAKEFLAGS) all-am
+
+.SUFFIXES:
+.SUFFIXES: .c .o .obj
+am--refresh: Makefile
+       @:
+$(srcdir)/Makefile.in:  $(srcdir)/Makefile.am  $(am__configure_deps)
+       @for dep in $?; do \
+         case '$(am__configure_deps)' in \
+           *$$dep*) \
+             echo ' cd $(srcdir) && $(AUTOMAKE) --gnu'; \
+             $(am__cd) $(srcdir) && $(AUTOMAKE) --gnu \
+               && exit 0; \
+             exit 1;; \
+         esac; \
+       done; \
+       echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu Makefile'; \
+       $(am__cd) $(top_srcdir) && \
+         $(AUTOMAKE) --gnu Makefile
+.PRECIOUS: Makefile
+Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
+       @case '$?' in \
+         *config.status*) \
+           echo ' $(SHELL) ./config.status'; \
+           $(SHELL) ./config.status;; \
+         *) \
+           echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe)'; \
+           cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe);; \
+       esac;
+
+$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
+       $(SHELL) ./config.status --recheck
+
+$(top_srcdir)/configure:  $(am__configure_deps)
+       $(am__cd) $(srcdir) && $(AUTOCONF)
+$(ACLOCAL_M4):  $(am__aclocal_m4_deps)
+       $(am__cd) $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS)
+$(am__aclocal_m4_deps):
+
+config.h: stamp-h1
+       @test -f $@ || rm -f stamp-h1
+       @test -f $@ || $(MAKE) $(AM_MAKEFLAGS) stamp-h1
+
+stamp-h1: $(srcdir)/config.h.in $(top_builddir)/config.status
+       @rm -f stamp-h1
+       cd $(top_builddir) && $(SHELL) ./config.status config.h
+$(srcdir)/config.h.in:  $(am__configure_deps) 
+       ($(am__cd) $(top_srcdir) && $(AUTOHEADER))
+       rm -f stamp-h1
+       touch $@
+
+distclean-hdr:
+       -rm -f config.h stamp-h1
+install-binPROGRAMS: $(bin_PROGRAMS)
+       @$(NORMAL_INSTALL)
+       @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \
+       if test -n "$$list"; then \
+         echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \
+         $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \
+       fi; \
+       for p in $$list; do echo "$$p $$p"; done | \
+       sed 's/$(EXEEXT)$$//' | \
+       while read p p1; do if test -f $$p \
+         ; then echo "$$p"; echo "$$p"; else :; fi; \
+       done | \
+       sed -e 'p;s,.*/,,;n;h' \
+           -e 's|.*|.|' \
+           -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \
+       sed 'N;N;N;s,\n, ,g' | \
+       $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \
+         { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \
+           if ($$2 == $$4) files[d] = files[d] " " $$1; \
+           else { print "f", $$3 "/" $$4, $$1; } } \
+         END { for (d in files) print "f", d, files[d] }' | \
+       while read type dir files; do \
+           if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \
+           test -z "$$files" || { \
+             echo " $(INSTALL_PROGRAM_ENV) $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \
+             $(INSTALL_PROGRAM_ENV) $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \
+           } \
+       ; done
+
+uninstall-binPROGRAMS:
+       @$(NORMAL_UNINSTALL)
+       @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \
+       files=`for p in $$list; do echo "$$p"; done | \
+         sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \
+             -e 's/$$/$(EXEEXT)/' \
+       `; \
+       test -n "$$list" || exit 0; \
+       echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \
+       cd "$(DESTDIR)$(bindir)" && rm -f $$files
+
+clean-binPROGRAMS:
+       -test -z "$(bin_PROGRAMS)" || rm -f $(bin_PROGRAMS)
+
+clean-noinstPROGRAMS:
+       -test -z "$(noinst_PROGRAMS)" || rm -f $(noinst_PROGRAMS)
+
+history$(EXEEXT): $(history_OBJECTS) $(history_DEPENDENCIES) $(EXTRA_history_DEPENDENCIES) 
+       @rm -f history$(EXEEXT)
+       $(AM_V_CCLD)$(LINK) $(history_OBJECTS) $(history_LDADD) $(LIBS)
+
+mksignal$(EXEEXT): $(mksignal_OBJECTS) $(mksignal_DEPENDENCIES) $(EXTRA_mksignal_DEPENDENCIES) 
+       @rm -f mksignal$(EXEEXT)
+       $(AM_V_CCLD)$(LINK) $(mksignal_OBJECTS) $(mksignal_LDADD) $(LIBS)
+
+mkstatval$(EXEEXT): $(mkstatval_OBJECTS) $(mkstatval_DEPENDENCIES) $(EXTRA_mkstatval_DEPENDENCIES) 
+       @rm -f mkstatval$(EXEEXT)
+       $(AM_V_CCLD)$(LINK) $(mkstatval_OBJECTS) $(mkstatval_LDADD) $(LIBS)
+
+rc$(EXEEXT): $(rc_OBJECTS) $(rc_DEPENDENCIES) $(EXTRA_rc_DEPENDENCIES) 
+       @rm -f rc$(EXEEXT)
+       $(AM_V_CCLD)$(LINK) $(rc_OBJECTS) $(rc_LDADD) $(LIBS)
+
+tripping$(EXEEXT): $(tripping_OBJECTS) $(tripping_DEPENDENCIES) $(EXTRA_tripping_DEPENDENCIES) 
+       @rm -f tripping$(EXEEXT)
+       $(AM_V_CCLD)$(LINK) $(tripping_OBJECTS) $(tripping_LDADD) $(LIBS)
+
+mostlyclean-compile:
+       -rm -f *.$(OBJEXT)
+
+distclean-compile:
+       -rm -f *.tab.c
+
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/addon.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/builtins.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/edit-edit.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/edit-editline.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/edit-null.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/edit-readline.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/edit-vrl.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/except.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/exec.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/execve.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fn.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/footobar.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/getopt.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/glob.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/glom.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/hash.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/heredoc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/history.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/input.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/lex.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/list.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/main.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/match.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mksignal.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mkstatval.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/nalloc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/open.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/parse.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/print.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/redir.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/signal.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/status.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/system-bsd.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/system.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tree.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tripping.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/utils.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/var.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/wait.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/walk.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/which.Po@am__quote@
+
+.c.o:
+@am__fastdepCC_TRUE@   $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $<
+@am__fastdepCC_TRUE@   $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@  $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $<
+
+.c.obj:
+@am__fastdepCC_TRUE@   $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'`
+@am__fastdepCC_TRUE@   $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@  $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
+install-man1: $(man_MANS)
+       @$(NORMAL_INSTALL)
+       @list1=''; \
+       list2='$(man_MANS)'; \
+       test -n "$(man1dir)" \
+         && test -n "`echo $$list1$$list2`" \
+         || exit 0; \
+       echo " $(MKDIR_P) '$(DESTDIR)$(man1dir)'"; \
+       $(MKDIR_P) "$(DESTDIR)$(man1dir)" || exit 1; \
+       { for i in $$list1; do echo "$$i"; done;  \
+       if test -n "$$list2"; then \
+         for i in $$list2; do echo "$$i"; done \
+           | sed -n '/\.1[a-z]*$$/p'; \
+       fi; \
+       } | while read p; do \
+         if test -f $$p; then d=; else d="$(srcdir)/"; fi; \
+         echo "$$d$$p"; echo "$$p"; \
+       done | \
+       sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \
+             -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \
+       sed 'N;N;s,\n, ,g' | { \
+       list=; while read file base inst; do \
+         if test "$$base" = "$$inst"; then list="$$list $$file"; else \
+           echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \
+           $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst" || exit $$?; \
+         fi; \
+       done; \
+       for i in $$list; do echo "$$i"; done | $(am__base_list) | \
+       while read files; do \
+         test -z "$$files" || { \
+           echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man1dir)'"; \
+           $(INSTALL_DATA) $$files "$(DESTDIR)$(man1dir)" || exit $$?; }; \
+       done; }
+
+uninstall-man1:
+       @$(NORMAL_UNINSTALL)
+       @list=''; test -n "$(man1dir)" || exit 0; \
+       files=`{ for i in $$list; do echo "$$i"; done; \
+       l2='$(man_MANS)'; for i in $$l2; do echo "$$i"; done | \
+         sed -n '/\.1[a-z]*$$/p'; \
+       } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \
+             -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \
+       dir='$(DESTDIR)$(man1dir)'; $(am__uninstall_files_from_dir)
+
+ID: $(am__tagged_files)
+       $(am__define_uniq_tagged_files); mkid -fID $$unique
+tags: tags-am
+TAGS: tags
+
+tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)
+       set x; \
+       here=`pwd`; \
+       $(am__define_uniq_tagged_files); \
+       shift; \
+       if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \
+         test -n "$$unique" || unique=$$empty_fix; \
+         if test $$# -gt 0; then \
+           $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
+             "$$@" $$unique; \
+         else \
+           $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
+             $$unique; \
+         fi; \
+       fi
+ctags: ctags-am
+
+CTAGS: ctags
+ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)
+       $(am__define_uniq_tagged_files); \
+       test -z "$(CTAGS_ARGS)$$unique" \
+         || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
+            $$unique
+
+GTAGS:
+       here=`$(am__cd) $(top_builddir) && pwd` \
+         && $(am__cd) $(top_srcdir) \
+         && gtags -i $(GTAGS_ARGS) "$$here"
+cscope: cscope.files
+       test ! -s cscope.files \
+         || $(CSCOPE) -b -q $(AM_CSCOPEFLAGS) $(CSCOPEFLAGS) -i cscope.files $(CSCOPE_ARGS)
+clean-cscope:
+       -rm -f cscope.files
+cscope.files: clean-cscope cscopelist
+cscopelist: cscopelist-am
+
+cscopelist-am: $(am__tagged_files)
+       list='$(am__tagged_files)'; \
+       case "$(srcdir)" in \
+         [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \
+         *) sdir=$(subdir)/$(srcdir) ;; \
+       esac; \
+       for i in $$list; do \
+         if test -f "$$i"; then \
+           echo "$(subdir)/$$i"; \
+         else \
+           echo "$$sdir/$$i"; \
+         fi; \
+       done >> $(top_builddir)/cscope.files
+
+distclean-tags:
+       -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+       -rm -f cscope.out cscope.in.out cscope.po.out cscope.files
+
+distdir: $(DISTFILES)
+       $(am__remove_distdir)
+       test -d "$(distdir)" || mkdir "$(distdir)"
+       @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
+       topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
+       list='$(DISTFILES)'; \
+         dist_files=`for file in $$list; do echo $$file; done | \
+         sed -e "s|^$$srcdirstrip/||;t" \
+             -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \
+       case $$dist_files in \
+         */*) $(MKDIR_P) `echo "$$dist_files" | \
+                          sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \
+                          sort -u` ;; \
+       esac; \
+       for file in $$dist_files; do \
+         if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
+         if test -d $$d/$$file; then \
+           dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \
+           if test -d "$(distdir)/$$file"; then \
+             find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \
+           fi; \
+           if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
+             cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \
+             find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \
+           fi; \
+           cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \
+         else \
+           test -f "$(distdir)/$$file" \
+           || cp -p $$d/$$file "$(distdir)/$$file" \
+           || exit 1; \
+         fi; \
+       done
+       -test -n "$(am__skip_mode_fix)" \
+       || find "$(distdir)" -type d ! -perm -755 \
+               -exec chmod u+rwx,go+rx {} \; -o \
+         ! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \
+         ! -type d ! -perm -400 -exec chmod a+r {} \; -o \
+         ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \
+       || chmod -R a+r "$(distdir)"
+dist-gzip: distdir
+       tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz
+       $(am__post_remove_distdir)
+
+dist-bzip2: distdir
+       tardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2
+       $(am__post_remove_distdir)
+
+dist-lzip: distdir
+       tardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz
+       $(am__post_remove_distdir)
+
+dist-xz: distdir
+       tardir=$(distdir) && $(am__tar) | XZ_OPT=$${XZ_OPT--e} xz -c >$(distdir).tar.xz
+       $(am__post_remove_distdir)
+
+dist-tarZ: distdir
+       @echo WARNING: "Support for shar distribution archives is" \
+                      "deprecated." >&2
+       @echo WARNING: "It will be removed altogether in Automake 2.0" >&2
+       tardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z
+       $(am__post_remove_distdir)
+
+dist-shar: distdir
+       @echo WARNING: "Support for distribution archives compressed with" \
+                      "legacy program 'compress' is deprecated." >&2
+       @echo WARNING: "It will be removed altogether in Automake 2.0" >&2
+       shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz
+       $(am__post_remove_distdir)
+
+dist-zip: distdir
+       -rm -f $(distdir).zip
+       zip -rq $(distdir).zip $(distdir)
+       $(am__post_remove_distdir)
+
+dist dist-all:
+       $(MAKE) $(AM_MAKEFLAGS) $(DIST_TARGETS) am__post_remove_distdir='@:'
+       $(am__post_remove_distdir)
+
+# This target untars the dist file and tries a VPATH configuration.  Then
+# it guarantees that the distribution is self-contained by making another
+# tarfile.
+distcheck: dist
+       case '$(DIST_ARCHIVES)' in \
+       *.tar.gz*) \
+         GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
+       *.tar.bz2*) \
+         bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
+       *.tar.lz*) \
+         lzip -dc $(distdir).tar.lz | $(am__untar) ;;\
+       *.tar.xz*) \
+         xz -dc $(distdir).tar.xz | $(am__untar) ;;\
+       *.tar.Z*) \
+         uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
+       *.shar.gz*) \
+         GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\
+       *.zip*) \
+         unzip $(distdir).zip ;;\
+       esac
+       chmod -R a-w $(distdir)
+       chmod u+w $(distdir)
+       mkdir $(distdir)/_build $(distdir)/_inst
+       chmod a-w $(distdir)
+       test -d $(distdir)/_build || exit 0; \
+       dc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\/]:[\\/],/,'` \
+         && dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \
+         && am__cwd=`pwd` \
+         && $(am__cd) $(distdir)/_build \
+         && ../configure \
+           $(AM_DISTCHECK_CONFIGURE_FLAGS) \
+           $(DISTCHECK_CONFIGURE_FLAGS) \
+           --srcdir=.. --prefix="$$dc_install_base" \
+         && $(MAKE) $(AM_MAKEFLAGS) \
+         && $(MAKE) $(AM_MAKEFLAGS) dvi \
+         && $(MAKE) $(AM_MAKEFLAGS) check \
+         && $(MAKE) $(AM_MAKEFLAGS) install \
+         && $(MAKE) $(AM_MAKEFLAGS) installcheck \
+         && $(MAKE) $(AM_MAKEFLAGS) uninstall \
+         && $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir="$$dc_install_base" \
+               distuninstallcheck \
+         && chmod -R a-w "$$dc_install_base" \
+         && ({ \
+              (cd ../.. && umask 077 && mkdir "$$dc_destdir") \
+              && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" install \
+              && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" uninstall \
+              && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" \
+                   distuninstallcheck_dir="$$dc_destdir" distuninstallcheck; \
+             } || { rm -rf "$$dc_destdir"; exit 1; }) \
+         && rm -rf "$$dc_destdir" \
+         && $(MAKE) $(AM_MAKEFLAGS) dist \
+         && rm -rf $(DIST_ARCHIVES) \
+         && $(MAKE) $(AM_MAKEFLAGS) distcleancheck \
+         && cd "$$am__cwd" \
+         || exit 1
+       $(am__post_remove_distdir)
+       @(echo "$(distdir) archives ready for distribution: "; \
+         list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \
+         sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x'
+distuninstallcheck:
+       @test -n '$(distuninstallcheck_dir)' || { \
+         echo 'ERROR: trying to run $@ with an empty' \
+              '$$(distuninstallcheck_dir)' >&2; \
+         exit 1; \
+       }; \
+       $(am__cd) '$(distuninstallcheck_dir)' || { \
+         echo 'ERROR: cannot chdir into $(distuninstallcheck_dir)' >&2; \
+         exit 1; \
+       }; \
+       test `$(am__distuninstallcheck_listfiles) | wc -l` -eq 0 \
+          || { echo "ERROR: files left after uninstall:" ; \
+               if test -n "$(DESTDIR)"; then \
+                 echo "  (check DESTDIR support)"; \
+               fi ; \
+               $(distuninstallcheck_listfiles) ; \
+               exit 1; } >&2
+distcleancheck: distclean
+       @if test '$(srcdir)' = . ; then \
+         echo "ERROR: distcleancheck can only run from a VPATH build" ; \
+         exit 1 ; \
+       fi
+       @test `$(distcleancheck_listfiles) | wc -l` -eq 0 \
+         || { echo "ERROR: files left in build directory after distclean:" ; \
+              $(distcleancheck_listfiles) ; \
+              exit 1; } >&2
+check-am: all-am
+check: $(BUILT_SOURCES)
+       $(MAKE) $(AM_MAKEFLAGS) check-am
+all-am: Makefile $(PROGRAMS) $(MANS) $(HEADERS) config.h
+installdirs:
+       for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(man1dir)"; do \
+         test -z "$$dir" || $(MKDIR_P) "$$dir"; \
+       done
+install: $(BUILT_SOURCES)
+       $(MAKE) $(AM_MAKEFLAGS) install-am
+install-exec: install-exec-am
+install-data: install-data-am
+uninstall: uninstall-am
+
+install-am: all-am
+       @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
+
+installcheck: installcheck-am
+install-strip:
+       if test -z '$(STRIP)'; then \
+         $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
+           install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
+             install; \
+       else \
+         $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
+           install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
+           "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \
+       fi
+mostlyclean-generic:
+
+clean-generic:
+
+distclean-generic:
+       -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
+       -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+       -test -z "$(DISTCLEANFILES)" || rm -f $(DISTCLEANFILES)
+
+maintainer-clean-generic:
+       @echo "This command is intended for maintainers to use"
+       @echo "it deletes files that may require special tools to rebuild."
+       -test -z "$(BUILT_SOURCES)" || rm -f $(BUILT_SOURCES)
+clean: clean-am
+
+clean-am: clean-binPROGRAMS clean-generic clean-noinstPROGRAMS \
+       mostlyclean-am
+
+distclean: distclean-am
+       -rm -f $(am__CONFIG_DISTCLEAN_FILES)
+       -rm -rf ./$(DEPDIR)
+       -rm -f Makefile
+distclean-am: clean-am distclean-compile distclean-generic \
+       distclean-hdr distclean-tags
+
+dvi: dvi-am
+
+dvi-am:
+
+html: html-am
+
+html-am:
+
+info: info-am
+
+info-am:
+
+install-data-am: install-man
+
+install-dvi: install-dvi-am
+
+install-dvi-am:
+
+install-exec-am: install-binPROGRAMS
+       @$(NORMAL_INSTALL)
+       $(MAKE) $(AM_MAKEFLAGS) install-exec-hook
+install-html: install-html-am
+
+install-html-am:
+
+install-info: install-info-am
+
+install-info-am:
+
+install-man: install-man1
+
+install-pdf: install-pdf-am
+
+install-pdf-am:
+
+install-ps: install-ps-am
+
+install-ps-am:
+
+installcheck-am:
+
+maintainer-clean: maintainer-clean-am
+       -rm -f $(am__CONFIG_DISTCLEAN_FILES)
+       -rm -rf $(top_srcdir)/autom4te.cache
+       -rm -rf ./$(DEPDIR)
+       -rm -f Makefile
+maintainer-clean-am: distclean-am maintainer-clean-generic
+
+mostlyclean: mostlyclean-am
+
+mostlyclean-am: mostlyclean-compile mostlyclean-generic
+
+pdf: pdf-am
+
+pdf-am:
+
+ps: ps-am
+
+ps-am:
+
+uninstall-am: uninstall-binPROGRAMS uninstall-man
+
+uninstall-man: uninstall-man1
+
+.MAKE: all check install install-am install-exec-am install-strip
+
+.PHONY: CTAGS GTAGS TAGS all all-am am--refresh check check-am clean \
+       clean-binPROGRAMS clean-cscope clean-generic \
+       clean-noinstPROGRAMS cscope cscopelist-am ctags ctags-am dist \
+       dist-all dist-bzip2 dist-gzip dist-lzip dist-shar dist-tarZ \
+       dist-xz dist-zip distcheck distclean distclean-compile \
+       distclean-generic distclean-hdr distclean-tags distcleancheck \
+       distdir distuninstallcheck dvi dvi-am html html-am info \
+       info-am install install-am install-binPROGRAMS install-data \
+       install-data-am install-dvi install-dvi-am install-exec \
+       install-exec-am install-exec-hook install-html install-html-am \
+       install-info install-info-am install-man install-man1 \
+       install-pdf install-pdf-am install-ps install-ps-am \
+       install-strip installcheck installcheck-am installdirs \
+       maintainer-clean maintainer-clean-generic mostlyclean \
+       mostlyclean-compile mostlyclean-generic pdf pdf-am ps ps-am \
+       tags tags-am uninstall uninstall-am uninstall-binPROGRAMS \
+       uninstall-man uninstall-man1
+
+
+sigmsgs.c sigmsgs.h: mksignal
+       ./mksignal
+
+# Newer automake's buildtime dependency tracking can't seem to figure
+# this one out.
+status.o: statval.h
+
+statval.h: mkstatval
+       ./mkstatval > statval.h
+
+# Of course, parse.c and parse.h depend on parse.y.  However, unless
+# you're hacking on rc's grammar, it's not useful to have this
+# dependency expressed, since the distributed parse.[ch] (generated with
+# byacc, and lightly edited to remove a couple of gcc warnings) are
+# portable (I hope).
+#parse.c parse.h: $(srcdir)/parse.y
+#      $(YACC) -d $(srcdir)/parse.y
+#      mv y.tab.c parse.c
+#      mv y.tab.h parse.h
+
+check: trip
+
+trip: rc tripping
+       ./rc -p < $(srcdir)/trip.rc
+
+install-exec-hook:
+@AMC_HISTORY_TRUE@     $(INSTALL_PROGRAM) history $(bindir)/- ;\
+@AMC_HISTORY_TRUE@     rm -f $(bindir)/--;  $(LN) $(bindir)/- $(bindir)/-- ;\
+@AMC_HISTORY_TRUE@     rm -f $(bindir)/-p;  $(LN) $(bindir)/- $(bindir)/-p ;\
+@AMC_HISTORY_TRUE@     rm -f $(bindir)/--p; $(LN) $(bindir)/- $(bindir)/--p
+
+# Tell versions [3.59,3.63) of GNU make to not export all variables.
+# Otherwise a system limit (for SysV at least) may be exceeded.
+.NOEXPORT:
diff --git a/MyMakefile b/MyMakefile
new file mode 100644 (file)
index 0000000..68909c5
--- /dev/null
@@ -0,0 +1,23 @@
+CPPFLAGS = -DHAVE_CONFIG_H -I.
+CCCMD = $(CC) $(CPPFLAGS) $(CFLAGS) -o $@ $^ $(LDFLAGS) $(LDLIBS)
+RCOBJS = builtins.o except.o builtins.o except.o exec.o fn.o footobar.o getopt.o glob.o glom.o hash.o heredoc.o input.o lex.o list.o main.o match.o nalloc.o open.o parse.o print.o redir.o signal.o status.o tree.o utils.o var.o wait.o walk.o which.o sigmsgs.o edit-null.o system.o
+
+all: rc
+
+# Generate signal messages
+mksignal: mksignal.o
+sigmsgs.c sigmsgs.h: mksignal
+       ./mksignal
+builtins.o: sigmsgs.h
+
+# Generate mkstatval
+mkstatval: mkstatval.o
+statval.h: mkstatval
+       ./mkstatval > statval.h
+status.o: statval.h
+
+rc: $(RCOBJS)
+       $(CCCMD)
+
+clean:
+       $(RM) rc *.o
diff --git a/NEWS b/NEWS
new file mode 100644 (file)
index 0000000..3b55faf
--- /dev/null
+++ b/NEWS
@@ -0,0 +1,24 @@
+Highlights of changes since rc-1.7. See ChangeLog for further details.
+
+Portability. A fix to the autoconfiguration means that the nasty
+longjmp() code is now omitted for all modern Unix systems; previously rc
+only did the Right Thing on Linux. The test for large files in trip.rc
+was removed, as this causes indigestion on file systems that don't
+support sparse files (the configuration and implementation of large file
+support is still present of course).
+
+Bug fixes. Fix a use of uninitialized memory. Fix for CVE-2014-1936.
+Broken symlinks now glob correctly.  The variables $prompt and $version
+are now exported if they are inherited from the environment when rc
+starts. EIO handling is now enabled for readline too. A few bogosities
+in the history program were fixed. A regression introduced by the fix
+for the $(a.b) quoting bug was fixed, and that bug was correctly fixed.
+
+New features. Added $"x as a synonym for $^x. Minimal support for
+various alternative line editing libraries. Filename completion with GNU
+readline now quotes special characters.
+
+Documentation. Licence updated to the zlib licence.
+
+Toby Goodwin
+2015-05-13
diff --git a/README b/README
new file mode 100644 (file)
index 0000000..1431b04
--- /dev/null
+++ b/README
@@ -0,0 +1,38 @@
+This is release rc-1.7.4.
+
+See COPYING for copying information. All files are
+
+   Copyright 1991, 1999, 2001-2003, 2014, 2015 Byron Rakitzis.
+
+See INSTALL for build and installation information.
+
+
+BUGS
+
+Send bug reports to <toby@paccrat.org>. If a core dump is generated,
+sending a backtrace will help a great deal. You can get a backtrace
+like this.
+
+       ; gdb rc core
+       (gdb) where
+       <<<BACKTRACE INFO>>>
+       (gdb)
+
+Also, always report the machine, OS (`uname -a'), and compiler used to
+make rc; this information is extremely valuable.
+
+
+FEEPING CREATURISM
+
+See the end of the man page, under "INCOMPATIBILITIES" for (known?)
+differences from the "real" rc. Most of these changes were necessary
+to get rc to work in a reasonable fashion on a real (i.e. commercial,
+non-Labs) Unix system; a few were changes motivated by concern about
+some inadequacies in the original design.
+
+
+WWW
+
+More information on releases of rc can be found at this web page.
+
+    http://tobold.org/article/rc
diff --git a/acinclude.m4 b/acinclude.m4
new file mode 100644 (file)
index 0000000..3f9ec93
--- /dev/null
@@ -0,0 +1,210 @@
+dnl This macro sets HAVE_POSIX_GETGROUPS if the
+dnl getgroups() function accepts a zero first argument.
+AC_DEFUN([RC_FUNC_GETGROUPS], [
+       AC_CACHE_CHECK(for POSIX getgroups, rc_cv_func_posix_getgroups, AC_TRY_RUN([
+#include <sys/types.h>
+#include <unistd.h>
+int main(void) {
+       return getgroups(0, (void *)0) == -1;
+}
+       ], rc_cv_func_posix_getgroups=yes, rc_cv_func_posix_getgroups=no, rc_cv_func_posix_getgroups=yes))
+       case "$rc_cv_func_posix_getgroups" in
+       yes) AC_DEFINE(HAVE_POSIX_GETGROUPS, 1, [Define to 1 if you have the `getgroups' function with POSIX semantics.]) ;;
+       esac
+])
+
+
+dnl We can't use AC_CHECK_FUNCS for sigsetjmp(), since it's a macro in
+dnl some places.
+AC_DEFUN([RC_FUNC_SIGSETJMP], [
+       AC_CACHE_CHECK(for sigsetjmp, rc_cv_sigsetjmp,
+               AC_TRY_LINK([
+#include <setjmp.h>
+               ], [
+sigjmp_buf e;
+sigsetjmp(e, 1);
+               ], rc_cv_sigsetjmp=yes, rc_cv_sigsetjmp=no))
+       case "$rc_cv_sigsetjmp" in
+       yes)    AC_DEFINE(HAVE_SIGSETJMP, 1, [Define to 1 if you have the `sigsetjmp' function or macro.]) ;;
+       esac
+])
+
+dnl Similarly, AC_CHECK_FUNCS doesn't find strerror() on NetBSD.
+AC_DEFUN([RC_FUNC_STRERROR], [
+       AC_CACHE_CHECK(for strerror, rc_cv_strerror,
+               AC_TRY_LINK([
+#include <string.h>
+               ], [
+strerror(0);
+               ], rc_cv_strerror=yes, rc_cv_strerror=no))
+       case "$rc_cv_strerror" in
+       yes)    AC_DEFINE(HAVE_STRERROR, 1, [Define to 1 if you have the `strerror' function or macro.]) ;;
+       esac
+])
+
+dnl HPUX needs _KERNEL defined to pick up RLIMIT_foo defines.  (Why?)
+AC_DEFUN([RC_NEED_KERNEL], [
+       AC_CACHE_CHECK(if _KERNEL is required for RLIMIT defines, rc_cv_kernel_rlimit,
+               AC_TRY_COMPILE([
+#include <sys/types.h>
+#include <sys/resource.h>
+               ], [
+int f;
+f = RLIMIT_DATA;
+               ], rc_cv_kernel_rlimit=no, [ AC_TRY_COMPILE([
+#include <sys/types.h>
+#define _KERNEL
+#include <sys/resource.h>
+#undef _KERNEL
+                       ], [
+int f;
+f = RLIMIT_DATA;
+                       ], rc_cv_kernel_rlimit=yes, rc_cv_kernel_rlimit=no)]))
+       case "$rc_cv_kernel_rlimit" in
+       yes)    AC_DEFINE(RLIMIT_NEEDS_KERNEL, 1, [Define to 1 if `_KERNEL' must be defined for `RLIMIT_*' macros.]) ;;
+       esac
+])
+
+dnl Look for rlim_t in sys/types.h and sys/resource.h
+AC_DEFUN([RC_TYPE_RLIM_T], [
+       AC_CACHE_CHECK(for rlim_t, rc_cv_have_rlim_t,
+               AC_EGREP_CPP(rlim_t, [
+#include <sys/types.h>
+#if RLIMIT_NEEDS_KERNEL
+#define _KERNEL
+#endif
+#include <sys/resource.h>
+               ], rc_cv_have_rlim_t=yes, rc_cv_have_rlim_t=no))
+
+       case "$rc_cv_have_rlim_t" in
+       yes)    AC_DEFINE(HAVE_RLIM_T, 1, [Define to 1 if you have the `rlim_t' type.]) ;;
+       no)     AC_CACHE_CHECK(for native quad_t, rc_cv_have_quad_t,
+                       AC_TRY_COMPILE([
+#include <sys/types.h>
+                       ], [
+typedef quad_t align_t;
+align_t a;
+a = (quad_t)0;
+                       ], rc_cv_have_quad_t=yes, rc_cv_have_quad_t=no))
+
+               case "$rc_cv_have_quad_t" in
+               yes)    AC_DEFINE(HAVE_QUAD_T, 1, [Define to 1 if you have the `quad_t' type.])
+                       AC_CACHE_CHECK(if rlimit values are quad_t, rc_cv_rlim_t_is_quad_t,
+                               AC_TRY_RUN([
+#include <sys/types.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#if RLIMIT_NEEDS_KERNEL
+#define _KERNEL
+#endif
+#include <sys/resource.h>
+#if RLIMIT_NEEDS_KERNEL
+#undef _KERNEL
+#endif
+main(){
+       struct rlimit rl;
+       exit(sizeof rl.rlim_cur != sizeof(quad_t));
+}
+                               ], rc_cv_rlim_t_is_quad_t=yes, rc_cv_rlim_t_is_quad_t=no, $ac_cv_type_quad_t))
+
+                       case "$rc_cv_rlim_t_is_quad_t" in
+                       yes)    AC_DEFINE(RLIM_T_IS_QUAD_T, 1, [Define to 1 if `rlim_t' is `quad_t'.]) ;;
+                       esac
+                       ;;
+               esac
+               ;;
+       esac
+])
+
+
+dnl Check type of sig_atomic_t.
+AC_DEFUN([RC_TYPE_SIG_ATOMIC_T], [
+       AC_CACHE_CHECK(for sig_atomic_t, rc_cv_sig_atomic_t,
+               AC_EGREP_HEADER(sig_atomic_t, signal.h,
+                       rc_cv_sig_atomic_t=yes, rc_cv_sig_atomic_t=no))
+       case "$rc_cv_sig_atomic_t" in
+       no)     AC_DEFINE(sig_atomic_t, int, [Define to 1 if you have the `sig_atomic_t' type.]) ;;
+       esac
+])
+
+
+dnl Do we have SysV SIGCLD semantics?  In other words, if we set the
+dnl action for SIGCLD to SIG_IGN does wait() always say ECHILD?  Linux,
+dnl of course, is bizarre here.  It basically implements the SysV
+dnl semantics, but if the parent calls wait() before the child calls
+dnl exit(), wait() returns with the PID of the child as normal.  (Real
+dnl SysV waits for all children to exit, then returns with ECHILD.)
+dnl Anyway, this is why the `sleep(1)' is there.
+AC_DEFUN([RC_SYS_V_SIGCLD], [
+       AC_CACHE_CHECK(for SysV SIGCLD semantics, rc_cv_sysv_sigcld,
+               AC_TRY_RUN([
+#include <errno.h>
+#include <signal.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+int main(void) {
+       int i;
+       signal(SIGCLD, SIG_IGN);
+       switch (fork()) {
+       case -1:
+               return 1;
+       case 0:
+               return 0;
+       default:
+               sleep(1);
+               if (wait(&i) == -1 && errno == ECHILD) return 0;
+               else return 1;
+       }
+}
+               ], rc_cv_sysv_sigcld=yes, rc_cv_sysv_sigcld=no, rc_cv_sysv_sigcld=yes))
+       case "$rc_cv_sysv_sigcld" in
+       yes)    AC_DEFINE(HAVE_SYSV_SIGCLD, 1, [Has SysV SIGCLD]) ;;
+       esac
+])
+
+
+dnl Do we have /dev/fd or /proc/self/fd?
+AC_DEFUN([RC_SYS_DEV_FD], [
+       AC_CACHE_CHECK(for /dev/fd, rc_cv_sys_dev_fd,
+               if test -d /dev/fd && test -r /dev/fd/0; then
+                       rc_cv_sys_dev_fd=yes
+               elif test -d /proc/self/fd && test -r /proc/self/fd/0; then
+                       rc_cv_sys_dev_fd=odd
+               else
+                       rc_cv_sys_dev_fd=no
+               fi
+       )
+])
+
+
+dnl Can mknod make FIFOs?
+AC_DEFUN([RC_SYS_MKNOD_FIFO], [
+       AC_CACHE_CHECK(for mknod FIFOs, rc_cv_sys_fifo,
+               AC_TRY_RUN([
+#include <sys/types.h>
+#include <sys/stat.h>
+
+main() {
+       exit(mknod("/tmp/rc$$.0", S_IFIFO | 0666, 0) != 0);
+}
+               ], rc_cv_sys_fifo=yes, rc_cv_sys_fifo=no, rc_cv_sys_fifo=no))
+       rm -f /tmp/rc$$.0
+       case "$rc_cv_sys_fifo" in
+       yes)    AC_DEFINE(HAVE_FIFO) ;;
+       esac
+])
+
+dnl Where is tgetent()?
+AC_DEFUN([RC_LIB_TGETENT], [
+       AC_CHECK_LIB(tinfo, tgetent,
+               rc_lib_tgetent=-ltinfo,
+               AC_CHECK_LIB(termcap, tgetent,
+                       rc_lib_tgetent=-ltermcap,
+                       AC_CHECK_LIB(ncurses, tgetent,
+                               rc_lib_tgetent=-lncurses,
+                               AC_MSG_ERROR(tgetent not found)
+                       )
+               )
+       )
+])
diff --git a/aclocal.m4 b/aclocal.m4
new file mode 100644 (file)
index 0000000..d2198f2
--- /dev/null
@@ -0,0 +1,1150 @@
+# generated automatically by aclocal 1.14.1 -*- Autoconf -*-
+
+# Copyright (C) 1996-2013 Free Software Foundation, Inc.
+
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
+# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+# PARTICULAR PURPOSE.
+
+m4_ifndef([AC_CONFIG_MACRO_DIRS], [m4_defun([_AM_CONFIG_MACRO_DIRS], [])m4_defun([AC_CONFIG_MACRO_DIRS], [_AM_CONFIG_MACRO_DIRS($@)])])
+m4_ifndef([AC_AUTOCONF_VERSION],
+  [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
+m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.69],,
+[m4_warning([this file was generated for autoconf 2.69.
+You have another version of autoconf.  It may work, but is not guaranteed to.
+If you have problems, you may need to regenerate the build system entirely.
+To do so, use the procedure documented by the package, typically 'autoreconf'.])])
+
+# Copyright (C) 2002-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_AUTOMAKE_VERSION(VERSION)
+# ----------------------------
+# Automake X.Y traces this macro to ensure aclocal.m4 has been
+# generated from the m4 files accompanying Automake X.Y.
+# (This private macro should not be called outside this file.)
+AC_DEFUN([AM_AUTOMAKE_VERSION],
+[am__api_version='1.14'
+dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
+dnl require some minimum version.  Point them to the right macro.
+m4_if([$1], [1.14.1], [],
+      [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
+])
+
+# _AM_AUTOCONF_VERSION(VERSION)
+# -----------------------------
+# aclocal traces this macro to find the Autoconf version.
+# This is a private macro too.  Using m4_define simplifies
+# the logic in aclocal, which can simply ignore this definition.
+m4_define([_AM_AUTOCONF_VERSION], [])
+
+# AM_SET_CURRENT_AUTOMAKE_VERSION
+# -------------------------------
+# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
+# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
+AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
+[AM_AUTOMAKE_VERSION([1.14.1])dnl
+m4_ifndef([AC_AUTOCONF_VERSION],
+  [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
+_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
+
+# AM_AUX_DIR_EXPAND                                         -*- Autoconf -*-
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets
+# $ac_aux_dir to '$srcdir/foo'.  In other projects, it is set to
+# '$srcdir', '$srcdir/..', or '$srcdir/../..'.
+#
+# Of course, Automake must honor this variable whenever it calls a
+# tool from the auxiliary directory.  The problem is that $srcdir (and
+# therefore $ac_aux_dir as well) can be either absolute or relative,
+# depending on how configure is run.  This is pretty annoying, since
+# it makes $ac_aux_dir quite unusable in subdirectories: in the top
+# source directory, any form will work fine, but in subdirectories a
+# relative path needs to be adjusted first.
+#
+# $ac_aux_dir/missing
+#    fails when called from a subdirectory if $ac_aux_dir is relative
+# $top_srcdir/$ac_aux_dir/missing
+#    fails if $ac_aux_dir is absolute,
+#    fails when called from a subdirectory in a VPATH build with
+#          a relative $ac_aux_dir
+#
+# The reason of the latter failure is that $top_srcdir and $ac_aux_dir
+# are both prefixed by $srcdir.  In an in-source build this is usually
+# harmless because $srcdir is '.', but things will broke when you
+# start a VPATH build or use an absolute $srcdir.
+#
+# So we could use something similar to $top_srcdir/$ac_aux_dir/missing,
+# iff we strip the leading $srcdir from $ac_aux_dir.  That would be:
+#   am_aux_dir='\$(top_srcdir)/'`expr "$ac_aux_dir" : "$srcdir//*\(.*\)"`
+# and then we would define $MISSING as
+#   MISSING="\${SHELL} $am_aux_dir/missing"
+# This will work as long as MISSING is not called from configure, because
+# unfortunately $(top_srcdir) has no meaning in configure.
+# However there are other variables, like CC, which are often used in
+# configure, and could therefore not use this "fixed" $ac_aux_dir.
+#
+# Another solution, used here, is to always expand $ac_aux_dir to an
+# absolute PATH.  The drawback is that using absolute paths prevent a
+# configured tree to be moved without reconfiguration.
+
+AC_DEFUN([AM_AUX_DIR_EXPAND],
+[dnl Rely on autoconf to set up CDPATH properly.
+AC_PREREQ([2.50])dnl
+# expand $ac_aux_dir to an absolute path
+am_aux_dir=`cd $ac_aux_dir && pwd`
+])
+
+# AM_CONDITIONAL                                            -*- Autoconf -*-
+
+# Copyright (C) 1997-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_CONDITIONAL(NAME, SHELL-CONDITION)
+# -------------------------------------
+# Define a conditional.
+AC_DEFUN([AM_CONDITIONAL],
+[AC_PREREQ([2.52])dnl
+ m4_if([$1], [TRUE],  [AC_FATAL([$0: invalid condition: $1])],
+       [$1], [FALSE], [AC_FATAL([$0: invalid condition: $1])])dnl
+AC_SUBST([$1_TRUE])dnl
+AC_SUBST([$1_FALSE])dnl
+_AM_SUBST_NOTMAKE([$1_TRUE])dnl
+_AM_SUBST_NOTMAKE([$1_FALSE])dnl
+m4_define([_AM_COND_VALUE_$1], [$2])dnl
+if $2; then
+  $1_TRUE=
+  $1_FALSE='#'
+else
+  $1_TRUE='#'
+  $1_FALSE=
+fi
+AC_CONFIG_COMMANDS_PRE(
+[if test -z "${$1_TRUE}" && test -z "${$1_FALSE}"; then
+  AC_MSG_ERROR([[conditional "$1" was never defined.
+Usually this means the macro was only invoked conditionally.]])
+fi])])
+
+# Copyright (C) 1999-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+
+# There are a few dirty hacks below to avoid letting 'AC_PROG_CC' be
+# written in clear, in which case automake, when reading aclocal.m4,
+# will think it sees a *use*, and therefore will trigger all it's
+# C support machinery.  Also note that it means that autoscan, seeing
+# CC etc. in the Makefile, will ask for an AC_PROG_CC use...
+
+
+# _AM_DEPENDENCIES(NAME)
+# ----------------------
+# See how the compiler implements dependency checking.
+# NAME is "CC", "CXX", "OBJC", "OBJCXX", "UPC", or "GJC".
+# We try a few techniques and use that to set a single cache variable.
+#
+# We don't AC_REQUIRE the corresponding AC_PROG_CC since the latter was
+# modified to invoke _AM_DEPENDENCIES(CC); we would have a circular
+# dependency, and given that the user is not expected to run this macro,
+# just rely on AC_PROG_CC.
+AC_DEFUN([_AM_DEPENDENCIES],
+[AC_REQUIRE([AM_SET_DEPDIR])dnl
+AC_REQUIRE([AM_OUTPUT_DEPENDENCY_COMMANDS])dnl
+AC_REQUIRE([AM_MAKE_INCLUDE])dnl
+AC_REQUIRE([AM_DEP_TRACK])dnl
+
+m4_if([$1], [CC],   [depcc="$CC"   am_compiler_list=],
+      [$1], [CXX],  [depcc="$CXX"  am_compiler_list=],
+      [$1], [OBJC], [depcc="$OBJC" am_compiler_list='gcc3 gcc'],
+      [$1], [OBJCXX], [depcc="$OBJCXX" am_compiler_list='gcc3 gcc'],
+      [$1], [UPC],  [depcc="$UPC"  am_compiler_list=],
+      [$1], [GCJ],  [depcc="$GCJ"  am_compiler_list='gcc3 gcc'],
+                    [depcc="$$1"   am_compiler_list=])
+
+AC_CACHE_CHECK([dependency style of $depcc],
+               [am_cv_$1_dependencies_compiler_type],
+[if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then
+  # We make a subdir and do the tests there.  Otherwise we can end up
+  # making bogus files that we don't know about and never remove.  For
+  # instance it was reported that on HP-UX the gcc test will end up
+  # making a dummy file named 'D' -- because '-MD' means "put the output
+  # in D".
+  rm -rf conftest.dir
+  mkdir conftest.dir
+  # Copy depcomp to subdir because otherwise we won't find it if we're
+  # using a relative directory.
+  cp "$am_depcomp" conftest.dir
+  cd conftest.dir
+  # We will build objects and dependencies in a subdirectory because
+  # it helps to detect inapplicable dependency modes.  For instance
+  # both Tru64's cc and ICC support -MD to output dependencies as a
+  # side effect of compilation, but ICC will put the dependencies in
+  # the current directory while Tru64 will put them in the object
+  # directory.
+  mkdir sub
+
+  am_cv_$1_dependencies_compiler_type=none
+  if test "$am_compiler_list" = ""; then
+     am_compiler_list=`sed -n ['s/^#*\([a-zA-Z0-9]*\))$/\1/p'] < ./depcomp`
+  fi
+  am__universal=false
+  m4_case([$1], [CC],
+    [case " $depcc " in #(
+     *\ -arch\ *\ -arch\ *) am__universal=true ;;
+     esac],
+    [CXX],
+    [case " $depcc " in #(
+     *\ -arch\ *\ -arch\ *) am__universal=true ;;
+     esac])
+
+  for depmode in $am_compiler_list; do
+    # Setup a source with many dependencies, because some compilers
+    # like to wrap large dependency lists on column 80 (with \), and
+    # we should not choose a depcomp mode which is confused by this.
+    #
+    # We need to recreate these files for each test, as the compiler may
+    # overwrite some of them when testing with obscure command lines.
+    # This happens at least with the AIX C compiler.
+    : > sub/conftest.c
+    for i in 1 2 3 4 5 6; do
+      echo '#include "conftst'$i'.h"' >> sub/conftest.c
+      # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with
+      # Solaris 10 /bin/sh.
+      echo '/* dummy */' > sub/conftst$i.h
+    done
+    echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf
+
+    # We check with '-c' and '-o' for the sake of the "dashmstdout"
+    # mode.  It turns out that the SunPro C++ compiler does not properly
+    # handle '-M -o', and we need to detect this.  Also, some Intel
+    # versions had trouble with output in subdirs.
+    am__obj=sub/conftest.${OBJEXT-o}
+    am__minus_obj="-o $am__obj"
+    case $depmode in
+    gcc)
+      # This depmode causes a compiler race in universal mode.
+      test "$am__universal" = false || continue
+      ;;
+    nosideeffect)
+      # After this tag, mechanisms are not by side-effect, so they'll
+      # only be used when explicitly requested.
+      if test "x$enable_dependency_tracking" = xyes; then
+       continue
+      else
+       break
+      fi
+      ;;
+    msvc7 | msvc7msys | msvisualcpp | msvcmsys)
+      # This compiler won't grok '-c -o', but also, the minuso test has
+      # not run yet.  These depmodes are late enough in the game, and
+      # so weak that their functioning should not be impacted.
+      am__obj=conftest.${OBJEXT-o}
+      am__minus_obj=
+      ;;
+    none) break ;;
+    esac
+    if depmode=$depmode \
+       source=sub/conftest.c object=$am__obj \
+       depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \
+       $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \
+         >/dev/null 2>conftest.err &&
+       grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&
+       grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&
+       grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&
+       ${MAKE-make} -s -f confmf > /dev/null 2>&1; then
+      # icc doesn't choke on unknown options, it will just issue warnings
+      # or remarks (even with -Werror).  So we grep stderr for any message
+      # that says an option was ignored or not supported.
+      # When given -MP, icc 7.0 and 7.1 complain thusly:
+      #   icc: Command line warning: ignoring option '-M'; no argument required
+      # The diagnosis changed in icc 8.0:
+      #   icc: Command line remark: option '-MP' not supported
+      if (grep 'ignoring option' conftest.err ||
+          grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else
+        am_cv_$1_dependencies_compiler_type=$depmode
+        break
+      fi
+    fi
+  done
+
+  cd ..
+  rm -rf conftest.dir
+else
+  am_cv_$1_dependencies_compiler_type=none
+fi
+])
+AC_SUBST([$1DEPMODE], [depmode=$am_cv_$1_dependencies_compiler_type])
+AM_CONDITIONAL([am__fastdep$1], [
+  test "x$enable_dependency_tracking" != xno \
+  && test "$am_cv_$1_dependencies_compiler_type" = gcc3])
+])
+
+
+# AM_SET_DEPDIR
+# -------------
+# Choose a directory name for dependency files.
+# This macro is AC_REQUIREd in _AM_DEPENDENCIES.
+AC_DEFUN([AM_SET_DEPDIR],
+[AC_REQUIRE([AM_SET_LEADING_DOT])dnl
+AC_SUBST([DEPDIR], ["${am__leading_dot}deps"])dnl
+])
+
+
+# AM_DEP_TRACK
+# ------------
+AC_DEFUN([AM_DEP_TRACK],
+[AC_ARG_ENABLE([dependency-tracking], [dnl
+AS_HELP_STRING(
+  [--enable-dependency-tracking],
+  [do not reject slow dependency extractors])
+AS_HELP_STRING(
+  [--disable-dependency-tracking],
+  [speeds up one-time build])])
+if test "x$enable_dependency_tracking" != xno; then
+  am_depcomp="$ac_aux_dir/depcomp"
+  AMDEPBACKSLASH='\'
+  am__nodep='_no'
+fi
+AM_CONDITIONAL([AMDEP], [test "x$enable_dependency_tracking" != xno])
+AC_SUBST([AMDEPBACKSLASH])dnl
+_AM_SUBST_NOTMAKE([AMDEPBACKSLASH])dnl
+AC_SUBST([am__nodep])dnl
+_AM_SUBST_NOTMAKE([am__nodep])dnl
+])
+
+# Generate code to set up dependency tracking.              -*- Autoconf -*-
+
+# Copyright (C) 1999-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+
+# _AM_OUTPUT_DEPENDENCY_COMMANDS
+# ------------------------------
+AC_DEFUN([_AM_OUTPUT_DEPENDENCY_COMMANDS],
+[{
+  # Older Autoconf quotes --file arguments for eval, but not when files
+  # are listed without --file.  Let's play safe and only enable the eval
+  # if we detect the quoting.
+  case $CONFIG_FILES in
+  *\'*) eval set x "$CONFIG_FILES" ;;
+  *)   set x $CONFIG_FILES ;;
+  esac
+  shift
+  for mf
+  do
+    # Strip MF so we end up with the name of the file.
+    mf=`echo "$mf" | sed -e 's/:.*$//'`
+    # Check whether this is an Automake generated Makefile or not.
+    # We used to match only the files named 'Makefile.in', but
+    # some people rename them; so instead we look at the file content.
+    # Grep'ing the first line is not enough: some people post-process
+    # each Makefile.in and add a new line on top of each file to say so.
+    # Grep'ing the whole file is not good either: AIX grep has a line
+    # limit of 2048, but all sed's we know have understand at least 4000.
+    if sed -n 's,^#.*generated by automake.*,X,p' "$mf" | grep X >/dev/null 2>&1; then
+      dirpart=`AS_DIRNAME("$mf")`
+    else
+      continue
+    fi
+    # Extract the definition of DEPDIR, am__include, and am__quote
+    # from the Makefile without running 'make'.
+    DEPDIR=`sed -n 's/^DEPDIR = //p' < "$mf"`
+    test -z "$DEPDIR" && continue
+    am__include=`sed -n 's/^am__include = //p' < "$mf"`
+    test -z "$am__include" && continue
+    am__quote=`sed -n 's/^am__quote = //p' < "$mf"`
+    # Find all dependency output files, they are included files with
+    # $(DEPDIR) in their names.  We invoke sed twice because it is the
+    # simplest approach to changing $(DEPDIR) to its actual value in the
+    # expansion.
+    for file in `sed -n "
+      s/^$am__include $am__quote\(.*(DEPDIR).*\)$am__quote"'$/\1/p' <"$mf" | \
+        sed -e 's/\$(DEPDIR)/'"$DEPDIR"'/g'`; do
+      # Make sure the directory exists.
+      test -f "$dirpart/$file" && continue
+      fdir=`AS_DIRNAME(["$file"])`
+      AS_MKDIR_P([$dirpart/$fdir])
+      # echo "creating $dirpart/$file"
+      echo '# dummy' > "$dirpart/$file"
+    done
+  done
+}
+])# _AM_OUTPUT_DEPENDENCY_COMMANDS
+
+
+# AM_OUTPUT_DEPENDENCY_COMMANDS
+# -----------------------------
+# This macro should only be invoked once -- use via AC_REQUIRE.
+#
+# This code is only required when automatic dependency tracking
+# is enabled.  FIXME.  This creates each '.P' file that we will
+# need in order to bootstrap the dependency handling code.
+AC_DEFUN([AM_OUTPUT_DEPENDENCY_COMMANDS],
+[AC_CONFIG_COMMANDS([depfiles],
+     [test x"$AMDEP_TRUE" != x"" || _AM_OUTPUT_DEPENDENCY_COMMANDS],
+     [AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"])
+])
+
+# Do all the work for Automake.                             -*- Autoconf -*-
+
+# Copyright (C) 1996-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This macro actually does too much.  Some checks are only needed if
+# your package does certain things.  But this isn't really a big deal.
+
+dnl Redefine AC_PROG_CC to automatically invoke _AM_PROG_CC_C_O.
+m4_define([AC_PROG_CC],
+m4_defn([AC_PROG_CC])
+[_AM_PROG_CC_C_O
+])
+
+# AM_INIT_AUTOMAKE(PACKAGE, VERSION, [NO-DEFINE])
+# AM_INIT_AUTOMAKE([OPTIONS])
+# -----------------------------------------------
+# The call with PACKAGE and VERSION arguments is the old style
+# call (pre autoconf-2.50), which is being phased out.  PACKAGE
+# and VERSION should now be passed to AC_INIT and removed from
+# the call to AM_INIT_AUTOMAKE.
+# We support both call styles for the transition.  After
+# the next Automake release, Autoconf can make the AC_INIT
+# arguments mandatory, and then we can depend on a new Autoconf
+# release and drop the old call support.
+AC_DEFUN([AM_INIT_AUTOMAKE],
+[AC_PREREQ([2.65])dnl
+dnl Autoconf wants to disallow AM_ names.  We explicitly allow
+dnl the ones we care about.
+m4_pattern_allow([^AM_[A-Z]+FLAGS$])dnl
+AC_REQUIRE([AM_SET_CURRENT_AUTOMAKE_VERSION])dnl
+AC_REQUIRE([AC_PROG_INSTALL])dnl
+if test "`cd $srcdir && pwd`" != "`pwd`"; then
+  # Use -I$(srcdir) only when $(srcdir) != ., so that make's output
+  # is not polluted with repeated "-I."
+  AC_SUBST([am__isrc], [' -I$(srcdir)'])_AM_SUBST_NOTMAKE([am__isrc])dnl
+  # test to see if srcdir already configured
+  if test -f $srcdir/config.status; then
+    AC_MSG_ERROR([source directory already configured; run "make distclean" there first])
+  fi
+fi
+
+# test whether we have cygpath
+if test -z "$CYGPATH_W"; then
+  if (cygpath --version) >/dev/null 2>/dev/null; then
+    CYGPATH_W='cygpath -w'
+  else
+    CYGPATH_W=echo
+  fi
+fi
+AC_SUBST([CYGPATH_W])
+
+# Define the identity of the package.
+dnl Distinguish between old-style and new-style calls.
+m4_ifval([$2],
+[AC_DIAGNOSE([obsolete],
+             [$0: two- and three-arguments forms are deprecated.])
+m4_ifval([$3], [_AM_SET_OPTION([no-define])])dnl
+ AC_SUBST([PACKAGE], [$1])dnl
+ AC_SUBST([VERSION], [$2])],
+[_AM_SET_OPTIONS([$1])dnl
+dnl Diagnose old-style AC_INIT with new-style AM_AUTOMAKE_INIT.
+m4_if(
+  m4_ifdef([AC_PACKAGE_NAME], [ok]):m4_ifdef([AC_PACKAGE_VERSION], [ok]),
+  [ok:ok],,
+  [m4_fatal([AC_INIT should be called with package and version arguments])])dnl
+ AC_SUBST([PACKAGE], ['AC_PACKAGE_TARNAME'])dnl
+ AC_SUBST([VERSION], ['AC_PACKAGE_VERSION'])])dnl
+
+_AM_IF_OPTION([no-define],,
+[AC_DEFINE_UNQUOTED([PACKAGE], ["$PACKAGE"], [Name of package])
+ AC_DEFINE_UNQUOTED([VERSION], ["$VERSION"], [Version number of package])])dnl
+
+# Some tools Automake needs.
+AC_REQUIRE([AM_SANITY_CHECK])dnl
+AC_REQUIRE([AC_ARG_PROGRAM])dnl
+AM_MISSING_PROG([ACLOCAL], [aclocal-${am__api_version}])
+AM_MISSING_PROG([AUTOCONF], [autoconf])
+AM_MISSING_PROG([AUTOMAKE], [automake-${am__api_version}])
+AM_MISSING_PROG([AUTOHEADER], [autoheader])
+AM_MISSING_PROG([MAKEINFO], [makeinfo])
+AC_REQUIRE([AM_PROG_INSTALL_SH])dnl
+AC_REQUIRE([AM_PROG_INSTALL_STRIP])dnl
+AC_REQUIRE([AC_PROG_MKDIR_P])dnl
+# For better backward compatibility.  To be removed once Automake 1.9.x
+# dies out for good.  For more background, see:
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>
+AC_SUBST([mkdir_p], ['$(MKDIR_P)'])
+# We need awk for the "check" target.  The system "awk" is bad on
+# some platforms.
+AC_REQUIRE([AC_PROG_AWK])dnl
+AC_REQUIRE([AC_PROG_MAKE_SET])dnl
+AC_REQUIRE([AM_SET_LEADING_DOT])dnl
+_AM_IF_OPTION([tar-ustar], [_AM_PROG_TAR([ustar])],
+             [_AM_IF_OPTION([tar-pax], [_AM_PROG_TAR([pax])],
+                            [_AM_PROG_TAR([v7])])])
+_AM_IF_OPTION([no-dependencies],,
+[AC_PROVIDE_IFELSE([AC_PROG_CC],
+                 [_AM_DEPENDENCIES([CC])],
+                 [m4_define([AC_PROG_CC],
+                            m4_defn([AC_PROG_CC])[_AM_DEPENDENCIES([CC])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_CXX],
+                 [_AM_DEPENDENCIES([CXX])],
+                 [m4_define([AC_PROG_CXX],
+                            m4_defn([AC_PROG_CXX])[_AM_DEPENDENCIES([CXX])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_OBJC],
+                 [_AM_DEPENDENCIES([OBJC])],
+                 [m4_define([AC_PROG_OBJC],
+                            m4_defn([AC_PROG_OBJC])[_AM_DEPENDENCIES([OBJC])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_OBJCXX],
+                 [_AM_DEPENDENCIES([OBJCXX])],
+                 [m4_define([AC_PROG_OBJCXX],
+                            m4_defn([AC_PROG_OBJCXX])[_AM_DEPENDENCIES([OBJCXX])])])dnl
+])
+AC_REQUIRE([AM_SILENT_RULES])dnl
+dnl The testsuite driver may need to know about EXEEXT, so add the
+dnl 'am__EXEEXT' conditional if _AM_COMPILER_EXEEXT was seen.  This
+dnl macro is hooked onto _AC_COMPILER_EXEEXT early, see below.
+AC_CONFIG_COMMANDS_PRE(dnl
+[m4_provide_if([_AM_COMPILER_EXEEXT],
+  [AM_CONDITIONAL([am__EXEEXT], [test -n "$EXEEXT"])])])dnl
+
+# POSIX will say in a future version that running "rm -f" with no argument
+# is OK; and we want to be able to make that assumption in our Makefile
+# recipes.  So use an aggressive probe to check that the usage we want is
+# actually supported "in the wild" to an acceptable degree.
+# See automake bug#10828.
+# To make any issue more visible, cause the running configure to be aborted
+# by default if the 'rm' program in use doesn't match our expectations; the
+# user can still override this though.
+if rm -f && rm -fr && rm -rf; then : OK; else
+  cat >&2 <<'END'
+Oops!
+
+Your 'rm' program seems unable to run without file operands specified
+on the command line, even when the '-f' option is present.  This is contrary
+to the behaviour of most rm programs out there, and not conforming with
+the upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>
+
+Please tell bug-automake@gnu.org about your system, including the value
+of your $PATH and any error possibly output before this message.  This
+can help us improve future automake versions.
+
+END
+  if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then
+    echo 'Configuration will proceed anyway, since you have set the' >&2
+    echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2
+    echo >&2
+  else
+    cat >&2 <<'END'
+Aborting the configuration process, to ensure you take notice of the issue.
+
+You can download and install GNU coreutils to get an 'rm' implementation
+that behaves properly: <http://www.gnu.org/software/coreutils/>.
+
+If you want to complete the configuration process using your problematic
+'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM
+to "yes", and re-run configure.
+
+END
+    AC_MSG_ERROR([Your 'rm' program is bad, sorry.])
+  fi
+fi])
+
+dnl Hook into '_AC_COMPILER_EXEEXT' early to learn its expansion.  Do not
+dnl add the conditional right here, as _AC_COMPILER_EXEEXT may be further
+dnl mangled by Autoconf and run in a shell conditional statement.
+m4_define([_AC_COMPILER_EXEEXT],
+m4_defn([_AC_COMPILER_EXEEXT])[m4_provide([_AM_COMPILER_EXEEXT])])
+
+# When config.status generates a header, we must update the stamp-h file.
+# This file resides in the same directory as the config header
+# that is generated.  The stamp files are numbered to have different names.
+
+# Autoconf calls _AC_AM_CONFIG_HEADER_HOOK (when defined) in the
+# loop where config.status creates the headers, so we can generate
+# our stamp files there.
+AC_DEFUN([_AC_AM_CONFIG_HEADER_HOOK],
+[# Compute $1's index in $config_headers.
+_am_arg=$1
+_am_stamp_count=1
+for _am_header in $config_headers :; do
+  case $_am_header in
+    $_am_arg | $_am_arg:* )
+      break ;;
+    * )
+      _am_stamp_count=`expr $_am_stamp_count + 1` ;;
+  esac
+done
+echo "timestamp for $_am_arg" >`AS_DIRNAME(["$_am_arg"])`/stamp-h[]$_am_stamp_count])
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_INSTALL_SH
+# ------------------
+# Define $install_sh.
+AC_DEFUN([AM_PROG_INSTALL_SH],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+if test x"${install_sh}" != xset; then
+  case $am_aux_dir in
+  *\ * | *\    *)
+    install_sh="\${SHELL} '$am_aux_dir/install-sh'" ;;
+  *)
+    install_sh="\${SHELL} $am_aux_dir/install-sh"
+  esac
+fi
+AC_SUBST([install_sh])])
+
+# Copyright (C) 2003-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# Check whether the underlying file-system supports filenames
+# with a leading dot.  For instance MS-DOS doesn't.
+AC_DEFUN([AM_SET_LEADING_DOT],
+[rm -rf .tst 2>/dev/null
+mkdir .tst 2>/dev/null
+if test -d .tst; then
+  am__leading_dot=.
+else
+  am__leading_dot=_
+fi
+rmdir .tst 2>/dev/null
+AC_SUBST([am__leading_dot])])
+
+# Check to see how 'make' treats includes.                 -*- Autoconf -*-
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_MAKE_INCLUDE()
+# -----------------
+# Check to see how make treats includes.
+AC_DEFUN([AM_MAKE_INCLUDE],
+[am_make=${MAKE-make}
+cat > confinc << 'END'
+am__doit:
+       @echo this is the am__doit target
+.PHONY: am__doit
+END
+# If we don't find an include directive, just comment out the code.
+AC_MSG_CHECKING([for style of include used by $am_make])
+am__include="#"
+am__quote=
+_am_result=none
+# First try GNU make style include.
+echo "include confinc" > confmf
+# Ignore all kinds of additional output from 'make'.
+case `$am_make -s -f confmf 2> /dev/null` in #(
+*the\ am__doit\ target*)
+  am__include=include
+  am__quote=
+  _am_result=GNU
+  ;;
+esac
+# Now try BSD make style include.
+if test "$am__include" = "#"; then
+   echo '.include "confinc"' > confmf
+   case `$am_make -s -f confmf 2> /dev/null` in #(
+   *the\ am__doit\ target*)
+     am__include=.include
+     am__quote="\""
+     _am_result=BSD
+     ;;
+   esac
+fi
+AC_SUBST([am__include])
+AC_SUBST([am__quote])
+AC_MSG_RESULT([$_am_result])
+rm -f confinc confmf
+])
+
+# Fake the existence of programs that GNU maintainers use.  -*- Autoconf -*-
+
+# Copyright (C) 1997-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_MISSING_PROG(NAME, PROGRAM)
+# ------------------------------
+AC_DEFUN([AM_MISSING_PROG],
+[AC_REQUIRE([AM_MISSING_HAS_RUN])
+$1=${$1-"${am_missing_run}$2"}
+AC_SUBST($1)])
+
+# AM_MISSING_HAS_RUN
+# ------------------
+# Define MISSING if not defined so far and test if it is modern enough.
+# If it is, set am_missing_run to use it, otherwise, to nothing.
+AC_DEFUN([AM_MISSING_HAS_RUN],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+AC_REQUIRE_AUX_FILE([missing])dnl
+if test x"${MISSING+set}" != xset; then
+  case $am_aux_dir in
+  *\ * | *\    *)
+    MISSING="\${SHELL} \"$am_aux_dir/missing\"" ;;
+  *)
+    MISSING="\${SHELL} $am_aux_dir/missing" ;;
+  esac
+fi
+# Use eval to expand $SHELL
+if eval "$MISSING --is-lightweight"; then
+  am_missing_run="$MISSING "
+else
+  am_missing_run=
+  AC_MSG_WARN(['missing' script is too old or missing])
+fi
+])
+
+# Helper functions for option handling.                     -*- Autoconf -*-
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_MANGLE_OPTION(NAME)
+# -----------------------
+AC_DEFUN([_AM_MANGLE_OPTION],
+[[_AM_OPTION_]m4_bpatsubst($1, [[^a-zA-Z0-9_]], [_])])
+
+# _AM_SET_OPTION(NAME)
+# --------------------
+# Set option NAME.  Presently that only means defining a flag for this option.
+AC_DEFUN([_AM_SET_OPTION],
+[m4_define(_AM_MANGLE_OPTION([$1]), [1])])
+
+# _AM_SET_OPTIONS(OPTIONS)
+# ------------------------
+# OPTIONS is a space-separated list of Automake options.
+AC_DEFUN([_AM_SET_OPTIONS],
+[m4_foreach_w([_AM_Option], [$1], [_AM_SET_OPTION(_AM_Option)])])
+
+# _AM_IF_OPTION(OPTION, IF-SET, [IF-NOT-SET])
+# -------------------------------------------
+# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise.
+AC_DEFUN([_AM_IF_OPTION],
+[m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])])
+
+# Copyright (C) 1999-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_CC_C_O
+# ---------------
+# Like AC_PROG_CC_C_O, but changed for automake.  We rewrite AC_PROG_CC
+# to automatically call this.
+AC_DEFUN([_AM_PROG_CC_C_O],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+AC_REQUIRE_AUX_FILE([compile])dnl
+AC_LANG_PUSH([C])dnl
+AC_CACHE_CHECK(
+  [whether $CC understands -c and -o together],
+  [am_cv_prog_cc_c_o],
+  [AC_LANG_CONFTEST([AC_LANG_PROGRAM([])])
+  # Make sure it works both with $CC and with simple cc.
+  # Following AC_PROG_CC_C_O, we do the test twice because some
+  # compilers refuse to overwrite an existing .o file with -o,
+  # though they will create one.
+  am_cv_prog_cc_c_o=yes
+  for am_i in 1 2; do
+    if AM_RUN_LOG([$CC -c conftest.$ac_ext -o conftest2.$ac_objext]) \
+         && test -f conftest2.$ac_objext; then
+      : OK
+    else
+      am_cv_prog_cc_c_o=no
+      break
+    fi
+  done
+  rm -f core conftest*
+  unset am_i])
+if test "$am_cv_prog_cc_c_o" != yes; then
+   # Losing compiler, so override with the script.
+   # FIXME: It is wrong to rewrite CC.
+   # But if we don't then we get into trouble of one sort or another.
+   # A longer-term fix would be to have automake use am__CC in this case,
+   # and then we could set am__CC="\$(top_srcdir)/compile \$(CC)"
+   CC="$am_aux_dir/compile $CC"
+fi
+AC_LANG_POP([C])])
+
+# For backward compatibility.
+AC_DEFUN_ONCE([AM_PROG_CC_C_O], [AC_REQUIRE([AC_PROG_CC])])
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_RUN_LOG(COMMAND)
+# -------------------
+# Run COMMAND, save the exit status in ac_status, and log it.
+# (This has been adapted from Autoconf's _AC_RUN_LOG macro.)
+AC_DEFUN([AM_RUN_LOG],
+[{ echo "$as_me:$LINENO: $1" >&AS_MESSAGE_LOG_FD
+   ($1) >&AS_MESSAGE_LOG_FD 2>&AS_MESSAGE_LOG_FD
+   ac_status=$?
+   echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD
+   (exit $ac_status); }])
+
+# Check to make sure that the build environment is sane.    -*- Autoconf -*-
+
+# Copyright (C) 1996-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_SANITY_CHECK
+# ---------------
+AC_DEFUN([AM_SANITY_CHECK],
+[AC_MSG_CHECKING([whether build environment is sane])
+# Reject unsafe characters in $srcdir or the absolute working directory
+# name.  Accept space and tab only in the latter.
+am_lf='
+'
+case `pwd` in
+  *[[\\\"\#\$\&\'\`$am_lf]]*)
+    AC_MSG_ERROR([unsafe absolute working directory name]);;
+esac
+case $srcdir in
+  *[[\\\"\#\$\&\'\`$am_lf\ \   ]]*)
+    AC_MSG_ERROR([unsafe srcdir value: '$srcdir']);;
+esac
+
+# Do 'set' in a subshell so we don't clobber the current shell's
+# arguments.  Must try -L first in case configure is actually a
+# symlink; some systems play weird games with the mod time of symlinks
+# (eg FreeBSD returns the mod time of the symlink's containing
+# directory).
+if (
+   am_has_slept=no
+   for am_try in 1 2; do
+     echo "timestamp, slept: $am_has_slept" > conftest.file
+     set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
+     if test "$[*]" = "X"; then
+       # -L didn't work.
+       set X `ls -t "$srcdir/configure" conftest.file`
+     fi
+     if test "$[*]" != "X $srcdir/configure conftest.file" \
+       && test "$[*]" != "X conftest.file $srcdir/configure"; then
+
+       # If neither matched, then we have a broken ls.  This can happen
+       # if, for instance, CONFIG_SHELL is bash and it inherits a
+       # broken ls alias from the environment.  This has actually
+       # happened.  Such a system could not be considered "sane".
+       AC_MSG_ERROR([ls -t appears to fail.  Make sure there is not a broken
+  alias in your environment])
+     fi
+     if test "$[2]" = conftest.file || test $am_try -eq 2; then
+       break
+     fi
+     # Just in case.
+     sleep 1
+     am_has_slept=yes
+   done
+   test "$[2]" = conftest.file
+   )
+then
+   # Ok.
+   :
+else
+   AC_MSG_ERROR([newly created file is older than distributed files!
+Check your system clock])
+fi
+AC_MSG_RESULT([yes])
+# If we didn't sleep, we still need to ensure time stamps of config.status and
+# generated files are strictly newer.
+am_sleep_pid=
+if grep 'slept: no' conftest.file >/dev/null 2>&1; then
+  ( sleep 1 ) &
+  am_sleep_pid=$!
+fi
+AC_CONFIG_COMMANDS_PRE(
+  [AC_MSG_CHECKING([that generated files are newer than configure])
+   if test -n "$am_sleep_pid"; then
+     # Hide warnings about reused PIDs.
+     wait $am_sleep_pid 2>/dev/null
+   fi
+   AC_MSG_RESULT([done])])
+rm -f conftest.file
+])
+
+# Copyright (C) 2009-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_SILENT_RULES([DEFAULT])
+# --------------------------
+# Enable less verbose build rules; with the default set to DEFAULT
+# ("yes" being less verbose, "no" or empty being verbose).
+AC_DEFUN([AM_SILENT_RULES],
+[AC_ARG_ENABLE([silent-rules], [dnl
+AS_HELP_STRING(
+  [--enable-silent-rules],
+  [less verbose build output (undo: "make V=1")])
+AS_HELP_STRING(
+  [--disable-silent-rules],
+  [verbose build output (undo: "make V=0")])dnl
+])
+case $enable_silent_rules in @%:@ (((
+  yes) AM_DEFAULT_VERBOSITY=0;;
+   no) AM_DEFAULT_VERBOSITY=1;;
+    *) AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1]);;
+esac
+dnl
+dnl A few 'make' implementations (e.g., NonStop OS and NextStep)
+dnl do not support nested variable expansions.
+dnl See automake bug#9928 and bug#10237.
+am_make=${MAKE-make}
+AC_CACHE_CHECK([whether $am_make supports nested variables],
+   [am_cv_make_support_nested_variables],
+   [if AS_ECHO([['TRUE=$(BAR$(V))
+BAR0=false
+BAR1=true
+V=1
+am__doit:
+       @$(TRUE)
+.PHONY: am__doit']]) | $am_make -f - >/dev/null 2>&1; then
+  am_cv_make_support_nested_variables=yes
+else
+  am_cv_make_support_nested_variables=no
+fi])
+if test $am_cv_make_support_nested_variables = yes; then
+  dnl Using '$V' instead of '$(V)' breaks IRIX make.
+  AM_V='$(V)'
+  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
+else
+  AM_V=$AM_DEFAULT_VERBOSITY
+  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
+fi
+AC_SUBST([AM_V])dnl
+AM_SUBST_NOTMAKE([AM_V])dnl
+AC_SUBST([AM_DEFAULT_V])dnl
+AM_SUBST_NOTMAKE([AM_DEFAULT_V])dnl
+AC_SUBST([AM_DEFAULT_VERBOSITY])dnl
+AM_BACKSLASH='\'
+AC_SUBST([AM_BACKSLASH])dnl
+_AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl
+])
+
+# Copyright (C) 2001-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_INSTALL_STRIP
+# ---------------------
+# One issue with vendor 'install' (even GNU) is that you can't
+# specify the program used to strip binaries.  This is especially
+# annoying in cross-compiling environments, where the build's strip
+# is unlikely to handle the host's binaries.
+# Fortunately install-sh will honor a STRIPPROG variable, so we
+# always use install-sh in "make install-strip", and initialize
+# STRIPPROG with the value of the STRIP variable (set by the user).
+AC_DEFUN([AM_PROG_INSTALL_STRIP],
+[AC_REQUIRE([AM_PROG_INSTALL_SH])dnl
+# Installed binaries are usually stripped using 'strip' when the user
+# run "make install-strip".  However 'strip' might not be the right
+# tool to use in cross-compilation environments, therefore Automake
+# will honor the 'STRIP' environment variable to overrule this program.
+dnl Don't test for $cross_compiling = yes, because it might be 'maybe'.
+if test "$cross_compiling" != no; then
+  AC_CHECK_TOOL([STRIP], [strip], :)
+fi
+INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
+AC_SUBST([INSTALL_STRIP_PROGRAM])])
+
+# Copyright (C) 2006-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_SUBST_NOTMAKE(VARIABLE)
+# ---------------------------
+# Prevent Automake from outputting VARIABLE = @VARIABLE@ in Makefile.in.
+# This macro is traced by Automake.
+AC_DEFUN([_AM_SUBST_NOTMAKE])
+
+# AM_SUBST_NOTMAKE(VARIABLE)
+# --------------------------
+# Public sister of _AM_SUBST_NOTMAKE.
+AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)])
+
+# Check how to create a tarball.                            -*- Autoconf -*-
+
+# Copyright (C) 2004-2013 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_TAR(FORMAT)
+# --------------------
+# Check how to create a tarball in format FORMAT.
+# FORMAT should be one of 'v7', 'ustar', or 'pax'.
+#
+# Substitute a variable $(am__tar) that is a command
+# writing to stdout a FORMAT-tarball containing the directory
+# $tardir.
+#     tardir=directory && $(am__tar) > result.tar
+#
+# Substitute a variable $(am__untar) that extract such
+# a tarball read from stdin.
+#     $(am__untar) < result.tar
+#
+AC_DEFUN([_AM_PROG_TAR],
+[# Always define AMTAR for backward compatibility.  Yes, it's still used
+# in the wild :-(  We should find a proper way to deprecate it ...
+AC_SUBST([AMTAR], ['$${TAR-tar}'])
+
+# We'll loop over all known methods to create a tar archive until one works.
+_am_tools='gnutar m4_if([$1], [ustar], [plaintar]) pax cpio none'
+
+m4_if([$1], [v7],
+  [am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -'],
+
+  [m4_case([$1],
+    [ustar],
+     [# The POSIX 1988 'ustar' format is defined with fixed-size fields.
+      # There is notably a 21 bits limit for the UID and the GID.  In fact,
+      # the 'pax' utility can hang on bigger UID/GID (see automake bug#8343
+      # and bug#13588).
+      am_max_uid=2097151 # 2^21 - 1
+      am_max_gid=$am_max_uid
+      # The $UID and $GID variables are not portable, so we need to resort
+      # to the POSIX-mandated id(1) utility.  Errors in the 'id' calls
+      # below are definitely unexpected, so allow the users to see them
+      # (that is, avoid stderr redirection).
+      am_uid=`id -u || echo unknown`
+      am_gid=`id -g || echo unknown`
+      AC_MSG_CHECKING([whether UID '$am_uid' is supported by ustar format])
+      if test $am_uid -le $am_max_uid; then
+         AC_MSG_RESULT([yes])
+      else
+         AC_MSG_RESULT([no])
+         _am_tools=none
+      fi
+      AC_MSG_CHECKING([whether GID '$am_gid' is supported by ustar format])
+      if test $am_gid -le $am_max_gid; then
+         AC_MSG_RESULT([yes])
+      else
+        AC_MSG_RESULT([no])
+        _am_tools=none
+      fi],
+
+  [pax],
+    [],
+
+  [m4_fatal([Unknown tar format])])
+
+  AC_MSG_CHECKING([how to create a $1 tar archive])
+
+  # Go ahead even if we have the value already cached.  We do so because we
+  # need to set the values for the 'am__tar' and 'am__untar' variables.
+  _am_tools=${am_cv_prog_tar_$1-$_am_tools}
+
+  for _am_tool in $_am_tools; do
+    case $_am_tool in
+    gnutar)
+      for _am_tar in tar gnutar gtar; do
+        AM_RUN_LOG([$_am_tar --version]) && break
+      done
+      am__tar="$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - "'"$$tardir"'
+      am__tar_="$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - "'"$tardir"'
+      am__untar="$_am_tar -xf -"
+      ;;
+    plaintar)
+      # Must skip GNU tar: if it does not support --format= it doesn't create
+      # ustar tarball either.
+      (tar --version) >/dev/null 2>&1 && continue
+      am__tar='tar chf - "$$tardir"'
+      am__tar_='tar chf - "$tardir"'
+      am__untar='tar xf -'
+      ;;
+    pax)
+      am__tar='pax -L -x $1 -w "$$tardir"'
+      am__tar_='pax -L -x $1 -w "$tardir"'
+      am__untar='pax -r'
+      ;;
+    cpio)
+      am__tar='find "$$tardir" -print | cpio -o -H $1 -L'
+      am__tar_='find "$tardir" -print | cpio -o -H $1 -L'
+      am__untar='cpio -i -H $1 -d'
+      ;;
+    none)
+      am__tar=false
+      am__tar_=false
+      am__untar=false
+      ;;
+    esac
+
+    # If the value was cached, stop now.  We just wanted to have am__tar
+    # and am__untar set.
+    test -n "${am_cv_prog_tar_$1}" && break
+
+    # tar/untar a dummy directory, and stop if the command works.
+    rm -rf conftest.dir
+    mkdir conftest.dir
+    echo GrepMe > conftest.dir/file
+    AM_RUN_LOG([tardir=conftest.dir && eval $am__tar_ >conftest.tar])
+    rm -rf conftest.dir
+    if test -s conftest.tar; then
+      AM_RUN_LOG([$am__untar <conftest.tar])
+      AM_RUN_LOG([cat conftest.dir/file])
+      grep GrepMe conftest.dir/file >/dev/null 2>&1 && break
+    fi
+  done
+  rm -rf conftest.dir
+
+  AC_CACHE_VAL([am_cv_prog_tar_$1], [am_cv_prog_tar_$1=$_am_tool])
+  AC_MSG_RESULT([$am_cv_prog_tar_$1])])
+
+AC_SUBST([am__tar])
+AC_SUBST([am__untar])
+]) # _AM_PROG_TAR
+
+m4_include([acinclude.m4])
diff --git a/addon.c b/addon.c
new file mode 100644 (file)
index 0000000..6e6c232
--- /dev/null
+++ b/addon.c
@@ -0,0 +1,25 @@
+/*
+   This file is NOT BUILT by default.  Together with addon.h, it
+   provides an example of how to add new builtins to rc.
+*/
+
+#include "rc.h"
+#include "addon.h"
+
+void b_sum(char **av) {
+       long sum = 0;
+
+       while (*++av)
+               sum += atol(*av);
+       fprint(1, "%ld\n", sum);
+       set(TRUE);
+}
+
+void b_prod(char **av) {
+       long sum = 1;
+
+       while (*++av)
+               sum *= atol(*av);
+       fprint(1, "%ld\n", sum);
+       set(TRUE);
+}
diff --git a/addon.h b/addon.h
new file mode 100644 (file)
index 0000000..4a69375
--- /dev/null
+++ b/addon.h
@@ -0,0 +1,31 @@
+/*
+   This file is NOT BUILT by default.  Together with addon.c, it
+   provides an example of how to add new builtins to rc.
+
+   To define a new builtin, it must appear in the macro ADDONS, which
+   is a comma-separated list of pairs of function pointers (the
+   implementation of the new builtin) and string literals (the name of
+   the new builtin).
+
+   Any new builtin functions must also have proper prototypes in this
+   file.  This is always of the same form.
+
+       void b_NAME(char **av);
+
+   The first argument, av[0], is the name of the builtin.  The last
+   argument is followed by a NULL pointer.
+
+   Builtins report their exit status using set(TRUE) or set(FALSE).
+
+*/
+
+#if RC_ADDON
+
+#define ADDONS \
+       { b_sum,        "+" }, \
+       { b_prod, "x" },
+
+extern void b_sum(char **av);
+extern void b_prod(char **av);
+
+#endif
diff --git a/builtins.c b/builtins.c
new file mode 100644 (file)
index 0000000..75ac9cf
--- /dev/null
@@ -0,0 +1,558 @@
+/* builtins.c: the collection of rc's builtin commands */
+
+/*
+       NOTE: rc's builtins do not call "rc_error" because they are
+       commands, and rc errors usually arise from syntax errors. e.g.,
+       you probably don't want interpretation of a shell script to stop
+       because of a bad umask.
+*/
+
+#include "rc.h"
+
+#include <sys/ioctl.h>
+#include <sys/stat.h>
+#include <setjmp.h>
+#include <errno.h>
+
+#include "addon.h"
+#include "input.h"
+#include "jbwrap.h"
+#include "rlimit.h"
+#include "sigmsgs.h"
+
+static void b_break(char **), b_cd(char **), b_eval(char **), b_exit(char **),
+       b_newpgrp(char **), b_return(char **), b_shift(char **), b_umask(char **),
+       b_wait(char **), b_whatis(char **);
+
+#if HAVE_SETRLIMIT
+static void b_limit(char **);
+#endif
+
+#if RC_ECHO
+static void b_echo(char **);
+#endif
+
+static struct {
+       builtin_t *p;
+       char *name;
+} builtins[] = {
+       { b_break,      "break" },
+       { b_builtin,    "builtin" },
+       { b_cd,         "cd" },
+#if RC_ECHO
+       { b_echo,       "echo" },
+#endif
+       { b_eval,       "eval" },
+       { b_exec,       "exec" },
+       { b_exit,       "exit" },
+#if HAVE_SETRLIMIT
+       { b_limit,      "limit" },
+#endif
+       { b_newpgrp,    "newpgrp" },
+       { b_return,     "return" },
+       { b_shift,      "shift" },
+       { b_umask,      "umask" },
+       { b_wait,       "wait" },
+       { b_whatis,     "whatis" },
+       { b_dot,        "." },
+#ifdef ADDONS
+       ADDONS
+#endif
+};
+
+extern builtin_t *isbuiltin(char *s) {
+       int i;
+       for (i = 0; i < arraysize(builtins); i++)
+               if (streq(builtins[i].name, s))
+                       return builtins[i].p;
+       return NULL;
+}
+
+/* funcall() is the wrapper used to invoke shell functions. pushes $*, and "return" returns here. */
+
+extern void funcall(char **av) {
+       Jbwrap j;
+       Estack e1, e2;
+       Edata jreturn, star;
+       if (sigsetjmp(j.j, 1))
+               return;
+       starassign(*av, av+1, TRUE);
+       jreturn.jb = &j;
+       star.name = "*";
+       except(eReturn, jreturn, &e1);
+       except(eVarstack, star, &e2);
+       walk(treecpy(fnlookup(*av), nalloc), TRUE);
+       varrm("*", TRUE);
+       unexcept(); /* eVarstack */
+       unexcept(); /* eReturn */
+}
+
+static void arg_count(char *name) {
+       fprint(2, RC "too many arguments to %s\n", name);
+       set(FALSE);
+}
+
+static void badnum(char *num) {
+       fprint(2, RC "`%s' is a bad number\n", num);
+       set(FALSE);
+}
+
+/* a dummy command. (exec() performs "exec" simply by not forking) */
+
+extern void b_exec(char **ignore) {
+}
+
+#if RC_ECHO
+/* echo -n omits a newline. echo -- -n echos '-n' */
+
+static void b_echo(char **av) {
+       char *format = "%A\n";
+       if (*++av != NULL) {
+               if (streq(*av, "-n"))
+                       format = "%A", av++;
+               else if (streq(*av, "--"))
+                       av++;
+       }
+       fprint(1, format, av);
+       set(TRUE);
+}
+#endif
+
+/* cd. traverse $cdpath if the directory given is not an absolute pathname */
+
+static void b_cd(char **av) {
+       List *s, nil;
+       char *path = NULL;
+       size_t t, pathlen = 0;
+       if (*++av == NULL) {
+               s = varlookup("home");
+               *av = (s == NULL) ? "/" : s->w;
+       } else if (av[1] != NULL) {
+               arg_count("cd");
+               return;
+       }
+       if (isabsolute(*av) || streq(*av, ".") || streq(*av, "..")) { /* absolute pathname? */
+               if (chdir(*av) < 0) {
+                       set(FALSE);
+                       uerror(*av);
+               } else
+                       set(TRUE);
+       } else {
+               s = varlookup("cdpath");
+               if (s == NULL) {
+                       s = &nil;
+                       nil.w = "";
+                       nil.n = NULL;
+               }
+               do {
+                       if (s != &nil && *s->w != '\0') {
+                               t = strlen(*av) + strlen(s->w) + 2;
+                               if (t > pathlen)
+                                       path = nalloc(pathlen = t);
+                               strcpy(path, s->w);
+                               if (!streq(s->w, "/")) /* "//" is special to POSIX */
+                                       strcat(path, "/");
+                               strcat(path, *av);
+                       } else {
+                               pathlen = 0;
+                               path = *av;
+                       }
+                       if (chdir(path) >= 0) {
+                               set(TRUE);
+                               if (interactive && *s->w != '\0' && !streq(s->w, "."))
+                                       fprint(1, "%s\n", path);
+                               return;
+                       }
+                       s = s->n;
+               } while (s != NULL);
+               fprint(2, "couldn't cd to %s\n", *av);
+               set(FALSE);
+       }
+}
+
+static void b_umask(char **av) {
+       int i;
+       if (*++av == NULL) {
+               set(TRUE);
+               i = umask(0);
+               umask(i);
+               fprint(1, "0%o\n", i);
+       } else if (av[1] == NULL) {
+               i = o2u(*av);
+               if ((unsigned int) i > 0777) {
+                       fprint(2, "bad umask\n");
+                       set(FALSE);
+               } else {
+                       umask(i);
+                       set(TRUE);
+               }
+       } else {
+               arg_count("umask");
+               return;
+       }
+}
+
+static void b_exit(char **av) {
+       if (*++av != NULL)
+               ssetstatus(av);
+       rc_exit(getstatus());
+}
+
+/* raise a "return" exception, i.e., return from a function. if an integer argument is present, set $status to it */
+
+static void b_return(char **av) {
+       if (*++av != NULL)
+               ssetstatus(av);
+       rc_raise(eReturn);
+}
+
+/* raise a "break" exception for breaking out of for and while loops */
+
+static void b_break(char **av) {
+       if (av[1] != NULL) {
+               arg_count("break");
+               return;
+       }
+       rc_raise(eBreak);
+}
+
+/* shift $* n places (default 1) */
+
+static void b_shift(char **av) {
+       int shift = (av[1] == NULL ? 1 : a2u(av[1]));
+       List *s, *dollarzero;
+       if (av[1] != NULL && av[2] != NULL) {
+               arg_count("shift");
+               return;
+       }
+       if (shift < 0) {
+               badnum(av[1]);
+               return;
+       }
+       s = varlookup("*")->n;
+       dollarzero = varlookup("0");
+       while (s != NULL && shift != 0) {
+               s = s->n;
+               --shift;
+       }
+       if (s == NULL && shift != 0) {
+               fprint(2, "cannot shift\n");
+               set(FALSE);
+       } else {
+               varassign("*", append(dollarzero, s), FALSE);
+               set(TRUE);
+       }
+}
+
+/* dud function */
+
+extern void b_builtin(char **ignore) {
+}
+
+/* wait for a given process, or all outstanding processes */
+
+static void b_wait(char **av) {
+       int status;
+       pid_t pid;
+       if (av[1] == NULL) {
+               waitforall();
+               return;
+       }
+       if (av[2] != NULL) {
+               arg_count("wait");
+               return;
+       }
+       if ((pid = a2u(av[1])) < 0) {
+               badnum(av[1]);
+               return;
+       }
+       if (rc_wait4(pid, &status, FALSE) > 0)
+               setstatus(pid, status);
+       else
+               set(FALSE);
+       sigchk();
+}
+
+/*
+   whatis without arguments prints all variables and functions. Otherwise, check to see if a name
+   is defined as a variable, function or pathname.
+*/
+
+#define not(b) ((b)^TRUE)
+#define show(b)        (not(eff|vee|pee|bee|ess)|(b))
+
+static bool issig(char *s) {
+       int i;
+       for (i = 0; i < NUMOFSIGNALS; i++)
+               if (streq(s, signals[i].name))
+                       return TRUE;
+       return FALSE;
+}
+
+static void b_whatis(char **av) {
+       bool ess, eff, vee, pee, bee;
+       bool f, found;
+       int i, ac, c;
+       List *s;
+       Node *n;
+       char *e;
+       for (rc_optind = ac = 0; av[ac] != NULL; ac++)
+               ; /* count the arguments for getopt */
+       ess = eff = vee = pee = bee = FALSE;
+       while ((c = rc_getopt(ac, av, "sfvpb")) != -1)
+               switch (c) {
+               default: set(FALSE); return;
+               case 's': ess = TRUE; break;
+               case 'f': eff = TRUE; break;
+               case 'v': vee = TRUE; break;
+               case 'p': pee = TRUE; break;
+               case 'b': bee = TRUE; break;
+               }
+       av += rc_optind;
+       if (*av == NULL) {
+               if (vee|eff)
+                       whatare_all_vars(eff, vee);
+               if (ess)
+                       whatare_all_signals();
+               if (bee)
+                       for (i = 0; i < arraysize(builtins); i++)
+                               fprint(1, "builtin %s\n", builtins[i].name);
+               if (pee)
+                       fprint(2, "whatis -p: must specify argument\n");
+               if (show(FALSE)) /* no options? */
+                       whatare_all_vars(TRUE, TRUE);
+               set(TRUE);
+               return;
+       }
+       found = TRUE;
+       for (i = 0; av[i] != NULL; i++) {
+               f = FALSE;
+               errno = ENOENT;
+               if (show(vee) && (s = varlookup(av[i])) != NULL) {
+                       f = TRUE;
+                       prettyprint_var(1, av[i], s);
+               }
+               if (((show(ess)&&issig(av[i])) || show(eff)) && (n = fnlookup(av[i])) != NULL) {
+                       f = TRUE;
+                       prettyprint_fn(1, av[i], n);
+               } else if (show(bee) && isbuiltin(av[i]) != NULL) {
+                       f = TRUE;
+                       fprint(1, "builtin %s\n", av[i]);
+               } else if (show(pee) && (e = which(av[i], FALSE)) != NULL) {
+                       f = TRUE;
+                       fprint(1, "%S\n", e);
+               }
+               if (!f) {
+                       found = FALSE;
+                       if (errno != ENOENT)
+                               uerror(av[i]);
+                       else
+                               fprint(2, "%s not found\n", av[i]);
+               }
+       }
+       set(found);
+}
+
+/* push a string to be eval'ed onto the input stack. evaluate it */
+
+static void b_eval(char **av) {
+       bool i = interactive;
+       if (av[1] == NULL)
+               return;
+       interactive = FALSE;
+       pushstring(av + 1, i); /* don't reset line numbers on noninteractive eval */
+       doit(TRUE);
+       interactive = i;
+}
+
+/*
+   push a file to be interpreted onto the input stack. with "-i" treat this as an interactive
+   input source.
+*/
+
+extern void b_dot(char **av) {
+       int fd;
+       bool old_i = interactive, i = FALSE;
+       Estack e;
+       Edata star;
+       av++;
+       if (*av == NULL)
+               return;
+       if (streq(*av, "-i")) {
+               av++;
+               i = TRUE;
+       }
+       if (dasheye) { /* rc -i file has to do the right thing. reset the dasheye state to FALSE, though. */
+               dasheye = FALSE;
+               i = TRUE;
+       }
+       if (*av == NULL)
+               return;
+       fd = rc_open(*av, rFrom);
+       if (fd < 0) {
+               uerror(*av);
+               set(FALSE);
+               return;
+       }
+       starassign(*av, av+1, TRUE);
+       interactive = i;
+       pushfd(fd);
+       star.name = "*";
+       except(eVarstack, star, &e);
+       doit(TRUE);
+       varrm("*", TRUE);
+       unexcept(); /* eVarstack */
+       interactive = old_i;
+}
+
+/* put rc into a new pgrp. Used on the NeXT where the Terminal program is broken (sigh) */
+
+static void b_newpgrp(char **av) {
+       if (av[1] != NULL) {
+               arg_count("newpgrp");
+               return;
+       }
+       setpgid(rc_pid, rc_pid); /* XXX check return value */
+       tcsetpgrp(2, rc_pid); /* XXX check return value */
+}
+
+/* Berkeley limit support was cleaned up by Paul Haahr. */
+
+#if HAVE_SETRLIMIT
+static const struct Suffix
+       kbsuf = { NULL, 1024, "k" },
+       mbsuf = { &kbsuf, 1024*1024, "m" },
+       gbsuf = { &mbsuf, 1024*1024*1024, "g" },
+       stsuf = { NULL, 1, "s" },
+       mtsuf = { &stsuf, 60, "m" },
+       htsuf = { &mtsuf, 60*60, "h" };
+#define        SIZESUF &gbsuf
+#define        TIMESUF &htsuf
+#define        NOSUF ((struct Suffix *) NULL)  /* for RLIMIT_NOFILE on SunOS 4.1 */
+
+static const struct Limit limits[] = {
+       { "cputime",            RLIMIT_CPU,     TIMESUF },
+       { "filesize",           RLIMIT_FSIZE,   SIZESUF },
+       { "datasize",           RLIMIT_DATA,    SIZESUF },
+       { "stacksize",          RLIMIT_STACK,   SIZESUF },
+       { "coredumpsize",       RLIMIT_CORE,    SIZESUF },
+#ifdef RLIMIT_NOFILE  /* SUSv2, but not universal */
+       { "descriptors",        RLIMIT_NOFILE,  NOSUF },
+#endif
+#ifdef RLIMIT_AS /* SUSv2, but not universal */
+       { "memoryuse",          RLIMIT_AS,      SIZESUF },
+#endif
+#if defined(RLIMIT_VMEM) && !defined(RLIMIT_AS) /* old name for AS */
+       { "memoryuse",          RLIMIT_VMEM,    SIZESUF },
+#endif
+#ifdef RLIMIT_RSS
+       { "memoryrss",          RLIMIT_RSS,     SIZESUF },
+#endif
+#ifdef RLIMIT_NPROC
+       { "maxproc",            RLIMIT_NPROC,   NOSUF },
+#endif
+#ifdef RLIMIT_MEMLOCK
+       { "memorylocked",       RLIMIT_MEMLOCK, SIZESUF },
+#endif
+#ifdef RLIMIT_LOCKS
+       { "filelocks",          RLIMIT_LOCKS,   NOSUF },
+#endif
+       { NULL, 0, NULL }
+};
+
+static void printlimit(const struct Limit *limit, bool hard) {
+       struct rlimit rlim;
+       rlim_t lim;
+       getrlimit(limit->flag, &rlim);
+       if (hard)
+               lim = rlim.rlim_max;
+       else
+               lim = rlim.rlim_cur;
+       if (lim == RLIM_INFINITY)
+               fprint(1, "%s \tunlimited\n", limit->name);
+       else {
+               const struct Suffix *suf;
+               for (suf = limit->suffix; suf != NULL; suf = suf->next)
+                       if (lim % suf->amount == 0 && (lim != 0 || suf->amount > 1)) {
+                               lim /= suf->amount;
+                               break;
+                       }
+               fprint(1, RLIM_FMT, limit->name, (RLIM_CONV)lim, (suf == NULL || lim == 0) ? "" : suf->name);
+       }
+}
+
+static bool parselimit(const struct Limit *resource, rlim_t *limit, char *s) {
+       char *t;
+       int len = strlen(s);
+       const struct Suffix *suf = resource->suffix;
+
+       *limit = 1;
+       if (streq(s, "unlimited")) {
+               *limit = RLIM_INFINITY;
+               return TRUE;
+       }
+       if (suf == TIMESUF && (t = strchr(s, ':')) != NULL) {
+               int min, sec;
+               *t++ = '\0';
+               min = a2u(s); sec = a2u(t);
+               if (min == -1 || sec == -1) return FALSE;
+               *limit = 60 * min + sec;
+       } else {
+               int n;
+               for (; suf != NULL; suf = suf->next)
+                       if (streq(suf->name, s + len - strlen(suf->name))) {
+                               s[len - strlen(suf->name)] = '\0';
+                               *limit *= suf->amount;
+                               break;
+                       }
+               n = a2u(s);
+               if (n == -1) return FALSE;
+               *limit *= n;
+       }
+       return TRUE;
+}
+
+static void b_limit(char **av) {
+       const struct Limit *lp = limits;
+       bool hard = FALSE;
+       if (*++av != NULL && streq(*av, "-h")) {
+               av++;
+               hard = TRUE;
+       }
+       if (*av == NULL) {
+               for (; lp->name != NULL; lp++)
+                       printlimit(lp, hard);
+               return;
+       }
+       for (;; lp++) {
+               if (lp->name == NULL) {
+                       fprint(2, "no such limit\n");
+                       set(FALSE);
+                       return;
+               }
+               if (streq(*av, lp->name))
+                       break;
+       }
+       if (*++av == NULL)
+               printlimit(lp, hard);
+       else {
+               struct rlimit rlim;
+               rlim_t pl;
+               getrlimit(lp->flag, &rlim);
+               if (!parselimit(lp, &pl, *av)) {
+                       fprint(2, "bad limit\n");
+                       set(FALSE);
+                       return;
+               }
+               if (hard)
+                       rlim.rlim_max = pl;
+               else
+                       rlim.rlim_cur = pl;
+               if (setrlimit(lp->flag, &rlim) == -1) {
+                       uerror("setrlimit");
+                       set(FALSE);
+               } else
+                       set(TRUE);
+       }
+}
+#endif
diff --git a/compile b/compile
new file mode 100755 (executable)
index 0000000..531136b
--- /dev/null
+++ b/compile
@@ -0,0 +1,347 @@
+#! /bin/sh
+# Wrapper for compilers which do not understand '-c -o'.
+
+scriptversion=2012-10-14.11; # UTC
+
+# Copyright (C) 1999-2013 Free Software Foundation, Inc.
+# Written by Tom Tromey <tromey@cygnus.com>.
+#
+# 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, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# This file is maintained in Automake, please report
+# bugs to <bug-automake@gnu.org> or send patches to
+# <automake-patches@gnu.org>.
+
+nl='
+'
+
+# We need space, tab and new line, in precisely that order.  Quoting is
+# there to prevent tools from complaining about whitespace usage.
+IFS=" ""       $nl"
+
+file_conv=
+
+# func_file_conv build_file lazy
+# Convert a $build file to $host form and store it in $file
+# Currently only supports Windows hosts. If the determined conversion
+# type is listed in (the comma separated) LAZY, no conversion will
+# take place.
+func_file_conv ()
+{
+  file=$1
+  case $file in
+    / | /[!/]*) # absolute file, and not a UNC file
+      if test -z "$file_conv"; then
+       # lazily determine how to convert abs files
+       case `uname -s` in
+         MINGW*)
+           file_conv=mingw
+           ;;
+         CYGWIN*)
+           file_conv=cygwin
+           ;;
+         *)
+           file_conv=wine
+           ;;
+       esac
+      fi
+      case $file_conv/,$2, in
+       *,$file_conv,*)
+         ;;
+       mingw/*)
+         file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'`
+         ;;
+       cygwin/*)
+         file=`cygpath -m "$file" || echo "$file"`
+         ;;
+       wine/*)
+         file=`winepath -w "$file" || echo "$file"`
+         ;;
+      esac
+      ;;
+  esac
+}
+
+# func_cl_dashL linkdir
+# Make cl look for libraries in LINKDIR
+func_cl_dashL ()
+{
+  func_file_conv "$1"
+  if test -z "$lib_path"; then
+    lib_path=$file
+  else
+    lib_path="$lib_path;$file"
+  fi
+  linker_opts="$linker_opts -LIBPATH:$file"
+}
+
+# func_cl_dashl library
+# Do a library search-path lookup for cl
+func_cl_dashl ()
+{
+  lib=$1
+  found=no
+  save_IFS=$IFS
+  IFS=';'
+  for dir in $lib_path $LIB
+  do
+    IFS=$save_IFS
+    if $shared && test -f "$dir/$lib.dll.lib"; then
+      found=yes
+      lib=$dir/$lib.dll.lib
+      break
+    fi
+    if test -f "$dir/$lib.lib"; then
+      found=yes
+      lib=$dir/$lib.lib
+      break
+    fi
+    if test -f "$dir/lib$lib.a"; then
+      found=yes
+      lib=$dir/lib$lib.a
+      break
+    fi
+  done
+  IFS=$save_IFS
+
+  if test "$found" != yes; then
+    lib=$lib.lib
+  fi
+}
+
+# func_cl_wrapper cl arg...
+# Adjust compile command to suit cl
+func_cl_wrapper ()
+{
+  # Assume a capable shell
+  lib_path=
+  shared=:
+  linker_opts=
+  for arg
+  do
+    if test -n "$eat"; then
+      eat=
+    else
+      case $1 in
+       -o)
+         # configure might choose to run compile as 'compile cc -o foo foo.c'.
+         eat=1
+         case $2 in
+           *.o | *.[oO][bB][jJ])
+             func_file_conv "$2"
+             set x "$@" -Fo"$file"
+             shift
+             ;;
+           *)
+             func_file_conv "$2"
+             set x "$@" -Fe"$file"
+             shift
+             ;;
+         esac
+         ;;
+       -I)
+         eat=1
+         func_file_conv "$2" mingw
+         set x "$@" -I"$file"
+         shift
+         ;;
+       -I*)
+         func_file_conv "${1#-I}" mingw
+         set x "$@" -I"$file"
+         shift
+         ;;
+       -l)
+         eat=1
+         func_cl_dashl "$2"
+         set x "$@" "$lib"
+         shift
+         ;;
+       -l*)
+         func_cl_dashl "${1#-l}"
+         set x "$@" "$lib"
+         shift
+         ;;
+       -L)
+         eat=1
+         func_cl_dashL "$2"
+         ;;
+       -L*)
+         func_cl_dashL "${1#-L}"
+         ;;
+       -static)
+         shared=false
+         ;;
+       -Wl,*)
+         arg=${1#-Wl,}
+         save_ifs="$IFS"; IFS=','
+         for flag in $arg; do
+           IFS="$save_ifs"
+           linker_opts="$linker_opts $flag"
+         done
+         IFS="$save_ifs"
+         ;;
+       -Xlinker)
+         eat=1
+         linker_opts="$linker_opts $2"
+         ;;
+       -*)
+         set x "$@" "$1"
+         shift
+         ;;
+       *.cc | *.CC | *.cxx | *.CXX | *.[cC]++)
+         func_file_conv "$1"
+         set x "$@" -Tp"$file"
+         shift
+         ;;
+       *.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO])
+         func_file_conv "$1" mingw
+         set x "$@" "$file"
+         shift
+         ;;
+       *)
+         set x "$@" "$1"
+         shift
+         ;;
+      esac
+    fi
+    shift
+  done
+  if test -n "$linker_opts"; then
+    linker_opts="-link$linker_opts"
+  fi
+  exec "$@" $linker_opts
+  exit 1
+}
+
+eat=
+
+case $1 in
+  '')
+     echo "$0: No command.  Try '$0 --help' for more information." 1>&2
+     exit 1;
+     ;;
+  -h | --h*)
+    cat <<\EOF
+Usage: compile [--help] [--version] PROGRAM [ARGS]
+
+Wrapper for compilers which do not understand '-c -o'.
+Remove '-o dest.o' from ARGS, run PROGRAM with the remaining
+arguments, and rename the output as expected.
+
+If you are trying to build a whole package this is not the
+right script to run: please start by reading the file 'INSTALL'.
+
+Report bugs to <bug-automake@gnu.org>.
+EOF
+    exit $?
+    ;;
+  -v | --v*)
+    echo "compile $scriptversion"
+    exit $?
+    ;;
+  cl | *[/\\]cl | cl.exe | *[/\\]cl.exe )
+    func_cl_wrapper "$@"      # Doesn't return...
+    ;;
+esac
+
+ofile=
+cfile=
+
+for arg
+do
+  if test -n "$eat"; then
+    eat=
+  else
+    case $1 in
+      -o)
+       # configure might choose to run compile as 'compile cc -o foo foo.c'.
+       # So we strip '-o arg' only if arg is an object.
+       eat=1
+       case $2 in
+         *.o | *.obj)
+           ofile=$2
+           ;;
+         *)
+           set x "$@" -o "$2"
+           shift
+           ;;
+       esac
+       ;;
+      *.c)
+       cfile=$1
+       set x "$@" "$1"
+       shift
+       ;;
+      *)
+       set x "$@" "$1"
+       shift
+       ;;
+    esac
+  fi
+  shift
+done
+
+if test -z "$ofile" || test -z "$cfile"; then
+  # If no '-o' option was seen then we might have been invoked from a
+  # pattern rule where we don't need one.  That is ok -- this is a
+  # normal compilation that the losing compiler can handle.  If no
+  # '.c' file was seen then we are probably linking.  That is also
+  # ok.
+  exec "$@"
+fi
+
+# Name of file we expect compiler to create.
+cofile=`echo "$cfile" | sed 's|^.*[\\/]||; s|^[a-zA-Z]:||; s/\.c$/.o/'`
+
+# Create the lock directory.
+# Note: use '[/\\:.-]' here to ensure that we don't use the same name
+# that we are using for the .o file.  Also, base the name on the expected
+# object file name, since that is what matters with a parallel build.
+lockdir=`echo "$cofile" | sed -e 's|[/\\:.-]|_|g'`.d
+while true; do
+  if mkdir "$lockdir" >/dev/null 2>&1; then
+    break
+  fi
+  sleep 1
+done
+# FIXME: race condition here if user kills between mkdir and trap.
+trap "rmdir '$lockdir'; exit 1" 1 2 15
+
+# Run the compile.
+"$@"
+ret=$?
+
+if test -f "$cofile"; then
+  test "$cofile" = "$ofile" || mv "$cofile" "$ofile"
+elif test -f "${cofile}bj"; then
+  test "${cofile}bj" = "$ofile" || mv "${cofile}bj" "$ofile"
+fi
+
+rmdir "$lockdir"
+exit $ret
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/config.h.in b/config.h.in
new file mode 100644 (file)
index 0000000..b094a45
--- /dev/null
@@ -0,0 +1,194 @@
+/* config.h.in.  Generated from configure.ac by autoheader.  */
+
+/* The default interpreter */
+#undef DEFAULTINTERP
+
+/* The default path */
+#undef DEFAULTPATH
+
+/* Define to the type of elements in the array set by `getgroups'. Usually
+   this is either `int' or `gid_t'. */
+#undef GETGROUPS_T
+
+/* Define to 1 if your kernel understands `#!' magic numbers */
+#undef HASH_BANG
+
+/* Define to 1 if you have /dev/fd. */
+#undef HAVE_DEV_FD
+
+/* Define to 1 if you have the <dirent.h> header file, and it defines `DIR'.
+   */
+#undef HAVE_DIRENT_H
+
+/* Define to 1 if you have the `mkfifo' function. */
+#undef HAVE_FIFO
+
+/* Define to 1 if you have the `getgroups' function. */
+#undef HAVE_GETGROUPS
+
+/* Define to 1 if you have the <inttypes.h> header file. */
+#undef HAVE_INTTYPES_H
+
+/* Define to 1 if you have the `lstat' function. */
+#undef HAVE_LSTAT
+
+/* Define to 1 if you have the <memory.h> header file. */
+#undef HAVE_MEMORY_H
+
+/* Define to 1 if you have the `mkfifo' function. */
+#undef HAVE_MKFIFO
+
+/* Define to 1 if you have the <ndir.h> header file, and it defines `DIR'. */
+#undef HAVE_NDIR_H
+
+/* Define to 1 if you have the `getgroups' function with POSIX semantics. */
+#undef HAVE_POSIX_GETGROUPS
+
+/* Define to 1 if you have /proc/self/fd. */
+#undef HAVE_PROC_SELF_FD
+
+/* Define to 1 if you have the `quad_t' type. */
+#undef HAVE_QUAD_T
+
+/* Define to 1 if system calls automatically restart after interruption by a
+   signal. */
+#undef HAVE_RESTARTABLE_SYSCALLS
+
+/* Define to 1 if you have the `rlim_t' type. */
+#undef HAVE_RLIM_T
+
+/* Define to 1 if you have the `setpgrp' function. */
+#undef HAVE_SETPGRP
+
+/* Define to 1 if you have the `setrlimit' function. */
+#undef HAVE_SETRLIMIT
+
+/* Define to 1 if you have the `sigaction' function. */
+#undef HAVE_SIGACTION
+
+/* Define to 1 if you have the `sigsetjmp' function or macro. */
+#undef HAVE_SIGSETJMP
+
+/* Define to 1 if you have the <stdint.h> header file. */
+#undef HAVE_STDINT_H
+
+/* Define to 1 if you have the <stdlib.h> header file. */
+#undef HAVE_STDLIB_H
+
+/* Define to 1 if you have the `strerror' function or macro. */
+#undef HAVE_STRERROR
+
+/* Define to 1 if you have the <strings.h> header file. */
+#undef HAVE_STRINGS_H
+
+/* Define to 1 if you have the <string.h> header file. */
+#undef HAVE_STRING_H
+
+/* Has SysV SIGCLD */
+#undef HAVE_SYSV_SIGCLD
+
+/* Define to 1 if you have the <sys/dir.h> header file, and it defines `DIR'.
+   */
+#undef HAVE_SYS_DIR_H
+
+/* Define to 1 if you have the <sys/ndir.h> header file, and it defines `DIR'.
+   */
+#undef HAVE_SYS_NDIR_H
+
+/* Define to 1 if you have the <sys/resource.h> header file. */
+#undef HAVE_SYS_RESOURCE_H
+
+/* Define to 1 if you have the <sys/stat.h> header file. */
+#undef HAVE_SYS_STAT_H
+
+/* Define to 1 if you have the <sys/time.h> header file. */
+#undef HAVE_SYS_TIME_H
+
+/* Define to 1 if you have the <sys/types.h> header file. */
+#undef HAVE_SYS_TYPES_H
+
+/* Define to 1 if you have <sys/wait.h> that is POSIX.1 compatible. */
+#undef HAVE_SYS_WAIT_H
+
+/* Define to 1 if you have the <unistd.h> header file. */
+#undef HAVE_UNISTD_H
+
+/* Name of package */
+#undef PACKAGE
+
+/* Define to the address where bug reports for this package should be sent. */
+#undef PACKAGE_BUGREPORT
+
+/* Define to the full name of this package. */
+#undef PACKAGE_NAME
+
+/* Define to the full name and version of this package. */
+#undef PACKAGE_STRING
+
+/* Define to the one symbol short name of this package. */
+#undef PACKAGE_TARNAME
+
+/* Define to the home page for this package. */
+#undef PACKAGE_URL
+
+/* Define to the version of this package. */
+#undef PACKAGE_VERSION
+
+/* Define to 1 to encode exported environment names. */
+#undef PROTECT_ENV
+
+/* Define to 1 to use addon functions. */
+#undef RC_ADDON
+
+/* Define to 1 to include `echo' as a builtin. */
+#undef RC_ECHO
+
+/* Define to 1 to use job-control-style backgrounding. */
+#undef RC_JOB
+
+/* Release date */
+#undef RELDATE
+
+/* Define to 1 if `_KERNEL' must be defined for `RLIMIT_*' macros. */
+#undef RLIMIT_NEEDS_KERNEL
+
+/* Define to 1 if `rlim_t' is `quad_t'. */
+#undef RLIM_T_IS_QUAD_T
+
+/* Define to 1 if the `setpgrp' function takes no argument. */
+#undef SETPGRP_VOID
+
+/* Define to 1 if you have the ANSI C header files. */
+#undef STDC_HEADERS
+
+/* Version number of package */
+#undef VERSION
+
+/* Enable large inode numbers on Mac OS X 10.5.  */
+#ifndef _DARWIN_USE_64_BIT_INODE
+# define _DARWIN_USE_64_BIT_INODE 1
+#endif
+
+/* Number of bits in a file offset, on hosts where this is settable. */
+#undef _FILE_OFFSET_BITS
+
+/* Define for large files, on AIX-style hosts. */
+#undef _LARGE_FILES
+
+/* Define to `int' if <sys/types.h> doesn't define. */
+#undef gid_t
+
+/* Define to `int' if <sys/types.h> does not define. */
+#undef pid_t
+
+/* Define to 1 if you have the `sig_atomic_t' type. */
+#undef sig_atomic_t
+
+/* Define to `unsigned int' if <sys/types.h> does not define. */
+#undef size_t
+
+/* Define to `long' if <sys/types.h> does not define. */
+#undef ssize_t
+
+/* Define to `int' if <sys/types.h> doesn't define. */
+#undef uid_t
diff --git a/configure b/configure
new file mode 100755 (executable)
index 0000000..9211d95
--- /dev/null
+++ b/configure
@@ -0,0 +1,8025 @@
+#! /bin/sh
+# Guess values for system-dependent variables and create Makefiles.
+# Generated by GNU Autoconf 2.69 for rc 1.7.4.
+#
+#
+# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
+#
+#
+# This configure script is free software; the Free Software Foundation
+# gives unlimited permission to copy, distribute and modify it.
+## -------------------- ##
+## M4sh Initialization. ##
+## -------------------- ##
+
+# Be more Bourne compatible
+DUALCASE=1; export DUALCASE # for MKS sh
+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :
+  emulate sh
+  NULLCMD=:
+  # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which
+  # is contrary to our usage.  Disable this feature.
+  alias -g '${1+"$@"}'='"$@"'
+  setopt NO_GLOB_SUBST
+else
+  case `(set -o) 2>/dev/null` in #(
+  *posix*) :
+    set -o posix ;; #(
+  *) :
+     ;;
+esac
+fi
+
+
+as_nl='
+'
+export as_nl
+# Printing a long string crashes Solaris 7 /usr/bin/printf.
+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo
+# Prefer a ksh shell builtin over an external printf program on Solaris,
+# but without wasting forks for bash or zsh.
+if test -z "$BASH_VERSION$ZSH_VERSION" \
+    && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then
+  as_echo='print -r --'
+  as_echo_n='print -rn --'
+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then
+  as_echo='printf %s\n'
+  as_echo_n='printf %s'
+else
+  if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then
+    as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'
+    as_echo_n='/usr/ucb/echo -n'
+  else
+    as_echo_body='eval expr "X$1" : "X\\(.*\\)"'
+    as_echo_n_body='eval
+      arg=$1;
+      case $arg in #(
+      *"$as_nl"*)
+       expr "X$arg" : "X\\(.*\\)$as_nl";
+       arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;
+      esac;
+      expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"
+    '
+    export as_echo_n_body
+    as_echo_n='sh -c $as_echo_n_body as_echo'
+  fi
+  export as_echo_body
+  as_echo='sh -c $as_echo_body as_echo'
+fi
+
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+  PATH_SEPARATOR=:
+  (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {
+    (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||
+      PATH_SEPARATOR=';'
+  }
+fi
+
+
+# IFS
+# We need space, tab and new line, in precisely that order.  Quoting is
+# there to prevent editors from complaining about space-tab.
+# (If _AS_PATH_WALK were called with IFS unset, it would disable word
+# splitting by setting IFS to empty value.)
+IFS=" ""       $as_nl"
+
+# Find who we are.  Look in the path if we contain no directory separator.
+as_myself=
+case $0 in #((
+  *[\\/]* ) as_myself=$0 ;;
+  *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break
+  done
+IFS=$as_save_IFS
+
+     ;;
+esac
+# We did not find ourselves, most probably we were run as `sh COMMAND'
+# in which case we are not to be found in the path.
+if test "x$as_myself" = x; then
+  as_myself=$0
+fi
+if test ! -f "$as_myself"; then
+  $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2
+  exit 1
+fi
+
+# Unset variables that we do not need and which cause bugs (e.g. in
+# pre-3.0 UWIN ksh).  But do not cause bugs in bash 2.01; the "|| exit 1"
+# suppresses any "Segmentation fault" message there.  '((' could
+# trigger a bug in pdksh 5.2.14.
+for as_var in BASH_ENV ENV MAIL MAILPATH
+do eval test x\${$as_var+set} = xset \
+  && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :
+done
+PS1='$ '
+PS2='> '
+PS4='+ '
+
+# NLS nuisances.
+LC_ALL=C
+export LC_ALL
+LANGUAGE=C
+export LANGUAGE
+
+# CDPATH.
+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH
+
+# Use a proper internal environment variable to ensure we don't fall
+  # into an infinite loop, continuously re-executing ourselves.
+  if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then
+    _as_can_reexec=no; export _as_can_reexec;
+    # We cannot yet assume a decent shell, so we have to provide a
+# neutralization value for shells without unset; and this also
+# works around shells that cannot unset nonexistent variables.
+# Preserve -v and -x to the replacement shell.
+BASH_ENV=/dev/null
+ENV=/dev/null
+(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV
+case $- in # ((((
+  *v*x* | *x*v* ) as_opts=-vx ;;
+  *v* ) as_opts=-v ;;
+  *x* ) as_opts=-x ;;
+  * ) as_opts= ;;
+esac
+exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"}
+# Admittedly, this is quite paranoid, since all the known shells bail
+# out after a failed `exec'.
+$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2
+as_fn_exit 255
+  fi
+  # We don't want this to propagate to other subprocesses.
+          { _as_can_reexec=; unset _as_can_reexec;}
+if test "x$CONFIG_SHELL" = x; then
+  as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then :
+  emulate sh
+  NULLCMD=:
+  # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which
+  # is contrary to our usage.  Disable this feature.
+  alias -g '\${1+\"\$@\"}'='\"\$@\"'
+  setopt NO_GLOB_SUBST
+else
+  case \`(set -o) 2>/dev/null\` in #(
+  *posix*) :
+    set -o posix ;; #(
+  *) :
+     ;;
+esac
+fi
+"
+  as_required="as_fn_return () { (exit \$1); }
+as_fn_success () { as_fn_return 0; }
+as_fn_failure () { as_fn_return 1; }
+as_fn_ret_success () { return 0; }
+as_fn_ret_failure () { return 1; }
+
+exitcode=0
+as_fn_success || { exitcode=1; echo as_fn_success failed.; }
+as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; }
+as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; }
+as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; }
+if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then :
+
+else
+  exitcode=1; echo positional parameters were not saved.
+fi
+test x\$exitcode = x0 || exit 1
+test -x / || exit 1"
+  as_suggested="  as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO
+  as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO
+  eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" &&
+  test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1
+test \$(( 1 + 1 )) = 2 || exit 1"
+  if (eval "$as_required") 2>/dev/null; then :
+  as_have_required=yes
+else
+  as_have_required=no
+fi
+  if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then :
+
+else
+  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+as_found=false
+for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+  as_found=:
+  case $as_dir in #(
+        /*)
+          for as_base in sh bash ksh sh5; do
+            # Try only shells that exist, to save several forks.
+            as_shell=$as_dir/$as_base
+            if { test -f "$as_shell" || test -f "$as_shell.exe"; } &&
+                   { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then :
+  CONFIG_SHELL=$as_shell as_have_required=yes
+                  if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then :
+  break 2
+fi
+fi
+          done;;
+       esac
+  as_found=false
+done
+$as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } &&
+             { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then :
+  CONFIG_SHELL=$SHELL as_have_required=yes
+fi; }
+IFS=$as_save_IFS
+
+
+      if test "x$CONFIG_SHELL" != x; then :
+  export CONFIG_SHELL
+             # We cannot yet assume a decent shell, so we have to provide a
+# neutralization value for shells without unset; and this also
+# works around shells that cannot unset nonexistent variables.
+# Preserve -v and -x to the replacement shell.
+BASH_ENV=/dev/null
+ENV=/dev/null
+(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV
+case $- in # ((((
+  *v*x* | *x*v* ) as_opts=-vx ;;
+  *v* ) as_opts=-v ;;
+  *x* ) as_opts=-x ;;
+  * ) as_opts= ;;
+esac
+exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"}
+# Admittedly, this is quite paranoid, since all the known shells bail
+# out after a failed `exec'.
+$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2
+exit 255
+fi
+
+    if test x$as_have_required = xno; then :
+  $as_echo "$0: This script requires a shell more modern than all"
+  $as_echo "$0: the shells that I found on your system."
+  if test x${ZSH_VERSION+set} = xset ; then
+    $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should"
+    $as_echo "$0: be upgraded to zsh 4.3.4 or later."
+  else
+    $as_echo "$0: Please tell bug-autoconf@gnu.org about your system,
+$0: including any error possibly output before this
+$0: message. Then install a modern shell, or manually run
+$0: the script under such a shell if you do have one."
+  fi
+  exit 1
+fi
+fi
+fi
+SHELL=${CONFIG_SHELL-/bin/sh}
+export SHELL
+# Unset more variables known to interfere with behavior of common tools.
+CLICOLOR_FORCE= GREP_OPTIONS=
+unset CLICOLOR_FORCE GREP_OPTIONS
+
+## --------------------- ##
+## M4sh Shell Functions. ##
+## --------------------- ##
+# as_fn_unset VAR
+# ---------------
+# Portably unset VAR.
+as_fn_unset ()
+{
+  { eval $1=; unset $1;}
+}
+as_unset=as_fn_unset
+
+# as_fn_set_status STATUS
+# -----------------------
+# Set $? to STATUS, without forking.
+as_fn_set_status ()
+{
+  return $1
+} # as_fn_set_status
+
+# as_fn_exit STATUS
+# -----------------
+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.
+as_fn_exit ()
+{
+  set +e
+  as_fn_set_status $1
+  exit $1
+} # as_fn_exit
+
+# as_fn_mkdir_p
+# -------------
+# Create "$as_dir" as a directory, including parents if necessary.
+as_fn_mkdir_p ()
+{
+
+  case $as_dir in #(
+  -*) as_dir=./$as_dir;;
+  esac
+  test -d "$as_dir" || eval $as_mkdir_p || {
+    as_dirs=
+    while :; do
+      case $as_dir in #(
+      *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(
+      *) as_qdir=$as_dir;;
+      esac
+      as_dirs="'$as_qdir' $as_dirs"
+      as_dir=`$as_dirname -- "$as_dir" ||
+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$as_dir" : 'X\(//\)[^/]' \| \
+        X"$as_dir" : 'X\(//\)$' \| \
+        X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_dir" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+      test -d "$as_dir" && break
+    done
+    test -z "$as_dirs" || eval "mkdir $as_dirs"
+  } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"
+
+
+} # as_fn_mkdir_p
+
+# as_fn_executable_p FILE
+# -----------------------
+# Test if FILE is an executable regular file.
+as_fn_executable_p ()
+{
+  test -f "$1" && test -x "$1"
+} # as_fn_executable_p
+# as_fn_append VAR VALUE
+# ----------------------
+# Append the text in VALUE to the end of the definition contained in VAR. Take
+# advantage of any shell optimizations that allow amortized linear growth over
+# repeated appends, instead of the typical quadratic growth present in naive
+# implementations.
+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :
+  eval 'as_fn_append ()
+  {
+    eval $1+=\$2
+  }'
+else
+  as_fn_append ()
+  {
+    eval $1=\$$1\$2
+  }
+fi # as_fn_append
+
+# as_fn_arith ARG...
+# ------------------
+# Perform arithmetic evaluation on the ARGs, and store the result in the
+# global $as_val. Take advantage of shells that can avoid forks. The arguments
+# must be portable across $(()) and expr.
+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :
+  eval 'as_fn_arith ()
+  {
+    as_val=$(( $* ))
+  }'
+else
+  as_fn_arith ()
+  {
+    as_val=`expr "$@" || test $? -eq 1`
+  }
+fi # as_fn_arith
+
+
+# as_fn_error STATUS ERROR [LINENO LOG_FD]
+# ----------------------------------------
+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are
+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the
+# script with STATUS, using 1 if that was 0.
+as_fn_error ()
+{
+  as_status=$1; test $as_status -eq 0 && as_status=1
+  if test "$4"; then
+    as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+    $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4
+  fi
+  $as_echo "$as_me: error: $2" >&2
+  as_fn_exit $as_status
+} # as_fn_error
+
+if expr a : '\(a\)' >/dev/null 2>&1 &&
+   test "X`expr 00001 : '.*\(...\)'`" = X001; then
+  as_expr=expr
+else
+  as_expr=false
+fi
+
+if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then
+  as_basename=basename
+else
+  as_basename=false
+fi
+
+if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then
+  as_dirname=dirname
+else
+  as_dirname=false
+fi
+
+as_me=`$as_basename -- "$0" ||
+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \
+        X"$0" : 'X\(//\)$' \| \
+        X"$0" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X/"$0" |
+    sed '/^.*\/\([^/][^/]*\)\/*$/{
+           s//\1/
+           q
+         }
+         /^X\/\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\/\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+
+# Avoid depending upon Character Ranges.
+as_cr_letters='abcdefghijklmnopqrstuvwxyz'
+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'
+as_cr_Letters=$as_cr_letters$as_cr_LETTERS
+as_cr_digits='0123456789'
+as_cr_alnum=$as_cr_Letters$as_cr_digits
+
+
+  as_lineno_1=$LINENO as_lineno_1a=$LINENO
+  as_lineno_2=$LINENO as_lineno_2a=$LINENO
+  eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" &&
+  test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || {
+  # Blame Lee E. McMahon (1931-1989) for sed's syntax.  :-)
+  sed -n '
+    p
+    /[$]LINENO/=
+  ' <$as_myself |
+    sed '
+      s/[$]LINENO.*/&-/
+      t lineno
+      b
+      :lineno
+      N
+      :loop
+      s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/
+      t loop
+      s/-\n.*//
+    ' >$as_me.lineno &&
+  chmod +x "$as_me.lineno" ||
+    { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; }
+
+  # If we had to re-execute with $CONFIG_SHELL, we're ensured to have
+  # already done that, so ensure we don't try to do so again and fall
+  # in an infinite loop.  This has already happened in practice.
+  _as_can_reexec=no; export _as_can_reexec
+  # Don't try to exec as it changes $[0], causing all sort of problems
+  # (the dirname of $[0] is not the place where we might find the
+  # original and so on.  Autoconf is especially sensitive to this).
+  . "./$as_me.lineno"
+  # Exit status is that of the last command.
+  exit
+}
+
+ECHO_C= ECHO_N= ECHO_T=
+case `echo -n x` in #(((((
+-n*)
+  case `echo 'xy\c'` in
+  *c*) ECHO_T='        ';;     # ECHO_T is single tab character.
+  xy)  ECHO_C='\c';;
+  *)   echo `echo ksh88 bug on AIX 6.1` > /dev/null
+       ECHO_T='        ';;
+  esac;;
+*)
+  ECHO_N='-n';;
+esac
+
+rm -f conf$$ conf$$.exe conf$$.file
+if test -d conf$$.dir; then
+  rm -f conf$$.dir/conf$$.file
+else
+  rm -f conf$$.dir
+  mkdir conf$$.dir 2>/dev/null
+fi
+if (echo >conf$$.file) 2>/dev/null; then
+  if ln -s conf$$.file conf$$ 2>/dev/null; then
+    as_ln_s='ln -s'
+    # ... but there are two gotchas:
+    # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.
+    # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.
+    # In both cases, we have to default to `cp -pR'.
+    ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||
+      as_ln_s='cp -pR'
+  elif ln conf$$.file conf$$ 2>/dev/null; then
+    as_ln_s=ln
+  else
+    as_ln_s='cp -pR'
+  fi
+else
+  as_ln_s='cp -pR'
+fi
+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file
+rmdir conf$$.dir 2>/dev/null
+
+if mkdir -p . 2>/dev/null; then
+  as_mkdir_p='mkdir -p "$as_dir"'
+else
+  test -d ./-p && rmdir ./-p
+  as_mkdir_p=false
+fi
+
+as_test_x='test -x'
+as_executable_p=as_fn_executable_p
+
+# Sed expression to map a string onto a valid CPP name.
+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"
+
+# Sed expression to map a string onto a valid variable name.
+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"
+
+
+test -n "$DJDIR" || exec 7<&0 </dev/null
+exec 6>&1
+
+# Name of the host.
+# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status,
+# so uname gets run too.
+ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q`
+
+#
+# Initializations.
+#
+ac_default_prefix=/usr/local
+ac_clean_files=
+ac_config_libobj_dir=.
+LIBOBJS=
+cross_compiling=no
+subdirs=
+MFLAGS=
+MAKEFLAGS=
+
+# Identity of this package.
+PACKAGE_NAME='rc'
+PACKAGE_TARNAME='rc'
+PACKAGE_VERSION='1.7.4'
+PACKAGE_STRING='rc 1.7.4'
+PACKAGE_BUGREPORT=''
+PACKAGE_URL=''
+
+ac_unique_file="rc.h"
+# Factoring default headers for most tests.
+ac_includes_default="\
+#include <stdio.h>
+#ifdef HAVE_SYS_TYPES_H
+# include <sys/types.h>
+#endif
+#ifdef HAVE_SYS_STAT_H
+# include <sys/stat.h>
+#endif
+#ifdef STDC_HEADERS
+# include <stdlib.h>
+# include <stddef.h>
+#else
+# ifdef HAVE_STDLIB_H
+#  include <stdlib.h>
+# endif
+#endif
+#ifdef HAVE_STRING_H
+# if !defined STDC_HEADERS && defined HAVE_MEMORY_H
+#  include <memory.h>
+# endif
+# include <string.h>
+#endif
+#ifdef HAVE_STRINGS_H
+# include <strings.h>
+#endif
+#ifdef HAVE_INTTYPES_H
+# include <inttypes.h>
+#endif
+#ifdef HAVE_STDINT_H
+# include <stdint.h>
+#endif
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif"
+
+ac_subst_vars='am__EXEEXT_FALSE
+am__EXEEXT_TRUE
+LTLIBOBJS
+LIBOBJS
+EDIT
+ADDON
+AMC_ADDON_FALSE
+AMC_ADDON_TRUE
+AMC_HISTORY_FALSE
+AMC_HISTORY_TRUE
+AMC_NO_HASHBANG_FALSE
+AMC_NO_HASHBANG_TRUE
+AMC_RESTART_FALSE
+AMC_RESTART_TRUE
+EGREP
+GREP
+LN
+CPP
+am__fastdepCC_FALSE
+am__fastdepCC_TRUE
+CCDEPMODE
+am__nodep
+AMDEPBACKSLASH
+AMDEP_FALSE
+AMDEP_TRUE
+am__quote
+am__include
+DEPDIR
+OBJEXT
+EXEEXT
+ac_ct_CC
+CPPFLAGS
+LDFLAGS
+CFLAGS
+CC
+AM_BACKSLASH
+AM_DEFAULT_VERBOSITY
+AM_DEFAULT_V
+AM_V
+am__untar
+am__tar
+AMTAR
+am__leading_dot
+SET_MAKE
+AWK
+mkdir_p
+MKDIR_P
+INSTALL_STRIP_PROGRAM
+STRIP
+install_sh
+MAKEINFO
+AUTOHEADER
+AUTOMAKE
+AUTOCONF
+ACLOCAL
+VERSION
+PACKAGE
+CYGPATH_W
+am__isrc
+INSTALL_DATA
+INSTALL_SCRIPT
+INSTALL_PROGRAM
+target_alias
+host_alias
+build_alias
+LIBS
+ECHO_T
+ECHO_N
+ECHO_C
+DEFS
+mandir
+localedir
+libdir
+psdir
+pdfdir
+dvidir
+htmldir
+infodir
+docdir
+oldincludedir
+includedir
+localstatedir
+sharedstatedir
+sysconfdir
+datadir
+datarootdir
+libexecdir
+sbindir
+bindir
+program_transform_name
+prefix
+exec_prefix
+PACKAGE_URL
+PACKAGE_BUGREPORT
+PACKAGE_STRING
+PACKAGE_VERSION
+PACKAGE_TARNAME
+PACKAGE_NAME
+PATH_SEPARATOR
+SHELL'
+ac_subst_files=''
+ac_user_opts='
+enable_option_checking
+enable_silent_rules
+enable_dependency_tracking
+enable_largefile
+enable_builtin_echo
+enable_job
+enable_protect_env
+enable_def_interp
+enable_def_path
+with_history
+with_addon
+with_edit
+'
+      ac_precious_vars='build_alias
+host_alias
+target_alias
+CC
+CFLAGS
+LDFLAGS
+LIBS
+CPPFLAGS
+CPP'
+
+
+# Initialize some variables set by options.
+ac_init_help=
+ac_init_version=false
+ac_unrecognized_opts=
+ac_unrecognized_sep=
+# The variables have the same names as the options, with
+# dashes changed to underlines.
+cache_file=/dev/null
+exec_prefix=NONE
+no_create=
+no_recursion=
+prefix=NONE
+program_prefix=NONE
+program_suffix=NONE
+program_transform_name=s,x,x,
+silent=
+site=
+srcdir=
+verbose=
+x_includes=NONE
+x_libraries=NONE
+
+# Installation directory options.
+# These are left unexpanded so users can "make install exec_prefix=/foo"
+# and all the variables that are supposed to be based on exec_prefix
+# by default will actually change.
+# Use braces instead of parens because sh, perl, etc. also accept them.
+# (The list follows the same order as the GNU Coding Standards.)
+bindir='${exec_prefix}/bin'
+sbindir='${exec_prefix}/sbin'
+libexecdir='${exec_prefix}/libexec'
+datarootdir='${prefix}/share'
+datadir='${datarootdir}'
+sysconfdir='${prefix}/etc'
+sharedstatedir='${prefix}/com'
+localstatedir='${prefix}/var'
+includedir='${prefix}/include'
+oldincludedir='/usr/include'
+docdir='${datarootdir}/doc/${PACKAGE_TARNAME}'
+infodir='${datarootdir}/info'
+htmldir='${docdir}'
+dvidir='${docdir}'
+pdfdir='${docdir}'
+psdir='${docdir}'
+libdir='${exec_prefix}/lib'
+localedir='${datarootdir}/locale'
+mandir='${datarootdir}/man'
+
+ac_prev=
+ac_dashdash=
+for ac_option
+do
+  # If the previous option needs an argument, assign it.
+  if test -n "$ac_prev"; then
+    eval $ac_prev=\$ac_option
+    ac_prev=
+    continue
+  fi
+
+  case $ac_option in
+  *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;;
+  *=)   ac_optarg= ;;
+  *)    ac_optarg=yes ;;
+  esac
+
+  # Accept the important Cygnus configure options, so we can diagnose typos.
+
+  case $ac_dashdash$ac_option in
+  --)
+    ac_dashdash=yes ;;
+
+  -bindir | --bindir | --bindi | --bind | --bin | --bi)
+    ac_prev=bindir ;;
+  -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*)
+    bindir=$ac_optarg ;;
+
+  -build | --build | --buil | --bui | --bu)
+    ac_prev=build_alias ;;
+  -build=* | --build=* | --buil=* | --bui=* | --bu=*)
+    build_alias=$ac_optarg ;;
+
+  -cache-file | --cache-file | --cache-fil | --cache-fi \
+  | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c)
+    ac_prev=cache_file ;;
+  -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \
+  | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*)
+    cache_file=$ac_optarg ;;
+
+  --config-cache | -C)
+    cache_file=config.cache ;;
+
+  -datadir | --datadir | --datadi | --datad)
+    ac_prev=datadir ;;
+  -datadir=* | --datadir=* | --datadi=* | --datad=*)
+    datadir=$ac_optarg ;;
+
+  -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \
+  | --dataroo | --dataro | --datar)
+    ac_prev=datarootdir ;;
+  -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \
+  | --dataroot=* | --dataroo=* | --dataro=* | --datar=*)
+    datarootdir=$ac_optarg ;;
+
+  -disable-* | --disable-*)
+    ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'`
+    # Reject names that are not valid shell variable names.
+    expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+      as_fn_error $? "invalid feature name: $ac_useropt"
+    ac_useropt_orig=$ac_useropt
+    ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+    case $ac_user_opts in
+      *"
+"enable_$ac_useropt"
+"*) ;;
+      *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig"
+        ac_unrecognized_sep=', ';;
+    esac
+    eval enable_$ac_useropt=no ;;
+
+  -docdir | --docdir | --docdi | --doc | --do)
+    ac_prev=docdir ;;
+  -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*)
+    docdir=$ac_optarg ;;
+
+  -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv)
+    ac_prev=dvidir ;;
+  -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*)
+    dvidir=$ac_optarg ;;
+
+  -enable-* | --enable-*)
+    ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'`
+    # Reject names that are not valid shell variable names.
+    expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+      as_fn_error $? "invalid feature name: $ac_useropt"
+    ac_useropt_orig=$ac_useropt
+    ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+    case $ac_user_opts in
+      *"
+"enable_$ac_useropt"
+"*) ;;
+      *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig"
+        ac_unrecognized_sep=', ';;
+    esac
+    eval enable_$ac_useropt=\$ac_optarg ;;
+
+  -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \
+  | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \
+  | --exec | --exe | --ex)
+    ac_prev=exec_prefix ;;
+  -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \
+  | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \
+  | --exec=* | --exe=* | --ex=*)
+    exec_prefix=$ac_optarg ;;
+
+  -gas | --gas | --ga | --g)
+    # Obsolete; use --with-gas.
+    with_gas=yes ;;
+
+  -help | --help | --hel | --he | -h)
+    ac_init_help=long ;;
+  -help=r* | --help=r* | --hel=r* | --he=r* | -hr*)
+    ac_init_help=recursive ;;
+  -help=s* | --help=s* | --hel=s* | --he=s* | -hs*)
+    ac_init_help=short ;;
+
+  -host | --host | --hos | --ho)
+    ac_prev=host_alias ;;
+  -host=* | --host=* | --hos=* | --ho=*)
+    host_alias=$ac_optarg ;;
+
+  -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht)
+    ac_prev=htmldir ;;
+  -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \
+  | --ht=*)
+    htmldir=$ac_optarg ;;
+
+  -includedir | --includedir | --includedi | --included | --include \
+  | --includ | --inclu | --incl | --inc)
+    ac_prev=includedir ;;
+  -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \
+  | --includ=* | --inclu=* | --incl=* | --inc=*)
+    includedir=$ac_optarg ;;
+
+  -infodir | --infodir | --infodi | --infod | --info | --inf)
+    ac_prev=infodir ;;
+  -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*)
+    infodir=$ac_optarg ;;
+
+  -libdir | --libdir | --libdi | --libd)
+    ac_prev=libdir ;;
+  -libdir=* | --libdir=* | --libdi=* | --libd=*)
+    libdir=$ac_optarg ;;
+
+  -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \
+  | --libexe | --libex | --libe)
+    ac_prev=libexecdir ;;
+  -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \
+  | --libexe=* | --libex=* | --libe=*)
+    libexecdir=$ac_optarg ;;
+
+  -localedir | --localedir | --localedi | --localed | --locale)
+    ac_prev=localedir ;;
+  -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*)
+    localedir=$ac_optarg ;;
+
+  -localstatedir | --localstatedir | --localstatedi | --localstated \
+  | --localstate | --localstat | --localsta | --localst | --locals)
+    ac_prev=localstatedir ;;
+  -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \
+  | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*)
+    localstatedir=$ac_optarg ;;
+
+  -mandir | --mandir | --mandi | --mand | --man | --ma | --m)
+    ac_prev=mandir ;;
+  -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*)
+    mandir=$ac_optarg ;;
+
+  -nfp | --nfp | --nf)
+    # Obsolete; use --without-fp.
+    with_fp=no ;;
+
+  -no-create | --no-create | --no-creat | --no-crea | --no-cre \
+  | --no-cr | --no-c | -n)
+    no_create=yes ;;
+
+  -no-recursion | --no-recursion | --no-recursio | --no-recursi \
+  | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r)
+    no_recursion=yes ;;
+
+  -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \
+  | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \
+  | --oldin | --oldi | --old | --ol | --o)
+    ac_prev=oldincludedir ;;
+  -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \
+  | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \
+  | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*)
+    oldincludedir=$ac_optarg ;;
+
+  -prefix | --prefix | --prefi | --pref | --pre | --pr | --p)
+    ac_prev=prefix ;;
+  -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*)
+    prefix=$ac_optarg ;;
+
+  -program-prefix | --program-prefix | --program-prefi | --program-pref \
+  | --program-pre | --program-pr | --program-p)
+    ac_prev=program_prefix ;;
+  -program-prefix=* | --program-prefix=* | --program-prefi=* \
+  | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*)
+    program_prefix=$ac_optarg ;;
+
+  -program-suffix | --program-suffix | --program-suffi | --program-suff \
+  | --program-suf | --program-su | --program-s)
+    ac_prev=program_suffix ;;
+  -program-suffix=* | --program-suffix=* | --program-suffi=* \
+  | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*)
+    program_suffix=$ac_optarg ;;
+
+  -program-transform-name | --program-transform-name \
+  | --program-transform-nam | --program-transform-na \
+  | --program-transform-n | --program-transform- \
+  | --program-transform | --program-transfor \
+  | --program-transfo | --program-transf \
+  | --program-trans | --program-tran \
+  | --progr-tra | --program-tr | --program-t)
+    ac_prev=program_transform_name ;;
+  -program-transform-name=* | --program-transform-name=* \
+  | --program-transform-nam=* | --program-transform-na=* \
+  | --program-transform-n=* | --program-transform-=* \
+  | --program-transform=* | --program-transfor=* \
+  | --program-transfo=* | --program-transf=* \
+  | --program-trans=* | --program-tran=* \
+  | --progr-tra=* | --program-tr=* | --program-t=*)
+    program_transform_name=$ac_optarg ;;
+
+  -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd)
+    ac_prev=pdfdir ;;
+  -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*)
+    pdfdir=$ac_optarg ;;
+
+  -psdir | --psdir | --psdi | --psd | --ps)
+    ac_prev=psdir ;;
+  -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*)
+    psdir=$ac_optarg ;;
+
+  -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+  | -silent | --silent | --silen | --sile | --sil)
+    silent=yes ;;
+
+  -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)
+    ac_prev=sbindir ;;
+  -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \
+  | --sbi=* | --sb=*)
+    sbindir=$ac_optarg ;;
+
+  -sharedstatedir | --sharedstatedir | --sharedstatedi \
+  | --sharedstated | --sharedstate | --sharedstat | --sharedsta \
+  | --sharedst | --shareds | --shared | --share | --shar \
+  | --sha | --sh)
+    ac_prev=sharedstatedir ;;
+  -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \
+  | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \
+  | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \
+  | --sha=* | --sh=*)
+    sharedstatedir=$ac_optarg ;;
+
+  -site | --site | --sit)
+    ac_prev=site ;;
+  -site=* | --site=* | --sit=*)
+    site=$ac_optarg ;;
+
+  -srcdir | --srcdir | --srcdi | --srcd | --src | --sr)
+    ac_prev=srcdir ;;
+  -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*)
+    srcdir=$ac_optarg ;;
+
+  -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \
+  | --syscon | --sysco | --sysc | --sys | --sy)
+    ac_prev=sysconfdir ;;
+  -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \
+  | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*)
+    sysconfdir=$ac_optarg ;;
+
+  -target | --target | --targe | --targ | --tar | --ta | --t)
+    ac_prev=target_alias ;;
+  -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*)
+    target_alias=$ac_optarg ;;
+
+  -v | -verbose | --verbose | --verbos | --verbo | --verb)
+    verbose=yes ;;
+
+  -version | --version | --versio | --versi | --vers | -V)
+    ac_init_version=: ;;
+
+  -with-* | --with-*)
+    ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'`
+    # Reject names that are not valid shell variable names.
+    expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+      as_fn_error $? "invalid package name: $ac_useropt"
+    ac_useropt_orig=$ac_useropt
+    ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+    case $ac_user_opts in
+      *"
+"with_$ac_useropt"
+"*) ;;
+      *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig"
+        ac_unrecognized_sep=', ';;
+    esac
+    eval with_$ac_useropt=\$ac_optarg ;;
+
+  -without-* | --without-*)
+    ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'`
+    # Reject names that are not valid shell variable names.
+    expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+      as_fn_error $? "invalid package name: $ac_useropt"
+    ac_useropt_orig=$ac_useropt
+    ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+    case $ac_user_opts in
+      *"
+"with_$ac_useropt"
+"*) ;;
+      *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig"
+        ac_unrecognized_sep=', ';;
+    esac
+    eval with_$ac_useropt=no ;;
+
+  --x)
+    # Obsolete; use --with-x.
+    with_x=yes ;;
+
+  -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \
+  | --x-incl | --x-inc | --x-in | --x-i)
+    ac_prev=x_includes ;;
+  -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \
+  | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*)
+    x_includes=$ac_optarg ;;
+
+  -x-libraries | --x-libraries | --x-librarie | --x-librari \
+  | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l)
+    ac_prev=x_libraries ;;
+  -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \
+  | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*)
+    x_libraries=$ac_optarg ;;
+
+  -*) as_fn_error $? "unrecognized option: \`$ac_option'
+Try \`$0 --help' for more information"
+    ;;
+
+  *=*)
+    ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='`
+    # Reject names that are not valid shell variable names.
+    case $ac_envvar in #(
+      '' | [0-9]* | *[!_$as_cr_alnum]* )
+      as_fn_error $? "invalid variable name: \`$ac_envvar'" ;;
+    esac
+    eval $ac_envvar=\$ac_optarg
+    export $ac_envvar ;;
+
+  *)
+    # FIXME: should be removed in autoconf 3.0.
+    $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2
+    expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null &&
+      $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2
+    : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}"
+    ;;
+
+  esac
+done
+
+if test -n "$ac_prev"; then
+  ac_option=--`echo $ac_prev | sed 's/_/-/g'`
+  as_fn_error $? "missing argument to $ac_option"
+fi
+
+if test -n "$ac_unrecognized_opts"; then
+  case $enable_option_checking in
+    no) ;;
+    fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;;
+    *)     $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;;
+  esac
+fi
+
+# Check all directory arguments for consistency.
+for ac_var in  exec_prefix prefix bindir sbindir libexecdir datarootdir \
+               datadir sysconfdir sharedstatedir localstatedir includedir \
+               oldincludedir docdir infodir htmldir dvidir pdfdir psdir \
+               libdir localedir mandir
+do
+  eval ac_val=\$$ac_var
+  # Remove trailing slashes.
+  case $ac_val in
+    */ )
+      ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'`
+      eval $ac_var=\$ac_val;;
+  esac
+  # Be sure to have absolute directory names.
+  case $ac_val in
+    [\\/$]* | ?:[\\/]* )  continue;;
+    NONE | '' ) case $ac_var in *prefix ) continue;; esac;;
+  esac
+  as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val"
+done
+
+# There might be people who depend on the old broken behavior: `$host'
+# used to hold the argument of --host etc.
+# FIXME: To remove some day.
+build=$build_alias
+host=$host_alias
+target=$target_alias
+
+# FIXME: To remove some day.
+if test "x$host_alias" != x; then
+  if test "x$build_alias" = x; then
+    cross_compiling=maybe
+  elif test "x$build_alias" != "x$host_alias"; then
+    cross_compiling=yes
+  fi
+fi
+
+ac_tool_prefix=
+test -n "$host_alias" && ac_tool_prefix=$host_alias-
+
+test "$silent" = yes && exec 6>/dev/null
+
+
+ac_pwd=`pwd` && test -n "$ac_pwd" &&
+ac_ls_di=`ls -di .` &&
+ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` ||
+  as_fn_error $? "working directory cannot be determined"
+test "X$ac_ls_di" = "X$ac_pwd_ls_di" ||
+  as_fn_error $? "pwd does not report name of working directory"
+
+
+# Find the source files, if location was not specified.
+if test -z "$srcdir"; then
+  ac_srcdir_defaulted=yes
+  # Try the directory containing this script, then the parent directory.
+  ac_confdir=`$as_dirname -- "$as_myself" ||
+$as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$as_myself" : 'X\(//\)[^/]' \| \
+        X"$as_myself" : 'X\(//\)$' \| \
+        X"$as_myself" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_myself" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+  srcdir=$ac_confdir
+  if test ! -r "$srcdir/$ac_unique_file"; then
+    srcdir=..
+  fi
+else
+  ac_srcdir_defaulted=no
+fi
+if test ! -r "$srcdir/$ac_unique_file"; then
+  test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .."
+  as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir"
+fi
+ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work"
+ac_abs_confdir=`(
+       cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg"
+       pwd)`
+# When building in place, set srcdir=.
+if test "$ac_abs_confdir" = "$ac_pwd"; then
+  srcdir=.
+fi
+# Remove unnecessary trailing slashes from srcdir.
+# Double slashes in file names in object file debugging info
+# mess up M-x gdb in Emacs.
+case $srcdir in
+*/) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;;
+esac
+for ac_var in $ac_precious_vars; do
+  eval ac_env_${ac_var}_set=\${${ac_var}+set}
+  eval ac_env_${ac_var}_value=\$${ac_var}
+  eval ac_cv_env_${ac_var}_set=\${${ac_var}+set}
+  eval ac_cv_env_${ac_var}_value=\$${ac_var}
+done
+
+#
+# Report the --help message.
+#
+if test "$ac_init_help" = "long"; then
+  # Omit some internal or obsolete options to make the list less imposing.
+  # This message is too long to be a string in the A/UX 3.1 sh.
+  cat <<_ACEOF
+\`configure' configures rc 1.7.4 to adapt to many kinds of systems.
+
+Usage: $0 [OPTION]... [VAR=VALUE]...
+
+To assign environment variables (e.g., CC, CFLAGS...), specify them as
+VAR=VALUE.  See below for descriptions of some of the useful variables.
+
+Defaults for the options are specified in brackets.
+
+Configuration:
+  -h, --help              display this help and exit
+      --help=short        display options specific to this package
+      --help=recursive    display the short help of all the included packages
+  -V, --version           display version information and exit
+  -q, --quiet, --silent   do not print \`checking ...' messages
+      --cache-file=FILE   cache test results in FILE [disabled]
+  -C, --config-cache      alias for \`--cache-file=config.cache'
+  -n, --no-create         do not create output files
+      --srcdir=DIR        find the sources in DIR [configure dir or \`..']
+
+Installation directories:
+  --prefix=PREFIX         install architecture-independent files in PREFIX
+                          [$ac_default_prefix]
+  --exec-prefix=EPREFIX   install architecture-dependent files in EPREFIX
+                          [PREFIX]
+
+By default, \`make install' will install all the files in
+\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc.  You can specify
+an installation prefix other than \`$ac_default_prefix' using \`--prefix',
+for instance \`--prefix=\$HOME'.
+
+For better control, use the options below.
+
+Fine tuning of the installation directories:
+  --bindir=DIR            user executables [EPREFIX/bin]
+  --sbindir=DIR           system admin executables [EPREFIX/sbin]
+  --libexecdir=DIR        program executables [EPREFIX/libexec]
+  --sysconfdir=DIR        read-only single-machine data [PREFIX/etc]
+  --sharedstatedir=DIR    modifiable architecture-independent data [PREFIX/com]
+  --localstatedir=DIR     modifiable single-machine data [PREFIX/var]
+  --libdir=DIR            object code libraries [EPREFIX/lib]
+  --includedir=DIR        C header files [PREFIX/include]
+  --oldincludedir=DIR     C header files for non-gcc [/usr/include]
+  --datarootdir=DIR       read-only arch.-independent data root [PREFIX/share]
+  --datadir=DIR           read-only architecture-independent data [DATAROOTDIR]
+  --infodir=DIR           info documentation [DATAROOTDIR/info]
+  --localedir=DIR         locale-dependent data [DATAROOTDIR/locale]
+  --mandir=DIR            man documentation [DATAROOTDIR/man]
+  --docdir=DIR            documentation root [DATAROOTDIR/doc/rc]
+  --htmldir=DIR           html documentation [DOCDIR]
+  --dvidir=DIR            dvi documentation [DOCDIR]
+  --pdfdir=DIR            pdf documentation [DOCDIR]
+  --psdir=DIR             ps documentation [DOCDIR]
+_ACEOF
+
+  cat <<\_ACEOF
+
+Program names:
+  --program-prefix=PREFIX            prepend PREFIX to installed program names
+  --program-suffix=SUFFIX            append SUFFIX to installed program names
+  --program-transform-name=PROGRAM   run sed PROGRAM on installed program names
+_ACEOF
+fi
+
+if test -n "$ac_init_help"; then
+  case $ac_init_help in
+     short | recursive ) echo "Configuration of rc 1.7.4:";;
+   esac
+  cat <<\_ACEOF
+
+Optional Features:
+  --disable-option-checking  ignore unrecognized --enable/--with options
+  --disable-FEATURE       do not include FEATURE (same as --enable-FEATURE=no)
+  --enable-FEATURE[=ARG]  include FEATURE [ARG=yes]
+  --enable-silent-rules   less verbose build output (undo: "make V=1")
+  --disable-silent-rules  verbose build output (undo: "make V=0")
+  --enable-dependency-tracking
+                          do not reject slow dependency extractors
+  --disable-dependency-tracking
+                          speeds up one-time build
+  --disable-largefile     omit support for large files
+  --disable-builtin-echo  Don't include `echo' as a builtin
+  --disable-job           Don't do job-control-style backgrounding
+  --disable-protect-env   Don't protect environment names
+  --enable-def-interp=/bin/foo
+                          Use /bin/foo as default interpreter [/bin/sh]
+  --enable-def-path=\"/usr/local/bin/\",\"/usr/bin\"
+                          Default path [All of these that exist
+                          (/usr/local/bin /usr/bin /usr/bsd /usr/ucb /bin .)]
+
+Optional Packages:
+  --with-PACKAGE[=ARG]    use PACKAGE [ARG=yes]
+  --without-PACKAGE       do not use PACKAGE (same as --with-PACKAGE=no)
+  --with-history          Build history subprograms
+  --with-addon[=foo.c]    Extra builtins, from addon.c by default
+  --with-edit=(edit,editline,readline,vrl)  Command line editing library
+
+Some influential environment variables:
+  CC          C compiler command
+  CFLAGS      C compiler flags
+  LDFLAGS     linker flags, e.g. -L<lib dir> if you have libraries in a
+              nonstandard directory <lib dir>
+  LIBS        libraries to pass to the linker, e.g. -l<library>
+  CPPFLAGS    (Objective) C/C++ preprocessor flags, e.g. -I<include dir> if
+              you have headers in a nonstandard directory <include dir>
+  CPP         C preprocessor
+
+Use these variables to override the choices made by `configure' or to help
+it to find libraries and programs with nonstandard names/locations.
+
+Report bugs to the package provider.
+_ACEOF
+ac_status=$?
+fi
+
+if test "$ac_init_help" = "recursive"; then
+  # If there are subdirs, report their specific --help.
+  for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue
+    test -d "$ac_dir" ||
+      { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } ||
+      continue
+    ac_builddir=.
+
+case "$ac_dir" in
+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;
+*)
+  ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`
+  # A ".." for each directory in $ac_dir_suffix.
+  ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`
+  case $ac_top_builddir_sub in
+  "") ac_top_builddir_sub=. ac_top_build_prefix= ;;
+  *)  ac_top_build_prefix=$ac_top_builddir_sub/ ;;
+  esac ;;
+esac
+ac_abs_top_builddir=$ac_pwd
+ac_abs_builddir=$ac_pwd$ac_dir_suffix
+# for backward compatibility:
+ac_top_builddir=$ac_top_build_prefix
+
+case $srcdir in
+  .)  # We are building in place.
+    ac_srcdir=.
+    ac_top_srcdir=$ac_top_builddir_sub
+    ac_abs_top_srcdir=$ac_pwd ;;
+  [\\/]* | ?:[\\/]* )  # Absolute name.
+    ac_srcdir=$srcdir$ac_dir_suffix;
+    ac_top_srcdir=$srcdir
+    ac_abs_top_srcdir=$srcdir ;;
+  *) # Relative name.
+    ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix
+    ac_top_srcdir=$ac_top_build_prefix$srcdir
+    ac_abs_top_srcdir=$ac_pwd/$srcdir ;;
+esac
+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix
+
+    cd "$ac_dir" || { ac_status=$?; continue; }
+    # Check for guested configure.
+    if test -f "$ac_srcdir/configure.gnu"; then
+      echo &&
+      $SHELL "$ac_srcdir/configure.gnu" --help=recursive
+    elif test -f "$ac_srcdir/configure"; then
+      echo &&
+      $SHELL "$ac_srcdir/configure" --help=recursive
+    else
+      $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2
+    fi || ac_status=$?
+    cd "$ac_pwd" || { ac_status=$?; break; }
+  done
+fi
+
+test -n "$ac_init_help" && exit $ac_status
+if $ac_init_version; then
+  cat <<\_ACEOF
+rc configure 1.7.4
+generated by GNU Autoconf 2.69
+
+Copyright (C) 2012 Free Software Foundation, Inc.
+This configure script is free software; the Free Software Foundation
+gives unlimited permission to copy, distribute and modify it.
+_ACEOF
+  exit
+fi
+
+## ------------------------ ##
+## Autoconf initialization. ##
+## ------------------------ ##
+
+# ac_fn_c_try_compile LINENO
+# --------------------------
+# Try to compile conftest.$ac_ext, and return whether this succeeded.
+ac_fn_c_try_compile ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  rm -f conftest.$ac_objext
+  if { { ac_try="$ac_compile"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_compile") 2>conftest.err
+  ac_status=$?
+  if test -s conftest.err; then
+    grep -v '^ *+' conftest.err >conftest.er1
+    cat conftest.er1 >&5
+    mv -f conftest.er1 conftest.err
+  fi
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; } && {
+        test -z "$ac_c_werror_flag" ||
+        test ! -s conftest.err
+       } && test -s conftest.$ac_objext; then :
+  ac_retval=0
+else
+  $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+       ac_retval=1
+fi
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+  as_fn_set_status $ac_retval
+
+} # ac_fn_c_try_compile
+
+# ac_fn_c_try_cpp LINENO
+# ----------------------
+# Try to preprocess conftest.$ac_ext, and return whether this succeeded.
+ac_fn_c_try_cpp ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  if { { ac_try="$ac_cpp conftest.$ac_ext"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_cpp conftest.$ac_ext") 2>conftest.err
+  ac_status=$?
+  if test -s conftest.err; then
+    grep -v '^ *+' conftest.err >conftest.er1
+    cat conftest.er1 >&5
+    mv -f conftest.er1 conftest.err
+  fi
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; } > conftest.i && {
+        test -z "$ac_c_preproc_warn_flag$ac_c_werror_flag" ||
+        test ! -s conftest.err
+       }; then :
+  ac_retval=0
+else
+  $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+    ac_retval=1
+fi
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+  as_fn_set_status $ac_retval
+
+} # ac_fn_c_try_cpp
+
+# ac_fn_c_check_header_mongrel LINENO HEADER VAR INCLUDES
+# -------------------------------------------------------
+# Tests whether HEADER exists, giving a warning if it cannot be compiled using
+# the include files in INCLUDES and setting the cache variable VAR
+# accordingly.
+ac_fn_c_check_header_mongrel ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  if eval \${$3+:} false; then :
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
+$as_echo_n "checking for $2... " >&6; }
+if eval \${$3+:} false; then :
+  $as_echo_n "(cached) " >&6
+fi
+eval ac_res=\$$3
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+else
+  # Is the header compilable?
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 usability" >&5
+$as_echo_n "checking $2 usability... " >&6; }
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+$4
+#include <$2>
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_header_compiler=yes
+else
+  ac_header_compiler=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_compiler" >&5
+$as_echo "$ac_header_compiler" >&6; }
+
+# Is the header present?
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 presence" >&5
+$as_echo_n "checking $2 presence... " >&6; }
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <$2>
+_ACEOF
+if ac_fn_c_try_cpp "$LINENO"; then :
+  ac_header_preproc=yes
+else
+  ac_header_preproc=no
+fi
+rm -f conftest.err conftest.i conftest.$ac_ext
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_preproc" >&5
+$as_echo "$ac_header_preproc" >&6; }
+
+# So?  What about this header?
+case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in #((
+  yes:no: )
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&5
+$as_echo "$as_me: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&2;}
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5
+$as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;}
+    ;;
+  no:yes:* )
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: present but cannot be compiled" >&5
+$as_echo "$as_me: WARNING: $2: present but cannot be compiled" >&2;}
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2:     check for missing prerequisite headers?" >&5
+$as_echo "$as_me: WARNING: $2:     check for missing prerequisite headers?" >&2;}
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: see the Autoconf documentation" >&5
+$as_echo "$as_me: WARNING: $2: see the Autoconf documentation" >&2;}
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2:     section \"Present But Cannot Be Compiled\"" >&5
+$as_echo "$as_me: WARNING: $2:     section \"Present But Cannot Be Compiled\"" >&2;}
+    { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5
+$as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;}
+    ;;
+esac
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
+$as_echo_n "checking for $2... " >&6; }
+if eval \${$3+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  eval "$3=\$ac_header_compiler"
+fi
+eval ac_res=\$$3
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+fi
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+
+} # ac_fn_c_check_header_mongrel
+
+# ac_fn_c_try_run LINENO
+# ----------------------
+# Try to link conftest.$ac_ext, and return whether this succeeded. Assumes
+# that executables *can* be run.
+ac_fn_c_try_run ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  if { { ac_try="$ac_link"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_link") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; } && { ac_try='./conftest$ac_exeext'
+  { { case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_try") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; }; then :
+  ac_retval=0
+else
+  $as_echo "$as_me: program exited with status $ac_status" >&5
+       $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+       ac_retval=$ac_status
+fi
+  rm -rf conftest.dSYM conftest_ipa8_conftest.oo
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+  as_fn_set_status $ac_retval
+
+} # ac_fn_c_try_run
+
+# ac_fn_c_check_header_compile LINENO HEADER VAR INCLUDES
+# -------------------------------------------------------
+# Tests whether HEADER exists and can be compiled using the include files in
+# INCLUDES, setting the cache variable VAR accordingly.
+ac_fn_c_check_header_compile ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
+$as_echo_n "checking for $2... " >&6; }
+if eval \${$3+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+$4
+#include <$2>
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  eval "$3=yes"
+else
+  eval "$3=no"
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+eval ac_res=\$$3
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+
+} # ac_fn_c_check_header_compile
+
+# ac_fn_c_try_link LINENO
+# -----------------------
+# Try to link conftest.$ac_ext, and return whether this succeeded.
+ac_fn_c_try_link ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  rm -f conftest.$ac_objext conftest$ac_exeext
+  if { { ac_try="$ac_link"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_link") 2>conftest.err
+  ac_status=$?
+  if test -s conftest.err; then
+    grep -v '^ *+' conftest.err >conftest.er1
+    cat conftest.er1 >&5
+    mv -f conftest.er1 conftest.err
+  fi
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; } && {
+        test -z "$ac_c_werror_flag" ||
+        test ! -s conftest.err
+       } && test -s conftest$ac_exeext && {
+        test "$cross_compiling" = yes ||
+        test -x conftest$ac_exeext
+       }; then :
+  ac_retval=0
+else
+  $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+       ac_retval=1
+fi
+  # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information
+  # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would
+  # interfere with the next link command; also delete a directory that is
+  # left behind by Apple's compiler.  We do this before executing the actions.
+  rm -rf conftest.dSYM conftest_ipa8_conftest.oo
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+  as_fn_set_status $ac_retval
+
+} # ac_fn_c_try_link
+
+# ac_fn_c_check_type LINENO TYPE VAR INCLUDES
+# -------------------------------------------
+# Tests whether TYPE exists after having included INCLUDES, setting cache
+# variable VAR accordingly.
+ac_fn_c_check_type ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
+$as_echo_n "checking for $2... " >&6; }
+if eval \${$3+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  eval "$3=no"
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+$4
+int
+main ()
+{
+if (sizeof ($2))
+        return 0;
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+$4
+int
+main ()
+{
+if (sizeof (($2)))
+           return 0;
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+
+else
+  eval "$3=yes"
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+eval ac_res=\$$3
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+
+} # ac_fn_c_check_type
+
+# ac_fn_c_check_func LINENO FUNC VAR
+# ----------------------------------
+# Tests whether FUNC exists, setting the cache variable VAR accordingly
+ac_fn_c_check_func ()
+{
+  as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
+$as_echo_n "checking for $2... " >&6; }
+if eval \${$3+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+/* Define $2 to an innocuous variant, in case <limits.h> declares $2.
+   For example, HP-UX 11i <limits.h> declares gettimeofday.  */
+#define $2 innocuous_$2
+
+/* System header to define __stub macros and hopefully few prototypes,
+    which can conflict with char $2 (); below.
+    Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
+    <limits.h> exists even on freestanding compilers.  */
+
+#ifdef __STDC__
+# include <limits.h>
+#else
+# include <assert.h>
+#endif
+
+#undef $2
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char $2 ();
+/* The GNU C library defines this for functions which it implements
+    to always fail with ENOSYS.  Some functions are actually named
+    something starting with __ and the normal name is an alias.  */
+#if defined __stub_$2 || defined __stub___$2
+choke me
+#endif
+
+int
+main ()
+{
+return $2 ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  eval "$3=yes"
+else
+  eval "$3=no"
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+eval ac_res=\$$3
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+
+} # ac_fn_c_check_func
+cat >config.log <<_ACEOF
+This file contains any messages produced by compilers while
+running configure, to aid debugging if configure makes a mistake.
+
+It was created by rc $as_me 1.7.4, which was
+generated by GNU Autoconf 2.69.  Invocation command line was
+
+  $ $0 $@
+
+_ACEOF
+exec 5>>config.log
+{
+cat <<_ASUNAME
+## --------- ##
+## Platform. ##
+## --------- ##
+
+hostname = `(hostname || uname -n) 2>/dev/null | sed 1q`
+uname -m = `(uname -m) 2>/dev/null || echo unknown`
+uname -r = `(uname -r) 2>/dev/null || echo unknown`
+uname -s = `(uname -s) 2>/dev/null || echo unknown`
+uname -v = `(uname -v) 2>/dev/null || echo unknown`
+
+/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown`
+/bin/uname -X     = `(/bin/uname -X) 2>/dev/null     || echo unknown`
+
+/bin/arch              = `(/bin/arch) 2>/dev/null              || echo unknown`
+/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null       || echo unknown`
+/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown`
+/usr/bin/hostinfo      = `(/usr/bin/hostinfo) 2>/dev/null      || echo unknown`
+/bin/machine           = `(/bin/machine) 2>/dev/null           || echo unknown`
+/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null       || echo unknown`
+/bin/universe          = `(/bin/universe) 2>/dev/null          || echo unknown`
+
+_ASUNAME
+
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    $as_echo "PATH: $as_dir"
+  done
+IFS=$as_save_IFS
+
+} >&5
+
+cat >&5 <<_ACEOF
+
+
+## ----------- ##
+## Core tests. ##
+## ----------- ##
+
+_ACEOF
+
+
+# Keep a trace of the command line.
+# Strip out --no-create and --no-recursion so they do not pile up.
+# Strip out --silent because we don't want to record it for future runs.
+# Also quote any args containing shell meta-characters.
+# Make two passes to allow for proper duplicate-argument suppression.
+ac_configure_args=
+ac_configure_args0=
+ac_configure_args1=
+ac_must_keep_next=false
+for ac_pass in 1 2
+do
+  for ac_arg
+  do
+    case $ac_arg in
+    -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;;
+    -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+    | -silent | --silent | --silen | --sile | --sil)
+      continue ;;
+    *\'*)
+      ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;;
+    esac
+    case $ac_pass in
+    1) as_fn_append ac_configure_args0 " '$ac_arg'" ;;
+    2)
+      as_fn_append ac_configure_args1 " '$ac_arg'"
+      if test $ac_must_keep_next = true; then
+       ac_must_keep_next=false # Got value, back to normal.
+      else
+       case $ac_arg in
+         *=* | --config-cache | -C | -disable-* | --disable-* \
+         | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \
+         | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \
+         | -with-* | --with-* | -without-* | --without-* | --x)
+           case "$ac_configure_args0 " in
+             "$ac_configure_args1"*" '$ac_arg' "* ) continue ;;
+           esac
+           ;;
+         -* ) ac_must_keep_next=true ;;
+       esac
+      fi
+      as_fn_append ac_configure_args " '$ac_arg'"
+      ;;
+    esac
+  done
+done
+{ ac_configure_args0=; unset ac_configure_args0;}
+{ ac_configure_args1=; unset ac_configure_args1;}
+
+# When interrupted or exit'd, cleanup temporary files, and complete
+# config.log.  We remove comments because anyway the quotes in there
+# would cause problems or look ugly.
+# WARNING: Use '\'' to represent an apostrophe within the trap.
+# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug.
+trap 'exit_status=$?
+  # Save into config.log some information that might help in debugging.
+  {
+    echo
+
+    $as_echo "## ---------------- ##
+## Cache variables. ##
+## ---------------- ##"
+    echo
+    # The following way of writing the cache mishandles newlines in values,
+(
+  for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do
+    eval ac_val=\$$ac_var
+    case $ac_val in #(
+    *${as_nl}*)
+      case $ac_var in #(
+      *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5
+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;
+      esac
+      case $ac_var in #(
+      _ | IFS | as_nl) ;; #(
+      BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(
+      *) { eval $ac_var=; unset $ac_var;} ;;
+      esac ;;
+    esac
+  done
+  (set) 2>&1 |
+    case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #(
+    *${as_nl}ac_space=\ *)
+      sed -n \
+       "s/'\''/'\''\\\\'\'''\''/g;
+         s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p"
+      ;; #(
+    *)
+      sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"
+      ;;
+    esac |
+    sort
+)
+    echo
+
+    $as_echo "## ----------------- ##
+## Output variables. ##
+## ----------------- ##"
+    echo
+    for ac_var in $ac_subst_vars
+    do
+      eval ac_val=\$$ac_var
+      case $ac_val in
+      *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;
+      esac
+      $as_echo "$ac_var='\''$ac_val'\''"
+    done | sort
+    echo
+
+    if test -n "$ac_subst_files"; then
+      $as_echo "## ------------------- ##
+## File substitutions. ##
+## ------------------- ##"
+      echo
+      for ac_var in $ac_subst_files
+      do
+       eval ac_val=\$$ac_var
+       case $ac_val in
+       *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;
+       esac
+       $as_echo "$ac_var='\''$ac_val'\''"
+      done | sort
+      echo
+    fi
+
+    if test -s confdefs.h; then
+      $as_echo "## ----------- ##
+## confdefs.h. ##
+## ----------- ##"
+      echo
+      cat confdefs.h
+      echo
+    fi
+    test "$ac_signal" != 0 &&
+      $as_echo "$as_me: caught signal $ac_signal"
+    $as_echo "$as_me: exit $exit_status"
+  } >&5
+  rm -f core *.core core.conftest.* &&
+    rm -f -r conftest* confdefs* conf$$* $ac_clean_files &&
+    exit $exit_status
+' 0
+for ac_signal in 1 2 13 15; do
+  trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal
+done
+ac_signal=0
+
+# confdefs.h avoids OS command line length limits that DEFS can exceed.
+rm -f -r conftest* confdefs.h
+
+$as_echo "/* confdefs.h */" > confdefs.h
+
+# Predefined preprocessor variables.
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_NAME "$PACKAGE_NAME"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_TARNAME "$PACKAGE_TARNAME"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_VERSION "$PACKAGE_VERSION"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_STRING "$PACKAGE_STRING"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_URL "$PACKAGE_URL"
+_ACEOF
+
+
+# Let the site file select an alternate cache file if it wants to.
+# Prefer an explicitly selected file to automatically selected ones.
+ac_site_file1=NONE
+ac_site_file2=NONE
+if test -n "$CONFIG_SITE"; then
+  # We do not want a PATH search for config.site.
+  case $CONFIG_SITE in #((
+    -*)  ac_site_file1=./$CONFIG_SITE;;
+    */*) ac_site_file1=$CONFIG_SITE;;
+    *)   ac_site_file1=./$CONFIG_SITE;;
+  esac
+elif test "x$prefix" != xNONE; then
+  ac_site_file1=$prefix/share/config.site
+  ac_site_file2=$prefix/etc/config.site
+else
+  ac_site_file1=$ac_default_prefix/share/config.site
+  ac_site_file2=$ac_default_prefix/etc/config.site
+fi
+for ac_site_file in "$ac_site_file1" "$ac_site_file2"
+do
+  test "x$ac_site_file" = xNONE && continue
+  if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then
+    { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5
+$as_echo "$as_me: loading site script $ac_site_file" >&6;}
+    sed 's/^/| /' "$ac_site_file" >&5
+    . "$ac_site_file" \
+      || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "failed to load site script $ac_site_file
+See \`config.log' for more details" "$LINENO" 5; }
+  fi
+done
+
+if test -r "$cache_file"; then
+  # Some versions of bash will fail to source /dev/null (special files
+  # actually), so we avoid doing that.  DJGPP emulates it as a regular file.
+  if test /dev/null != "$cache_file" && test -f "$cache_file"; then
+    { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5
+$as_echo "$as_me: loading cache $cache_file" >&6;}
+    case $cache_file in
+      [\\/]* | ?:[\\/]* ) . "$cache_file";;
+      *)                      . "./$cache_file";;
+    esac
+  fi
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5
+$as_echo "$as_me: creating cache $cache_file" >&6;}
+  >$cache_file
+fi
+
+# Check that the precious variables saved in the cache have kept the same
+# value.
+ac_cache_corrupted=false
+for ac_var in $ac_precious_vars; do
+  eval ac_old_set=\$ac_cv_env_${ac_var}_set
+  eval ac_new_set=\$ac_env_${ac_var}_set
+  eval ac_old_val=\$ac_cv_env_${ac_var}_value
+  eval ac_new_val=\$ac_env_${ac_var}_value
+  case $ac_old_set,$ac_new_set in
+    set,)
+      { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5
+$as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;}
+      ac_cache_corrupted=: ;;
+    ,set)
+      { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5
+$as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;}
+      ac_cache_corrupted=: ;;
+    ,);;
+    *)
+      if test "x$ac_old_val" != "x$ac_new_val"; then
+       # differences in whitespace do not lead to failure.
+       ac_old_val_w=`echo x $ac_old_val`
+       ac_new_val_w=`echo x $ac_new_val`
+       if test "$ac_old_val_w" != "$ac_new_val_w"; then
+         { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5
+$as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;}
+         ac_cache_corrupted=:
+       else
+         { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5
+$as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;}
+         eval $ac_var=\$ac_old_val
+       fi
+       { $as_echo "$as_me:${as_lineno-$LINENO}:   former value:  \`$ac_old_val'" >&5
+$as_echo "$as_me:   former value:  \`$ac_old_val'" >&2;}
+       { $as_echo "$as_me:${as_lineno-$LINENO}:   current value: \`$ac_new_val'" >&5
+$as_echo "$as_me:   current value: \`$ac_new_val'" >&2;}
+      fi;;
+  esac
+  # Pass precious variables to config.status.
+  if test "$ac_new_set" = set; then
+    case $ac_new_val in
+    *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;;
+    *) ac_arg=$ac_var=$ac_new_val ;;
+    esac
+    case " $ac_configure_args " in
+      *" '$ac_arg' "*) ;; # Avoid dups.  Use of quotes ensures accuracy.
+      *) as_fn_append ac_configure_args " '$ac_arg'" ;;
+    esac
+  fi
+done
+if $ac_cache_corrupted; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+  { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5
+$as_echo "$as_me: error: changes in the environment can compromise the build" >&2;}
+  as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5
+fi
+## -------------------- ##
+## Main body of script. ##
+## -------------------- ##
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+
+
+RELDATE=`date -I`
+
+cat >>confdefs.h <<_ACEOF
+#define RELDATE "$RELDATE"
+_ACEOF
+
+
+
+am__api_version='1.14'
+
+ac_aux_dir=
+for ac_dir in "$srcdir" "$srcdir/.." "$srcdir/../.."; do
+  if test -f "$ac_dir/install-sh"; then
+    ac_aux_dir=$ac_dir
+    ac_install_sh="$ac_aux_dir/install-sh -c"
+    break
+  elif test -f "$ac_dir/install.sh"; then
+    ac_aux_dir=$ac_dir
+    ac_install_sh="$ac_aux_dir/install.sh -c"
+    break
+  elif test -f "$ac_dir/shtool"; then
+    ac_aux_dir=$ac_dir
+    ac_install_sh="$ac_aux_dir/shtool install -c"
+    break
+  fi
+done
+if test -z "$ac_aux_dir"; then
+  as_fn_error $? "cannot find install-sh, install.sh, or shtool in \"$srcdir\" \"$srcdir/..\" \"$srcdir/../..\"" "$LINENO" 5
+fi
+
+# These three variables are undocumented and unsupported,
+# and are intended to be withdrawn in a future Autoconf release.
+# They can cause serious problems if a builder's source tree is in a directory
+# whose full name contains unusual characters.
+ac_config_guess="$SHELL $ac_aux_dir/config.guess"  # Please don't use this var.
+ac_config_sub="$SHELL $ac_aux_dir/config.sub"  # Please don't use this var.
+ac_configure="$SHELL $ac_aux_dir/configure"  # Please don't use this var.
+
+
+# Find a good install program.  We prefer a C program (faster),
+# so one script is as good as another.  But avoid the broken or
+# incompatible versions:
+# SysV /etc/install, /usr/sbin/install
+# SunOS /usr/etc/install
+# IRIX /sbin/install
+# AIX /bin/install
+# AmigaOS /C/install, which installs bootblocks on floppy discs
+# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag
+# AFS /usr/afsws/bin/install, which mishandles nonexistent args
+# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff"
+# OS/2's system install, which has a completely different semantic
+# ./install, which can be erroneously created by make from ./install.sh.
+# Reject install programs that cannot install multiple files.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5
+$as_echo_n "checking for a BSD-compatible install... " >&6; }
+if test -z "$INSTALL"; then
+if ${ac_cv_path_install+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    # Account for people who put trailing slashes in PATH elements.
+case $as_dir/ in #((
+  ./ | .// | /[cC]/* | \
+  /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \
+  ?:[\\/]os2[\\/]install[\\/]* | ?:[\\/]OS2[\\/]INSTALL[\\/]* | \
+  /usr/ucb/* ) ;;
+  *)
+    # OSF1 and SCO ODT 3.0 have their own names for install.
+    # Don't use installbsd from OSF since it installs stuff as root
+    # by default.
+    for ac_prog in ginstall scoinst install; do
+      for ac_exec_ext in '' $ac_executable_extensions; do
+       if as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then
+         if test $ac_prog = install &&
+           grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then
+           # AIX install.  It has an incompatible calling convention.
+           :
+         elif test $ac_prog = install &&
+           grep pwplus "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then
+           # program-specific install script used by HP pwplus--don't use.
+           :
+         else
+           rm -rf conftest.one conftest.two conftest.dir
+           echo one > conftest.one
+           echo two > conftest.two
+           mkdir conftest.dir
+           if "$as_dir/$ac_prog$ac_exec_ext" -c conftest.one conftest.two "`pwd`/conftest.dir" &&
+             test -s conftest.one && test -s conftest.two &&
+             test -s conftest.dir/conftest.one &&
+             test -s conftest.dir/conftest.two
+           then
+             ac_cv_path_install="$as_dir/$ac_prog$ac_exec_ext -c"
+             break 3
+           fi
+         fi
+       fi
+      done
+    done
+    ;;
+esac
+
+  done
+IFS=$as_save_IFS
+
+rm -rf conftest.one conftest.two conftest.dir
+
+fi
+  if test "${ac_cv_path_install+set}" = set; then
+    INSTALL=$ac_cv_path_install
+  else
+    # As a last resort, use the slow shell script.  Don't cache a
+    # value for INSTALL within a source directory, because that will
+    # break other packages using the cache if that directory is
+    # removed, or if the value is a relative name.
+    INSTALL=$ac_install_sh
+  fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $INSTALL" >&5
+$as_echo "$INSTALL" >&6; }
+
+# Use test -z because SunOS4 sh mishandles braces in ${var-val}.
+# It thinks the first close brace ends the variable substitution.
+test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}'
+
+test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}'
+
+test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644'
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether build environment is sane" >&5
+$as_echo_n "checking whether build environment is sane... " >&6; }
+# Reject unsafe characters in $srcdir or the absolute working directory
+# name.  Accept space and tab only in the latter.
+am_lf='
+'
+case `pwd` in
+  *[\\\"\#\$\&\'\`$am_lf]*)
+    as_fn_error $? "unsafe absolute working directory name" "$LINENO" 5;;
+esac
+case $srcdir in
+  *[\\\"\#\$\&\'\`$am_lf\ \    ]*)
+    as_fn_error $? "unsafe srcdir value: '$srcdir'" "$LINENO" 5;;
+esac
+
+# Do 'set' in a subshell so we don't clobber the current shell's
+# arguments.  Must try -L first in case configure is actually a
+# symlink; some systems play weird games with the mod time of symlinks
+# (eg FreeBSD returns the mod time of the symlink's containing
+# directory).
+if (
+   am_has_slept=no
+   for am_try in 1 2; do
+     echo "timestamp, slept: $am_has_slept" > conftest.file
+     set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
+     if test "$*" = "X"; then
+       # -L didn't work.
+       set X `ls -t "$srcdir/configure" conftest.file`
+     fi
+     if test "$*" != "X $srcdir/configure conftest.file" \
+       && test "$*" != "X conftest.file $srcdir/configure"; then
+
+       # If neither matched, then we have a broken ls.  This can happen
+       # if, for instance, CONFIG_SHELL is bash and it inherits a
+       # broken ls alias from the environment.  This has actually
+       # happened.  Such a system could not be considered "sane".
+       as_fn_error $? "ls -t appears to fail.  Make sure there is not a broken
+  alias in your environment" "$LINENO" 5
+     fi
+     if test "$2" = conftest.file || test $am_try -eq 2; then
+       break
+     fi
+     # Just in case.
+     sleep 1
+     am_has_slept=yes
+   done
+   test "$2" = conftest.file
+   )
+then
+   # Ok.
+   :
+else
+   as_fn_error $? "newly created file is older than distributed files!
+Check your system clock" "$LINENO" 5
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+# If we didn't sleep, we still need to ensure time stamps of config.status and
+# generated files are strictly newer.
+am_sleep_pid=
+if grep 'slept: no' conftest.file >/dev/null 2>&1; then
+  ( sleep 1 ) &
+  am_sleep_pid=$!
+fi
+
+rm -f conftest.file
+
+test "$program_prefix" != NONE &&
+  program_transform_name="s&^&$program_prefix&;$program_transform_name"
+# Use a double $ so make ignores it.
+test "$program_suffix" != NONE &&
+  program_transform_name="s&\$&$program_suffix&;$program_transform_name"
+# Double any \ or $.
+# By default was `s,x,x', remove it if useless.
+ac_script='s/[\\$]/&&/g;s/;s,x,x,$//'
+program_transform_name=`$as_echo "$program_transform_name" | sed "$ac_script"`
+
+# expand $ac_aux_dir to an absolute path
+am_aux_dir=`cd $ac_aux_dir && pwd`
+
+if test x"${MISSING+set}" != xset; then
+  case $am_aux_dir in
+  *\ * | *\    *)
+    MISSING="\${SHELL} \"$am_aux_dir/missing\"" ;;
+  *)
+    MISSING="\${SHELL} $am_aux_dir/missing" ;;
+  esac
+fi
+# Use eval to expand $SHELL
+if eval "$MISSING --is-lightweight"; then
+  am_missing_run="$MISSING "
+else
+  am_missing_run=
+  { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: 'missing' script is too old or missing" >&5
+$as_echo "$as_me: WARNING: 'missing' script is too old or missing" >&2;}
+fi
+
+if test x"${install_sh}" != xset; then
+  case $am_aux_dir in
+  *\ * | *\    *)
+    install_sh="\${SHELL} '$am_aux_dir/install-sh'" ;;
+  *)
+    install_sh="\${SHELL} $am_aux_dir/install-sh"
+  esac
+fi
+
+# Installed binaries are usually stripped using 'strip' when the user
+# run "make install-strip".  However 'strip' might not be the right
+# tool to use in cross-compilation environments, therefore Automake
+# will honor the 'STRIP' environment variable to overrule this program.
+if test "$cross_compiling" != no; then
+  if test -n "$ac_tool_prefix"; then
+  # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args.
+set dummy ${ac_tool_prefix}strip; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_STRIP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$STRIP"; then
+  ac_cv_prog_STRIP="$STRIP" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_STRIP="${ac_tool_prefix}strip"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+STRIP=$ac_cv_prog_STRIP
+if test -n "$STRIP"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $STRIP" >&5
+$as_echo "$STRIP" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$ac_cv_prog_STRIP"; then
+  ac_ct_STRIP=$STRIP
+  # Extract the first word of "strip", so it can be a program name with args.
+set dummy strip; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_STRIP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$ac_ct_STRIP"; then
+  ac_cv_prog_ac_ct_STRIP="$ac_ct_STRIP" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_ac_ct_STRIP="strip"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP
+if test -n "$ac_ct_STRIP"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP" >&5
+$as_echo "$ac_ct_STRIP" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+  if test "x$ac_ct_STRIP" = x; then
+    STRIP=":"
+  else
+    case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+    STRIP=$ac_ct_STRIP
+  fi
+else
+  STRIP="$ac_cv_prog_STRIP"
+fi
+
+fi
+INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for a thread-safe mkdir -p" >&5
+$as_echo_n "checking for a thread-safe mkdir -p... " >&6; }
+if test -z "$MKDIR_P"; then
+  if ${ac_cv_path_mkdir+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH$PATH_SEPARATOR/opt/sfw/bin
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_prog in mkdir gmkdir; do
+        for ac_exec_ext in '' $ac_executable_extensions; do
+          as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext" || continue
+          case `"$as_dir/$ac_prog$ac_exec_ext" --version 2>&1` in #(
+            'mkdir (GNU coreutils) '* | \
+            'mkdir (coreutils) '* | \
+            'mkdir (fileutils) '4.1*)
+              ac_cv_path_mkdir=$as_dir/$ac_prog$ac_exec_ext
+              break 3;;
+          esac
+        done
+       done
+  done
+IFS=$as_save_IFS
+
+fi
+
+  test -d ./--version && rmdir ./--version
+  if test "${ac_cv_path_mkdir+set}" = set; then
+    MKDIR_P="$ac_cv_path_mkdir -p"
+  else
+    # As a last resort, use the slow shell script.  Don't cache a
+    # value for MKDIR_P within a source directory, because that will
+    # break other packages using the cache if that directory is
+    # removed, or if the value is a relative name.
+    MKDIR_P="$ac_install_sh -d"
+  fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $MKDIR_P" >&5
+$as_echo "$MKDIR_P" >&6; }
+
+for ac_prog in gawk mawk nawk awk
+do
+  # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_AWK+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$AWK"; then
+  ac_cv_prog_AWK="$AWK" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_AWK="$ac_prog"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+AWK=$ac_cv_prog_AWK
+if test -n "$AWK"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AWK" >&5
+$as_echo "$AWK" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+  test -n "$AWK" && break
+done
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} sets \$(MAKE)" >&5
+$as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; }
+set x ${MAKE-make}
+ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'`
+if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat >conftest.make <<\_ACEOF
+SHELL = /bin/sh
+all:
+       @echo '@@@%%%=$(MAKE)=@@@%%%'
+_ACEOF
+# GNU make sometimes prints "make[1]: Entering ...", which would confuse us.
+case `${MAKE-make} -f conftest.make 2>/dev/null` in
+  *@@@%%%=?*=@@@%%%*)
+    eval ac_cv_prog_make_${ac_make}_set=yes;;
+  *)
+    eval ac_cv_prog_make_${ac_make}_set=no;;
+esac
+rm -f conftest.make
+fi
+if eval test \$ac_cv_prog_make_${ac_make}_set = yes; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+  SET_MAKE=
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+  SET_MAKE="MAKE=${MAKE-make}"
+fi
+
+rm -rf .tst 2>/dev/null
+mkdir .tst 2>/dev/null
+if test -d .tst; then
+  am__leading_dot=.
+else
+  am__leading_dot=_
+fi
+rmdir .tst 2>/dev/null
+
+# Check whether --enable-silent-rules was given.
+if test "${enable_silent_rules+set}" = set; then :
+  enableval=$enable_silent_rules;
+fi
+
+case $enable_silent_rules in # (((
+  yes) AM_DEFAULT_VERBOSITY=0;;
+   no) AM_DEFAULT_VERBOSITY=1;;
+    *) AM_DEFAULT_VERBOSITY=1;;
+esac
+am_make=${MAKE-make}
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $am_make supports nested variables" >&5
+$as_echo_n "checking whether $am_make supports nested variables... " >&6; }
+if ${am_cv_make_support_nested_variables+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if $as_echo 'TRUE=$(BAR$(V))
+BAR0=false
+BAR1=true
+V=1
+am__doit:
+       @$(TRUE)
+.PHONY: am__doit' | $am_make -f - >/dev/null 2>&1; then
+  am_cv_make_support_nested_variables=yes
+else
+  am_cv_make_support_nested_variables=no
+fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_make_support_nested_variables" >&5
+$as_echo "$am_cv_make_support_nested_variables" >&6; }
+if test $am_cv_make_support_nested_variables = yes; then
+    AM_V='$(V)'
+  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
+else
+  AM_V=$AM_DEFAULT_VERBOSITY
+  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
+fi
+AM_BACKSLASH='\'
+
+if test "`cd $srcdir && pwd`" != "`pwd`"; then
+  # Use -I$(srcdir) only when $(srcdir) != ., so that make's output
+  # is not polluted with repeated "-I."
+  am__isrc=' -I$(srcdir)'
+  # test to see if srcdir already configured
+  if test -f $srcdir/config.status; then
+    as_fn_error $? "source directory already configured; run \"make distclean\" there first" "$LINENO" 5
+  fi
+fi
+
+# test whether we have cygpath
+if test -z "$CYGPATH_W"; then
+  if (cygpath --version) >/dev/null 2>/dev/null; then
+    CYGPATH_W='cygpath -w'
+  else
+    CYGPATH_W=echo
+  fi
+fi
+
+
+# Define the identity of the package.
+ PACKAGE='rc'
+ VERSION='1.7.4'
+
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE "$PACKAGE"
+_ACEOF
+
+
+cat >>confdefs.h <<_ACEOF
+#define VERSION "$VERSION"
+_ACEOF
+
+# Some tools Automake needs.
+
+ACLOCAL=${ACLOCAL-"${am_missing_run}aclocal-${am__api_version}"}
+
+
+AUTOCONF=${AUTOCONF-"${am_missing_run}autoconf"}
+
+
+AUTOMAKE=${AUTOMAKE-"${am_missing_run}automake-${am__api_version}"}
+
+
+AUTOHEADER=${AUTOHEADER-"${am_missing_run}autoheader"}
+
+
+MAKEINFO=${MAKEINFO-"${am_missing_run}makeinfo"}
+
+# For better backward compatibility.  To be removed once Automake 1.9.x
+# dies out for good.  For more background, see:
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>
+mkdir_p='$(MKDIR_P)'
+
+# We need awk for the "check" target.  The system "awk" is bad on
+# some platforms.
+# Always define AMTAR for backward compatibility.  Yes, it's still used
+# in the wild :-(  We should find a proper way to deprecate it ...
+AMTAR='$${TAR-tar}'
+
+
+# We'll loop over all known methods to create a tar archive until one works.
+_am_tools='gnutar  pax cpio none'
+
+am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -'
+
+
+
+
+
+
+# POSIX will say in a future version that running "rm -f" with no argument
+# is OK; and we want to be able to make that assumption in our Makefile
+# recipes.  So use an aggressive probe to check that the usage we want is
+# actually supported "in the wild" to an acceptable degree.
+# See automake bug#10828.
+# To make any issue more visible, cause the running configure to be aborted
+# by default if the 'rm' program in use doesn't match our expectations; the
+# user can still override this though.
+if rm -f && rm -fr && rm -rf; then : OK; else
+  cat >&2 <<'END'
+Oops!
+
+Your 'rm' program seems unable to run without file operands specified
+on the command line, even when the '-f' option is present.  This is contrary
+to the behaviour of most rm programs out there, and not conforming with
+the upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>
+
+Please tell bug-automake@gnu.org about your system, including the value
+of your $PATH and any error possibly output before this message.  This
+can help us improve future automake versions.
+
+END
+  if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then
+    echo 'Configuration will proceed anyway, since you have set the' >&2
+    echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2
+    echo >&2
+  else
+    cat >&2 <<'END'
+Aborting the configuration process, to ensure you take notice of the issue.
+
+You can download and install GNU coreutils to get an 'rm' implementation
+that behaves properly: <http://www.gnu.org/software/coreutils/>.
+
+If you want to complete the configuration process using your problematic
+'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM
+to "yes", and re-run configure.
+
+END
+    as_fn_error $? "Your 'rm' program is bad, sorry." "$LINENO" 5
+  fi
+fi
+
+ac_config_headers="$ac_config_headers config.h"
+
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+if test -n "$ac_tool_prefix"; then
+  # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args.
+set dummy ${ac_tool_prefix}gcc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$CC"; then
+  ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_CC="${ac_tool_prefix}gcc"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$ac_cv_prog_CC"; then
+  ac_ct_CC=$CC
+  # Extract the first word of "gcc", so it can be a program name with args.
+set dummy gcc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$ac_ct_CC"; then
+  ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_ac_ct_CC="gcc"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_CC=$ac_cv_prog_ac_ct_CC
+if test -n "$ac_ct_CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5
+$as_echo "$ac_ct_CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+  if test "x$ac_ct_CC" = x; then
+    CC=""
+  else
+    case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+    CC=$ac_ct_CC
+  fi
+else
+  CC="$ac_cv_prog_CC"
+fi
+
+if test -z "$CC"; then
+          if test -n "$ac_tool_prefix"; then
+    # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args.
+set dummy ${ac_tool_prefix}cc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$CC"; then
+  ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_CC="${ac_tool_prefix}cc"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+  fi
+fi
+if test -z "$CC"; then
+  # Extract the first word of "cc", so it can be a program name with args.
+set dummy cc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$CC"; then
+  ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+  ac_prog_rejected=no
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then
+       ac_prog_rejected=yes
+       continue
+     fi
+    ac_cv_prog_CC="cc"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+if test $ac_prog_rejected = yes; then
+  # We found a bogon in the path, so make sure we never use it.
+  set dummy $ac_cv_prog_CC
+  shift
+  if test $# != 0; then
+    # We chose a different compiler from the bogus one.
+    # However, it has the same basename, so the bogon will be chosen
+    # first if we set CC to just the basename; use the full file name.
+    shift
+    ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@"
+  fi
+fi
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$CC"; then
+  if test -n "$ac_tool_prefix"; then
+  for ac_prog in cl.exe
+  do
+    # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args.
+set dummy $ac_tool_prefix$ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$CC"; then
+  ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_CC="$ac_tool_prefix$ac_prog"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+    test -n "$CC" && break
+  done
+fi
+if test -z "$CC"; then
+  ac_ct_CC=$CC
+  for ac_prog in cl.exe
+do
+  # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$ac_ct_CC"; then
+  ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_ac_ct_CC="$ac_prog"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_CC=$ac_cv_prog_ac_ct_CC
+if test -n "$ac_ct_CC"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5
+$as_echo "$ac_ct_CC" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+  test -n "$ac_ct_CC" && break
+done
+
+  if test "x$ac_ct_CC" = x; then
+    CC=""
+  else
+    case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+    CC=$ac_ct_CC
+  fi
+fi
+
+fi
+
+
+test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "no acceptable C compiler found in \$PATH
+See \`config.log' for more details" "$LINENO" 5; }
+
+# Provide some information about the compiler.
+$as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5
+set X $ac_compile
+ac_compiler=$2
+for ac_option in --version -v -V -qversion; do
+  { { ac_try="$ac_compiler $ac_option >&5"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_compiler $ac_option >&5") 2>conftest.err
+  ac_status=$?
+  if test -s conftest.err; then
+    sed '10a\
+... rest of stderr output deleted ...
+         10q' conftest.err >conftest.er1
+    cat conftest.er1 >&5
+  fi
+  rm -f conftest.er1 conftest.err
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }
+done
+
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+ac_clean_files_save=$ac_clean_files
+ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out"
+# Try to create an executable without -o first, disregard a.out.
+# It will help us diagnose broken compilers, and finding out an intuition
+# of exeext.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler works" >&5
+$as_echo_n "checking whether the C compiler works... " >&6; }
+ac_link_default=`$as_echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'`
+
+# The possible output files:
+ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*"
+
+ac_rmfiles=
+for ac_file in $ac_files
+do
+  case $ac_file in
+    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;
+    * ) ac_rmfiles="$ac_rmfiles $ac_file";;
+  esac
+done
+rm -f $ac_rmfiles
+
+if { { ac_try="$ac_link_default"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_link_default") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; then :
+  # Autoconf-2.13 could set the ac_cv_exeext variable to `no'.
+# So ignore a value of `no', otherwise this would lead to `EXEEXT = no'
+# in a Makefile.  We should not override ac_cv_exeext if it was cached,
+# so that the user can short-circuit this test for compilers unknown to
+# Autoconf.
+for ac_file in $ac_files ''
+do
+  test -f "$ac_file" || continue
+  case $ac_file in
+    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj )
+       ;;
+    [ab].out )
+       # We found the default executable, but exeext='' is most
+       # certainly right.
+       break;;
+    *.* )
+       if test "${ac_cv_exeext+set}" = set && test "$ac_cv_exeext" != no;
+       then :; else
+          ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'`
+       fi
+       # We set ac_cv_exeext here because the later test for it is not
+       # safe: cross compilers may not add the suffix if given an `-o'
+       # argument, so we may need to know it at that point already.
+       # Even if this section looks crufty: it has the advantage of
+       # actually working.
+       break;;
+    * )
+       break;;
+  esac
+done
+test "$ac_cv_exeext" = no && ac_cv_exeext=
+
+else
+  ac_file=''
+fi
+if test -z "$ac_file"; then :
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+$as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error 77 "C compiler cannot create executables
+See \`config.log' for more details" "$LINENO" 5; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name" >&5
+$as_echo_n "checking for C compiler default output file name... " >&6; }
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5
+$as_echo "$ac_file" >&6; }
+ac_exeext=$ac_cv_exeext
+
+rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out
+ac_clean_files=$ac_clean_files_save
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5
+$as_echo_n "checking for suffix of executables... " >&6; }
+if { { ac_try="$ac_link"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_link") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; then :
+  # If both `conftest.exe' and `conftest' are `present' (well, observable)
+# catch `conftest.exe'.  For instance with Cygwin, `ls conftest' will
+# work properly (i.e., refer to `conftest.exe'), while it won't with
+# `rm'.
+for ac_file in conftest.exe conftest conftest.*; do
+  test -f "$ac_file" || continue
+  case $ac_file in
+    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;
+    *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'`
+         break;;
+    * ) break;;
+  esac
+done
+else
+  { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot compute suffix of executables: cannot compile and link
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+rm -f conftest conftest$ac_cv_exeext
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5
+$as_echo "$ac_cv_exeext" >&6; }
+
+rm -f conftest.$ac_ext
+EXEEXT=$ac_cv_exeext
+ac_exeext=$EXEEXT
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdio.h>
+int
+main ()
+{
+FILE *f = fopen ("conftest.out", "w");
+ return ferror (f) || fclose (f) != 0;
+
+  ;
+  return 0;
+}
+_ACEOF
+ac_clean_files="$ac_clean_files conftest.out"
+# Check that the compiler produces executables we can run.  If not, either
+# the compiler is broken, or we cross compile.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5
+$as_echo_n "checking whether we are cross compiling... " >&6; }
+if test "$cross_compiling" != yes; then
+  { { ac_try="$ac_link"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_link") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }
+  if { ac_try='./conftest$ac_cv_exeext'
+  { { case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_try") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; }; then
+    cross_compiling=no
+  else
+    if test "$cross_compiling" = maybe; then
+       cross_compiling=yes
+    else
+       { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot run C compiled programs.
+If you meant to cross compile, use \`--host'.
+See \`config.log' for more details" "$LINENO" 5; }
+    fi
+  fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5
+$as_echo "$cross_compiling" >&6; }
+
+rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out
+ac_clean_files=$ac_clean_files_save
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5
+$as_echo_n "checking for suffix of object files... " >&6; }
+if ${ac_cv_objext+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+rm -f conftest.o conftest.obj
+if { { ac_try="$ac_compile"
+case "(($ac_try" in
+  *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+  *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+  (eval "$ac_compile") 2>&5
+  ac_status=$?
+  $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; then :
+  for ac_file in conftest.o conftest.obj conftest.*; do
+  test -f "$ac_file" || continue;
+  case $ac_file in
+    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;;
+    *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'`
+       break;;
+  esac
+done
+else
+  $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot compute suffix of object files: cannot compile
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+rm -f conftest.$ac_cv_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5
+$as_echo "$ac_cv_objext" >&6; }
+OBJEXT=$ac_cv_objext
+ac_objext=$OBJEXT
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5
+$as_echo_n "checking whether we are using the GNU C compiler... " >&6; }
+if ${ac_cv_c_compiler_gnu+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+#ifndef __GNUC__
+       choke me
+#endif
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_compiler_gnu=yes
+else
+  ac_compiler_gnu=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+ac_cv_c_compiler_gnu=$ac_compiler_gnu
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5
+$as_echo "$ac_cv_c_compiler_gnu" >&6; }
+if test $ac_compiler_gnu = yes; then
+  GCC=yes
+else
+  GCC=
+fi
+ac_test_CFLAGS=${CFLAGS+set}
+ac_save_CFLAGS=$CFLAGS
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5
+$as_echo_n "checking whether $CC accepts -g... " >&6; }
+if ${ac_cv_prog_cc_g+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_save_c_werror_flag=$ac_c_werror_flag
+   ac_c_werror_flag=yes
+   ac_cv_prog_cc_g=no
+   CFLAGS="-g"
+   cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_prog_cc_g=yes
+else
+  CFLAGS=""
+      cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+
+else
+  ac_c_werror_flag=$ac_save_c_werror_flag
+        CFLAGS="-g"
+        cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_prog_cc_g=yes
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+   ac_c_werror_flag=$ac_save_c_werror_flag
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5
+$as_echo "$ac_cv_prog_cc_g" >&6; }
+if test "$ac_test_CFLAGS" = set; then
+  CFLAGS=$ac_save_CFLAGS
+elif test $ac_cv_prog_cc_g = yes; then
+  if test "$GCC" = yes; then
+    CFLAGS="-g -O2"
+  else
+    CFLAGS="-g"
+  fi
+else
+  if test "$GCC" = yes; then
+    CFLAGS="-O2"
+  else
+    CFLAGS=
+  fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5
+$as_echo_n "checking for $CC option to accept ISO C89... " >&6; }
+if ${ac_cv_prog_cc_c89+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_cv_prog_cc_c89=no
+ac_save_CC=$CC
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdarg.h>
+#include <stdio.h>
+struct stat;
+/* Most of the following tests are stolen from RCS 5.7's src/conf.sh.  */
+struct buf { int x; };
+FILE * (*rcsopen) (struct buf *, struct stat *, int);
+static char *e (p, i)
+     char **p;
+     int i;
+{
+  return p[i];
+}
+static char *f (char * (*g) (char **, int), char **p, ...)
+{
+  char *s;
+  va_list v;
+  va_start (v,p);
+  s = g (p, va_arg (v,int));
+  va_end (v);
+  return s;
+}
+
+/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default.  It has
+   function prototypes and stuff, but not '\xHH' hex character constants.
+   These don't provoke an error unfortunately, instead are silently treated
+   as 'x'.  The following induces an error, until -std is added to get
+   proper ANSI mode.  Curiously '\x00'!='x' always comes out true, for an
+   array size at least.  It's necessary to write '\x00'==0 to get something
+   that's true only with -std.  */
+int osf4_cc_array ['\x00' == 0 ? 1 : -1];
+
+/* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters
+   inside strings and character constants.  */
+#define FOO(x) 'x'
+int xlc6_cc_array[FOO(a) == 'x' ? 1 : -1];
+
+int test (int i, double x);
+struct s1 {int (*f) (int a);};
+struct s2 {int (*f) (double a);};
+int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int);
+int argc;
+char **argv;
+int
+main ()
+{
+return f (e, argv, 0) != argv[0]  ||  f (e, argv, 1) != argv[1];
+  ;
+  return 0;
+}
+_ACEOF
+for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std \
+       -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__"
+do
+  CC="$ac_save_CC $ac_arg"
+  if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_prog_cc_c89=$ac_arg
+fi
+rm -f core conftest.err conftest.$ac_objext
+  test "x$ac_cv_prog_cc_c89" != "xno" && break
+done
+rm -f conftest.$ac_ext
+CC=$ac_save_CC
+
+fi
+# AC_CACHE_VAL
+case "x$ac_cv_prog_cc_c89" in
+  x)
+    { $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5
+$as_echo "none needed" >&6; } ;;
+  xno)
+    { $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5
+$as_echo "unsupported" >&6; } ;;
+  *)
+    CC="$CC $ac_cv_prog_cc_c89"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5
+$as_echo "$ac_cv_prog_cc_c89" >&6; } ;;
+esac
+if test "x$ac_cv_prog_cc_c89" != xno; then :
+
+fi
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC understands -c and -o together" >&5
+$as_echo_n "checking whether $CC understands -c and -o together... " >&6; }
+if ${am_cv_prog_cc_c_o+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+  # Make sure it works both with $CC and with simple cc.
+  # Following AC_PROG_CC_C_O, we do the test twice because some
+  # compilers refuse to overwrite an existing .o file with -o,
+  # though they will create one.
+  am_cv_prog_cc_c_o=yes
+  for am_i in 1 2; do
+    if { echo "$as_me:$LINENO: $CC -c conftest.$ac_ext -o conftest2.$ac_objext" >&5
+   ($CC -c conftest.$ac_ext -o conftest2.$ac_objext) >&5 2>&5
+   ac_status=$?
+   echo "$as_me:$LINENO: \$? = $ac_status" >&5
+   (exit $ac_status); } \
+         && test -f conftest2.$ac_objext; then
+      : OK
+    else
+      am_cv_prog_cc_c_o=no
+      break
+    fi
+  done
+  rm -f core conftest*
+  unset am_i
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_prog_cc_c_o" >&5
+$as_echo "$am_cv_prog_cc_c_o" >&6; }
+if test "$am_cv_prog_cc_c_o" != yes; then
+   # Losing compiler, so override with the script.
+   # FIXME: It is wrong to rewrite CC.
+   # But if we don't then we get into trouble of one sort or another.
+   # A longer-term fix would be to have automake use am__CC in this case,
+   # and then we could set am__CC="\$(top_srcdir)/compile \$(CC)"
+   CC="$am_aux_dir/compile $CC"
+fi
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+DEPDIR="${am__leading_dot}deps"
+
+ac_config_commands="$ac_config_commands depfiles"
+
+
+am_make=${MAKE-make}
+cat > confinc << 'END'
+am__doit:
+       @echo this is the am__doit target
+.PHONY: am__doit
+END
+# If we don't find an include directive, just comment out the code.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for style of include used by $am_make" >&5
+$as_echo_n "checking for style of include used by $am_make... " >&6; }
+am__include="#"
+am__quote=
+_am_result=none
+# First try GNU make style include.
+echo "include confinc" > confmf
+# Ignore all kinds of additional output from 'make'.
+case `$am_make -s -f confmf 2> /dev/null` in #(
+*the\ am__doit\ target*)
+  am__include=include
+  am__quote=
+  _am_result=GNU
+  ;;
+esac
+# Now try BSD make style include.
+if test "$am__include" = "#"; then
+   echo '.include "confinc"' > confmf
+   case `$am_make -s -f confmf 2> /dev/null` in #(
+   *the\ am__doit\ target*)
+     am__include=.include
+     am__quote="\""
+     _am_result=BSD
+     ;;
+   esac
+fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $_am_result" >&5
+$as_echo "$_am_result" >&6; }
+rm -f confinc confmf
+
+# Check whether --enable-dependency-tracking was given.
+if test "${enable_dependency_tracking+set}" = set; then :
+  enableval=$enable_dependency_tracking;
+fi
+
+if test "x$enable_dependency_tracking" != xno; then
+  am_depcomp="$ac_aux_dir/depcomp"
+  AMDEPBACKSLASH='\'
+  am__nodep='_no'
+fi
+ if test "x$enable_dependency_tracking" != xno; then
+  AMDEP_TRUE=
+  AMDEP_FALSE='#'
+else
+  AMDEP_TRUE='#'
+  AMDEP_FALSE=
+fi
+
+
+
+depcc="$CC"   am_compiler_list=
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5
+$as_echo_n "checking dependency style of $depcc... " >&6; }
+if ${am_cv_CC_dependencies_compiler_type+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then
+  # We make a subdir and do the tests there.  Otherwise we can end up
+  # making bogus files that we don't know about and never remove.  For
+  # instance it was reported that on HP-UX the gcc test will end up
+  # making a dummy file named 'D' -- because '-MD' means "put the output
+  # in D".
+  rm -rf conftest.dir
+  mkdir conftest.dir
+  # Copy depcomp to subdir because otherwise we won't find it if we're
+  # using a relative directory.
+  cp "$am_depcomp" conftest.dir
+  cd conftest.dir
+  # We will build objects and dependencies in a subdirectory because
+  # it helps to detect inapplicable dependency modes.  For instance
+  # both Tru64's cc and ICC support -MD to output dependencies as a
+  # side effect of compilation, but ICC will put the dependencies in
+  # the current directory while Tru64 will put them in the object
+  # directory.
+  mkdir sub
+
+  am_cv_CC_dependencies_compiler_type=none
+  if test "$am_compiler_list" = ""; then
+     am_compiler_list=`sed -n 's/^#*\([a-zA-Z0-9]*\))$/\1/p' < ./depcomp`
+  fi
+  am__universal=false
+  case " $depcc " in #(
+     *\ -arch\ *\ -arch\ *) am__universal=true ;;
+     esac
+
+  for depmode in $am_compiler_list; do
+    # Setup a source with many dependencies, because some compilers
+    # like to wrap large dependency lists on column 80 (with \), and
+    # we should not choose a depcomp mode which is confused by this.
+    #
+    # We need to recreate these files for each test, as the compiler may
+    # overwrite some of them when testing with obscure command lines.
+    # This happens at least with the AIX C compiler.
+    : > sub/conftest.c
+    for i in 1 2 3 4 5 6; do
+      echo '#include "conftst'$i'.h"' >> sub/conftest.c
+      # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with
+      # Solaris 10 /bin/sh.
+      echo '/* dummy */' > sub/conftst$i.h
+    done
+    echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf
+
+    # We check with '-c' and '-o' for the sake of the "dashmstdout"
+    # mode.  It turns out that the SunPro C++ compiler does not properly
+    # handle '-M -o', and we need to detect this.  Also, some Intel
+    # versions had trouble with output in subdirs.
+    am__obj=sub/conftest.${OBJEXT-o}
+    am__minus_obj="-o $am__obj"
+    case $depmode in
+    gcc)
+      # This depmode causes a compiler race in universal mode.
+      test "$am__universal" = false || continue
+      ;;
+    nosideeffect)
+      # After this tag, mechanisms are not by side-effect, so they'll
+      # only be used when explicitly requested.
+      if test "x$enable_dependency_tracking" = xyes; then
+       continue
+      else
+       break
+      fi
+      ;;
+    msvc7 | msvc7msys | msvisualcpp | msvcmsys)
+      # This compiler won't grok '-c -o', but also, the minuso test has
+      # not run yet.  These depmodes are late enough in the game, and
+      # so weak that their functioning should not be impacted.
+      am__obj=conftest.${OBJEXT-o}
+      am__minus_obj=
+      ;;
+    none) break ;;
+    esac
+    if depmode=$depmode \
+       source=sub/conftest.c object=$am__obj \
+       depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \
+       $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \
+         >/dev/null 2>conftest.err &&
+       grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&
+       grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&
+       grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&
+       ${MAKE-make} -s -f confmf > /dev/null 2>&1; then
+      # icc doesn't choke on unknown options, it will just issue warnings
+      # or remarks (even with -Werror).  So we grep stderr for any message
+      # that says an option was ignored or not supported.
+      # When given -MP, icc 7.0 and 7.1 complain thusly:
+      #   icc: Command line warning: ignoring option '-M'; no argument required
+      # The diagnosis changed in icc 8.0:
+      #   icc: Command line remark: option '-MP' not supported
+      if (grep 'ignoring option' conftest.err ||
+          grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else
+        am_cv_CC_dependencies_compiler_type=$depmode
+        break
+      fi
+    fi
+  done
+
+  cd ..
+  rm -rf conftest.dir
+else
+  am_cv_CC_dependencies_compiler_type=none
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_CC_dependencies_compiler_type" >&5
+$as_echo "$am_cv_CC_dependencies_compiler_type" >&6; }
+CCDEPMODE=depmode=$am_cv_CC_dependencies_compiler_type
+
+ if
+  test "x$enable_dependency_tracking" != xno \
+  && test "$am_cv_CC_dependencies_compiler_type" = gcc3; then
+  am__fastdepCC_TRUE=
+  am__fastdepCC_FALSE='#'
+else
+  am__fastdepCC_TRUE='#'
+  am__fastdepCC_FALSE=
+fi
+
+
+
+case "$GCC" in
+yes) CFLAGS="-Wall $CFLAGS" ;;
+esac
+
+
+# Check whether --enable-largefile was given.
+if test "${enable_largefile+set}" = set; then :
+  enableval=$enable_largefile;
+fi
+
+if test "$enable_largefile" != no; then
+
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for special C compiler options needed for large files" >&5
+$as_echo_n "checking for special C compiler options needed for large files... " >&6; }
+if ${ac_cv_sys_largefile_CC+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_cv_sys_largefile_CC=no
+     if test "$GCC" != yes; then
+       ac_save_CC=$CC
+       while :; do
+        # IRIX 6.2 and later do not support large files by default,
+        # so use the C compiler's -n32 option if that helps.
+        cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+ /* Check that off_t can represent 2**63 - 1 correctly.
+    We can't simply define LARGE_OFF_T to be 9223372036854775807,
+    since some C++ compilers masquerading as C compilers
+    incorrectly reject 9223372036854775807.  */
+#define LARGE_OFF_T (((off_t) 1 << 62) - 1 + ((off_t) 1 << 62))
+  int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721
+                      && LARGE_OFF_T % 2147483647 == 1)
+                     ? 1 : -1];
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+        if ac_fn_c_try_compile "$LINENO"; then :
+  break
+fi
+rm -f core conftest.err conftest.$ac_objext
+        CC="$CC -n32"
+        if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_sys_largefile_CC=' -n32'; break
+fi
+rm -f core conftest.err conftest.$ac_objext
+        break
+       done
+       CC=$ac_save_CC
+       rm -f conftest.$ac_ext
+    fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_largefile_CC" >&5
+$as_echo "$ac_cv_sys_largefile_CC" >&6; }
+  if test "$ac_cv_sys_largefile_CC" != no; then
+    CC=$CC$ac_cv_sys_largefile_CC
+  fi
+
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _FILE_OFFSET_BITS value needed for large files" >&5
+$as_echo_n "checking for _FILE_OFFSET_BITS value needed for large files... " >&6; }
+if ${ac_cv_sys_file_offset_bits+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  while :; do
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+ /* Check that off_t can represent 2**63 - 1 correctly.
+    We can't simply define LARGE_OFF_T to be 9223372036854775807,
+    since some C++ compilers masquerading as C compilers
+    incorrectly reject 9223372036854775807.  */
+#define LARGE_OFF_T (((off_t) 1 << 62) - 1 + ((off_t) 1 << 62))
+  int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721
+                      && LARGE_OFF_T % 2147483647 == 1)
+                     ? 1 : -1];
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_sys_file_offset_bits=no; break
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#define _FILE_OFFSET_BITS 64
+#include <sys/types.h>
+ /* Check that off_t can represent 2**63 - 1 correctly.
+    We can't simply define LARGE_OFF_T to be 9223372036854775807,
+    since some C++ compilers masquerading as C compilers
+    incorrectly reject 9223372036854775807.  */
+#define LARGE_OFF_T (((off_t) 1 << 62) - 1 + ((off_t) 1 << 62))
+  int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721
+                      && LARGE_OFF_T % 2147483647 == 1)
+                     ? 1 : -1];
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_sys_file_offset_bits=64; break
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+  ac_cv_sys_file_offset_bits=unknown
+  break
+done
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_file_offset_bits" >&5
+$as_echo "$ac_cv_sys_file_offset_bits" >&6; }
+case $ac_cv_sys_file_offset_bits in #(
+  no | unknown) ;;
+  *)
+cat >>confdefs.h <<_ACEOF
+#define _FILE_OFFSET_BITS $ac_cv_sys_file_offset_bits
+_ACEOF
+;;
+esac
+rm -rf conftest*
+  if test $ac_cv_sys_file_offset_bits = unknown; then
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _LARGE_FILES value needed for large files" >&5
+$as_echo_n "checking for _LARGE_FILES value needed for large files... " >&6; }
+if ${ac_cv_sys_large_files+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  while :; do
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+ /* Check that off_t can represent 2**63 - 1 correctly.
+    We can't simply define LARGE_OFF_T to be 9223372036854775807,
+    since some C++ compilers masquerading as C compilers
+    incorrectly reject 9223372036854775807.  */
+#define LARGE_OFF_T (((off_t) 1 << 62) - 1 + ((off_t) 1 << 62))
+  int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721
+                      && LARGE_OFF_T % 2147483647 == 1)
+                     ? 1 : -1];
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_sys_large_files=no; break
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#define _LARGE_FILES 1
+#include <sys/types.h>
+ /* Check that off_t can represent 2**63 - 1 correctly.
+    We can't simply define LARGE_OFF_T to be 9223372036854775807,
+    since some C++ compilers masquerading as C compilers
+    incorrectly reject 9223372036854775807.  */
+#define LARGE_OFF_T (((off_t) 1 << 62) - 1 + ((off_t) 1 << 62))
+  int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721
+                      && LARGE_OFF_T % 2147483647 == 1)
+                     ? 1 : -1];
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_sys_large_files=1; break
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+  ac_cv_sys_large_files=unknown
+  break
+done
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_large_files" >&5
+$as_echo "$ac_cv_sys_large_files" >&6; }
+case $ac_cv_sys_large_files in #(
+  no | unknown) ;;
+  *)
+cat >>confdefs.h <<_ACEOF
+#define _LARGE_FILES $ac_cv_sys_large_files
+_ACEOF
+;;
+esac
+rm -rf conftest*
+  fi
+
+
+fi
+
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to run the C preprocessor" >&5
+$as_echo_n "checking how to run the C preprocessor... " >&6; }
+# On Suns, sometimes $CPP names a directory.
+if test -n "$CPP" && test -d "$CPP"; then
+  CPP=
+fi
+if test -z "$CPP"; then
+  if ${ac_cv_prog_CPP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+      # Double quotes because CPP needs to be expanded
+    for CPP in "$CC -E" "$CC -E -traditional-cpp" "/lib/cpp"
+    do
+      ac_preproc_ok=false
+for ac_c_preproc_warn_flag in '' yes
+do
+  # Use a header file that comes with gcc, so configuring glibc
+  # with a fresh cross-compiler works.
+  # Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
+  # <limits.h> exists even on freestanding compilers.
+  # On the NeXT, cc -E runs the code through the compiler's parser,
+  # not just through cpp. "Syntax error" is here to catch this case.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#ifdef __STDC__
+# include <limits.h>
+#else
+# include <assert.h>
+#endif
+                    Syntax error
+_ACEOF
+if ac_fn_c_try_cpp "$LINENO"; then :
+
+else
+  # Broken: fails on valid input.
+continue
+fi
+rm -f conftest.err conftest.i conftest.$ac_ext
+
+  # OK, works on sane cases.  Now check whether nonexistent headers
+  # can be detected and how.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <ac_nonexistent.h>
+_ACEOF
+if ac_fn_c_try_cpp "$LINENO"; then :
+  # Broken: success on invalid input.
+continue
+else
+  # Passes both tests.
+ac_preproc_ok=:
+break
+fi
+rm -f conftest.err conftest.i conftest.$ac_ext
+
+done
+# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped.
+rm -f conftest.i conftest.err conftest.$ac_ext
+if $ac_preproc_ok; then :
+  break
+fi
+
+    done
+    ac_cv_prog_CPP=$CPP
+
+fi
+  CPP=$ac_cv_prog_CPP
+else
+  ac_cv_prog_CPP=$CPP
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $CPP" >&5
+$as_echo "$CPP" >&6; }
+ac_preproc_ok=false
+for ac_c_preproc_warn_flag in '' yes
+do
+  # Use a header file that comes with gcc, so configuring glibc
+  # with a fresh cross-compiler works.
+  # Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
+  # <limits.h> exists even on freestanding compilers.
+  # On the NeXT, cc -E runs the code through the compiler's parser,
+  # not just through cpp. "Syntax error" is here to catch this case.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#ifdef __STDC__
+# include <limits.h>
+#else
+# include <assert.h>
+#endif
+                    Syntax error
+_ACEOF
+if ac_fn_c_try_cpp "$LINENO"; then :
+
+else
+  # Broken: fails on valid input.
+continue
+fi
+rm -f conftest.err conftest.i conftest.$ac_ext
+
+  # OK, works on sane cases.  Now check whether nonexistent headers
+  # can be detected and how.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <ac_nonexistent.h>
+_ACEOF
+if ac_fn_c_try_cpp "$LINENO"; then :
+  # Broken: success on invalid input.
+continue
+else
+  # Passes both tests.
+ac_preproc_ok=:
+break
+fi
+rm -f conftest.err conftest.i conftest.$ac_ext
+
+done
+# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped.
+rm -f conftest.i conftest.err conftest.$ac_ext
+if $ac_preproc_ok; then :
+
+else
+  { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "C preprocessor \"$CPP\" fails sanity check
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+for ac_prog in ln cp
+do
+  # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_LN+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -n "$LN"; then
+  ac_cv_prog_LN="$LN" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_exec_ext in '' $ac_executable_extensions; do
+  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+    ac_cv_prog_LN="$ac_prog"
+    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+    break 2
+  fi
+done
+  done
+IFS=$as_save_IFS
+
+fi
+fi
+LN=$ac_cv_prog_LN
+if test -n "$LN"; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LN" >&5
+$as_echo "$LN" >&6; }
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+  test -n "$LN" && break
+done
+
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e" >&5
+$as_echo_n "checking for grep that handles long lines and -e... " >&6; }
+if ${ac_cv_path_GREP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -z "$GREP"; then
+  ac_path_GREP_found=false
+  # Loop through the user's path and test for each of PROGNAME-LIST
+  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_prog in grep ggrep; do
+    for ac_exec_ext in '' $ac_executable_extensions; do
+      ac_path_GREP="$as_dir/$ac_prog$ac_exec_ext"
+      as_fn_executable_p "$ac_path_GREP" || continue
+# Check for GNU ac_path_GREP and select it if it is found.
+  # Check for GNU $ac_path_GREP
+case `"$ac_path_GREP" --version 2>&1` in
+*GNU*)
+  ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_found=:;;
+*)
+  ac_count=0
+  $as_echo_n 0123456789 >"conftest.in"
+  while :
+  do
+    cat "conftest.in" "conftest.in" >"conftest.tmp"
+    mv "conftest.tmp" "conftest.in"
+    cp "conftest.in" "conftest.nl"
+    $as_echo 'GREP' >> "conftest.nl"
+    "$ac_path_GREP" -e 'GREP$' -e '-(cannot match)-' < "conftest.nl" >"conftest.out" 2>/dev/null || break
+    diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break
+    as_fn_arith $ac_count + 1 && ac_count=$as_val
+    if test $ac_count -gt ${ac_path_GREP_max-0}; then
+      # Best one so far, save it but keep looking for a better one
+      ac_cv_path_GREP="$ac_path_GREP"
+      ac_path_GREP_max=$ac_count
+    fi
+    # 10*(2^10) chars as input seems more than enough
+    test $ac_count -gt 10 && break
+  done
+  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;
+esac
+
+      $ac_path_GREP_found && break 3
+    done
+  done
+  done
+IFS=$as_save_IFS
+  if test -z "$ac_cv_path_GREP"; then
+    as_fn_error $? "no acceptable grep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5
+  fi
+else
+  ac_cv_path_GREP=$GREP
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_GREP" >&5
+$as_echo "$ac_cv_path_GREP" >&6; }
+ GREP="$ac_cv_path_GREP"
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for egrep" >&5
+$as_echo_n "checking for egrep... " >&6; }
+if ${ac_cv_path_EGREP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if echo a | $GREP -E '(a|b)' >/dev/null 2>&1
+   then ac_cv_path_EGREP="$GREP -E"
+   else
+     if test -z "$EGREP"; then
+  ac_path_EGREP_found=false
+  # Loop through the user's path and test for each of PROGNAME-LIST
+  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    for ac_prog in egrep; do
+    for ac_exec_ext in '' $ac_executable_extensions; do
+      ac_path_EGREP="$as_dir/$ac_prog$ac_exec_ext"
+      as_fn_executable_p "$ac_path_EGREP" || continue
+# Check for GNU ac_path_EGREP and select it if it is found.
+  # Check for GNU $ac_path_EGREP
+case `"$ac_path_EGREP" --version 2>&1` in
+*GNU*)
+  ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_found=:;;
+*)
+  ac_count=0
+  $as_echo_n 0123456789 >"conftest.in"
+  while :
+  do
+    cat "conftest.in" "conftest.in" >"conftest.tmp"
+    mv "conftest.tmp" "conftest.in"
+    cp "conftest.in" "conftest.nl"
+    $as_echo 'EGREP' >> "conftest.nl"
+    "$ac_path_EGREP" 'EGREP$' < "conftest.nl" >"conftest.out" 2>/dev/null || break
+    diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break
+    as_fn_arith $ac_count + 1 && ac_count=$as_val
+    if test $ac_count -gt ${ac_path_EGREP_max-0}; then
+      # Best one so far, save it but keep looking for a better one
+      ac_cv_path_EGREP="$ac_path_EGREP"
+      ac_path_EGREP_max=$ac_count
+    fi
+    # 10*(2^10) chars as input seems more than enough
+    test $ac_count -gt 10 && break
+  done
+  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;
+esac
+
+      $ac_path_EGREP_found && break 3
+    done
+  done
+  done
+IFS=$as_save_IFS
+  if test -z "$ac_cv_path_EGREP"; then
+    as_fn_error $? "no acceptable egrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5
+  fi
+else
+  ac_cv_path_EGREP=$EGREP
+fi
+
+   fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_EGREP" >&5
+$as_echo "$ac_cv_path_EGREP" >&6; }
+ EGREP="$ac_cv_path_EGREP"
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5
+$as_echo_n "checking for ANSI C header files... " >&6; }
+if ${ac_cv_header_stdc+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdlib.h>
+#include <stdarg.h>
+#include <string.h>
+#include <float.h>
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_header_stdc=yes
+else
+  ac_cv_header_stdc=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
+if test $ac_cv_header_stdc = yes; then
+  # SunOS 4.x string.h does not declare mem*, contrary to ANSI.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <string.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "memchr" >/dev/null 2>&1; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f conftest*
+
+fi
+
+if test $ac_cv_header_stdc = yes; then
+  # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdlib.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "free" >/dev/null 2>&1; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f conftest*
+
+fi
+
+if test $ac_cv_header_stdc = yes; then
+  # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi.
+  if test "$cross_compiling" = yes; then :
+  :
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <ctype.h>
+#include <stdlib.h>
+#if ((' ' & 0x0FF) == 0x020)
+# define ISLOWER(c) ('a' <= (c) && (c) <= 'z')
+# define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c))
+#else
+# define ISLOWER(c) \
+                  (('a' <= (c) && (c) <= 'i') \
+                    || ('j' <= (c) && (c) <= 'r') \
+                    || ('s' <= (c) && (c) <= 'z'))
+# define TOUPPER(c) (ISLOWER(c) ? ((c) | 0x40) : (c))
+#endif
+
+#define XOR(e, f) (((e) && !(f)) || (!(e) && (f)))
+int
+main ()
+{
+  int i;
+  for (i = 0; i < 256; i++)
+    if (XOR (islower (i), ISLOWER (i))
+       || toupper (i) != TOUPPER (i))
+      return 2;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdc" >&5
+$as_echo "$ac_cv_header_stdc" >&6; }
+if test $ac_cv_header_stdc = yes; then
+
+$as_echo "#define STDC_HEADERS 1" >>confdefs.h
+
+fi
+
+# On IRIX 5.3, sys/types and inttypes.h are conflicting.
+for ac_header in sys/types.h sys/stat.h stdlib.h string.h memory.h strings.h \
+                 inttypes.h stdint.h unistd.h
+do :
+  as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
+ac_fn_c_check_header_compile "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default
+"
+if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+
+done
+
+
+for ac_header in sys/resource.h sys/time.h sys/types.h unistd.h
+do :
+  as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
+ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
+if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+
+done
+
+ac_header_dirent=no
+for ac_hdr in dirent.h sys/ndir.h sys/dir.h ndir.h; do
+  as_ac_Header=`$as_echo "ac_cv_header_dirent_$ac_hdr" | $as_tr_sh`
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_hdr that defines DIR" >&5
+$as_echo_n "checking for $ac_hdr that defines DIR... " >&6; }
+if eval \${$as_ac_Header+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+#include <$ac_hdr>
+
+int
+main ()
+{
+if ((DIR *) 0)
+return 0;
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  eval "$as_ac_Header=yes"
+else
+  eval "$as_ac_Header=no"
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+eval ac_res=\$$as_ac_Header
+              { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
+$as_echo "$ac_res" >&6; }
+if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_hdr" | $as_tr_cpp` 1
+_ACEOF
+
+ac_header_dirent=$ac_hdr; break
+fi
+
+done
+# Two versions of opendir et al. are in -ldir and -lx on SCO Xenix.
+if test $ac_header_dirent = dirent.h; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5
+$as_echo_n "checking for library containing opendir... " >&6; }
+if ${ac_cv_search_opendir+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_func_search_save_LIBS=$LIBS
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char opendir ();
+int
+main ()
+{
+return opendir ();
+  ;
+  return 0;
+}
+_ACEOF
+for ac_lib in '' dir; do
+  if test -z "$ac_lib"; then
+    ac_res="none required"
+  else
+    ac_res=-l$ac_lib
+    LIBS="-l$ac_lib  $ac_func_search_save_LIBS"
+  fi
+  if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_search_opendir=$ac_res
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext
+  if ${ac_cv_search_opendir+:} false; then :
+  break
+fi
+done
+if ${ac_cv_search_opendir+:} false; then :
+
+else
+  ac_cv_search_opendir=no
+fi
+rm conftest.$ac_ext
+LIBS=$ac_func_search_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_opendir" >&5
+$as_echo "$ac_cv_search_opendir" >&6; }
+ac_res=$ac_cv_search_opendir
+if test "$ac_res" != no; then :
+  test "$ac_res" = "none required" || LIBS="$ac_res $LIBS"
+
+fi
+
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5
+$as_echo_n "checking for library containing opendir... " >&6; }
+if ${ac_cv_search_opendir+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_func_search_save_LIBS=$LIBS
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char opendir ();
+int
+main ()
+{
+return opendir ();
+  ;
+  return 0;
+}
+_ACEOF
+for ac_lib in '' x; do
+  if test -z "$ac_lib"; then
+    ac_res="none required"
+  else
+    ac_res=-l$ac_lib
+    LIBS="-l$ac_lib  $ac_func_search_save_LIBS"
+  fi
+  if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_search_opendir=$ac_res
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext
+  if ${ac_cv_search_opendir+:} false; then :
+  break
+fi
+done
+if ${ac_cv_search_opendir+:} false; then :
+
+else
+  ac_cv_search_opendir=no
+fi
+rm conftest.$ac_ext
+LIBS=$ac_func_search_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_opendir" >&5
+$as_echo "$ac_cv_search_opendir" >&6; }
+ac_res=$ac_cv_search_opendir
+if test "$ac_res" != no; then :
+  test "$ac_res" = "none required" || LIBS="$ac_res $LIBS"
+
+fi
+
+fi
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5
+$as_echo_n "checking for ANSI C header files... " >&6; }
+if ${ac_cv_header_stdc+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdlib.h>
+#include <stdarg.h>
+#include <string.h>
+#include <float.h>
+
+int
+main ()
+{
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_header_stdc=yes
+else
+  ac_cv_header_stdc=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
+if test $ac_cv_header_stdc = yes; then
+  # SunOS 4.x string.h does not declare mem*, contrary to ANSI.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <string.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "memchr" >/dev/null 2>&1; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f conftest*
+
+fi
+
+if test $ac_cv_header_stdc = yes; then
+  # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI.
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <stdlib.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "free" >/dev/null 2>&1; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f conftest*
+
+fi
+
+if test $ac_cv_header_stdc = yes; then
+  # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi.
+  if test "$cross_compiling" = yes; then :
+  :
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <ctype.h>
+#include <stdlib.h>
+#if ((' ' & 0x0FF) == 0x020)
+# define ISLOWER(c) ('a' <= (c) && (c) <= 'z')
+# define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c))
+#else
+# define ISLOWER(c) \
+                  (('a' <= (c) && (c) <= 'i') \
+                    || ('j' <= (c) && (c) <= 'r') \
+                    || ('s' <= (c) && (c) <= 'z'))
+# define TOUPPER(c) (ISLOWER(c) ? ((c) | 0x40) : (c))
+#endif
+
+#define XOR(e, f) (((e) && !(f)) || (!(e) && (f)))
+int
+main ()
+{
+  int i;
+  for (i = 0; i < 256; i++)
+    if (XOR (islower (i), ISLOWER (i))
+       || toupper (i) != TOUPPER (i))
+      return 2;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+
+else
+  ac_cv_header_stdc=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdc" >&5
+$as_echo "$ac_cv_header_stdc" >&6; }
+if test $ac_cv_header_stdc = yes; then
+
+$as_echo "#define STDC_HEADERS 1" >>confdefs.h
+
+fi
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for sys/wait.h that is POSIX.1 compatible" >&5
+$as_echo_n "checking for sys/wait.h that is POSIX.1 compatible... " >&6; }
+if ${ac_cv_header_sys_wait_h+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+#include <sys/wait.h>
+#ifndef WEXITSTATUS
+# define WEXITSTATUS(stat_val) ((unsigned int) (stat_val) >> 8)
+#endif
+#ifndef WIFEXITED
+# define WIFEXITED(stat_val) (((stat_val) & 255) == 0)
+#endif
+
+int
+main ()
+{
+  int s;
+  wait (&s);
+  s = WIFEXITED (s) ? WEXITSTATUS (s) : 1;
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_header_sys_wait_h=yes
+else
+  ac_cv_header_sys_wait_h=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_sys_wait_h" >&5
+$as_echo "$ac_cv_header_sys_wait_h" >&6; }
+if test $ac_cv_header_sys_wait_h = yes; then
+
+$as_echo "#define HAVE_SYS_WAIT_H 1" >>confdefs.h
+
+fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for uid_t in sys/types.h" >&5
+$as_echo_n "checking for uid_t in sys/types.h... " >&6; }
+if ${ac_cv_type_uid_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "uid_t" >/dev/null 2>&1; then :
+  ac_cv_type_uid_t=yes
+else
+  ac_cv_type_uid_t=no
+fi
+rm -f conftest*
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_type_uid_t" >&5
+$as_echo "$ac_cv_type_uid_t" >&6; }
+if test $ac_cv_type_uid_t = no; then
+
+$as_echo "#define uid_t int" >>confdefs.h
+
+
+$as_echo "#define gid_t int" >>confdefs.h
+
+fi
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking type of array argument to getgroups" >&5
+$as_echo_n "checking type of array argument to getgroups... " >&6; }
+if ${ac_cv_type_getgroups+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  ac_cv_type_getgroups=cross
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+/* Thanks to Mike Rendell for this test.  */
+$ac_includes_default
+#define NGID 256
+#undef MAX
+#define MAX(x, y) ((x) > (y) ? (x) : (y))
+
+int
+main ()
+{
+  gid_t gidset[NGID];
+  int i, n;
+  union { gid_t gval; long int lval; }  val;
+
+  val.lval = -1;
+  for (i = 0; i < NGID; i++)
+    gidset[i] = val.gval;
+  n = getgroups (sizeof (gidset) / MAX (sizeof (int), sizeof (gid_t)) - 1,
+                gidset);
+  /* Exit non-zero if getgroups seems to require an array of ints.  This
+     happens when gid_t is short int but getgroups modifies an array
+     of ints.  */
+  return n > 0 && gidset[n] != val.gval;
+}
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  ac_cv_type_getgroups=gid_t
+else
+  ac_cv_type_getgroups=int
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+if test $ac_cv_type_getgroups = cross; then
+        cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <unistd.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "getgroups.*int.*gid_t" >/dev/null 2>&1; then :
+  ac_cv_type_getgroups=gid_t
+else
+  ac_cv_type_getgroups=int
+fi
+rm -f conftest*
+
+fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_type_getgroups" >&5
+$as_echo "$ac_cv_type_getgroups" >&6; }
+
+cat >>confdefs.h <<_ACEOF
+#define GETGROUPS_T $ac_cv_type_getgroups
+_ACEOF
+
+
+ac_fn_c_check_type "$LINENO" "pid_t" "ac_cv_type_pid_t" "$ac_includes_default"
+if test "x$ac_cv_type_pid_t" = xyes; then :
+
+else
+
+cat >>confdefs.h <<_ACEOF
+#define pid_t int
+_ACEOF
+
+fi
+
+ac_fn_c_check_type "$LINENO" "size_t" "ac_cv_type_size_t" "$ac_includes_default"
+if test "x$ac_cv_type_size_t" = xyes; then :
+
+else
+
+cat >>confdefs.h <<_ACEOF
+#define size_t unsigned int
+_ACEOF
+
+fi
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for uid_t in sys/types.h" >&5
+$as_echo_n "checking for uid_t in sys/types.h... " >&6; }
+if ${ac_cv_type_uid_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "uid_t" >/dev/null 2>&1; then :
+  ac_cv_type_uid_t=yes
+else
+  ac_cv_type_uid_t=no
+fi
+rm -f conftest*
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_type_uid_t" >&5
+$as_echo "$ac_cv_type_uid_t" >&6; }
+if test $ac_cv_type_uid_t = no; then
+
+$as_echo "#define uid_t int" >>confdefs.h
+
+
+$as_echo "#define gid_t int" >>confdefs.h
+
+fi
+
+ac_fn_c_check_type "$LINENO" "ssize_t" "ac_cv_type_ssize_t" "$ac_includes_default"
+if test "x$ac_cv_type_ssize_t" = xyes; then :
+
+else
+
+cat >>confdefs.h <<_ACEOF
+#define ssize_t long
+_ACEOF
+
+fi
+
+
+for ac_func in getgroups lstat setpgrp setrlimit sigaction
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+done
+
+
+case "$ac_cv_func_sigaction" in
+no) { $as_echo "$as_me:${as_lineno-$LINENO}: checking for restartable system calls" >&5
+$as_echo_n "checking for restartable system calls... " >&6; }
+if ${ac_cv_sys_restartable_syscalls+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot run test program while cross compiling
+See \`config.log' for more details" "$LINENO" 5; }
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+/* Exit 0 (true) if wait returns something other than -1,
+   i.e. the pid of the child, which means that wait was restarted
+   after getting the signal.  */
+
+$ac_includes_default
+#include <signal.h>
+#ifdef HAVE_SYS_WAIT_H
+# include <sys/wait.h>
+#endif
+
+/* Some platforms explicitly require an extern "C" signal handler
+   when using C++. */
+#ifdef __cplusplus
+extern "C" void ucatch (int dummy) { }
+#else
+void ucatch (dummy) int dummy; { }
+#endif
+
+int
+main ()
+{
+  int i = fork (), status;
+
+  if (i == 0)
+    {
+      sleep (3);
+      kill (getppid (), SIGINT);
+      sleep (3);
+      return 0;
+    }
+
+  signal (SIGINT, ucatch);
+
+  status = wait (&i);
+  if (status == -1)
+    wait (&i);
+
+  return status == -1;
+}
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  ac_cv_sys_restartable_syscalls=yes
+else
+  ac_cv_sys_restartable_syscalls=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_restartable_syscalls" >&5
+$as_echo "$ac_cv_sys_restartable_syscalls" >&6; }
+if test $ac_cv_sys_restartable_syscalls = yes; then
+
+$as_echo "#define HAVE_RESTARTABLE_SYSCALLS 1" >>confdefs.h
+
+fi
+ ;;
+esac
+ if test "$ac_cv_sys_restartable_syscalls" = yes; then
+  AMC_RESTART_TRUE=
+  AMC_RESTART_FALSE='#'
+else
+  AMC_RESTART_TRUE='#'
+  AMC_RESTART_FALSE=
+fi
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for POSIX getgroups" >&5
+$as_echo_n "checking for POSIX getgroups... " >&6; }
+if ${rc_cv_func_posix_getgroups+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  rc_cv_func_posix_getgroups=yes
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#include <unistd.h>
+int main(void) {
+       return getgroups(0, (void *)0) == -1;
+}
+
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  rc_cv_func_posix_getgroups=yes
+else
+  rc_cv_func_posix_getgroups=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_func_posix_getgroups" >&5
+$as_echo "$rc_cv_func_posix_getgroups" >&6; }
+       case "$rc_cv_func_posix_getgroups" in
+       yes)
+$as_echo "#define HAVE_POSIX_GETGROUPS 1" >>confdefs.h
+ ;;
+       esac
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sigsetjmp" >&5
+$as_echo_n "checking for sigsetjmp... " >&6; }
+if ${rc_cv_sigsetjmp+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <setjmp.h>
+
+int
+main ()
+{
+
+sigjmp_buf e;
+sigsetjmp(e, 1);
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  rc_cv_sigsetjmp=yes
+else
+  rc_cv_sigsetjmp=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_sigsetjmp" >&5
+$as_echo "$rc_cv_sigsetjmp" >&6; }
+       case "$rc_cv_sigsetjmp" in
+       yes)
+$as_echo "#define HAVE_SIGSETJMP 1" >>confdefs.h
+ ;;
+       esac
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether setpgrp takes no argument" >&5
+$as_echo_n "checking whether setpgrp takes no argument... " >&6; }
+if ${ac_cv_func_setpgrp_void+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  as_fn_error $? "cannot check setpgrp when cross compiling" "$LINENO" 5
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+$ac_includes_default
+int
+main ()
+{
+/* If this system has a BSD-style setpgrp which takes arguments,
+  setpgrp(1, 1) will fail with ESRCH and return -1, in that case
+  exit successfully. */
+  return setpgrp (1,1) != -1;
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  ac_cv_func_setpgrp_void=no
+else
+  ac_cv_func_setpgrp_void=yes
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_func_setpgrp_void" >&5
+$as_echo "$ac_cv_func_setpgrp_void" >&6; }
+if test $ac_cv_func_setpgrp_void = yes; then
+
+$as_echo "#define SETPGRP_VOID 1" >>confdefs.h
+
+fi
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for strerror" >&5
+$as_echo_n "checking for strerror... " >&6; }
+if ${rc_cv_strerror+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <string.h>
+
+int
+main ()
+{
+
+strerror(0);
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  rc_cv_strerror=yes
+else
+  rc_cv_strerror=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_strerror" >&5
+$as_echo "$rc_cv_strerror" >&6; }
+       case "$rc_cv_strerror" in
+       yes)
+$as_echo "#define HAVE_STRERROR 1" >>confdefs.h
+ ;;
+       esac
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking if _KERNEL is required for RLIMIT defines" >&5
+$as_echo_n "checking if _KERNEL is required for RLIMIT defines... " >&6; }
+if ${rc_cv_kernel_rlimit+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#include <sys/resource.h>
+
+int
+main ()
+{
+
+int f;
+f = RLIMIT_DATA;
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  rc_cv_kernel_rlimit=no
+else
+   cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#define _KERNEL
+#include <sys/resource.h>
+#undef _KERNEL
+
+int
+main ()
+{
+
+int f;
+f = RLIMIT_DATA;
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  rc_cv_kernel_rlimit=yes
+else
+  rc_cv_kernel_rlimit=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_kernel_rlimit" >&5
+$as_echo "$rc_cv_kernel_rlimit" >&6; }
+       case "$rc_cv_kernel_rlimit" in
+       yes)
+$as_echo "#define RLIMIT_NEEDS_KERNEL 1" >>confdefs.h
+ ;;
+       esac
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for rlim_t" >&5
+$as_echo_n "checking for rlim_t... " >&6; }
+if ${rc_cv_have_rlim_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#if RLIMIT_NEEDS_KERNEL
+#define _KERNEL
+#endif
+#include <sys/resource.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "rlim_t" >/dev/null 2>&1; then :
+  rc_cv_have_rlim_t=yes
+else
+  rc_cv_have_rlim_t=no
+fi
+rm -f conftest*
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_have_rlim_t" >&5
+$as_echo "$rc_cv_have_rlim_t" >&6; }
+
+       case "$rc_cv_have_rlim_t" in
+       yes)
+$as_echo "#define HAVE_RLIM_T 1" >>confdefs.h
+ ;;
+       no)     { $as_echo "$as_me:${as_lineno-$LINENO}: checking for native quad_t" >&5
+$as_echo_n "checking for native quad_t... " >&6; }
+if ${rc_cv_have_quad_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+
+int
+main ()
+{
+
+typedef quad_t align_t;
+align_t a;
+a = (quad_t)0;
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  rc_cv_have_quad_t=yes
+else
+  rc_cv_have_quad_t=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_have_quad_t" >&5
+$as_echo "$rc_cv_have_quad_t" >&6; }
+
+               case "$rc_cv_have_quad_t" in
+               yes)
+$as_echo "#define HAVE_QUAD_T 1" >>confdefs.h
+
+                       { $as_echo "$as_me:${as_lineno-$LINENO}: checking if rlimit values are quad_t" >&5
+$as_echo_n "checking if rlimit values are quad_t... " >&6; }
+if ${rc_cv_rlim_t_is_quad_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  $ac_cv_type_quad_t
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#if RLIMIT_NEEDS_KERNEL
+#define _KERNEL
+#endif
+#include <sys/resource.h>
+#if RLIMIT_NEEDS_KERNEL
+#undef _KERNEL
+#endif
+main(){
+       struct rlimit rl;
+       exit(sizeof rl.rlim_cur != sizeof(quad_t));
+}
+
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  rc_cv_rlim_t_is_quad_t=yes
+else
+  rc_cv_rlim_t_is_quad_t=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_rlim_t_is_quad_t" >&5
+$as_echo "$rc_cv_rlim_t_is_quad_t" >&6; }
+
+                       case "$rc_cv_rlim_t_is_quad_t" in
+                       yes)
+$as_echo "#define RLIM_T_IS_QUAD_T 1" >>confdefs.h
+ ;;
+                       esac
+                       ;;
+               esac
+               ;;
+       esac
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sig_atomic_t" >&5
+$as_echo_n "checking for sig_atomic_t... " >&6; }
+if ${rc_cv_sig_atomic_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <signal.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "sig_atomic_t" >/dev/null 2>&1; then :
+  rc_cv_sig_atomic_t=yes
+else
+  rc_cv_sig_atomic_t=no
+fi
+rm -f conftest*
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_sig_atomic_t" >&5
+$as_echo "$rc_cv_sig_atomic_t" >&6; }
+       case "$rc_cv_sig_atomic_t" in
+       no)
+$as_echo "#define sig_atomic_t int" >>confdefs.h
+ ;;
+       esac
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for SysV SIGCLD semantics" >&5
+$as_echo_n "checking for SysV SIGCLD semantics... " >&6; }
+if ${rc_cv_sysv_sigcld+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  rc_cv_sysv_sigcld=yes
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <errno.h>
+#include <signal.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+int main(void) {
+       int i;
+       signal(SIGCLD, SIG_IGN);
+       switch (fork()) {
+       case -1:
+               return 1;
+       case 0:
+               return 0;
+       default:
+               sleep(1);
+               if (wait(&i) == -1 && errno == ECHILD) return 0;
+               else return 1;
+       }
+}
+
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  rc_cv_sysv_sigcld=yes
+else
+  rc_cv_sysv_sigcld=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_sysv_sigcld" >&5
+$as_echo "$rc_cv_sysv_sigcld" >&6; }
+       case "$rc_cv_sysv_sigcld" in
+       yes)
+$as_echo "#define HAVE_SYSV_SIGCLD 1" >>confdefs.h
+ ;;
+       esac
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether #! works in shell scripts" >&5
+$as_echo_n "checking whether #! works in shell scripts... " >&6; }
+if ${ac_cv_sys_interpreter+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  echo '#! /bin/cat
+exit 69
+' >conftest
+chmod u+x conftest
+(SHELL=/bin/sh; export SHELL; ./conftest >/dev/null 2>&1)
+if test $? -ne 69; then
+   ac_cv_sys_interpreter=yes
+else
+   ac_cv_sys_interpreter=no
+fi
+rm -f conftest
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_interpreter" >&5
+$as_echo "$ac_cv_sys_interpreter" >&6; }
+interpval=$ac_cv_sys_interpreter
+
+case "$ac_cv_sys_interpreter" in
+yes)
+$as_echo "#define HASH_BANG 1" >>confdefs.h
+ ;;
+esac
+ if test "$ac_cv_sys_interpreter" = no; then
+  AMC_NO_HASHBANG_TRUE=
+  AMC_NO_HASHBANG_FALSE='#'
+else
+  AMC_NO_HASHBANG_TRUE='#'
+  AMC_NO_HASHBANG_FALSE=
+fi
+
+
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for /dev/fd" >&5
+$as_echo_n "checking for /dev/fd... " >&6; }
+if ${rc_cv_sys_dev_fd+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test -d /dev/fd && test -r /dev/fd/0; then
+                       rc_cv_sys_dev_fd=yes
+               elif test -d /proc/self/fd && test -r /proc/self/fd/0; then
+                       rc_cv_sys_dev_fd=odd
+               else
+                       rc_cv_sys_dev_fd=no
+               fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_sys_dev_fd" >&5
+$as_echo "$rc_cv_sys_dev_fd" >&6; }
+
+case "$rc_cv_sys_dev_fd" in
+yes)
+$as_echo "#define HAVE_DEV_FD 1" >>confdefs.h
+ ;;
+odd)
+$as_echo "#define HAVE_PROC_SELF_FD 1" >>confdefs.h
+ ;;
+no)    for ac_func in mkfifo
+do :
+  ac_fn_c_check_func "$LINENO" "mkfifo" "ac_cv_func_mkfifo"
+if test "x$ac_cv_func_mkfifo" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_MKFIFO 1
+_ACEOF
+
+fi
+done
+ ;;
+esac
+
+case "$ac_cv_func_mkfifo" in
+yes)
+$as_echo "#define HAVE_FIFO 1" >>confdefs.h
+ ;;
+no)
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for mknod FIFOs" >&5
+$as_echo_n "checking for mknod FIFOs... " >&6; }
+if ${rc_cv_sys_fifo+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test "$cross_compiling" = yes; then :
+  rc_cv_sys_fifo=no
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <sys/types.h>
+#include <sys/stat.h>
+
+main() {
+       exit(mknod("/tmp/rc$$.0", S_IFIFO | 0666, 0) != 0);
+}
+
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  rc_cv_sys_fifo=yes
+else
+  rc_cv_sys_fifo=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_sys_fifo" >&5
+$as_echo "$rc_cv_sys_fifo" >&6; }
+       rm -f /tmp/rc$$.0
+       case "$rc_cv_sys_fifo" in
+       yes)    $as_echo "#define HAVE_FIFO 1" >>confdefs.h
+ ;;
+       esac
+ ;;
+esac
+
+# Check whether --enable-builtin-echo was given.
+if test "${enable_builtin_echo+set}" = set; then :
+  enableval=$enable_builtin_echo; test "x$enableval" != "xno" &&
+$as_echo "#define RC_ECHO 1" >>confdefs.h
+
+else
+  $as_echo "#define RC_ECHO 1" >>confdefs.h
+
+fi
+
+
+# Check whether --enable-job was given.
+if test "${enable_job+set}" = set; then :
+  enableval=$enable_job; test "x$enableval" != "xno" &&
+$as_echo "#define RC_JOB 1" >>confdefs.h
+
+else
+  $as_echo "#define RC_JOB 1" >>confdefs.h
+
+fi
+
+
+# Check whether --enable-protect-env was given.
+if test "${enable_protect_env+set}" = set; then :
+  enableval=$enable_protect_env; test "x$enableval" != "xno" &&
+$as_echo "#define PROTECT_ENV 1" >>confdefs.h
+
+else
+  $as_echo "#define PROTECT_ENV 1" >>confdefs.h
+
+fi
+
+
+# Check whether --enable-def-interp was given.
+if test "${enable_def_interp+set}" = set; then :
+  enableval=$enable_def_interp;
+       case "$enableval" in
+       no)
+               ;;
+       yes)
+
+$as_echo "#define DEFAULTINTERP \"/bin/sh\"" >>confdefs.h
+
+               ;;
+       *)
+               cat >>confdefs.h <<_ACEOF
+#define DEFAULTINTERP "$enableval"
+_ACEOF
+
+       esac
+
+else
+  $as_echo "#define DEFAULTINTERP \"/bin/sh\"" >>confdefs.h
+
+fi
+
+
+# Check whether --enable-def-path was given.
+if test "${enable_def_path+set}" = set; then :
+  enableval=$enable_def_path;
+       case "$enableval" in
+       no|yes) ;;
+       *)
+cat >>confdefs.h <<_ACEOF
+#define DEFAULTPATH $enableval
+_ACEOF
+ ;;
+       esac
+
+else
+  enable_def_path=yes
+fi
+
+
+case "$enable_def_path" in
+yes)   { $as_echo "$as_me:${as_lineno-$LINENO}: checking extant directories for default path" >&5
+$as_echo_n "checking extant directories for default path... " >&6; }
+if ${rc_cv_def_path+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+               rc_cv_def_path=''
+               for i in /usr/local/bin /usr/bin /usr/bsd /usr/ucb /bin .; do
+                       if test -d $i; then
+                               case "$rc_cv_def_path" in
+                               '')     rc_cv_def_path=\"$i\" ;;
+                               *)      rc_cv_def_path=$rc_cv_def_path,\"$i\" ;;
+                               esac
+                       fi
+               done
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $rc_cv_def_path" >&5
+$as_echo "$rc_cv_def_path" >&6; }
+       cat >>confdefs.h <<_ACEOF
+#define DEFAULTPATH $rc_cv_def_path
+_ACEOF
+
+       ;;
+esac
+
+
+# Check whether --with-history was given.
+if test "${with_history+set}" = set; then :
+  withval=$with_history;
+       case "$withval" in
+        yes) rc_history=yes ;;
+        *) rc_history=no ;;
+        esac
+
+else
+  rc_history=no
+fi
+
+ if test "$rc_history" = yes; then
+  AMC_HISTORY_TRUE=
+  AMC_HISTORY_FALSE='#'
+else
+  AMC_HISTORY_TRUE='#'
+  AMC_HISTORY_FALSE=
+fi
+
+
+
+
+# Check whether --with-addon was given.
+if test "${with_addon+set}" = set; then :
+  withval=$with_addon;
+       case "$withval" in
+       yes)    ADDON=addon.o ;;
+       no)     ADDON='' ;;
+       *)      ADDON=`echo $withval |sed 's/\.c$/\.o/'` ;;
+       esac
+
+fi
+
+ if test "$ADDON" != ""; then
+  AMC_ADDON_TRUE=
+  AMC_ADDON_FALSE='#'
+else
+  AMC_ADDON_TRUE='#'
+  AMC_ADDON_FALSE=
+fi
+
+case "$ADDON" in
+?*)
+$as_echo "#define RC_ADDON 1" >>confdefs.h
+ ;;
+esac
+
+
+
+EDIT=edit-null.o
+
+# Check whether --with-edit was given.
+if test "${with_edit+set}" = set; then :
+  withval=$with_edit;
+       case $withval in
+       yes)
+               as_fn_error $? "must specify which library" "$LINENO" 5
+               # might consider searching
+               ;;
+       no|null)
+               ;;
+       edit|bsd)
+               EDIT=edit-edit.o
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltinfo" >&5
+$as_echo_n "checking for tgetent in -ltinfo... " >&6; }
+if ${ac_cv_lib_tinfo_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltinfo  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_tinfo_tgetent=yes
+else
+  ac_cv_lib_tinfo_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_tinfo_tgetent" >&5
+$as_echo "$ac_cv_lib_tinfo_tgetent" >&6; }
+if test "x$ac_cv_lib_tinfo_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltinfo
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltermcap" >&5
+$as_echo_n "checking for tgetent in -ltermcap... " >&6; }
+if ${ac_cv_lib_termcap_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltermcap  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_termcap_tgetent=yes
+else
+  ac_cv_lib_termcap_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_termcap_tgetent" >&5
+$as_echo "$ac_cv_lib_termcap_tgetent" >&6; }
+if test "x$ac_cv_lib_termcap_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltermcap
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -lncurses" >&5
+$as_echo_n "checking for tgetent in -lncurses... " >&6; }
+if ${ac_cv_lib_ncurses_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lncurses  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ncurses_tgetent=yes
+else
+  ac_cv_lib_ncurses_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ncurses_tgetent" >&5
+$as_echo "$ac_cv_lib_ncurses_tgetent" >&6; }
+if test "x$ac_cv_lib_ncurses_tgetent" = xyes; then :
+  rc_lib_tgetent=-lncurses
+else
+  as_fn_error $? "tgetent not found" "$LINENO" 5
+
+fi
+
+
+fi
+
+
+fi
+
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: checking for el_init in -ledit" >&5
+$as_echo_n "checking for el_init in -ledit... " >&6; }
+if ${ac_cv_lib_edit_el_init+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ledit $rc_lib_tgetent $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char el_init ();
+int
+main ()
+{
+return el_init ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_edit_el_init=yes
+else
+  ac_cv_lib_edit_el_init=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_edit_el_init" >&5
+$as_echo "$ac_cv_lib_edit_el_init" >&6; }
+if test "x$ac_cv_lib_edit_el_init" = xyes; then :
+
+                       LIBS="$LIBS -ledit $rc_lib_tgetent"
+
+else
+  as_fn_error $? "edit library not found" "$LINENO" 5
+fi
+
+               ;;
+       editline)
+               EDIT=edit-editline.o
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltinfo" >&5
+$as_echo_n "checking for tgetent in -ltinfo... " >&6; }
+if ${ac_cv_lib_tinfo_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltinfo  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_tinfo_tgetent=yes
+else
+  ac_cv_lib_tinfo_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_tinfo_tgetent" >&5
+$as_echo "$ac_cv_lib_tinfo_tgetent" >&6; }
+if test "x$ac_cv_lib_tinfo_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltinfo
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltermcap" >&5
+$as_echo_n "checking for tgetent in -ltermcap... " >&6; }
+if ${ac_cv_lib_termcap_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltermcap  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_termcap_tgetent=yes
+else
+  ac_cv_lib_termcap_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_termcap_tgetent" >&5
+$as_echo "$ac_cv_lib_termcap_tgetent" >&6; }
+if test "x$ac_cv_lib_termcap_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltermcap
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -lncurses" >&5
+$as_echo_n "checking for tgetent in -lncurses... " >&6; }
+if ${ac_cv_lib_ncurses_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lncurses  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ncurses_tgetent=yes
+else
+  ac_cv_lib_ncurses_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ncurses_tgetent" >&5
+$as_echo "$ac_cv_lib_ncurses_tgetent" >&6; }
+if test "x$ac_cv_lib_ncurses_tgetent" = xyes; then :
+  rc_lib_tgetent=-lncurses
+else
+  as_fn_error $? "tgetent not found" "$LINENO" 5
+
+fi
+
+
+fi
+
+
+fi
+
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: checking for el_ring_bell in -leditline" >&5
+$as_echo_n "checking for el_ring_bell in -leditline... " >&6; }
+if ${ac_cv_lib_editline_el_ring_bell+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-leditline $rc_lib_tgetent $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char el_ring_bell ();
+int
+main ()
+{
+return el_ring_bell ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_editline_el_ring_bell=yes
+else
+  ac_cv_lib_editline_el_ring_bell=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_editline_el_ring_bell" >&5
+$as_echo "$ac_cv_lib_editline_el_ring_bell" >&6; }
+if test "x$ac_cv_lib_editline_el_ring_bell" = xyes; then :
+
+                       LIBS="$LIBS -leditline $rc_lib_tgetent"
+
+else
+  as_fn_error $? "editline library not found" "$LINENO" 5
+fi
+
+               ;;
+       readline|gnu)
+               EDIT=edit-readline.o
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltinfo" >&5
+$as_echo_n "checking for tgetent in -ltinfo... " >&6; }
+if ${ac_cv_lib_tinfo_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltinfo  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_tinfo_tgetent=yes
+else
+  ac_cv_lib_tinfo_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_tinfo_tgetent" >&5
+$as_echo "$ac_cv_lib_tinfo_tgetent" >&6; }
+if test "x$ac_cv_lib_tinfo_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltinfo
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltermcap" >&5
+$as_echo_n "checking for tgetent in -ltermcap... " >&6; }
+if ${ac_cv_lib_termcap_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltermcap  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_termcap_tgetent=yes
+else
+  ac_cv_lib_termcap_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_termcap_tgetent" >&5
+$as_echo "$ac_cv_lib_termcap_tgetent" >&6; }
+if test "x$ac_cv_lib_termcap_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltermcap
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -lncurses" >&5
+$as_echo_n "checking for tgetent in -lncurses... " >&6; }
+if ${ac_cv_lib_ncurses_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lncurses  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ncurses_tgetent=yes
+else
+  ac_cv_lib_ncurses_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ncurses_tgetent" >&5
+$as_echo "$ac_cv_lib_ncurses_tgetent" >&6; }
+if test "x$ac_cv_lib_ncurses_tgetent" = xyes; then :
+  rc_lib_tgetent=-lncurses
+else
+  as_fn_error $? "tgetent not found" "$LINENO" 5
+
+fi
+
+
+fi
+
+
+fi
+
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: checking for readline in -lreadline" >&5
+$as_echo_n "checking for readline in -lreadline... " >&6; }
+if ${ac_cv_lib_readline_readline+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lreadline $rc_lib_tgetent $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char readline ();
+int
+main ()
+{
+return readline ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_readline_readline=yes
+else
+  ac_cv_lib_readline_readline=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_readline_readline" >&5
+$as_echo "$ac_cv_lib_readline_readline" >&6; }
+if test "x$ac_cv_lib_readline_readline" = xyes; then :
+
+                       LIBS="$LIBS -lreadline $rc_lib_tgetent"
+
+else
+  as_fn_error $? "readline library not found" "$LINENO" 5
+fi
+
+               cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+                       #include <stdio.h>
+                       #include <readline/readline.h>
+
+int
+main ()
+{
+
+                       rl_catch_signals = 0;
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+
+else
+  as_fn_error $? "readline >= 4.0 not found" "$LINENO" 5
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+               ;;
+       vrl)
+               EDIT=edit-vrl.o
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltinfo" >&5
+$as_echo_n "checking for tgetent in -ltinfo... " >&6; }
+if ${ac_cv_lib_tinfo_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltinfo  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_tinfo_tgetent=yes
+else
+  ac_cv_lib_tinfo_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_tinfo_tgetent" >&5
+$as_echo "$ac_cv_lib_tinfo_tgetent" >&6; }
+if test "x$ac_cv_lib_tinfo_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltinfo
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -ltermcap" >&5
+$as_echo_n "checking for tgetent in -ltermcap... " >&6; }
+if ${ac_cv_lib_termcap_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-ltermcap  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_termcap_tgetent=yes
+else
+  ac_cv_lib_termcap_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_termcap_tgetent" >&5
+$as_echo "$ac_cv_lib_termcap_tgetent" >&6; }
+if test "x$ac_cv_lib_termcap_tgetent" = xyes; then :
+  rc_lib_tgetent=-ltermcap
+else
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tgetent in -lncurses" >&5
+$as_echo_n "checking for tgetent in -lncurses... " >&6; }
+if ${ac_cv_lib_ncurses_tgetent+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lncurses  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char tgetent ();
+int
+main ()
+{
+return tgetent ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ncurses_tgetent=yes
+else
+  ac_cv_lib_ncurses_tgetent=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ncurses_tgetent" >&5
+$as_echo "$ac_cv_lib_ncurses_tgetent" >&6; }
+if test "x$ac_cv_lib_ncurses_tgetent" = xyes; then :
+  rc_lib_tgetent=-lncurses
+else
+  as_fn_error $? "tgetent not found" "$LINENO" 5
+
+fi
+
+
+fi
+
+
+fi
+
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iline_peekch in -lvrl" >&5
+$as_echo_n "checking for iline_peekch in -lvrl... " >&6; }
+if ${ac_cv_lib_vrl_iline_peekch+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lvrl $rc_lib_tgetent $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char iline_peekch ();
+int
+main ()
+{
+return iline_peekch ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_vrl_iline_peekch=yes
+else
+  ac_cv_lib_vrl_iline_peekch=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_vrl_iline_peekch" >&5
+$as_echo "$ac_cv_lib_vrl_iline_peekch" >&6; }
+if test "x$ac_cv_lib_vrl_iline_peekch" = xyes; then :
+
+                       LIBS="$LIBS -lvrl $rc_lib_tgetent"
+
+else
+  as_fn_error $? "vrl library not found" "$LINENO" 5
+fi
+
+               ;;
+       *)
+               as_fn_error $? "unknown editing library $withval" "$LINENO" 5
+               ;;
+       esac
+
+fi
+
+
+
+
+
+
+
+ac_config_files="$ac_config_files Makefile"
+
+cat >confcache <<\_ACEOF
+# This file is a shell script that caches the results of configure
+# tests run on this system so they can be shared between configure
+# scripts and configure runs, see configure's option --config-cache.
+# It is not useful on other systems.  If it contains results you don't
+# want to keep, you may remove or edit it.
+#
+# config.status only pays attention to the cache file if you give it
+# the --recheck option to rerun configure.
+#
+# `ac_cv_env_foo' variables (set or unset) will be overridden when
+# loading this file, other *unset* `ac_cv_foo' will be assigned the
+# following values.
+
+_ACEOF
+
+# The following way of writing the cache mishandles newlines in values,
+# but we know of no workaround that is simple, portable, and efficient.
+# So, we kill variables containing newlines.
+# Ultrix sh set writes to stderr and can't be redirected directly,
+# and sets the high bit in the cache file unless we assign to the vars.
+(
+  for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do
+    eval ac_val=\$$ac_var
+    case $ac_val in #(
+    *${as_nl}*)
+      case $ac_var in #(
+      *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5
+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;
+      esac
+      case $ac_var in #(
+      _ | IFS | as_nl) ;; #(
+      BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(
+      *) { eval $ac_var=; unset $ac_var;} ;;
+      esac ;;
+    esac
+  done
+
+  (set) 2>&1 |
+    case $as_nl`(ac_space=' '; set) 2>&1` in #(
+    *${as_nl}ac_space=\ *)
+      # `set' does not quote correctly, so add quotes: double-quote
+      # substitution turns \\\\ into \\, and sed turns \\ into \.
+      sed -n \
+       "s/'/'\\\\''/g;
+         s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p"
+      ;; #(
+    *)
+      # `set' quotes correctly as required by POSIX, so do not add quotes.
+      sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"
+      ;;
+    esac |
+    sort
+) |
+  sed '
+     /^ac_cv_env_/b end
+     t clear
+     :clear
+     s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/
+     t end
+     s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/
+     :end' >>confcache
+if diff "$cache_file" confcache >/dev/null 2>&1; then :; else
+  if test -w "$cache_file"; then
+    if test "x$cache_file" != "x/dev/null"; then
+      { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5
+$as_echo "$as_me: updating cache $cache_file" >&6;}
+      if test ! -f "$cache_file" || test -h "$cache_file"; then
+       cat confcache >"$cache_file"
+      else
+        case $cache_file in #(
+        */* | ?:*)
+         mv -f confcache "$cache_file"$$ &&
+         mv -f "$cache_file"$$ "$cache_file" ;; #(
+        *)
+         mv -f confcache "$cache_file" ;;
+       esac
+      fi
+    fi
+  else
+    { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5
+$as_echo "$as_me: not updating unwritable cache $cache_file" >&6;}
+  fi
+fi
+rm -f confcache
+
+test "x$prefix" = xNONE && prefix=$ac_default_prefix
+# Let make expand exec_prefix.
+test "x$exec_prefix" = xNONE && exec_prefix='${prefix}'
+
+DEFS=-DHAVE_CONFIG_H
+
+ac_libobjs=
+ac_ltlibobjs=
+U=
+for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue
+  # 1. Remove the extension, and $U if already installed.
+  ac_script='s/\$U\././;s/\.o$//;s/\.obj$//'
+  ac_i=`$as_echo "$ac_i" | sed "$ac_script"`
+  # 2. Prepend LIBOBJDIR.  When used with automake>=1.10 LIBOBJDIR
+  #    will be set to the directory where LIBOBJS objects are built.
+  as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext"
+  as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo'
+done
+LIBOBJS=$ac_libobjs
+
+LTLIBOBJS=$ac_ltlibobjs
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking that generated files are newer than configure" >&5
+$as_echo_n "checking that generated files are newer than configure... " >&6; }
+   if test -n "$am_sleep_pid"; then
+     # Hide warnings about reused PIDs.
+     wait $am_sleep_pid 2>/dev/null
+   fi
+   { $as_echo "$as_me:${as_lineno-$LINENO}: result: done" >&5
+$as_echo "done" >&6; }
+ if test -n "$EXEEXT"; then
+  am__EXEEXT_TRUE=
+  am__EXEEXT_FALSE='#'
+else
+  am__EXEEXT_TRUE='#'
+  am__EXEEXT_FALSE=
+fi
+
+if test -z "${AMDEP_TRUE}" && test -z "${AMDEP_FALSE}"; then
+  as_fn_error $? "conditional \"AMDEP\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${am__fastdepCC_TRUE}" && test -z "${am__fastdepCC_FALSE}"; then
+  as_fn_error $? "conditional \"am__fastdepCC\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${AMC_RESTART_TRUE}" && test -z "${AMC_RESTART_FALSE}"; then
+  as_fn_error $? "conditional \"AMC_RESTART\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${AMC_NO_HASHBANG_TRUE}" && test -z "${AMC_NO_HASHBANG_FALSE}"; then
+  as_fn_error $? "conditional \"AMC_NO_HASHBANG\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${AMC_HISTORY_TRUE}" && test -z "${AMC_HISTORY_FALSE}"; then
+  as_fn_error $? "conditional \"AMC_HISTORY\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${AMC_ADDON_TRUE}" && test -z "${AMC_ADDON_FALSE}"; then
+  as_fn_error $? "conditional \"AMC_ADDON\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+
+: "${CONFIG_STATUS=./config.status}"
+ac_write_fail=0
+ac_clean_files_save=$ac_clean_files
+ac_clean_files="$ac_clean_files $CONFIG_STATUS"
+{ $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5
+$as_echo "$as_me: creating $CONFIG_STATUS" >&6;}
+as_write_fail=0
+cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1
+#! $SHELL
+# Generated by $as_me.
+# Run this file to recreate the current configuration.
+# Compiler output produced by configure, useful for debugging
+# configure, is in config.log if it exists.
+
+debug=false
+ac_cs_recheck=false
+ac_cs_silent=false
+
+SHELL=\${CONFIG_SHELL-$SHELL}
+export SHELL
+_ASEOF
+cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1
+## -------------------- ##
+## M4sh Initialization. ##
+## -------------------- ##
+
+# Be more Bourne compatible
+DUALCASE=1; export DUALCASE # for MKS sh
+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :
+  emulate sh
+  NULLCMD=:
+  # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which
+  # is contrary to our usage.  Disable this feature.
+  alias -g '${1+"$@"}'='"$@"'
+  setopt NO_GLOB_SUBST
+else
+  case `(set -o) 2>/dev/null` in #(
+  *posix*) :
+    set -o posix ;; #(
+  *) :
+     ;;
+esac
+fi
+
+
+as_nl='
+'
+export as_nl
+# Printing a long string crashes Solaris 7 /usr/bin/printf.
+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo
+# Prefer a ksh shell builtin over an external printf program on Solaris,
+# but without wasting forks for bash or zsh.
+if test -z "$BASH_VERSION$ZSH_VERSION" \
+    && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then
+  as_echo='print -r --'
+  as_echo_n='print -rn --'
+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then
+  as_echo='printf %s\n'
+  as_echo_n='printf %s'
+else
+  if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then
+    as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'
+    as_echo_n='/usr/ucb/echo -n'
+  else
+    as_echo_body='eval expr "X$1" : "X\\(.*\\)"'
+    as_echo_n_body='eval
+      arg=$1;
+      case $arg in #(
+      *"$as_nl"*)
+       expr "X$arg" : "X\\(.*\\)$as_nl";
+       arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;
+      esac;
+      expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"
+    '
+    export as_echo_n_body
+    as_echo_n='sh -c $as_echo_n_body as_echo'
+  fi
+  export as_echo_body
+  as_echo='sh -c $as_echo_body as_echo'
+fi
+
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+  PATH_SEPARATOR=:
+  (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {
+    (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||
+      PATH_SEPARATOR=';'
+  }
+fi
+
+
+# IFS
+# We need space, tab and new line, in precisely that order.  Quoting is
+# there to prevent editors from complaining about space-tab.
+# (If _AS_PATH_WALK were called with IFS unset, it would disable word
+# splitting by setting IFS to empty value.)
+IFS=" ""       $as_nl"
+
+# Find who we are.  Look in the path if we contain no directory separator.
+as_myself=
+case $0 in #((
+  *[\\/]* ) as_myself=$0 ;;
+  *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+  IFS=$as_save_IFS
+  test -z "$as_dir" && as_dir=.
+    test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break
+  done
+IFS=$as_save_IFS
+
+     ;;
+esac
+# We did not find ourselves, most probably we were run as `sh COMMAND'
+# in which case we are not to be found in the path.
+if test "x$as_myself" = x; then
+  as_myself=$0
+fi
+if test ! -f "$as_myself"; then
+  $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2
+  exit 1
+fi
+
+# Unset variables that we do not need and which cause bugs (e.g. in
+# pre-3.0 UWIN ksh).  But do not cause bugs in bash 2.01; the "|| exit 1"
+# suppresses any "Segmentation fault" message there.  '((' could
+# trigger a bug in pdksh 5.2.14.
+for as_var in BASH_ENV ENV MAIL MAILPATH
+do eval test x\${$as_var+set} = xset \
+  && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :
+done
+PS1='$ '
+PS2='> '
+PS4='+ '
+
+# NLS nuisances.
+LC_ALL=C
+export LC_ALL
+LANGUAGE=C
+export LANGUAGE
+
+# CDPATH.
+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH
+
+
+# as_fn_error STATUS ERROR [LINENO LOG_FD]
+# ----------------------------------------
+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are
+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the
+# script with STATUS, using 1 if that was 0.
+as_fn_error ()
+{
+  as_status=$1; test $as_status -eq 0 && as_status=1
+  if test "$4"; then
+    as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+    $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4
+  fi
+  $as_echo "$as_me: error: $2" >&2
+  as_fn_exit $as_status
+} # as_fn_error
+
+
+# as_fn_set_status STATUS
+# -----------------------
+# Set $? to STATUS, without forking.
+as_fn_set_status ()
+{
+  return $1
+} # as_fn_set_status
+
+# as_fn_exit STATUS
+# -----------------
+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.
+as_fn_exit ()
+{
+  set +e
+  as_fn_set_status $1
+  exit $1
+} # as_fn_exit
+
+# as_fn_unset VAR
+# ---------------
+# Portably unset VAR.
+as_fn_unset ()
+{
+  { eval $1=; unset $1;}
+}
+as_unset=as_fn_unset
+# as_fn_append VAR VALUE
+# ----------------------
+# Append the text in VALUE to the end of the definition contained in VAR. Take
+# advantage of any shell optimizations that allow amortized linear growth over
+# repeated appends, instead of the typical quadratic growth present in naive
+# implementations.
+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :
+  eval 'as_fn_append ()
+  {
+    eval $1+=\$2
+  }'
+else
+  as_fn_append ()
+  {
+    eval $1=\$$1\$2
+  }
+fi # as_fn_append
+
+# as_fn_arith ARG...
+# ------------------
+# Perform arithmetic evaluation on the ARGs, and store the result in the
+# global $as_val. Take advantage of shells that can avoid forks. The arguments
+# must be portable across $(()) and expr.
+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :
+  eval 'as_fn_arith ()
+  {
+    as_val=$(( $* ))
+  }'
+else
+  as_fn_arith ()
+  {
+    as_val=`expr "$@" || test $? -eq 1`
+  }
+fi # as_fn_arith
+
+
+if expr a : '\(a\)' >/dev/null 2>&1 &&
+   test "X`expr 00001 : '.*\(...\)'`" = X001; then
+  as_expr=expr
+else
+  as_expr=false
+fi
+
+if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then
+  as_basename=basename
+else
+  as_basename=false
+fi
+
+if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then
+  as_dirname=dirname
+else
+  as_dirname=false
+fi
+
+as_me=`$as_basename -- "$0" ||
+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \
+        X"$0" : 'X\(//\)$' \| \
+        X"$0" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X/"$0" |
+    sed '/^.*\/\([^/][^/]*\)\/*$/{
+           s//\1/
+           q
+         }
+         /^X\/\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\/\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+
+# Avoid depending upon Character Ranges.
+as_cr_letters='abcdefghijklmnopqrstuvwxyz'
+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'
+as_cr_Letters=$as_cr_letters$as_cr_LETTERS
+as_cr_digits='0123456789'
+as_cr_alnum=$as_cr_Letters$as_cr_digits
+
+ECHO_C= ECHO_N= ECHO_T=
+case `echo -n x` in #(((((
+-n*)
+  case `echo 'xy\c'` in
+  *c*) ECHO_T='        ';;     # ECHO_T is single tab character.
+  xy)  ECHO_C='\c';;
+  *)   echo `echo ksh88 bug on AIX 6.1` > /dev/null
+       ECHO_T='        ';;
+  esac;;
+*)
+  ECHO_N='-n';;
+esac
+
+rm -f conf$$ conf$$.exe conf$$.file
+if test -d conf$$.dir; then
+  rm -f conf$$.dir/conf$$.file
+else
+  rm -f conf$$.dir
+  mkdir conf$$.dir 2>/dev/null
+fi
+if (echo >conf$$.file) 2>/dev/null; then
+  if ln -s conf$$.file conf$$ 2>/dev/null; then
+    as_ln_s='ln -s'
+    # ... but there are two gotchas:
+    # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.
+    # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.
+    # In both cases, we have to default to `cp -pR'.
+    ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||
+      as_ln_s='cp -pR'
+  elif ln conf$$.file conf$$ 2>/dev/null; then
+    as_ln_s=ln
+  else
+    as_ln_s='cp -pR'
+  fi
+else
+  as_ln_s='cp -pR'
+fi
+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file
+rmdir conf$$.dir 2>/dev/null
+
+
+# as_fn_mkdir_p
+# -------------
+# Create "$as_dir" as a directory, including parents if necessary.
+as_fn_mkdir_p ()
+{
+
+  case $as_dir in #(
+  -*) as_dir=./$as_dir;;
+  esac
+  test -d "$as_dir" || eval $as_mkdir_p || {
+    as_dirs=
+    while :; do
+      case $as_dir in #(
+      *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(
+      *) as_qdir=$as_dir;;
+      esac
+      as_dirs="'$as_qdir' $as_dirs"
+      as_dir=`$as_dirname -- "$as_dir" ||
+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$as_dir" : 'X\(//\)[^/]' \| \
+        X"$as_dir" : 'X\(//\)$' \| \
+        X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_dir" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+      test -d "$as_dir" && break
+    done
+    test -z "$as_dirs" || eval "mkdir $as_dirs"
+  } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"
+
+
+} # as_fn_mkdir_p
+if mkdir -p . 2>/dev/null; then
+  as_mkdir_p='mkdir -p "$as_dir"'
+else
+  test -d ./-p && rmdir ./-p
+  as_mkdir_p=false
+fi
+
+
+# as_fn_executable_p FILE
+# -----------------------
+# Test if FILE is an executable regular file.
+as_fn_executable_p ()
+{
+  test -f "$1" && test -x "$1"
+} # as_fn_executable_p
+as_test_x='test -x'
+as_executable_p=as_fn_executable_p
+
+# Sed expression to map a string onto a valid CPP name.
+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"
+
+# Sed expression to map a string onto a valid variable name.
+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"
+
+
+exec 6>&1
+## ----------------------------------- ##
+## Main body of $CONFIG_STATUS script. ##
+## ----------------------------------- ##
+_ASEOF
+test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# Save the log message, to keep $0 and so on meaningful, and to
+# report actual input values of CONFIG_FILES etc. instead of their
+# values after options handling.
+ac_log="
+This file was extended by rc $as_me 1.7.4, which was
+generated by GNU Autoconf 2.69.  Invocation command line was
+
+  CONFIG_FILES    = $CONFIG_FILES
+  CONFIG_HEADERS  = $CONFIG_HEADERS
+  CONFIG_LINKS    = $CONFIG_LINKS
+  CONFIG_COMMANDS = $CONFIG_COMMANDS
+  $ $0 $@
+
+on `(hostname || uname -n) 2>/dev/null | sed 1q`
+"
+
+_ACEOF
+
+case $ac_config_files in *"
+"*) set x $ac_config_files; shift; ac_config_files=$*;;
+esac
+
+case $ac_config_headers in *"
+"*) set x $ac_config_headers; shift; ac_config_headers=$*;;
+esac
+
+
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+# Files that config.status was made for.
+config_files="$ac_config_files"
+config_headers="$ac_config_headers"
+config_commands="$ac_config_commands"
+
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+ac_cs_usage="\
+\`$as_me' instantiates files and other configuration actions
+from templates according to the current configuration.  Unless the files
+and actions are specified as TAGs, all are instantiated by default.
+
+Usage: $0 [OPTION]... [TAG]...
+
+  -h, --help       print this help, then exit
+  -V, --version    print version number and configuration settings, then exit
+      --config     print configuration, then exit
+  -q, --quiet, --silent
+                   do not print progress messages
+  -d, --debug      don't remove temporary files
+      --recheck    update $as_me by reconfiguring in the same conditions
+      --file=FILE[:TEMPLATE]
+                   instantiate the configuration file FILE
+      --header=FILE[:TEMPLATE]
+                   instantiate the configuration header FILE
+
+Configuration files:
+$config_files
+
+Configuration headers:
+$config_headers
+
+Configuration commands:
+$config_commands
+
+Report bugs to the package provider."
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
+ac_cs_version="\\
+rc config.status 1.7.4
+configured by $0, generated by GNU Autoconf 2.69,
+  with options \\"\$ac_cs_config\\"
+
+Copyright (C) 2012 Free Software Foundation, Inc.
+This config.status script is free software; the Free Software Foundation
+gives unlimited permission to copy, distribute and modify it."
+
+ac_pwd='$ac_pwd'
+srcdir='$srcdir'
+INSTALL='$INSTALL'
+MKDIR_P='$MKDIR_P'
+AWK='$AWK'
+test -n "\$AWK" || AWK=awk
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# The default lists apply if the user does not specify any file.
+ac_need_defaults=:
+while test $# != 0
+do
+  case $1 in
+  --*=?*)
+    ac_option=`expr "X$1" : 'X\([^=]*\)='`
+    ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'`
+    ac_shift=:
+    ;;
+  --*=)
+    ac_option=`expr "X$1" : 'X\([^=]*\)='`
+    ac_optarg=
+    ac_shift=:
+    ;;
+  *)
+    ac_option=$1
+    ac_optarg=$2
+    ac_shift=shift
+    ;;
+  esac
+
+  case $ac_option in
+  # Handling of the options.
+  -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r)
+    ac_cs_recheck=: ;;
+  --version | --versio | --versi | --vers | --ver | --ve | --v | -V )
+    $as_echo "$ac_cs_version"; exit ;;
+  --config | --confi | --conf | --con | --co | --c )
+    $as_echo "$ac_cs_config"; exit ;;
+  --debug | --debu | --deb | --de | --d | -d )
+    debug=: ;;
+  --file | --fil | --fi | --f )
+    $ac_shift
+    case $ac_optarg in
+    *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;;
+    '') as_fn_error $? "missing file argument" ;;
+    esac
+    as_fn_append CONFIG_FILES " '$ac_optarg'"
+    ac_need_defaults=false;;
+  --header | --heade | --head | --hea )
+    $ac_shift
+    case $ac_optarg in
+    *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;;
+    esac
+    as_fn_append CONFIG_HEADERS " '$ac_optarg'"
+    ac_need_defaults=false;;
+  --he | --h)
+    # Conflict between --help and --header
+    as_fn_error $? "ambiguous option: \`$1'
+Try \`$0 --help' for more information.";;
+  --help | --hel | -h )
+    $as_echo "$ac_cs_usage"; exit ;;
+  -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+  | -silent | --silent | --silen | --sile | --sil | --si | --s)
+    ac_cs_silent=: ;;
+
+  # This is an error.
+  -*) as_fn_error $? "unrecognized option: \`$1'
+Try \`$0 --help' for more information." ;;
+
+  *) as_fn_append ac_config_targets " $1"
+     ac_need_defaults=false ;;
+
+  esac
+  shift
+done
+
+ac_configure_extra_args=
+
+if $ac_cs_silent; then
+  exec 6>/dev/null
+  ac_configure_extra_args="$ac_configure_extra_args --silent"
+fi
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+if \$ac_cs_recheck; then
+  set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion
+  shift
+  \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6
+  CONFIG_SHELL='$SHELL'
+  export CONFIG_SHELL
+  exec "\$@"
+fi
+
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+exec 5>>config.log
+{
+  echo
+  sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX
+## Running $as_me. ##
+_ASBOX
+  $as_echo "$ac_log"
+} >&5
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+#
+# INIT-COMMANDS
+#
+AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"
+
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+
+# Handling of arguments.
+for ac_config_target in $ac_config_targets
+do
+  case $ac_config_target in
+    "config.h") CONFIG_HEADERS="$CONFIG_HEADERS config.h" ;;
+    "depfiles") CONFIG_COMMANDS="$CONFIG_COMMANDS depfiles" ;;
+    "Makefile") CONFIG_FILES="$CONFIG_FILES Makefile" ;;
+
+  *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;;
+  esac
+done
+
+
+# If the user did not use the arguments to specify the items to instantiate,
+# then the envvar interface is used.  Set only those that are not.
+# We use the long form for the default assignment because of an extremely
+# bizarre bug on SunOS 4.1.3.
+if $ac_need_defaults; then
+  test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files
+  test "${CONFIG_HEADERS+set}" = set || CONFIG_HEADERS=$config_headers
+  test "${CONFIG_COMMANDS+set}" = set || CONFIG_COMMANDS=$config_commands
+fi
+
+# Have a temporary directory for convenience.  Make it in the build tree
+# simply because there is no reason against having it here, and in addition,
+# creating and moving files from /tmp can sometimes cause problems.
+# Hook for its removal unless debugging.
+# Note that there is a small window in which the directory will not be cleaned:
+# after its creation but before its name has been assigned to `$tmp'.
+$debug ||
+{
+  tmp= ac_tmp=
+  trap 'exit_status=$?
+  : "${ac_tmp:=$tmp}"
+  { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status
+' 0
+  trap 'as_fn_exit 1' 1 2 13 15
+}
+# Create a (secure) tmp directory for tmp files.
+
+{
+  tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` &&
+  test -d "$tmp"
+}  ||
+{
+  tmp=./conf$$-$RANDOM
+  (umask 077 && mkdir "$tmp")
+} || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5
+ac_tmp=$tmp
+
+# Set up the scripts for CONFIG_FILES section.
+# No need to generate them if there are no CONFIG_FILES.
+# This happens for instance with `./config.status config.h'.
+if test -n "$CONFIG_FILES"; then
+
+
+ac_cr=`echo X | tr X '\015'`
+# On cygwin, bash can eat \r inside `` if the user requested igncr.
+# But we know of no other shell where ac_cr would be empty at this
+# point, so we can use a bashism as a fallback.
+if test "x$ac_cr" = x; then
+  eval ac_cr=\$\'\\r\'
+fi
+ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' </dev/null 2>/dev/null`
+if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then
+  ac_cs_awk_cr='\\r'
+else
+  ac_cs_awk_cr=$ac_cr
+fi
+
+echo 'BEGIN {' >"$ac_tmp/subs1.awk" &&
+_ACEOF
+
+
+{
+  echo "cat >conf$$subs.awk <<_ACEOF" &&
+  echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' &&
+  echo "_ACEOF"
+} >conf$$subs.sh ||
+  as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'`
+ac_delim='%!_!# '
+for ac_last_try in false false false false false :; do
+  . ./conf$$subs.sh ||
+    as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+
+  ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X`
+  if test $ac_delim_n = $ac_delim_num; then
+    break
+  elif $ac_last_try; then
+    as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+  else
+    ac_delim="$ac_delim!$ac_delim _$ac_delim!! "
+  fi
+done
+rm -f conf$$subs.sh
+
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK &&
+_ACEOF
+sed -n '
+h
+s/^/S["/; s/!.*/"]=/
+p
+g
+s/^[^!]*!//
+:repl
+t repl
+s/'"$ac_delim"'$//
+t delim
+:nl
+h
+s/\(.\{148\}\)..*/\1/
+t more1
+s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/
+p
+n
+b repl
+:more1
+s/["\\]/\\&/g; s/^/"/; s/$/"\\/
+p
+g
+s/.\{148\}//
+t nl
+:delim
+h
+s/\(.\{148\}\)..*/\1/
+t more2
+s/["\\]/\\&/g; s/^/"/; s/$/"/
+p
+b
+:more2
+s/["\\]/\\&/g; s/^/"/; s/$/"\\/
+p
+g
+s/.\{148\}//
+t delim
+' <conf$$subs.awk | sed '
+/^[^""]/{
+  N
+  s/\n//
+}
+' >>$CONFIG_STATUS || ac_write_fail=1
+rm -f conf$$subs.awk
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+_ACAWK
+cat >>"\$ac_tmp/subs1.awk" <<_ACAWK &&
+  for (key in S) S_is_set[key] = 1
+  FS = "\a"
+
+}
+{
+  line = $ 0
+  nfields = split(line, field, "@")
+  substed = 0
+  len = length(field[1])
+  for (i = 2; i < nfields; i++) {
+    key = field[i]
+    keylen = length(key)
+    if (S_is_set[key]) {
+      value = S[key]
+      line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3)
+      len += length(value) + length(field[++i])
+      substed = 1
+    } else
+      len += 1 + keylen
+  }
+
+  print line
+}
+
+_ACAWK
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then
+  sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g"
+else
+  cat
+fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \
+  || as_fn_error $? "could not setup config files machinery" "$LINENO" 5
+_ACEOF
+
+# VPATH may cause trouble with some makes, so we remove sole $(srcdir),
+# ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and
+# trailing colons and then remove the whole line if VPATH becomes empty
+# (actually we leave an empty line to preserve line numbers).
+if test "x$srcdir" = x.; then
+  ac_vpsub='/^[         ]*VPATH[        ]*=[    ]*/{
+h
+s///
+s/^/:/
+s/[     ]*$/:/
+s/:\$(srcdir):/:/g
+s/:\${srcdir}:/:/g
+s/:@srcdir@:/:/g
+s/^:*//
+s/:*$//
+x
+s/\(=[  ]*\).*/\1/
+G
+s/\n//
+s/^[^=]*=[      ]*$//
+}'
+fi
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+fi # test -n "$CONFIG_FILES"
+
+# Set up the scripts for CONFIG_HEADERS section.
+# No need to generate them if there are no CONFIG_HEADERS.
+# This happens for instance with `./config.status Makefile'.
+if test -n "$CONFIG_HEADERS"; then
+cat >"$ac_tmp/defines.awk" <<\_ACAWK ||
+BEGIN {
+_ACEOF
+
+# Transform confdefs.h into an awk script `defines.awk', embedded as
+# here-document in config.status, that substitutes the proper values into
+# config.h.in to produce config.h.
+
+# Create a delimiter string that does not exist in confdefs.h, to ease
+# handling of long lines.
+ac_delim='%!_!# '
+for ac_last_try in false false :; do
+  ac_tt=`sed -n "/$ac_delim/p" confdefs.h`
+  if test -z "$ac_tt"; then
+    break
+  elif $ac_last_try; then
+    as_fn_error $? "could not make $CONFIG_HEADERS" "$LINENO" 5
+  else
+    ac_delim="$ac_delim!$ac_delim _$ac_delim!! "
+  fi
+done
+
+# For the awk script, D is an array of macro values keyed by name,
+# likewise P contains macro parameters if any.  Preserve backslash
+# newline sequences.
+
+ac_word_re=[_$as_cr_Letters][_$as_cr_alnum]*
+sed -n '
+s/.\{148\}/&'"$ac_delim"'/g
+t rset
+:rset
+s/^[    ]*#[    ]*define[       ][      ]*/ /
+t def
+d
+:def
+s/\\$//
+t bsnl
+s/["\\]/\\&/g
+s/^ \('"$ac_word_re"'\)\(([^()]*)\)[    ]*\(.*\)/P["\1"]="\2"\
+D["\1"]=" \3"/p
+s/^ \('"$ac_word_re"'\)[        ]*\(.*\)/D["\1"]=" \2"/p
+d
+:bsnl
+s/["\\]/\\&/g
+s/^ \('"$ac_word_re"'\)\(([^()]*)\)[    ]*\(.*\)/P["\1"]="\2"\
+D["\1"]=" \3\\\\\\n"\\/p
+t cont
+s/^ \('"$ac_word_re"'\)[        ]*\(.*\)/D["\1"]=" \2\\\\\\n"\\/p
+t cont
+d
+:cont
+n
+s/.\{148\}/&'"$ac_delim"'/g
+t clear
+:clear
+s/\\$//
+t bsnlc
+s/["\\]/\\&/g; s/^/"/; s/$/"/p
+d
+:bsnlc
+s/["\\]/\\&/g; s/^/"/; s/$/\\\\\\n"\\/p
+b cont
+' <confdefs.h | sed '
+s/'"$ac_delim"'/"\\\
+"/g' >>$CONFIG_STATUS || ac_write_fail=1
+
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+  for (key in D) D_is_set[key] = 1
+  FS = "\a"
+}
+/^[\t ]*#[\t ]*(define|undef)[\t ]+$ac_word_re([\t (]|\$)/ {
+  line = \$ 0
+  split(line, arg, " ")
+  if (arg[1] == "#") {
+    defundef = arg[2]
+    mac1 = arg[3]
+  } else {
+    defundef = substr(arg[1], 2)
+    mac1 = arg[2]
+  }
+  split(mac1, mac2, "(") #)
+  macro = mac2[1]
+  prefix = substr(line, 1, index(line, defundef) - 1)
+  if (D_is_set[macro]) {
+    # Preserve the white space surrounding the "#".
+    print prefix "define", macro P[macro] D[macro]
+    next
+  } else {
+    # Replace #undef with comments.  This is necessary, for example,
+    # in the case of _POSIX_SOURCE, which is predefined and required
+    # on some systems where configure will not decide to define it.
+    if (defundef == "undef") {
+      print "/*", prefix defundef, macro, "*/"
+      next
+    }
+  }
+}
+{ print }
+_ACAWK
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+  as_fn_error $? "could not setup config headers machinery" "$LINENO" 5
+fi # test -n "$CONFIG_HEADERS"
+
+
+eval set X "  :F $CONFIG_FILES  :H $CONFIG_HEADERS    :C $CONFIG_COMMANDS"
+shift
+for ac_tag
+do
+  case $ac_tag in
+  :[FHLC]) ac_mode=$ac_tag; continue;;
+  esac
+  case $ac_mode$ac_tag in
+  :[FHL]*:*);;
+  :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;;
+  :[FH]-) ac_tag=-:-;;
+  :[FH]*) ac_tag=$ac_tag:$ac_tag.in;;
+  esac
+  ac_save_IFS=$IFS
+  IFS=:
+  set x $ac_tag
+  IFS=$ac_save_IFS
+  shift
+  ac_file=$1
+  shift
+
+  case $ac_mode in
+  :L) ac_source=$1;;
+  :[FH])
+    ac_file_inputs=
+    for ac_f
+    do
+      case $ac_f in
+      -) ac_f="$ac_tmp/stdin";;
+      *) # Look for the file first in the build tree, then in the source tree
+        # (if the path is not absolute).  The absolute path cannot be DOS-style,
+        # because $ac_f cannot contain `:'.
+        test -f "$ac_f" ||
+          case $ac_f in
+          [\\/$]*) false;;
+          *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";;
+          esac ||
+          as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;;
+      esac
+      case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac
+      as_fn_append ac_file_inputs " '$ac_f'"
+    done
+
+    # Let's still pretend it is `configure' which instantiates (i.e., don't
+    # use $as_me), people would be surprised to read:
+    #    /* config.h.  Generated by config.status.  */
+    configure_input='Generated from '`
+         $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g'
+       `' by configure.'
+    if test x"$ac_file" != x-; then
+      configure_input="$ac_file.  $configure_input"
+      { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5
+$as_echo "$as_me: creating $ac_file" >&6;}
+    fi
+    # Neutralize special characters interpreted by sed in replacement strings.
+    case $configure_input in #(
+    *\&* | *\|* | *\\* )
+       ac_sed_conf_input=`$as_echo "$configure_input" |
+       sed 's/[\\\\&|]/\\\\&/g'`;; #(
+    *) ac_sed_conf_input=$configure_input;;
+    esac
+
+    case $ac_tag in
+    *:-:* | *:-) cat >"$ac_tmp/stdin" \
+      || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;;
+    esac
+    ;;
+  esac
+
+  ac_dir=`$as_dirname -- "$ac_file" ||
+$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$ac_file" : 'X\(//\)[^/]' \| \
+        X"$ac_file" : 'X\(//\)$' \| \
+        X"$ac_file" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$ac_file" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+  as_dir="$ac_dir"; as_fn_mkdir_p
+  ac_builddir=.
+
+case "$ac_dir" in
+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;
+*)
+  ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`
+  # A ".." for each directory in $ac_dir_suffix.
+  ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`
+  case $ac_top_builddir_sub in
+  "") ac_top_builddir_sub=. ac_top_build_prefix= ;;
+  *)  ac_top_build_prefix=$ac_top_builddir_sub/ ;;
+  esac ;;
+esac
+ac_abs_top_builddir=$ac_pwd
+ac_abs_builddir=$ac_pwd$ac_dir_suffix
+# for backward compatibility:
+ac_top_builddir=$ac_top_build_prefix
+
+case $srcdir in
+  .)  # We are building in place.
+    ac_srcdir=.
+    ac_top_srcdir=$ac_top_builddir_sub
+    ac_abs_top_srcdir=$ac_pwd ;;
+  [\\/]* | ?:[\\/]* )  # Absolute name.
+    ac_srcdir=$srcdir$ac_dir_suffix;
+    ac_top_srcdir=$srcdir
+    ac_abs_top_srcdir=$srcdir ;;
+  *) # Relative name.
+    ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix
+    ac_top_srcdir=$ac_top_build_prefix$srcdir
+    ac_abs_top_srcdir=$ac_pwd/$srcdir ;;
+esac
+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix
+
+
+  case $ac_mode in
+  :F)
+  #
+  # CONFIG_FILE
+  #
+
+  case $INSTALL in
+  [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;;
+  *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;;
+  esac
+  ac_MKDIR_P=$MKDIR_P
+  case $MKDIR_P in
+  [\\/$]* | ?:[\\/]* ) ;;
+  */*) ac_MKDIR_P=$ac_top_build_prefix$MKDIR_P ;;
+  esac
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# If the template does not know about datarootdir, expand it.
+# FIXME: This hack should be removed a few years after 2.60.
+ac_datarootdir_hack=; ac_datarootdir_seen=
+ac_sed_dataroot='
+/datarootdir/ {
+  p
+  q
+}
+/@datadir@/p
+/@docdir@/p
+/@infodir@/p
+/@localedir@/p
+/@mandir@/p'
+case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in
+*datarootdir*) ac_datarootdir_seen=yes;;
+*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*)
+  { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5
+$as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;}
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+  ac_datarootdir_hack='
+  s&@datadir@&$datadir&g
+  s&@docdir@&$docdir&g
+  s&@infodir@&$infodir&g
+  s&@localedir@&$localedir&g
+  s&@mandir@&$mandir&g
+  s&\\\${datarootdir}&$datarootdir&g' ;;
+esac
+_ACEOF
+
+# Neutralize VPATH when `$srcdir' = `.'.
+# Shell code in configure.ac might set extrasub.
+# FIXME: do we really want to maintain this feature?
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+ac_sed_extra="$ac_vpsub
+$extrasub
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+:t
+/@[a-zA-Z_][a-zA-Z_0-9]*@/!b
+s|@configure_input@|$ac_sed_conf_input|;t t
+s&@top_builddir@&$ac_top_builddir_sub&;t t
+s&@top_build_prefix@&$ac_top_build_prefix&;t t
+s&@srcdir@&$ac_srcdir&;t t
+s&@abs_srcdir@&$ac_abs_srcdir&;t t
+s&@top_srcdir@&$ac_top_srcdir&;t t
+s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t
+s&@builddir@&$ac_builddir&;t t
+s&@abs_builddir@&$ac_abs_builddir&;t t
+s&@abs_top_builddir@&$ac_abs_top_builddir&;t t
+s&@INSTALL@&$ac_INSTALL&;t t
+s&@MKDIR_P@&$ac_MKDIR_P&;t t
+$ac_datarootdir_hack
+"
+eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \
+  >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+
+test -z "$ac_datarootdir_hack$ac_datarootdir_seen" &&
+  { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } &&
+  { ac_out=`sed -n '/^[         ]*datarootdir[  ]*:*=/p' \
+      "$ac_tmp/out"`; test -z "$ac_out"; } &&
+  { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir'
+which seems to be undefined.  Please make sure it is defined" >&5
+$as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir'
+which seems to be undefined.  Please make sure it is defined" >&2;}
+
+  rm -f "$ac_tmp/stdin"
+  case $ac_file in
+  -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";;
+  *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";;
+  esac \
+  || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+ ;;
+  :H)
+  #
+  # CONFIG_HEADER
+  #
+  if test x"$ac_file" != x-; then
+    {
+      $as_echo "/* $configure_input  */" \
+      && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs"
+    } >"$ac_tmp/config.h" \
+      || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+    if diff "$ac_file" "$ac_tmp/config.h" >/dev/null 2>&1; then
+      { $as_echo "$as_me:${as_lineno-$LINENO}: $ac_file is unchanged" >&5
+$as_echo "$as_me: $ac_file is unchanged" >&6;}
+    else
+      rm -f "$ac_file"
+      mv "$ac_tmp/config.h" "$ac_file" \
+       || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+    fi
+  else
+    $as_echo "/* $configure_input  */" \
+      && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" \
+      || as_fn_error $? "could not create -" "$LINENO" 5
+  fi
+# Compute "$ac_file"'s index in $config_headers.
+_am_arg="$ac_file"
+_am_stamp_count=1
+for _am_header in $config_headers :; do
+  case $_am_header in
+    $_am_arg | $_am_arg:* )
+      break ;;
+    * )
+      _am_stamp_count=`expr $_am_stamp_count + 1` ;;
+  esac
+done
+echo "timestamp for $_am_arg" >`$as_dirname -- "$_am_arg" ||
+$as_expr X"$_am_arg" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$_am_arg" : 'X\(//\)[^/]' \| \
+        X"$_am_arg" : 'X\(//\)$' \| \
+        X"$_am_arg" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$_am_arg" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`/stamp-h$_am_stamp_count
+ ;;
+
+  :C)  { $as_echo "$as_me:${as_lineno-$LINENO}: executing $ac_file commands" >&5
+$as_echo "$as_me: executing $ac_file commands" >&6;}
+ ;;
+  esac
+
+
+  case $ac_file$ac_mode in
+    "depfiles":C) test x"$AMDEP_TRUE" != x"" || {
+  # Older Autoconf quotes --file arguments for eval, but not when files
+  # are listed without --file.  Let's play safe and only enable the eval
+  # if we detect the quoting.
+  case $CONFIG_FILES in
+  *\'*) eval set x "$CONFIG_FILES" ;;
+  *)   set x $CONFIG_FILES ;;
+  esac
+  shift
+  for mf
+  do
+    # Strip MF so we end up with the name of the file.
+    mf=`echo "$mf" | sed -e 's/:.*$//'`
+    # Check whether this is an Automake generated Makefile or not.
+    # We used to match only the files named 'Makefile.in', but
+    # some people rename them; so instead we look at the file content.
+    # Grep'ing the first line is not enough: some people post-process
+    # each Makefile.in and add a new line on top of each file to say so.
+    # Grep'ing the whole file is not good either: AIX grep has a line
+    # limit of 2048, but all sed's we know have understand at least 4000.
+    if sed -n 's,^#.*generated by automake.*,X,p' "$mf" | grep X >/dev/null 2>&1; then
+      dirpart=`$as_dirname -- "$mf" ||
+$as_expr X"$mf" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$mf" : 'X\(//\)[^/]' \| \
+        X"$mf" : 'X\(//\)$' \| \
+        X"$mf" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$mf" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+    else
+      continue
+    fi
+    # Extract the definition of DEPDIR, am__include, and am__quote
+    # from the Makefile without running 'make'.
+    DEPDIR=`sed -n 's/^DEPDIR = //p' < "$mf"`
+    test -z "$DEPDIR" && continue
+    am__include=`sed -n 's/^am__include = //p' < "$mf"`
+    test -z "$am__include" && continue
+    am__quote=`sed -n 's/^am__quote = //p' < "$mf"`
+    # Find all dependency output files, they are included files with
+    # $(DEPDIR) in their names.  We invoke sed twice because it is the
+    # simplest approach to changing $(DEPDIR) to its actual value in the
+    # expansion.
+    for file in `sed -n "
+      s/^$am__include $am__quote\(.*(DEPDIR).*\)$am__quote"'$/\1/p' <"$mf" | \
+        sed -e 's/\$(DEPDIR)/'"$DEPDIR"'/g'`; do
+      # Make sure the directory exists.
+      test -f "$dirpart/$file" && continue
+      fdir=`$as_dirname -- "$file" ||
+$as_expr X"$file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+        X"$file" : 'X\(//\)[^/]' \| \
+        X"$file" : 'X\(//\)$' \| \
+        X"$file" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$file" |
+    sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)[^/].*/{
+           s//\1/
+           q
+         }
+         /^X\(\/\/\)$/{
+           s//\1/
+           q
+         }
+         /^X\(\/\).*/{
+           s//\1/
+           q
+         }
+         s/.*/./; q'`
+      as_dir=$dirpart/$fdir; as_fn_mkdir_p
+      # echo "creating $dirpart/$file"
+      echo '# dummy' > "$dirpart/$file"
+    done
+  done
+}
+ ;;
+
+  esac
+done # for ac_tag
+
+
+as_fn_exit 0
+_ACEOF
+ac_clean_files=$ac_clean_files_save
+
+test $ac_write_fail = 0 ||
+  as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5
+
+
+# configure is writing to config.log, and then calls config.status.
+# config.status does its own redirection, appending to config.log.
+# Unfortunately, on DOS this fails, as config.log is still kept open
+# by configure, so config.status won't be able to write to it; its
+# output is simply discarded.  So we exec the FD to /dev/null,
+# effectively closing config.log, so it can be properly (re)opened and
+# appended to by config.status.  When coming back to configure, we
+# need to make the FD available again.
+if test "$no_create" != yes; then
+  ac_cs_success=:
+  ac_config_status_args=
+  test "$silent" = yes &&
+    ac_config_status_args="$ac_config_status_args --quiet"
+  exec 5>/dev/null
+  $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false
+  exec 5>>config.log
+  # Use ||, not &&, to avoid exiting from the if with $? = 1, which
+  # would make configure fail if this is the last instruction.
+  $ac_cs_success || as_fn_exit 1
+fi
+if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5
+$as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;}
+fi
+
diff --git a/configure.ac b/configure.ac
new file mode 100644 (file)
index 0000000..acc75dc
--- /dev/null
@@ -0,0 +1,247 @@
+dnl Our package name, version, ...
+AC_INIT([rc], [1.7.4])
+
+dnl ... and release date
+RELDATE=`date -I`
+AC_DEFINE_UNQUOTED(RELDATE, "$RELDATE", [Release date])
+
+dnl Get things going...
+AC_CONFIG_SRCDIR([rc.h])
+AM_INIT_AUTOMAKE
+
+AC_CONFIG_HEADERS(config.h)
+
+dnl Find a standard C compiler
+AC_PROG_CC
+
+dnl If we're using gcc, specify `-Wall'.  I've also checked the code
+dnl with `-pedantic -W -Wall -Wpointer-arith -Wstrict-prototypes
+dnl -Wmissing-prototypes', and checked that all the warnings generated
+dnl are harmless.
+case "$GCC" in
+yes) CFLAGS="-Wall $CFLAGS" ;;
+esac
+
+AC_SYS_LARGEFILE
+
+AC_PROG_CPP
+AC_CHECK_PROGS(LN, ln cp)
+
+AC_CHECK_HEADERS(sys/resource.h sys/time.h sys/types.h unistd.h)
+AC_HEADER_DIRENT
+AC_HEADER_STDC
+AC_HEADER_SYS_WAIT
+
+AC_TYPE_GETGROUPS
+AC_TYPE_PID_T
+AC_TYPE_SIZE_T
+AC_TYPE_UID_T
+AC_CHECK_TYPE(ssize_t, long)
+
+AC_CHECK_FUNCS(getgroups lstat setpgrp setrlimit sigaction)
+
+dnl We prefer system calls that don't restart.  If we have sigaction()
+dnl we'll use it.  Otherwise, we check whether good ol' signal()
+dnl produces interruptible system calls.
+case "$ac_cv_func_sigaction" in
+no) AC_SYS_RESTARTABLE_SYSCALLS ;;
+esac
+AM_CONDITIONAL(AMC_RESTART, test "$ac_cv_sys_restartable_syscalls" = yes)
+
+RC_FUNC_GETGROUPS
+
+RC_FUNC_SIGSETJMP
+
+AC_FUNC_SETPGRP
+
+RC_FUNC_STRERROR
+
+RC_NEED_KERNEL
+
+RC_TYPE_RLIM_T
+
+RC_TYPE_SIG_ATOMIC_T
+
+RC_SYS_V_SIGCLD
+
+dnl Does the kernel handle `#! /interpreter'?
+AC_SYS_INTERPRETER
+case "$ac_cv_sys_interpreter" in
+yes)  AC_DEFINE(HASH_BANG, 1, [Define to 1 if your kernel understands `#!' magic numbers]) ;;
+esac
+AM_CONDITIONAL(AMC_NO_HASHBANG, test "$ac_cv_sys_interpreter" = no)
+
+
+dnl What do we do for command arguments?  We want /dev/fd or Linux's
+dnl /proc/self/fd.  Failing that, we'll try for POSIX mkfifo(), or a
+dnl mknod() that makes FIFOs.
+RC_SYS_DEV_FD
+case "$rc_cv_sys_dev_fd" in
+yes)   AC_DEFINE(HAVE_DEV_FD, 1, [Define to 1 if you have /dev/fd.]) ;;
+odd)   AC_DEFINE(HAVE_PROC_SELF_FD, 1, [Define to 1 if you have /proc/self/fd.]) ;;
+no)    AC_CHECK_FUNCS(mkfifo) ;;
+esac
+
+case "$ac_cv_func_mkfifo" in
+yes)   AC_DEFINE(HAVE_FIFO, 1, [Define to 1 if you have the `mkfifo' function.]) ;;
+no)    RC_SYS_MKNOD_FIFO ;;
+esac
+
+dnl Now handle arguments.
+AC_ARG_ENABLE(builtin-echo, [  --disable-builtin-echo  Don't include `echo' as a builtin],
+       test "x$enableval" != "xno" && AC_DEFINE(RC_ECHO, 1, [Define to 1 to include `echo' as a builtin.]),
+       AC_DEFINE(RC_ECHO))
+
+AC_ARG_ENABLE(job, [  --disable-job           Don't do job-control-style backgrounding],
+       test "x$enableval" != "xno" && AC_DEFINE(RC_JOB, 1, [Define to 1 to use job-control-style backgrounding.]),
+       AC_DEFINE(RC_JOB))
+
+AC_ARG_ENABLE(protect-env, [  --disable-protect-env   Don't protect environment names],
+       test "x$enableval" != "xno" && AC_DEFINE(PROTECT_ENV, 1, [Define to 1 to encode exported environment names.]),
+       AC_DEFINE(PROTECT_ENV))
+
+AC_ARG_ENABLE(def-interp,
+[  --enable-def-interp=/bin/foo
+                          Use /bin/foo as default interpreter [[/bin/sh]]],
+[
+       case "$enableval" in
+       no)
+               ;;
+       yes)
+               AC_DEFINE(DEFAULTINTERP, "/bin/sh", [The default interpreter])
+               ;;
+       *)
+               AC_DEFINE_UNQUOTED(DEFAULTINTERP, "$enableval")
+       esac
+],
+       AC_DEFINE(DEFAULTINTERP, "/bin/sh"))
+
+AC_ARG_ENABLE(def-path,
+[  --enable-def-path=\"/usr/local/bin/\",\"/usr/bin\"
+                          Default path [[All of these that exist
+                          (/usr/local/bin /usr/bin /usr/bsd /usr/ucb /bin .)]]],
+[
+       case "$enableval" in
+       no|yes) ;;
+       *)      AC_DEFINE_UNQUOTED(DEFAULTPATH, $enableval, [The default path]) ;;
+       esac
+],
+       enable_def_path=yes)
+
+case "$enable_def_path" in
+yes)   AC_CACHE_CHECK(extant directories for default path, rc_cv_def_path,[
+               rc_cv_def_path=''
+               for i in /usr/local/bin /usr/bin /usr/bsd /usr/ucb /bin .; do
+                       if test -d $i; then
+                               case "$rc_cv_def_path" in
+                               '')     rc_cv_def_path=\"$i\" ;;
+                               *)      rc_cv_def_path=$rc_cv_def_path,\"$i\" ;;
+                               esac
+                       fi
+               done
+       ])
+       AC_DEFINE_UNQUOTED(DEFAULTPATH, $rc_cv_def_path)
+       ;;
+esac
+
+AC_ARG_WITH(history,
+       [  --with-history          Build history subprograms],[
+       case "$withval" in
+        yes) rc_history=yes ;;
+        *) rc_history=no ;;
+        esac
+       ], rc_history=no)
+AM_CONDITIONAL(AMC_HISTORY, test "$rc_history" = yes)
+
+
+AC_ARG_WITH(addon, [  --with-addon[[=foo.c]]    Extra builtins, from addon.c by default ],[
+       case "$withval" in
+       yes)    ADDON=addon.o ;;
+       no)     ADDON='' ;;
+       *)      ADDON=`echo $withval |sed 's/\.c$/\.o/'` ;;
+       esac
+])
+AM_CONDITIONAL(AMC_ADDON, test "$ADDON" != "")
+case "$ADDON" in
+?*) AC_DEFINE(RC_ADDON, 1, [Define to 1 to use addon functions.]) ;;
+esac
+AC_SUBST(ADDON)
+
+
+EDIT=edit-null.o
+AC_ARG_WITH(edit, [  --with-edit=(edit,editline,readline,vrl)  Command line editing library], [
+       case $withval in
+       yes)
+               AC_MSG_ERROR(must specify which library)
+               # might consider searching
+               ;;
+       no|null)
+               ;;
+       edit|bsd)
+               EDIT=edit-edit.o
+               RC_LIB_TGETENT
+               AC_CHECK_LIB(edit, el_init, [
+                       LIBS="$LIBS -ledit $rc_lib_tgetent"
+               ], AC_MSG_ERROR(edit library not found), $rc_lib_tgetent)
+               ;;
+       editline)
+               EDIT=edit-editline.o
+               RC_LIB_TGETENT
+               AC_CHECK_LIB(editline, el_ring_bell, [
+                       LIBS="$LIBS -leditline $rc_lib_tgetent"
+               ], AC_MSG_ERROR(editline library not found), $rc_lib_tgetent)
+               ;;
+       readline|gnu)
+               EDIT=edit-readline.o
+               RC_LIB_TGETENT
+               AC_CHECK_LIB(readline, readline, [
+                       LIBS="$LIBS -lreadline $rc_lib_tgetent"
+               ], AC_MSG_ERROR(readline library not found), $rc_lib_tgetent)
+               AC_TRY_LINK([
+                       #include <stdio.h>
+                       #include <readline/readline.h>
+               ], [
+                       rl_catch_signals = 0;
+               ], [], AC_MSG_ERROR(readline >= 4.0 not found))
+               ;;
+       vrl)
+               EDIT=edit-vrl.o
+               RC_LIB_TGETENT
+               AC_CHECK_LIB(vrl, iline_peekch, [
+                       LIBS="$LIBS -lvrl $rc_lib_tgetent"
+               ], AC_MSG_ERROR(vrl library not found), $rc_lib_tgetent)
+               ;;
+       *)
+               AC_MSG_ERROR(unknown editing library $withval)
+               ;;
+       esac
+])
+AC_SUBST(EDIT)
+dnl    AC_CHECK_LIB(edit, readline,
+dnl            AC_DEFINE(EDITLINE, 1, [Define to 1 if you are using `editline' or `vrl'.]) LIBS="$LIBS -ledit",
+dnl            AC_MSG_ERROR(editline library not found)))
+
+dnl if test "${with_vrl+set}" = set -o "${with_readline+set}" = set; then
+dnl    RC_LIB_TGETENT
+dnl fi
+
+dnl AC_ARG_WITH(vrl, [  --with-vrl              Gert-Jan Vons's line editing],
+dnl    AC_CHECK_LIB(vrl, readline,
+dnl            AC_DEFINE(EDITLINE) LIBS="$LIBS -lvrl $rc_lib_tgetent",
+dnl            AC_MSG_ERROR(vrl library not found), $rc_lib_tgetent))
+
+dnl There are (at least) two incompatible versions of readline, and we
+dnl need to know which one we are using.  We don't support readline 2.0.
+dnl AC_ARG_WITH(readline, [  --with-readline         Bloated GNU line editing], [
+dnl    AC_CHECK_LIB(readline, readline, [
+dnl            AC_DEFINE(READLINE, 1, [Define to 1 if you are using GNU `readline'.])
+dnl            LIBS="$LIBS -lreadline $rc_lib_tgetent"
+dnl            AC_CHECK_LIB(readline, _rl_clean_up_for_exit, , AC_DEFINE(READLINE_OLD, 1, [Define to 1 for older versions GNU `readline'.]), $rc_lib_tgetent)
+dnl    ], AC_MSG_ERROR(readline library not found), $rc_lib_tgetent)
+dnl ])
+dnl AM_CONDITIONAL(AMC_READLINE, test "${with_readline+set}" = set)
+
+dnl For some reason CPPFLAGS doesn't get propagated.
+dnl AC_SUBST(CPPFLAGS)
+
+AC_OUTPUT(Makefile)
diff --git a/depcomp b/depcomp
new file mode 100755 (executable)
index 0000000..4ebd5b3
--- /dev/null
+++ b/depcomp
@@ -0,0 +1,791 @@
+#! /bin/sh
+# depcomp - compile a program generating dependencies as side-effects
+
+scriptversion=2013-05-30.07; # UTC
+
+# Copyright (C) 1999-2013 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, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Originally written by Alexandre Oliva <oliva@dcc.unicamp.br>.
+
+case $1 in
+  '')
+    echo "$0: No command.  Try '$0 --help' for more information." 1>&2
+    exit 1;
+    ;;
+  -h | --h*)
+    cat <<\EOF
+Usage: depcomp [--help] [--version] PROGRAM [ARGS]
+
+Run PROGRAMS ARGS to compile a file, generating dependencies
+as side-effects.
+
+Environment variables:
+  depmode     Dependency tracking mode.
+  source      Source file read by 'PROGRAMS ARGS'.
+  object      Object file output by 'PROGRAMS ARGS'.
+  DEPDIR      directory where to store dependencies.
+  depfile     Dependency file to output.
+  tmpdepfile  Temporary file to use when outputting dependencies.
+  libtool     Whether libtool is used (yes/no).
+
+Report bugs to <bug-automake@gnu.org>.
+EOF
+    exit $?
+    ;;
+  -v | --v*)
+    echo "depcomp $scriptversion"
+    exit $?
+    ;;
+esac
+
+# Get the directory component of the given path, and save it in the
+# global variables '$dir'.  Note that this directory component will
+# be either empty or ending with a '/' character.  This is deliberate.
+set_dir_from ()
+{
+  case $1 in
+    */*) dir=`echo "$1" | sed -e 's|/[^/]*$|/|'`;;
+      *) dir=;;
+  esac
+}
+
+# Get the suffix-stripped basename of the given path, and save it the
+# global variable '$base'.
+set_base_from ()
+{
+  base=`echo "$1" | sed -e 's|^.*/||' -e 's/\.[^.]*$//'`
+}
+
+# If no dependency file was actually created by the compiler invocation,
+# we still have to create a dummy depfile, to avoid errors with the
+# Makefile "include basename.Plo" scheme.
+make_dummy_depfile ()
+{
+  echo "#dummy" > "$depfile"
+}
+
+# Factor out some common post-processing of the generated depfile.
+# Requires the auxiliary global variable '$tmpdepfile' to be set.
+aix_post_process_depfile ()
+{
+  # If the compiler actually managed to produce a dependency file,
+  # post-process it.
+  if test -f "$tmpdepfile"; then
+    # Each line is of the form 'foo.o: dependency.h'.
+    # Do two passes, one to just change these to
+    #   $object: dependency.h
+    # and one to simply output
+    #   dependency.h:
+    # which is needed to avoid the deleted-header problem.
+    { sed -e "s,^.*\.[$lower]*:,$object:," < "$tmpdepfile"
+      sed -e "s,^.*\.[$lower]*:[$tab ]*,," -e 's,$,:,' < "$tmpdepfile"
+    } > "$depfile"
+    rm -f "$tmpdepfile"
+  else
+    make_dummy_depfile
+  fi
+}
+
+# A tabulation character.
+tab='  '
+# A newline character.
+nl='
+'
+# Character ranges might be problematic outside the C locale.
+# These definitions help.
+upper=ABCDEFGHIJKLMNOPQRSTUVWXYZ
+lower=abcdefghijklmnopqrstuvwxyz
+digits=0123456789
+alpha=${upper}${lower}
+
+if test -z "$depmode" || test -z "$source" || test -z "$object"; then
+  echo "depcomp: Variables source, object and depmode must be set" 1>&2
+  exit 1
+fi
+
+# Dependencies for sub/bar.o or sub/bar.obj go into sub/.deps/bar.Po.
+depfile=${depfile-`echo "$object" |
+  sed 's|[^\\/]*$|'${DEPDIR-.deps}'/&|;s|\.\([^.]*\)$|.P\1|;s|Pobj$|Po|'`}
+tmpdepfile=${tmpdepfile-`echo "$depfile" | sed 's/\.\([^.]*\)$/.T\1/'`}
+
+rm -f "$tmpdepfile"
+
+# Avoid interferences from the environment.
+gccflag= dashmflag=
+
+# Some modes work just like other modes, but use different flags.  We
+# parameterize here, but still list the modes in the big case below,
+# to make depend.m4 easier to write.  Note that we *cannot* use a case
+# here, because this file can only contain one case statement.
+if test "$depmode" = hp; then
+  # HP compiler uses -M and no extra arg.
+  gccflag=-M
+  depmode=gcc
+fi
+
+if test "$depmode" = dashXmstdout; then
+  # This is just like dashmstdout with a different argument.
+  dashmflag=-xM
+  depmode=dashmstdout
+fi
+
+cygpath_u="cygpath -u -f -"
+if test "$depmode" = msvcmsys; then
+  # This is just like msvisualcpp but w/o cygpath translation.
+  # Just convert the backslash-escaped backslashes to single forward
+  # slashes to satisfy depend.m4
+  cygpath_u='sed s,\\\\,/,g'
+  depmode=msvisualcpp
+fi
+
+if test "$depmode" = msvc7msys; then
+  # This is just like msvc7 but w/o cygpath translation.
+  # Just convert the backslash-escaped backslashes to single forward
+  # slashes to satisfy depend.m4
+  cygpath_u='sed s,\\\\,/,g'
+  depmode=msvc7
+fi
+
+if test "$depmode" = xlc; then
+  # IBM C/C++ Compilers xlc/xlC can output gcc-like dependency information.
+  gccflag=-qmakedep=gcc,-MF
+  depmode=gcc
+fi
+
+case "$depmode" in
+gcc3)
+## gcc 3 implements dependency tracking that does exactly what
+## we want.  Yay!  Note: for some reason libtool 1.4 doesn't like
+## it if -MD -MP comes after the -MF stuff.  Hmm.
+## Unfortunately, FreeBSD c89 acceptance of flags depends upon
+## the command line argument order; so add the flags where they
+## appear in depend2.am.  Note that the slowdown incurred here
+## affects only configure: in makefiles, %FASTDEP% shortcuts this.
+  for arg
+  do
+    case $arg in
+    -c) set fnord "$@" -MT "$object" -MD -MP -MF "$tmpdepfile" "$arg" ;;
+    *)  set fnord "$@" "$arg" ;;
+    esac
+    shift # fnord
+    shift # $arg
+  done
+  "$@"
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  mv "$tmpdepfile" "$depfile"
+  ;;
+
+gcc)
+## Note that this doesn't just cater to obsosete pre-3.x GCC compilers.
+## but also to in-use compilers like IMB xlc/xlC and the HP C compiler.
+## (see the conditional assignment to $gccflag above).
+## There are various ways to get dependency output from gcc.  Here's
+## why we pick this rather obscure method:
+## - Don't want to use -MD because we'd like the dependencies to end
+##   up in a subdir.  Having to rename by hand is ugly.
+##   (We might end up doing this anyway to support other compilers.)
+## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like
+##   -MM, not -M (despite what the docs say).  Also, it might not be
+##   supported by the other compilers which use the 'gcc' depmode.
+## - Using -M directly means running the compiler twice (even worse
+##   than renaming).
+  if test -z "$gccflag"; then
+    gccflag=-MD,
+  fi
+  "$@" -Wp,"$gccflag$tmpdepfile"
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  # The second -e expression handles DOS-style file names with drive
+  # letters.
+  sed -e 's/^[^:]*: / /' \
+      -e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile"
+## This next piece of magic avoids the "deleted header file" problem.
+## The problem is that when a header file which appears in a .P file
+## is deleted, the dependency causes make to die (because there is
+## typically no way to rebuild the header).  We avoid this by adding
+## dummy dependencies for each header file.  Too bad gcc doesn't do
+## this for us directly.
+## Some versions of gcc put a space before the ':'.  On the theory
+## that the space means something, we add a space to the output as
+## well.  hp depmode also adds that space, but also prefixes the VPATH
+## to the object.  Take care to not repeat it in the output.
+## Some versions of the HPUX 10.20 sed can't process this invocation
+## correctly.  Breaking it into two sed invocations is a workaround.
+  tr ' ' "$nl" < "$tmpdepfile" \
+    | sed -e 's/^\\$//' -e '/^$/d' -e "s|.*$object$||" -e '/:$/d' \
+    | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+hp)
+  # This case exists only to let depend.m4 do its work.  It works by
+  # looking at the text of this script.  This case will never be run,
+  # since it is checked for above.
+  exit 1
+  ;;
+
+sgi)
+  if test "$libtool" = yes; then
+    "$@" "-Wp,-MDupdate,$tmpdepfile"
+  else
+    "$@" -MDupdate "$tmpdepfile"
+  fi
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+
+  if test -f "$tmpdepfile"; then  # yes, the sourcefile depend on other files
+    echo "$object : \\" > "$depfile"
+    # Clip off the initial element (the dependent).  Don't try to be
+    # clever and replace this with sed code, as IRIX sed won't handle
+    # lines with more than a fixed number of characters (4096 in
+    # IRIX 6.2 sed, 8192 in IRIX 6.5).  We also remove comment lines;
+    # the IRIX cc adds comments like '#:fec' to the end of the
+    # dependency line.
+    tr ' ' "$nl" < "$tmpdepfile" \
+      | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' \
+      | tr "$nl" ' ' >> "$depfile"
+    echo >> "$depfile"
+    # The second pass generates a dummy entry for each header file.
+    tr ' ' "$nl" < "$tmpdepfile" \
+      | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \
+      >> "$depfile"
+  else
+    make_dummy_depfile
+  fi
+  rm -f "$tmpdepfile"
+  ;;
+
+xlc)
+  # This case exists only to let depend.m4 do its work.  It works by
+  # looking at the text of this script.  This case will never be run,
+  # since it is checked for above.
+  exit 1
+  ;;
+
+aix)
+  # The C for AIX Compiler uses -M and outputs the dependencies
+  # in a .u file.  In older versions, this file always lives in the
+  # current directory.  Also, the AIX compiler puts '$object:' at the
+  # start of each line; $object doesn't have directory information.
+  # Version 6 uses the directory in both cases.
+  set_dir_from "$object"
+  set_base_from "$object"
+  if test "$libtool" = yes; then
+    tmpdepfile1=$dir$base.u
+    tmpdepfile2=$base.u
+    tmpdepfile3=$dir.libs/$base.u
+    "$@" -Wc,-M
+  else
+    tmpdepfile1=$dir$base.u
+    tmpdepfile2=$dir$base.u
+    tmpdepfile3=$dir$base.u
+    "$@" -M
+  fi
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+    exit $stat
+  fi
+
+  for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+  do
+    test -f "$tmpdepfile" && break
+  done
+  aix_post_process_depfile
+  ;;
+
+tcc)
+  # tcc (Tiny C Compiler) understand '-MD -MF file' since version 0.9.26
+  # FIXME: That version still under development at the moment of writing.
+  #        Make that this statement remains true also for stable, released
+  #        versions.
+  # It will wrap lines (doesn't matter whether long or short) with a
+  # trailing '\', as in:
+  #
+  #   foo.o : \
+  #    foo.c \
+  #    foo.h \
+  #
+  # It will put a trailing '\' even on the last line, and will use leading
+  # spaces rather than leading tabs (at least since its commit 0394caf7
+  # "Emit spaces for -MD").
+  "$@" -MD -MF "$tmpdepfile"
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  # Each non-empty line is of the form 'foo.o : \' or ' dep.h \'.
+  # We have to change lines of the first kind to '$object: \'.
+  sed -e "s|.*:|$object :|" < "$tmpdepfile" > "$depfile"
+  # And for each line of the second kind, we have to emit a 'dep.h:'
+  # dummy dependency, to avoid the deleted-header problem.
+  sed -n -e 's|^  *\(.*\) *\\$|\1:|p' < "$tmpdepfile" >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+## The order of this option in the case statement is important, since the
+## shell code in configure will try each of these formats in the order
+## listed in this file.  A plain '-MD' option would be understood by many
+## compilers, so we must ensure this comes after the gcc and icc options.
+pgcc)
+  # Portland's C compiler understands '-MD'.
+  # Will always output deps to 'file.d' where file is the root name of the
+  # source file under compilation, even if file resides in a subdirectory.
+  # The object file name does not affect the name of the '.d' file.
+  # pgcc 10.2 will output
+  #    foo.o: sub/foo.c sub/foo.h
+  # and will wrap long lines using '\' :
+  #    foo.o: sub/foo.c ... \
+  #     sub/foo.h ... \
+  #     ...
+  set_dir_from "$object"
+  # Use the source, not the object, to determine the base name, since
+  # that's sadly what pgcc will do too.
+  set_base_from "$source"
+  tmpdepfile=$base.d
+
+  # For projects that build the same source file twice into different object
+  # files, the pgcc approach of using the *source* file root name can cause
+  # problems in parallel builds.  Use a locking strategy to avoid stomping on
+  # the same $tmpdepfile.
+  lockdir=$base.d-lock
+  trap "
+    echo '$0: caught signal, cleaning up...' >&2
+    rmdir '$lockdir'
+    exit 1
+  " 1 2 13 15
+  numtries=100
+  i=$numtries
+  while test $i -gt 0; do
+    # mkdir is a portable test-and-set.
+    if mkdir "$lockdir" 2>/dev/null; then
+      # This process acquired the lock.
+      "$@" -MD
+      stat=$?
+      # Release the lock.
+      rmdir "$lockdir"
+      break
+    else
+      # If the lock is being held by a different process, wait
+      # until the winning process is done or we timeout.
+      while test -d "$lockdir" && test $i -gt 0; do
+        sleep 1
+        i=`expr $i - 1`
+      done
+    fi
+    i=`expr $i - 1`
+  done
+  trap - 1 2 13 15
+  if test $i -le 0; then
+    echo "$0: failed to acquire lock after $numtries attempts" >&2
+    echo "$0: check lockdir '$lockdir'" >&2
+    exit 1
+  fi
+
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  # Each line is of the form `foo.o: dependent.h',
+  # or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'.
+  # Do two passes, one to just change these to
+  # `$object: dependent.h' and one to simply `dependent.h:'.
+  sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile"
+  # Some versions of the HPUX 10.20 sed can't process this invocation
+  # correctly.  Breaking it into two sed invocations is a workaround.
+  sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" \
+    | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+hp2)
+  # The "hp" stanza above does not work with aCC (C++) and HP's ia64
+  # compilers, which have integrated preprocessors.  The correct option
+  # to use with these is +Maked; it writes dependencies to a file named
+  # 'foo.d', which lands next to the object file, wherever that
+  # happens to be.
+  # Much of this is similar to the tru64 case; see comments there.
+  set_dir_from  "$object"
+  set_base_from "$object"
+  if test "$libtool" = yes; then
+    tmpdepfile1=$dir$base.d
+    tmpdepfile2=$dir.libs/$base.d
+    "$@" -Wc,+Maked
+  else
+    tmpdepfile1=$dir$base.d
+    tmpdepfile2=$dir$base.d
+    "$@" +Maked
+  fi
+  stat=$?
+  if test $stat -ne 0; then
+     rm -f "$tmpdepfile1" "$tmpdepfile2"
+     exit $stat
+  fi
+
+  for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2"
+  do
+    test -f "$tmpdepfile" && break
+  done
+  if test -f "$tmpdepfile"; then
+    sed -e "s,^.*\.[$lower]*:,$object:," "$tmpdepfile" > "$depfile"
+    # Add 'dependent.h:' lines.
+    sed -ne '2,${
+               s/^ *//
+               s/ \\*$//
+               s/$/:/
+               p
+             }' "$tmpdepfile" >> "$depfile"
+  else
+    make_dummy_depfile
+  fi
+  rm -f "$tmpdepfile" "$tmpdepfile2"
+  ;;
+
+tru64)
+  # The Tru64 compiler uses -MD to generate dependencies as a side
+  # effect.  'cc -MD -o foo.o ...' puts the dependencies into 'foo.o.d'.
+  # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put
+  # dependencies in 'foo.d' instead, so we check for that too.
+  # Subdirectories are respected.
+  set_dir_from  "$object"
+  set_base_from "$object"
+
+  if test "$libtool" = yes; then
+    # Libtool generates 2 separate objects for the 2 libraries.  These
+    # two compilations output dependencies in $dir.libs/$base.o.d and
+    # in $dir$base.o.d.  We have to check for both files, because
+    # one of the two compilations can be disabled.  We should prefer
+    # $dir$base.o.d over $dir.libs/$base.o.d because the latter is
+    # automatically cleaned when .libs/ is deleted, while ignoring
+    # the former would cause a distcleancheck panic.
+    tmpdepfile1=$dir$base.o.d          # libtool 1.5
+    tmpdepfile2=$dir.libs/$base.o.d    # Likewise.
+    tmpdepfile3=$dir.libs/$base.d      # Compaq CCC V6.2-504
+    "$@" -Wc,-MD
+  else
+    tmpdepfile1=$dir$base.d
+    tmpdepfile2=$dir$base.d
+    tmpdepfile3=$dir$base.d
+    "$@" -MD
+  fi
+
+  stat=$?
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+    exit $stat
+  fi
+
+  for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+  do
+    test -f "$tmpdepfile" && break
+  done
+  # Same post-processing that is required for AIX mode.
+  aix_post_process_depfile
+  ;;
+
+msvc7)
+  if test "$libtool" = yes; then
+    showIncludes=-Wc,-showIncludes
+  else
+    showIncludes=-showIncludes
+  fi
+  "$@" $showIncludes > "$tmpdepfile"
+  stat=$?
+  grep -v '^Note: including file: ' "$tmpdepfile"
+  if test $stat -ne 0; then
+    rm -f "$tmpdepfile"
+    exit $stat
+  fi
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  # The first sed program below extracts the file names and escapes
+  # backslashes for cygpath.  The second sed program outputs the file
+  # name when reading, but also accumulates all include files in the
+  # hold buffer in order to output them again at the end.  This only
+  # works with sed implementations that can handle large buffers.
+  sed < "$tmpdepfile" -n '
+/^Note: including file:  *\(.*\)/ {
+  s//\1/
+  s/\\/\\\\/g
+  p
+}' | $cygpath_u | sort -u | sed -n '
+s/ /\\ /g
+s/\(.*\)/'"$tab"'\1 \\/p
+s/.\(.*\) \\/\1:/
+H
+$ {
+  s/.*/'"$tab"'/
+  G
+  p
+}' >> "$depfile"
+  echo >> "$depfile" # make sure the fragment doesn't end with a backslash
+  rm -f "$tmpdepfile"
+  ;;
+
+msvc7msys)
+  # This case exists only to let depend.m4 do its work.  It works by
+  # looking at the text of this script.  This case will never be run,
+  # since it is checked for above.
+  exit 1
+  ;;
+
+#nosideeffect)
+  # This comment above is used by automake to tell side-effect
+  # dependency tracking mechanisms from slower ones.
+
+dashmstdout)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the preprocessed file to stdout, regardless of -o.
+  "$@" || exit $?
+
+  # Remove the call to Libtool.
+  if test "$libtool" = yes; then
+    while test "X$1" != 'X--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+
+  # Remove '-o $object'.
+  IFS=" "
+  for arg
+  do
+    case $arg in
+    -o)
+      shift
+      ;;
+    $object)
+      shift
+      ;;
+    *)
+      set fnord "$@" "$arg"
+      shift # fnord
+      shift # $arg
+      ;;
+    esac
+  done
+
+  test -z "$dashmflag" && dashmflag=-M
+  # Require at least two characters before searching for ':'
+  # in the target name.  This is to cope with DOS-style filenames:
+  # a dependency such as 'c:/foo/bar' could be seen as target 'c' otherwise.
+  "$@" $dashmflag |
+    sed "s|^[$tab ]*[^:$tab ][^:][^:]*:[$tab ]*|$object: |" > "$tmpdepfile"
+  rm -f "$depfile"
+  cat < "$tmpdepfile" > "$depfile"
+  # Some versions of the HPUX 10.20 sed can't process this sed invocation
+  # correctly.  Breaking it into two sed invocations is a workaround.
+  tr ' ' "$nl" < "$tmpdepfile" \
+    | sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
+    | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+dashXmstdout)
+  # This case only exists to satisfy depend.m4.  It is never actually
+  # run, as this mode is specially recognized in the preamble.
+  exit 1
+  ;;
+
+makedepend)
+  "$@" || exit $?
+  # Remove any Libtool call
+  if test "$libtool" = yes; then
+    while test "X$1" != 'X--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+  # X makedepend
+  shift
+  cleared=no eat=no
+  for arg
+  do
+    case $cleared in
+    no)
+      set ""; shift
+      cleared=yes ;;
+    esac
+    if test $eat = yes; then
+      eat=no
+      continue
+    fi
+    case "$arg" in
+    -D*|-I*)
+      set fnord "$@" "$arg"; shift ;;
+    # Strip any option that makedepend may not understand.  Remove
+    # the object too, otherwise makedepend will parse it as a source file.
+    -arch)
+      eat=yes ;;
+    -*|$object)
+      ;;
+    *)
+      set fnord "$@" "$arg"; shift ;;
+    esac
+  done
+  obj_suffix=`echo "$object" | sed 's/^.*\././'`
+  touch "$tmpdepfile"
+  ${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@"
+  rm -f "$depfile"
+  # makedepend may prepend the VPATH from the source file name to the object.
+  # No need to regex-escape $object, excess matching of '.' is harmless.
+  sed "s|^.*\($object *:\)|\1|" "$tmpdepfile" > "$depfile"
+  # Some versions of the HPUX 10.20 sed can't process the last invocation
+  # correctly.  Breaking it into two sed invocations is a workaround.
+  sed '1,2d' "$tmpdepfile" \
+    | tr ' ' "$nl" \
+    | sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
+    | sed -e 's/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile" "$tmpdepfile".bak
+  ;;
+
+cpp)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the preprocessed file to stdout.
+  "$@" || exit $?
+
+  # Remove the call to Libtool.
+  if test "$libtool" = yes; then
+    while test "X$1" != 'X--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+
+  # Remove '-o $object'.
+  IFS=" "
+  for arg
+  do
+    case $arg in
+    -o)
+      shift
+      ;;
+    $object)
+      shift
+      ;;
+    *)
+      set fnord "$@" "$arg"
+      shift # fnord
+      shift # $arg
+      ;;
+    esac
+  done
+
+  "$@" -E \
+    | sed -n -e '/^# [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
+             -e '/^#line [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
+    | sed '$ s: \\$::' > "$tmpdepfile"
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  cat < "$tmpdepfile" >> "$depfile"
+  sed < "$tmpdepfile" '/^$/d;s/^ //;s/ \\$//;s/$/ :/' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+msvisualcpp)
+  # Important note: in order to support this mode, a compiler *must*
+  # always write the preprocessed file to stdout.
+  "$@" || exit $?
+
+  # Remove the call to Libtool.
+  if test "$libtool" = yes; then
+    while test "X$1" != 'X--mode=compile'; do
+      shift
+    done
+    shift
+  fi
+
+  IFS=" "
+  for arg
+  do
+    case "$arg" in
+    -o)
+      shift
+      ;;
+    $object)
+      shift
+      ;;
+    "-Gm"|"/Gm"|"-Gi"|"/Gi"|"-ZI"|"/ZI")
+        set fnord "$@"
+        shift
+        shift
+        ;;
+    *)
+        set fnord "$@" "$arg"
+        shift
+        shift
+        ;;
+    esac
+  done
+  "$@" -E 2>/dev/null |
+  sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::\1:p' | $cygpath_u | sort -u > "$tmpdepfile"
+  rm -f "$depfile"
+  echo "$object : \\" > "$depfile"
+  sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::'"$tab"'\1 \\:p' >> "$depfile"
+  echo "$tab" >> "$depfile"
+  sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::\1\::p' >> "$depfile"
+  rm -f "$tmpdepfile"
+  ;;
+
+msvcmsys)
+  # This case exists only to let depend.m4 do its work.  It works by
+  # looking at the text of this script.  This case will never be run,
+  # since it is checked for above.
+  exit 1
+  ;;
+
+none)
+  exec "$@"
+  ;;
+
+*)
+  echo "Unknown depmode $depmode" 1>&2
+  exit 1
+  ;;
+esac
+
+exit 0
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/edit-edit.c b/edit-edit.c
new file mode 100644 (file)
index 0000000..c2a5260
--- /dev/null
@@ -0,0 +1,91 @@
+#include "rc.h"
+
+#include <stdio.h>
+
+#include <histedit.h>
+
+#include "edit.h"
+
+bool editing = 1;
+
+struct cookie {
+       EditLine *el;
+       History *hist;
+};
+
+static char *prompt;
+
+void *edit_begin(int fd) {
+       FILE *f;
+       HistEvent he;
+       struct cookie *c;
+
+       c = ealloc(sizeof *c);
+       if (fd == 0)
+               f = stdin;
+       else
+               f = fdopen(fd, "r");
+       c->el = el_init("rc", f, stdout, stderr);
+       el_set(c->el, EL_SIGNAL, 0);
+       el_source(c->el, NULL);
+
+       c->hist = history_init();
+       history(c->hist, &he, H_SETSIZE, 20);
+       el_set(c->el, EL_HIST, history, c->hist);
+
+       return c;
+}
+
+
+static void edit_catcher(int sig) {
+       write(2, "\n", 1);
+       rc_raise(eError);
+}
+
+char *edit_alloc(void *cookie, size_t *count) {
+       const char *r;
+       HistEvent he;
+       struct cookie *c = cookie;
+       void (*oldint)(int), (*oldquit)(int);
+
+       oldint = sys_signal(SIGINT, edit_catcher);
+       oldquit = sys_signal(SIGQUIT, edit_catcher);
+
+       r = el_gets(c->el, count);
+
+       sys_signal(SIGINT, oldint);
+       sys_signal(SIGQUIT, oldquit);
+
+       if (r)
+               history(c->hist, &he, H_ENTER, r);
+       return (char *)r; /* cast to avoid gcc warning */
+}
+
+static char *edit_prompter(EditLine *e) {
+       return prompt;
+}
+
+void edit_prompt(void *cookie, char *pr) {
+       struct cookie *c = cookie;
+
+       prompt = pr;
+       el_set(c->el, EL_PROMPT, edit_prompter);
+}
+
+void edit_free(void *cookie) {
+       /* this function deliberately left blank */
+}
+
+void edit_end(void *cookie) {
+       struct cookie *c = cookie;
+
+       el_end(c->el);
+       history_end(c->hist);
+       efree(c);
+}
+
+void edit_reset(void *cookie) {
+       struct cookie *c = cookie;
+
+       el_set(c->el, EL_TERMINAL, NULL);
+}
diff --git a/edit-editline.c b/edit-editline.c
new file mode 100644 (file)
index 0000000..85e3f40
--- /dev/null
@@ -0,0 +1,100 @@
+#include "rc.h"
+
+#include <errno.h>
+#include <stdio.h>
+
+#include "editline.h"
+
+bool editing = 1;
+
+struct cookie {
+       char *buffer;
+};
+
+static char *prompt;
+
+void *edit_begin(int fd) {
+       List *hist;
+       struct cookie *c;
+
+        hist = varlookup("history");
+        if (hist != NULL)
+                if (read_history(hist->w) != 0 &&
+                               errno != ENOENT) /* ignore if missing */
+                        uerror(hist->w);
+
+       c = ealloc(sizeof *c);
+       c->buffer = NULL;
+       return c;
+}
+
+/*
+static void edit_catcher(int sig) {
+       write(2, "\n", 1);
+       rc_raise(eError);
+}
+
+*/
+
+char *edit_alloc(void *cookie, size_t *count) {
+       struct cookie *c = cookie;
+/*
+       const char *r;
+       HistEvent he;
+       struct cookie *c = cookie;
+       void (*oldint)(int), (*oldquit)(int);
+
+       oldint = sys_signal(SIGINT, edit_catcher);
+       oldquit = sys_signal(SIGQUIT, edit_catcher);
+
+       r = el_gets(c->el, count);
+
+       sys_signal(SIGINT, oldint);
+       sys_signal(SIGQUIT, oldquit);
+
+       if (r)
+               history(c->hist, &he, H_ENTER, r);
+*/
+
+       c->buffer = readline(prompt);
+       if (c->buffer) {
+               *count = strlen(c->buffer);
+               c->buffer[*count] = '\n';
+               ++*count;
+       }
+       return c->buffer;
+}
+
+/*
+static char *edit_prompter(ne *e) {
+       return prompt;
+}
+*/
+
+void edit_prompt(void *cookie, char *pr) {
+       //struct cookie *c = cookie;
+
+       prompt = pr;
+       //el_set(c->el, EL_PROMPT, edit_prompter);
+}
+
+void edit_free(void *cookie) {
+       struct cookie *c = cookie;
+
+       efree(c->buffer);
+       c->buffer = NULL; /* allow "overfrees" */
+}
+
+void edit_end(void *cookie) {
+       //struct cookie *c = cookie;
+
+       //el_end(c->el);
+       //history_end(c->hist);
+       //efree(c);
+}
+
+void edit_reset(void *cookie) {
+       //struct cookie *c = cookie;
+
+       //el_set(c->el, EL_TERMINAL, NULL);
+}
diff --git a/edit-null.c b/edit-null.c
new file mode 100644 (file)
index 0000000..e3cbe13
--- /dev/null
@@ -0,0 +1,35 @@
+#include "rc.h"
+
+#include <errno.h>
+
+#include <sys/types.h>
+
+#include "edit.h"
+
+bool editing = 0;
+
+void *edit_begin(int fd) {
+       assert(0); /* should never be called */
+       return NULL;
+}
+
+char *edit_alloc(void *cookie, size_t *count) {
+       assert(0); /* should never be called */
+       return NULL;
+}
+
+void edit_prompt(void *cookie, char *prompt) {
+       assert(0); /* should never be called */
+}
+
+void edit_free(void *buffer) {
+       assert(0); /* should never be called */
+}
+
+void edit_end(void *cookie) {
+       assert(0); /* should never be called */
+}
+
+void edit_reset(void *cookie) {
+       assert(0); /* should never be called */
+}
diff --git a/edit-readline.c b/edit-readline.c
new file mode 100644 (file)
index 0000000..6a997c5
--- /dev/null
@@ -0,0 +1,87 @@
+#include "rc.h"
+
+#include <errno.h>
+#include <stdio.h>
+#include <readline/readline.h>
+#include <readline/history.h>
+#include <readline/rltypedefs.h>
+
+#include "edit.h"
+
+bool editing = 1;
+
+struct cookie {
+       char *buffer;
+};
+
+void *edit_begin(int fd) {
+       List *hist;
+       struct cookie *c;
+
+       rl_catch_signals = 0;
+       rl_completer_quote_characters = "'";
+       rl_filename_quote_characters = "\t\n !#$&'()*;<=>?@[\\]^`{|}~";
+
+       hist = varlookup("history");
+       if (hist != NULL)
+               if (read_history(hist->w) != 0 && errno != ENOENT) /* ignore if missing */
+                       uerror(hist->w);
+
+       c = ealloc(sizeof *c);
+       c->buffer = NULL;
+       return c;
+}
+
+static void edit_catcher(int sig) {
+       write(2, "\n", 1);
+       rc_raise(eError);
+}
+
+static char *prompt;
+
+char *edit_alloc(void *cookie, size_t *count) {
+       struct cookie *c = cookie;
+       void (*oldint)(int), (*oldquit)(int);
+
+       oldint = sys_signal(SIGINT, edit_catcher);
+       oldquit = sys_signal(SIGQUIT, edit_catcher);
+
+       c->buffer = readline(prompt);
+
+       sys_signal(SIGINT, oldint);
+       sys_signal(SIGQUIT, oldquit);
+
+       if (c->buffer) {
+               *count = strlen(c->buffer);
+               if (*count)
+                       add_history(c->buffer);
+               c->buffer[*count] = '\n';
+               ++*count; /* include the \n */
+       }
+       return c->buffer;
+}
+
+void edit_prompt(void *cookie, char *pr) {
+       prompt = pr;
+}
+
+void edit_free(void *cookie) {
+       struct cookie *c = cookie;
+
+       efree(c->buffer);
+       /* Set c->buffer to NULL, allowing us to "overfree" it.  This
+          is a bit of a kludge, but it's otherwise hard to deal with
+          the case where a signal causes an early return from
+          readline. */
+       c->buffer = NULL;
+}
+
+void edit_end(void *cookie) {
+       struct cookie *c = cookie;
+
+       efree(c);
+}
+
+void edit_reset(void *cookie) {
+       rl_reset_terminal(NULL);
+}
diff --git a/edit-vrl.c b/edit-vrl.c
new file mode 100644 (file)
index 0000000..5c8ab5a
--- /dev/null
@@ -0,0 +1,104 @@
+#include "rc.h"
+
+#include <errno.h>
+#include <stdio.h>
+
+#include "edit.h"
+
+extern char *readline(char *);
+extern void add_history(char *);
+
+bool editing = 1;
+
+struct cookie {
+       char *buffer;
+};
+
+static char *prompt;
+
+void *edit_begin(int fd) {
+       List *hist;
+       struct cookie *c;
+
+
+        hist = varlookup("history");
+        if (hist != NULL)
+               ;
+               /* XXX will need to loop calling add_history() */
+
+       c = ealloc(sizeof *c);
+       c->buffer = NULL;
+       return c;
+}
+
+/*
+static void edit_catcher(int sig) {
+       write(2, "\n", 1);
+       rc_raise(eError);
+}
+
+*/
+
+char *edit_alloc(void *cookie, size_t *count) {
+       struct cookie *c = cookie;
+/*
+       const char *r;
+       HistEvent he;
+       struct cookie *c = cookie;
+       void (*oldint)(int), (*oldquit)(int);
+
+       oldint = sys_signal(SIGINT, edit_catcher);
+       oldquit = sys_signal(SIGQUIT, edit_catcher);
+
+       r = el_gets(c->el, count);
+
+       sys_signal(SIGINT, oldint);
+       sys_signal(SIGQUIT, oldquit);
+
+       if (r)
+               history(c->hist, &he, H_ENTER, r);
+*/
+
+       c->buffer = readline(prompt);
+       if (c->buffer) {
+               add_history(c->buffer);
+               *count = strlen(c->buffer);
+               c->buffer[*count] = '\n';
+               ++*count;
+       }
+       return c->buffer;
+}
+
+/*
+static char *edit_prompter(ne *e) {
+       return prompt;
+}
+*/
+
+void edit_prompt(void *cookie, char *pr) {
+       //struct cookie *c = cookie;
+
+       prompt = pr;
+       //el_set(c->el, EL_PROMPT, edit_prompter);
+}
+
+void edit_free(void *cookie) {
+       struct cookie *c = cookie;
+
+       efree(c->buffer);
+       c->buffer = NULL; /* allow "overfrees" */
+}
+
+void edit_end(void *cookie) {
+       //struct cookie *c = cookie;
+
+       //el_end(c->el);
+       //history_end(c->hist);
+       //efree(c);
+}
+
+void edit_reset(void *cookie) {
+       //struct cookie *c = cookie;
+
+       //el_set(c->el, EL_TERMINAL, NULL);
+}
diff --git a/edit.h b/edit.h
new file mode 100644 (file)
index 0000000..5f4eb5c
--- /dev/null
+++ b/edit.h
@@ -0,0 +1,12 @@
+extern bool editing;
+
+extern void *edit_begin(int fd);
+
+extern char *edit_alloc(void *, size_t *);
+extern void edit_free(void *);
+
+extern void edit_prompt(void *, char *);
+
+extern void edit_end(void *);
+
+extern void edit_reset(void *);
diff --git a/except.c b/except.c
new file mode 100644 (file)
index 0000000..8f20676
--- /dev/null
+++ b/except.c
@@ -0,0 +1,143 @@
+#include "rc.h"
+
+#include <setjmp.h>
+#include <signal.h>
+
+#include "input.h"
+#include "jbwrap.h"
+
+/*
+   A return goes back stack frames to the last return. A break does
+   not. A signal goes to the last interactive level. (see below)
+*/
+
+bool nl_on_intr = TRUE;
+
+static Estack *estack;
+
+/* add an exception to the input stack. */
+
+extern void except(ecodes e, Edata data, Estack *ex) {
+       ex->prev = estack;
+       estack = ex;
+       estack->e = e;
+       estack->data = data;
+       if (e == eError || e == eBreak || e == eReturn)
+               estack->interactive = interactive;
+}
+
+/* remove an exception, restore last interactive value */
+
+extern void unexcept() {
+       switch (estack->e) {
+       default:
+               break;
+       case eError:
+               interactive = estack->interactive;
+               break;
+       case eArena:
+               restoreblock(estack->data.b);
+               break;
+       case eFifo:
+               unlink(estack->data.name);
+               break;
+       case eFd:
+               close(estack->data.fd);
+               break;
+       }
+       estack = estack->prev;
+}
+
+/*
+   Raise an exception. The rules are pretty complicated: you can return
+   from a loop inside a function, but you can't break from a function
+   inside of a loop. On errors, rc_raise() goes back to the LAST
+   INTERACTIVE stack frame. If no such frame exists, then rc_raise()
+   exits the shell.  This is what happens, say, when there is a syntax
+   error in a noninteractive shell script. While traversing the
+   exception stack backwards, rc_raise() also removes input sources
+   (closing file-descriptors, etc.) and pops instances of variables
+   that have been pushed onto the variable stack (e.g., for a function
+   call (for $*) or a local assignment).
+*/
+
+extern void rc_raise(ecodes e) {
+       if (e == eError && rc_pid != getpid())
+               exit(1); /* child processes exit on an error/signal */
+       for (; estack != NULL; estack = estack->prev)
+               if (estack->e != e) {
+                       if (e == eBreak && estack->e != eArena)
+                               rc_error("break outside of loop");
+                       else if (e == eReturn && estack->e == eError) /* can return from loops inside functions */
+                               rc_error("return outside of function");
+                       switch (estack->e) {
+                       default:
+                               break;
+                       case eVarstack:
+                               varrm(estack->data.name, TRUE);
+                               break;
+                       case eArena:
+                               restoreblock(estack->data.b);
+                               break;
+                       case eFifo:
+                               unlink(estack->data.name);
+                               break;
+                       case eFd:
+                               close(estack->data.fd);
+                               break;
+                       }
+               } else {
+                       if (e == eError && !estack->interactive) {
+                               popinput();
+                       } else {
+                               Jbwrap *j = estack->data.jb;
+
+                               interactive = estack->interactive;
+                               estack = estack->prev;
+                               siglongjmp(j->j, 1);
+                       }
+               }
+       rc_exit(1); /* top of exception stack */
+}
+
+extern bool outstanding_cmdarg() {
+       return estack->e == eFifo || estack->e == eFd;
+}
+
+extern void pop_cmdarg(bool remove) {
+       for (; estack != NULL; estack = estack->prev)
+               switch (estack->e) {
+               case eFifo:
+                       if (remove)
+                               unlink(estack->data.name);
+                       break;
+               case eFd:
+                       if (remove)
+                               close(estack->data.fd);
+                       break;
+               default:
+                       return;
+               }
+}
+
+/* exception handlers */
+
+extern void rc_error(char *s) {
+       pr_error(s, -1);
+       set(FALSE);
+       redirq = NULL;
+       cond = FALSE; /* no longer inside conditional */
+       rc_raise(eError);
+}
+
+extern void sigint(int s) {
+       if (s != SIGINT)
+               panic("s != SIGINT in sigint catcher");
+       /* this is the newline you see when you hit ^C while typing a command */
+       if (interactive && nl_on_intr)
+               fprint(2, "\n");
+       nl_on_intr = TRUE;
+       redirq = NULL;
+       cond = FALSE;
+       rc_raise(eError);
+}
diff --git a/exec.c b/exec.c
new file mode 100644 (file)
index 0000000..c9244c2
--- /dev/null
+++ b/exec.c
@@ -0,0 +1,131 @@
+/* exec.c */
+
+#include "rc.h"
+
+#include <errno.h>
+#include <signal.h>
+
+#include "wait.h"
+
+/*
+   Takes an argument list and does the appropriate thing (calls a
+   builtin, calls a function, etc.)
+*/
+
+extern void exec(List *s, bool parent) {
+       char **av, **ev = NULL;
+       int stat;
+       pid_t pid;
+       builtin_t *b;
+       char *path = NULL;
+       bool didfork, returning, saw_exec, saw_builtin;
+       av = list2array(s, dashex);
+       saw_builtin = saw_exec = FALSE;
+       do {
+               if (*av == NULL || isabsolute(*av))
+                       b = NULL;
+               else if (!saw_builtin && fnlookup(*av) != NULL)
+                       b = funcall;
+               else
+                       b = isbuiltin(*av);
+
+               /*
+                  a builtin applies only to the immmediately following
+                  command, e.g., builtin exec echo hi
+               */
+               saw_builtin = FALSE;
+
+               if (b == b_exec) {
+                       av++;
+                       saw_exec = TRUE;
+                       parent = FALSE;
+               } else if (b == b_builtin) {
+                       av++;
+                       saw_builtin = TRUE;
+               }
+       } while (b == b_exec || b == b_builtin);
+       if (*av == NULL && saw_exec) { /* do redirs and return on a null exec */
+               doredirs();
+               return;
+       }
+       /* force an exit on exec with any rc_error, but not for null commands as above */
+       if (saw_exec)
+               rc_pid = -1;
+       if (b == NULL) {
+               path = which(*av, TRUE);
+               if (path == NULL && *av != NULL) { /* perform null commands for redirections */
+                       set(FALSE);
+                       redirq = NULL;
+                       if (parent)
+                               return;
+                       rc_exit(1);
+               }
+               ev = makeenv(); /* environment only needs to be built for execve() */
+       }
+       /*
+          If parent & the redirq is nonnull, builtin or not it has to fork.
+          If the fifoq is nonnull, then it must be emptied at the end so we
+          must fork no matter what.
+        */
+       if ((parent && (b == NULL || redirq != NULL)) || outstanding_cmdarg()) {
+               pid = rc_fork();
+               didfork = TRUE;
+       } else {
+               pid = 0;
+               didfork = FALSE;
+       }
+       returning = (!didfork && parent);
+       switch (pid) {
+       case -1:
+               uerror("fork");
+               rc_error(NULL);
+               /* NOTREACHED */
+       case 0:
+               if (!returning)
+                       setsigdefaults(FALSE);
+               pop_cmdarg(FALSE);
+               doredirs();
+
+               /* null commands performed for redirections */
+               if (*av == NULL || b != NULL) {
+                       if (b != NULL)
+                               (*b)(av);
+                       if (returning)
+                               return;
+                       rc_exit(getstatus());
+               }
+               rc_execve(path, (char * const *) av, (char * const *) ev);
+
+#ifdef DEFAULTINTERP
+               if (errno == ENOEXEC) {
+                       *av = path;
+                       *--av = DEFAULTINTERP;
+                       execve(*av, (char * const *) av, (char * const *) ev);
+               }
+#endif
+
+               uerror(*av);
+               rc_exit(1);
+               /* NOTREACHED */
+       default:
+               redirq = NULL;
+               rc_wait4(pid, &stat, TRUE);
+               setstatus(-1, stat);
+               /*
+                  There is a very good reason for having this weird
+                  nl_on_intr variable: when rc and its child both
+                  process a SIGINT, (i.e., the child has a SIGINT
+                  catcher installed) then you don't want rc to print
+                  a newline when the child finally exits. Here's an
+                  example: ed, <type ^C>, <type "q">. rc does not
+                  and should not print a newline before the next
+                  prompt, even though there's a SIGINT in its signal
+                  vector.
+               */
+               if (WIFEXITED(stat))
+                       nl_on_intr = FALSE;
+               sigchk();
+               nl_on_intr = TRUE;
+               pop_cmdarg(TRUE);
+       }
+}
diff --git a/execve.c b/execve.c
new file mode 100644 (file)
index 0000000..5edde11
--- /dev/null
+++ b/execve.c
@@ -0,0 +1,62 @@
+/* execve.c: an execve() for geriatric unices without #! */
+
+/*
+   NOTE: this file depends on a hack in footobar.c which places two free
+   spots before av[][] so that execve does not have to call malloc.
+*/
+
+#include "rc.h"
+
+#include <errno.h>
+
+#define giveupif(x) { if (x) goto fail; }
+
+extern int rc_execve(char *path, char **av, char **ev) {
+       int fd, len, fst, snd, end;
+       bool noarg;
+       char pb[256]; /* arbitrary but generous limit */
+       execve(path, av, ev);
+       if (errno != ENOEXEC)
+               return -1;
+       fd = rc_open(path, rFrom);
+       giveupif(fd < 0);
+       len = read(fd, pb, sizeof pb);
+       close(fd);
+       /* reject scripts which don't begin with #! */
+       giveupif(len <= 0 || pb[0] != '#' || pb[1] != '!');
+       for (fst = 2; fst < len && (pb[fst] == ' ' || pb[fst] == '\t'); fst++)
+               ; /* skip leading whitespace */
+       giveupif(fst == len);
+       for (snd = fst; snd < len && pb[snd] != ' ' && pb[snd] != '\t' && pb[snd] != '\n'; snd++)
+               ; /* skip first arg */
+       giveupif(snd == len);
+       noarg = (pb[snd] == '\n');
+       pb[snd++] = '\0'; /* null terminate the first arg */
+       if (!noarg) {
+               while (snd < len && (pb[snd] == ' ' || pb[snd] == '\t'))
+                       snd++; /* skip whitespace to second arg */
+               giveupif(snd == len);
+               noarg = (pb[snd] == '\n'); /* could have trailing whitespace after only one arg */
+               if (!noarg) {
+                       for (end = snd; end < len && pb[end] != ' ' && pb[end] != '\t' && pb[end] != '\n'; end++)
+                               ; /* skip to the end of the second arg */
+                       giveupif(end == len);
+                       if (pb[end] == '\n') {
+                               pb[end] = '\0'; /* null terminate the first arg */
+                       } else {                /* else check for a spurious third arg */
+                               pb[end++] = '\0';
+                               while (end < len && (pb[end] == ' ' || pb[end] == '\t'))
+                                       end++;
+                               giveupif(end == len || pb[end] != '\n');
+                       }
+               }
+       }
+       *av = path;
+       if (!noarg)
+               *--av = pb + snd;
+       *--av = pb + fst;
+       execve(*av, av, ev);
+       return -1;
+fail:  errno = ENOEXEC;
+       return -1;
+}
diff --git a/fn.c b/fn.c
new file mode 100644 (file)
index 0000000..7d9e4f7
--- /dev/null
+++ b/fn.c
@@ -0,0 +1,261 @@
+/*
+   fn.c: functions for adding and deleting functions from the symbol table.
+   Support for signal handlers is also found here.
+*/
+
+#include "rc.h"
+
+#include <signal.h>
+#include <errno.h>
+
+#include "input.h"
+#include "sigmsgs.h"
+
+static void fn_handler(int), dud_handler(int);
+
+static bool runexit = FALSE;
+static Node *handlers[NUMOFSIGNALS], null;
+static void (*def_sigint)(int) = SIG_DFL;
+static void (*def_sigquit)(int) = SIG_DFL;
+static void (*def_sigterm)(int) = SIG_DFL;
+
+/*
+   Set signals to default values for rc. This means that interactive
+   shells ignore SIGTERM, etc.
+*/
+
+extern void inithandler() {
+       int i;
+       null.type = nBody;
+       null.u[0].p = null.u[1].p = NULL;
+       for (i = 1; i < NUMOFSIGNALS; i++)
+#if HAVE_SYSV_SIGCLD
+               if (i != SIGCLD)
+#endif
+               if (sighandlers[i] == SIG_IGN)
+                       fnassign(signals[i].name, NULL); /* ignore incoming ignored signals */
+       if (interactive || sighandlers[SIGINT] != SIG_IGN) {
+               def_sigint = sigint;
+               fnrm("sigint"); /* installs SIGINT catcher if not inherited ignored */
+       }
+       if (!dashdee) {
+               if (interactive || sighandlers[SIGQUIT] != SIG_IGN) {
+                       def_sigquit = dud_handler;
+                       fnrm("sigquit"); /* "ignores" SIGQUIT unless inherited ignored */
+               }
+               if (interactive) {
+                       def_sigterm = dud_handler;
+                       fnrm("sigterm"); /* ditto for SIGTERM */
+               }
+       }
+}
+
+/* only run this in a child process! resets signals to their default values */
+
+extern void setsigdefaults(bool sysvbackground) {
+       int i;
+       /*
+          General housekeeping: setsigdefaults happens after fork(),
+          so it's a convenient place to clean up open file descriptors.
+          (history file, scripts, etc.)
+       */
+       closefds();
+       /*
+          Restore signals to SIG_DFL, paying close attention to
+          a few quirks: SIGINT, SIGQUIT and are treated specially
+          depending on whether we are doing v7-style backgrounding
+          or not; the default action for SIGINT, SIGQUIT and SIGTERM
+          must be set to the appropriate action; finally, care must
+          be taken not to set to SIG_DFL any signals which are being
+          ignored.
+       */
+       for (i = 1; i < NUMOFSIGNALS; i++)
+               if (sighandlers[i] != SIG_IGN) {
+                       handlers[i] = NULL;
+                       switch (i) {
+                       case SIGINT:
+                               if (sysvbackground) {
+                                       def_sigint = SIG_IGN;
+                                       fnassign("sigint", NULL); /* ignore */
+                               } else {
+                                       def_sigint = SIG_DFL;
+                                       goto sigcommon;
+                               }
+                               break;
+                       case SIGQUIT:
+                               if (sysvbackground) {
+                                       def_sigquit = SIG_IGN;
+                                       fnassign("sigquit", NULL); /* ignore */
+                               } else {
+                                       def_sigquit = SIG_DFL;
+                                       goto sigcommon;
+                               }
+                               break;
+                       case SIGTERM:
+                               def_sigterm = SIG_DFL;
+                               /* FALLTHROUGH */
+                       sigcommon:
+                       default:
+                               if (sighandlers[i] != SIG_DFL) {
+                                       rc_signal(i, SIG_DFL);
+                                       delete_fn(signals[i].name);
+                               }
+                       }
+               }
+       delete_fn("sigexit");
+       runexit = FALSE; /* No sigexit on subshells */
+}
+
+/* rc's exit. if runexit is set, run the sigexit function. */
+
+extern void rc_exit(int stat) {
+       if (runexit) {
+               char *sig[2];
+               sig[0] = "sigexit";
+               sig[1] = NULL;
+               runexit = FALSE;
+               funcall(sig);
+               stat = getstatus();
+       }
+       exit(stat);
+}
+
+/* The signal handler for all functions. calls walk() */
+
+static void fn_handler(int s) {
+       char *sig[2];
+       int olderrno;
+       if (s < 1 || s >= NUMOFSIGNALS)
+               panic("unknown signal");
+       olderrno = errno;
+       sig[0] = signals[s].name;
+       sig[1] = NULL;
+       funcall(sig);
+       errno = olderrno;
+}
+
+/* A dud signal handler for SIGQUIT and SIGTERM */
+
+static void dud_handler(int ignore) {
+}
+
+/*
+   Assign a function in Node form. Check to see if the function is also
+   a signal, and set the signal vectors appropriately.
+*/
+
+extern void fnassign(char *name, Node *def) {
+       Node *newdef = treecpy(def == NULL ? &null : def, ealloc); /* important to do the treecopy first */
+       rc_Function *new = get_fn_place(name);
+       int i;
+       new->def = newdef;
+       new->extdef = NULL;
+       if (strncmp(name, "sig", conststrlen("sig")) == 0) { /* slight optimization */
+#if HAVE_SYSV_SIGCLD /* System V machines treat SIGCLD very specially */
+               if (streq(name, "sigcld"))
+                       rc_error("can't trap SIGCLD");
+#endif
+               if (streq(name, "sigexit"))
+                       runexit = TRUE;
+               for (i = 1; i < NUMOFSIGNALS; i++) /* zero is a bogus signal */
+                       if (streq(signals[i].name, name)) {
+                               handlers[i] = newdef;
+                               if (def == NULL)
+                                       rc_signal(i, SIG_IGN);
+                               else
+                                       rc_signal(i, fn_handler);
+                               break;
+                       }
+       }
+}
+
+/* Assign a function from the environment. Store just the external representation */
+
+extern void fnassign_string(char *extdef) {
+       char *name = get_name(extdef+3); /* +3 to skip over "fn_" */
+       rc_Function *new;
+       if (name == NULL)
+               return;
+       new = get_fn_place(name);
+       new->def = NULL;
+       new->extdef = ecpy(extdef);
+}
+
+/* Return a function in Node form, evaluating an entry from the environment if necessary */
+
+extern Node *fnlookup(char *name) {
+       rc_Function *look = lookup_fn(name);
+       Node *ret;
+       if (look == NULL)
+               return NULL; /* not found */
+       if (look->def != NULL)
+               return look->def;
+       if (look->extdef == NULL) /* function was set to null, e.g., fn foo {} */
+               return &null;
+       ret = parse_fn(look->extdef);
+       if (ret == NULL) {
+               efree(look->extdef);
+               look->extdef = NULL;
+               return &null;
+       } else {
+               return look->def = treecpy(ret, ealloc); /* Need to take it out of nalloc space */
+       }
+}
+
+/* Return a function in string form (used by makeenv) */
+
+extern char *fnlookup_string(char *name) {
+       rc_Function *look = lookup_fn(name);
+
+       if (look == NULL)
+               return NULL;
+       if (look->extdef != NULL)
+               return look->extdef;
+       return look->extdef = mprint("fn_%F={%T}", name, look->def);
+}
+
+/*
+   Remove a function from the symbol table. If it also defines a signal
+   handler, restore the signal handler to its default value.
+*/
+
+extern void fnrm(char *name) {
+       int i;
+       for (i = 1; i < NUMOFSIGNALS; i++)
+               if (streq(signals[i].name, name)) {
+                       handlers[i] = NULL;
+                       switch (i) {
+                       case SIGINT:
+                               rc_signal(i, def_sigint);
+                               break;
+                       case SIGQUIT:
+                               rc_signal(i, def_sigquit);
+                               break;
+                       case SIGTERM:
+                               rc_signal(i, def_sigterm);
+                               break;
+                       default:
+                               rc_signal(i, SIG_DFL);
+                       }
+               }
+       if (streq(name, "sigexit"))
+               runexit = FALSE;
+       delete_fn(name);
+}
+
+extern void whatare_all_signals() {
+       int i;
+       for (i = 1; i < NUMOFSIGNALS; i++)
+               if (*signals[i].name != '\0') {
+                       if (sighandlers[i] == SIG_IGN)
+                               fprint(1, "fn %s {}\n", signals[i].name);
+                       else if (sighandlers[i] == fn_handler)
+                               fprint(1, "fn %S {%T}\n", signals[i].name, handlers[i]);
+                       else
+                               fprint(1, "fn %s\n", signals[i].name);
+               }
+}
+
+extern void prettyprint_fn(int fd, char *name, Node *n) {
+       fprint(fd, "fn %S {%T}\n", name, n);
+}
diff --git a/footobar.c b/footobar.c
new file mode 100644 (file)
index 0000000..d6f6dfd
--- /dev/null
@@ -0,0 +1,387 @@
+/*
+   footobar.c: a collection of functions to convert internal representations of
+   variables and functions to external representations, and vice versa
+*/
+
+#include "rc.h"
+
+#include "input.h"
+
+/* protect an exported name from brain-dead shells */
+
+#if PROTECT_ENV
+static bool Fconv(Format *f, int ignore) {
+       unsigned const char *s = va_arg(f->args, unsigned const char *);
+       int c;
+
+       while ((c = *s++) != '\0')
+               if (dnw[c] || c == '*' || (c == '_' && *s == '_'))
+                       fmtprint(f, "__%02x", c);
+               else
+                       fmtputc(f, c);
+       return FALSE;
+}
+#endif
+
+/* convert a redirection to a printable form */
+
+static bool Dconv(Format *f, int ignore) {
+       const char *name = "?";
+       int n = va_arg(f->args, int);
+       switch (n) {
+       case rCreate:           name = ">";     break;
+       case rAppend:           name = ">>";    break;
+       case rFrom:             name = "<";     break;
+       case rHeredoc:          name = "<<";    break;
+       case rHerestring:       name = "<<<";   break;
+       }
+       fmtcat(f, name);
+       return FALSE;
+}
+
+/* defaultfd -- return the default fd for a given redirection operation */
+
+static int defaultfd(int op) {
+       return (op == rCreate || op == rAppend) ? 1 : 0;
+}
+
+/* convert a function in Node * form into something rc can parse (and humans can read?) */
+
+static bool Tconv(Format *f, int ignore) {
+       bool dollar = f->flags & FMT_altform;
+       Node *n = va_arg(f->args, Node *);
+
+       if (n == NULL) {
+               fmtprint(f, "()");
+               return FALSE;
+       }
+       switch (n->type) {
+       case nBang:     fmtprint(f, "!%T", n->u[0].p);                          break;
+       case nCase:     fmtprint(f, "case %T", n->u[0].p);                      break;
+       case nNowait:   fmtprint(f, "%T&", n->u[0].p);                          break;
+       case nRmfn:     fmtprint(f, "fn %T", n->u[0].p);                        break;
+       case nSubshell: fmtprint(f, "@ %T", n->u[0].p);                         break;
+       case nAndalso:  fmtprint(f, "%T&&%T", n->u[0].p, n->u[1].p);            break;
+       case nAssign:   fmtprint(f, "%T=%T", n->u[0].p, n->u[1].p);             break;
+       case nConcat:   fmtprint(f, "%T^%T", n->u[0].p, n->u[1].p);             break;
+       case nElse:     fmtprint(f, "{%T}else %T", n->u[0].p, n->u[1].p);       break;
+       case nNewfn:    fmtprint(f, "fn %T {%T}", n->u[0].p, n->u[1].p);        break;
+       case nIf:       fmtprint(f, "if(%T)%T", n->u[0].p, n->u[1].p);          break;
+       case nOrelse:   fmtprint(f, "%T||%T", n->u[0].p, n->u[1].p);            break;
+       case nArgs:     fmtprint(f, "%T %T", n->u[0].p, n->u[1].p);             break;
+       case nSwitch:   fmtprint(f, "switch(%T){%T}", n->u[0].p, n->u[1].p);    break;
+       case nMatch:    fmtprint(f, "~ %T %T", n->u[0].p, n->u[1].p);           break;
+       case nWhile:    fmtprint(f, "while(%T)%T", n->u[0].p, n->u[1].p);       break;
+       case nForin:    fmtprint(f, "for(%T in %T)%T", n->u[0].p, n->u[1].p, n->u[2].p); break;
+       case nVarsub:   fmtprint(f, "$%T(%T)", n->u[0].p, n->u[1].p);           break;
+       case nWord:
+               fmtprint(f, n->u[2].i && quotep(n->u[0].s, dollar) ?
+                               "%#S" : "%S", n->u[0].s);
+               break;
+       case nLappend: {
+               static bool inlist;
+               if (!inlist) {
+                       inlist = TRUE;
+                       fmtprint(f, "(%T %T)", n->u[0].p, n->u[1].p);
+                       inlist = FALSE;
+               } else {
+                       fmtprint(f, "%T %T", n->u[0].p, n->u[1].p);
+               }
+               break;
+       }
+       case nCount: case nFlat: case nVar: {
+               char *lp = "", *rp = "";
+               Node *n0 = n->u[0].p;
+
+               if (n0->type != nWord)
+                       lp = "(", rp = ")";
+
+               switch (n->type) {
+               default:        panic("this can't happen");             break;
+               case nCount:    fmtprint(f, "$#%s%#T%s", lp, n0, rp);   break;
+               case nFlat:     fmtprint(f, "$^%s%#T%s", lp, n0, rp);   break;
+               case nVar:      fmtprint(f, "$%s%#T%s", lp, n0, rp);    break;
+               }
+               break;
+       }
+       case nDup:
+               if (n->u[2].i != -1)
+                       fmtprint(f, "%D[%d=%d]", n->u[0].i, n->u[1].i, n->u[2].i);
+               else
+                       fmtprint(f, "%D[%d=]", n->u[0].i, n->u[1].i);
+               break;
+       case nBackq: {
+               Node *n0 = n->u[0].p, *n00;
+               if (n0 != NULL && n0->type == nVar
+                   && (n00 = n0->u[0].p) != NULL && n00->type == nWord && streq(n00->u[0].s, "ifs"))
+                       fmtprint(f, "`");
+               else
+                       fmtprint(f, "``%T", n0);
+               fmtprint(f, "{%T}", n->u[1].p);
+               break;
+       }
+       case nCbody:
+       case nBody: {
+               Node *n0 = n->u[0].p;
+               if (n0 != NULL)
+                       fmtprint(f, "%T", n->u[0].p);
+               if (n->u[1].p != NULL) {
+                       if (n0 != NULL && n0->type != nNowait)
+                               fmtprint(f, ";");
+                       fmtprint(f, "%T", n->u[1].p);
+               }
+               break;
+       }
+       case nBrace:
+               fmtprint(f, "{%T}", n->u[0].p);
+               if (n->u[1].p != NULL)
+                       fmtprint(f, "%T", n->u[1].p);
+               break;
+       case nEpilog:
+       case nPre:
+               fmtprint(f, "%T", n->u[0].p);
+               if (n->u[1].p != NULL)
+                       fmtprint(f, " %T", n->u[1].p);
+               break;
+       case nPipe: {
+               int ofd = n->u[0].i, ifd = n->u[1].i;
+               fmtprint(f, "%T|", n->u[2].p);
+               if (ifd != 0)
+                       fmtprint(f, "[%d=%d]", ofd, ifd);
+               else if (ofd != 1)
+                       fmtprint(f, "[%d]", ofd);
+               fmtprint(f, "%T", n->u[3].p);
+               break;
+       }
+       case nRedir: {
+               int op = n->u[0].i;
+               fmtprint(f, "%D", op);
+               if (n->u[1].i != defaultfd(op))
+                       fmtprint(f, "[%d]", n->u[1].i);
+               fmtprint(f, "%T", n->u[2].p);
+               break;
+       }
+       case nNmpipe: {
+               int op = n->u[0].i;
+               fmtprint(f, "%D", op);
+               if (n->u[1].i != defaultfd(op))
+                       fmtprint(f, "[%d]", n->u[1].i);
+               fmtprint(f, "{%T}", n->u[2].p);
+               break;
+       }
+       }
+       return FALSE;
+}
+
+/* convert a List to an array, for execve() */
+
+extern char **list2array(List *s, bool print) {
+       char **argv, **av;
+
+       if (print)
+               fprint(2, "%L\n", s, " ");
+       /*
+          Allocate 3 extra spots (2 for the fake execve & 1 for defaulting to
+          sh) and hide these from exec().
+       */
+       argv = av = (char **) nalloc((listnel(s) + 4) * sizeof *av) + 3;
+       while (s != NULL) {
+               *av++ = s->w;
+               s = s->n;
+       }
+       *av = NULL;
+       return argv;
+}
+
+/* figure out the name of a variable given an environment string. */
+
+extern char *get_name(char *s) {
+       char *eq = strchr(s, '=');
+       char *r, *result;
+       int c;
+       
+       if (eq == NULL)
+               return NULL;
+       r = result = nalloc(eq - s + 1);
+       while (1)
+               switch (c = *s++) {
+               case '=':
+                       *r++ = '\0';
+                       return result;
+#if PROTECT_ENV
+               case '_':
+                       if (*s == '_') {
+                               static const char hexchar[] = "0123456789abcdef";
+                               char *h1 = strchr(hexchar, s[1]);
+                               char *h2 = strchr(hexchar, s[2]);
+                               if (h1 != NULL && h2 != NULL) {
+                                       *r++ = ((h1 - hexchar) << 4) | (h2 - hexchar);
+                                       s += 3;
+                                       break;
+                               }
+                       }
+                       /* FALLTHROUGH */
+#endif
+               default:
+                       *r++ = c;
+                       break;
+               }
+}
+
+/* interpret a variable from environment.  ^A separates list elements;
+   ^B escapes a literal ^A or ^B.  For minimal surprise, ^B followed
+   by anything other than ^A or ^B is preserved. */
+
+extern List *parse_var(char *extdef) {
+       char *begin, *end, *from, *to;
+       int len;
+       List *first, *last, *new;
+
+       first = last = NULL;
+       begin = strchr(extdef, '=');
+       assert(begin); /* guaranteed by initenv() */
+       while (*begin) {
+               ++begin;
+               end = begin;
+               len = 0;
+               while (*end != ENV_SEP && *end != '\0') {
+                       if (*end == ENV_ESC) {
+                               ++end;
+                               if (*end != ENV_SEP && *end != ENV_ESC) --end;
+                       }
+                       ++end; ++len;
+               }
+               new = enew(List);
+               if (last)
+                       last->n = new;
+               else
+                       first = new;
+               last = new;
+               new->w = ealloc(len + 1);
+               new->m = NULL;
+               new->n = NULL;
+               to = new->w;
+               for (from = begin; from < end; ++from) {
+                       if (*from == ENV_ESC) {
+                               ++from;
+                               if (*from != ENV_SEP && *from != ENV_ESC)
+                                       --from;
+                       }
+                       *to = *from;
+                       ++to;
+               }
+               *to = '\0';
+               begin = end;
+       }
+       return first;
+}
+
+/* get an environment entry for a function and have rc parse it. */
+
+#define PREFIX "fn x"
+#define PRELEN conststrlen(PREFIX)
+extern Node *parse_fn(char *extdef) {
+       Node *def;
+       char *s, old[PRELEN];
+       if ((s = strchr(extdef, '=')) == NULL)
+               return NULL;
+       memcpy(old, s -= (PRELEN-1), PRELEN);
+       memcpy(s, PREFIX, PRELEN);
+       def = parseline(s);
+       memcpy(s, old, PRELEN);
+       return (def == NULL || def->type != nNewfn) ? NULL : def->u[1].p;
+}
+
+static bool Aconv(Format *f, int ignore) {
+       char **a = va_arg(f->args, char **);
+       if (*a != NULL) {
+               fmtcat(f, *a);
+               while (*++a != NULL)
+                       fmtprint(f, " %s", *a);
+       }
+       return FALSE;
+}
+
+/* %L -- print a list */
+static bool Lconv(Format *f, int ignore) {
+       bool plain;
+       char *sep;
+       List *l, *n;
+
+       plain = f->flags & FMT_leftside;
+       l = va_arg(f->args, List *);
+       sep = va_arg(f->args, char *);
+       if (l == NULL && (f->flags & FMT_leftside) == 0)
+               fmtprint(f, "()");
+       else {
+               for (; l != NULL; l = n) {
+                       n = l->n;
+                       fmtprint(f, plain ? "%s" : "%-S", l->w);
+                       if (n != NULL) fmtputc(f, *sep);
+               }
+       }
+       return FALSE;
+}
+
+/* %W -- print a list for exporting */
+static bool Wconv(Format *f, int ignore) {
+       List *l, *n;
+
+       l = va_arg(f->args, List *);
+       for (; l != NULL; l = n) {
+               char c, *s;
+
+               for (s = l->w; (c = *s) != '\0'; ++s) {
+                       if (c == ENV_SEP || c == ENV_ESC)
+                               fmtputc(f, ENV_ESC);
+                       fmtputc(f, c);
+               }
+               n = l->n;
+               if (n != NULL) fmtputc(f, ENV_SEP);
+       }
+       return FALSE;
+}
+
+#define        ISMETA(c)       (c == '*' || c == '?' || c == '[')
+
+static bool Sconv(Format *f, int ignore) {
+       int c;
+       unsigned char *s = va_arg(f->args, unsigned char *), *t = s;
+       bool quoted    = (f->flags & FMT_altform)  != 0;        /* '#' */
+       bool metaquote = (f->flags & FMT_leftside) != 0;        /* '-' */
+       if (*s == '\0') {
+               fmtprint(f, "''");
+               return FALSE;
+       }
+       if (!quoted) {
+               while ((c = *t++) != '\0')
+                       if (nw[c] == 1 || (metaquote && ISMETA(c)))
+                               goto quoteit;
+               fmtprint(f, "%s", s);
+               return FALSE;
+       }
+quoteit:
+       fmtputc(f, '\'');
+       while ((c = *s++) != '\0') {
+               fmtputc(f, c);
+               if (c == '\'')
+                       fmtputc(f, '\'');
+
+       }
+       fmtputc(f, '\'');
+       return FALSE;
+}
+
+void initprint(void) {
+       fmtinstall('A', Aconv);
+       fmtinstall('L', Lconv);
+       fmtinstall('S', Sconv);
+       fmtinstall('T', Tconv);
+       fmtinstall('D', Dconv);
+       fmtinstall('W', Wconv);
+#if PROTECT_ENV
+       fmtinstall('F', Fconv);
+#else
+       fmtinstall('F', fmtinstall('s', NULL));
+#endif
+}
diff --git a/getgroups.h b/getgroups.h
new file mode 100644 (file)
index 0000000..982dfa0
--- /dev/null
@@ -0,0 +1,10 @@
+#if HAVE_GETGROUPS
+#if HAVE_POSIX_GETGROUPS
+/* We love POSIX. */
+#else
+/* OK, so you've got getgroups, but you don't have the POSIX semantics
+of a zero first argument.  The conclusion is that you're on a reasonably
+pure BSD system, and we can include <sys/param.h> for NGROUPS. */
+#include <sys/param.h>
+#endif
+#endif
diff --git a/getopt.c b/getopt.c
new file mode 100644 (file)
index 0000000..3c54f53
--- /dev/null
+++ b/getopt.c
@@ -0,0 +1,51 @@
+#include "rc.h"
+
+int     rc_opterr = 1;
+int     rc_optind = 1;
+int     rc_optopt;
+char    *rc_optarg;
+
+/* getopt routine courtesy of David Sanderson */
+extern int rc_getopt(int argc, char **argv, char *opts) {
+        static int sp = 1;
+       int c;
+       char *cp;
+       if (rc_optind == 0) /* reset rc_getopt() */
+               rc_optind = sp = 1;
+       if (sp == 1) {
+               if (rc_optind >= argc || argv[rc_optind][0] != '-' || argv[rc_optind][1] == '\0') {
+                       return -1;
+               } else if (strcmp(argv[rc_optind], "--") == 0) {
+                       rc_optind++;
+                       return -1;
+               }
+       }
+       rc_optopt = c = argv[rc_optind][sp];
+       if (c == ':' || (cp=strchr(opts, c)) == 0) {
+               fprint(2, "%s: bad option: -%c\n", argv[0], c);
+               if (argv[rc_optind][++sp] == '\0') {
+                       rc_optind++;
+                       sp = 1;
+               }
+               return '?';
+       }
+       if (*++cp == ':') {
+               if (argv[rc_optind][sp+1] != '\0') {
+                       rc_optarg = &argv[rc_optind++][sp+1];
+               } else if (++rc_optind >= argc) {
+                       fprint(2, "%s: option requires an argument -- %c\n", argv[0], c);
+                       sp = 1;
+                       return '?';
+               } else
+                       rc_optarg = argv[rc_optind++];
+               sp = 1;
+       } else {
+               if (argv[rc_optind][++sp] == '\0') {
+                       sp = 1;
+                       rc_optind++;
+               }
+               rc_optarg = NULL;
+       }
+       return c;
+}
diff --git a/glob.c b/glob.c
new file mode 100644 (file)
index 0000000..5507678
--- /dev/null
+++ b/glob.c
@@ -0,0 +1,266 @@
+/* glob.c: rc's (ugly) globber. This code is not elegant, but it works */
+
+#include "rc.h"
+#include "stat.h"
+
+/* Lifted from autoconf documentation.*/
+#if HAVE_DIRENT_H
+# include <dirent.h>
+# define NAMLEN(dirent) strlen((dirent)->d_name)
+#else
+# define dirent direct
+# define NAMLEN(dirent) (dirent)->d_namlen
+# if HAVE_SYS_NDIR_H
+#  include <sys/ndir.h>
+# endif
+# if HAVE_SYS_DIR_H
+#  include <sys/dir.h>
+# endif
+# if HAVE_NDIR_H
+#  include <ndir.h>
+# endif
+#endif
+
+static List *dmatch(char *, char *, char *);
+static List *doglob(char *, char *);
+static List *lglob(List *, char *, char *, size_t);
+static List *sort(List *);
+
+/*
+   Matches a list of words s against a list of patterns p. Returns true iff
+   a pattern in p matches a word in s. () matches (), but otherwise null
+   patterns match nothing.
+*/
+
+extern bool lmatch(List *s, List *p) {
+       List *q;
+       if (s == NULL) {
+               if (p == NULL) /* null matches null */
+                       return TRUE;
+               for (; p != NULL; p = p->n) /* one or more stars match null */
+                       if (strspn(p->w, "*") == strlen(p->w) &&
+                           p->m != NULL && strlen(p->m) == strlen(p->w))
+                               return TRUE;
+               return FALSE;
+       }
+       for (; s != NULL; s = s->n)
+               for (q = p; q != NULL; q = q->n)
+                       if (match(q->w, q->m, s->w))
+                               return TRUE;
+       return FALSE;
+}
+
+/*
+   Globs a list; checks to see if each element in the list has a metacharacter. If it
+   does, it is globbed, and the output is sorted.
+*/
+
+extern List *glob(List *s) {
+       List *top, *r;
+       bool meta;
+       for (r = s, meta = FALSE; r != NULL; r = r->n)
+               if (r->m != NULL)
+                       meta = TRUE;
+       if (!meta)
+               return s; /* don't copy lists with no metacharacters in them */
+       for (top = r = NULL; s != NULL; s = s->n) {
+               if (s->m == NULL) { /* no metacharacters; just tack on to the return list */
+                       if (top == NULL)
+                               top = r = nnew(List);
+                       else
+                               r = r->n = nnew(List);
+                       r->w = s->w;
+               } else {
+                       if (top == NULL)
+                               top = r = sort(doglob(s->w, s->m));
+                       else
+                               r->n = sort(doglob(s->w, s->m));
+                       while (r->n != NULL)
+                               r = r->n;
+               }
+       }
+       r->n = NULL;
+       return top;
+}
+
+/* Matches a pattern p against the contents of directory d */
+
+static List *dmatch(char *d, char *p, char *m) {
+       bool matched;
+       List *top, *r;
+       static DIR *dirp;
+       static struct dirent *dp;
+       static struct stat s;
+       int i;
+
+       /*
+          return a match if there are no metacharacters; allows globbing through
+          directories with no read permission. make sure the file exists, though.
+        */
+       matched = TRUE;
+       if (m != NULL)
+               for (i = 0; p[i] != '\0'; i++)
+                       if (m[i]) {
+                               matched = FALSE;
+                               break;
+                       }
+
+       if (matched) {
+               char *path = nprint("%s/%s", d, p);
+               if (lstat(path, &s) < 0)
+                       return NULL;
+               r = nnew(List);
+               r->w = ncpy(p);
+               r->m = NULL;
+               r->n = NULL;
+               return r;
+       }
+
+       top = r = NULL;
+       if (*d == '\0') d = "/";
+       if ((dirp = opendir(d)) == NULL)
+               return NULL;
+       /* opendir succeeds on regular files on some systems, so the stat() call is necessary (sigh) */
+       if (stat(d, &s) < 0 || (s.st_mode & S_IFMT) != S_IFDIR) {
+               closedir(dirp);
+               return NULL;
+       }
+       while ((dp = readdir(dirp)) != NULL)
+               if ((*dp->d_name != '.' || *p == '.') && match(p, m, dp->d_name)) { /* match ^. explicitly */
+                       matched = TRUE;
+                       if (top == NULL)
+                               top = r = nnew(List);
+                       else
+                               r = r->n = nnew(List);
+                       r->w = ncpy(dp->d_name);
+                       r->m = NULL;
+               }
+       closedir(dirp);
+       if (!matched)
+               return NULL;
+       r->n = NULL;
+       return top;
+}
+
+/*
+   lglob() globs a pattern against a list of directory roots. e.g., (/tmp /usr /bin) "*"
+   will return a list with all the files in /tmp, /usr, and /bin. NULL on no match.
+   slashcount indicates the number of slashes to stick between the directory and the
+   matched name. e.g., for matching ////tmp/////foo*
+*/
+
+static List *lglob(List *s, char *p, char *m, size_t slashcount) {
+       List *q, *r, *top, foo;
+       static struct {
+               List l;
+               size_t size;
+       } slash;
+       if (slashcount+1 > slash.size) {
+               slash.size = 2*(slashcount+1);
+               slash.l.w = erealloc(slash.l.w, slash.size);
+       }
+       slash.l.w[slashcount] = '\0';
+       while (slashcount > 0)
+               slash.l.w[--slashcount] = '/';
+       for (top = r = NULL; s != NULL; s = s->n) {
+               q = dmatch(s->w, p, m);
+               if (q != NULL) {
+                       foo.w = s->w;
+                       foo.m = NULL;
+                       foo.n = NULL;
+                       if (!(s->w[0] == '/' && s->w[1] == '\0')) /* need to separate */
+                               q = concat(&slash.l, q);          /* dir/name with slash */
+                       q = concat(&foo, q);
+                       if (r == NULL)
+                               top = r = q;
+                       else
+                               r->n = q;
+                       while (r->n != NULL)
+                               r = r->n;
+               }
+       }
+       return top;
+}
+
+/*
+   Doglob globs a pathname in pattern form against a unix path. Returns the original
+   pattern (cleaned of metacharacters) on failure, or the globbed string(s).
+*/
+
+static List *doglob(char *w, char *m) {
+       static char *dir = NULL, *pattern = NULL, *metadir = NULL, *metapattern = NULL;
+       static size_t dsize = 0;
+       char *d, *p, *md, *mp;
+       size_t psize;
+       char *s = w;
+       List firstdir;
+       List *matched;
+       if ((psize = strlen(w) + 1) > dsize || dir == NULL) {
+               efree(dir); efree(pattern); efree(metadir); efree(metapattern);
+               dir = ealloc(psize);
+               pattern = ealloc(psize);
+               metadir = ealloc(psize);
+               metapattern = ealloc(psize);
+               dsize = psize;
+       }
+       d = dir;
+       p = pattern;
+       md = metadir;
+       mp = metapattern;
+       while (*s != '/' && *s != '\0') {
+               *d++ = *s++; /* get first directory component */
+               *md++ = *m++;
+       }
+       *d = '\0';
+       /*
+          Special case: no slashes in the pattern, i.e., open the current directory.
+          Remember that w cannot consist of slashes alone (the other way *s could be
+          zero) since doglob gets called iff there's a metacharacter to be matched
+       */
+       if (*s == '\0') {
+               matched = dmatch(".", dir, metadir);
+               goto end;
+       }
+       if (*w == '/') {
+               firstdir.w = dir;
+               firstdir.m = metadir;
+               firstdir.n = NULL;
+               matched = &firstdir;
+       } else {
+               /*
+                  we must glob against current directory,
+                  since the first character is not a slash.
+               */
+               matched = dmatch(".", dir, metadir);
+       }
+       do {
+               size_t slashcount;
+               sigchk();
+               for (slashcount = 0; *s == '/'; s++, m++)
+                       slashcount++; /* skip slashes */
+               while (*s != '/' && *s != '\0')
+                       *p++ = *s++, *mp++ = *m++; /* get pattern */
+               *p = '\0';
+               matched = lglob(matched, pattern, metapattern, slashcount);
+               p = pattern, mp = metapattern;
+       } while (*s != '\0');
+end:   if (matched == NULL) {
+               matched = nnew(List);
+               matched->w = w;
+               matched->m = NULL;
+               matched->n = NULL;
+       }
+       return matched;
+}
+
+static List *sort(List *s) {
+       size_t nel = listnel(s);
+       if (nel > 1) {
+               char **a;
+               List *t;
+               qsort(a = list2array(s, FALSE), nel, sizeof(char *), starstrcmp);
+               for (t = s; t != NULL; t = t->n)
+                       t->w = *a++;
+       }
+       return s;
+}
diff --git a/glom.c b/glom.c
new file mode 100644 (file)
index 0000000..c44f0d5
--- /dev/null
+++ b/glom.c
@@ -0,0 +1,439 @@
+/* glom.c: builds an argument list out of words, variables, etc. */
+
+#include "rc.h"
+
+#include <sys/stat.h>
+#include <signal.h>
+#include <errno.h>
+
+static List *backq(Node *, Node *);
+static List *bqinput(List *, int);
+static List *count(List *);
+static List *mkcmdarg(Node *);
+
+Rq *redirq = NULL;
+
+extern List *word(char *w, char *m) {
+       List *s = NULL;
+       if (w != NULL) {
+               s = nnew(List);
+               s->w = w;
+               s->m = m;
+               s->n = NULL;
+       }
+       return s;
+}
+
+/*
+   Append list s2 to list s1 by copying s1 and making the new copy
+   point at s2.
+*/
+
+extern List *append(List *s1, List *s2) {
+       List *r, *top;
+       if (s1 == NULL)
+               return s2;
+       if (s2 == NULL)
+               return s1;
+       for (r = top = nnew(List); 1; r = r->n = nnew(List)) {
+               r->w = s1->w;
+               r->m = s1->m;
+               if ((s1 = s1->n) == NULL)
+                       break;
+       }
+       r->n = s2;
+       return top;
+}
+
+extern List *concat(List *s1, List *s2) {
+       int n1, n2;
+       List *r, *top;
+       if (s1 == NULL)
+               return s2;
+       if (s2 == NULL)
+               return s1;
+       if ((n1 = listnel(s1)) != (n2 = listnel(s2)) && n1 != 1 && n2 != 1)
+               rc_error("bad concatenation");
+       for (r = top = nnew(List); 1; r = r->n = nnew(List)) {
+               size_t x = strlen(s1->w);
+               size_t y = strlen(s2->w);
+               size_t z = x + y + 1;
+               r->w = nalloc(z);
+               strcpy(r->w, s1->w);
+               strcat(r->w, s2->w);
+               if (s1->m == NULL && s2->m == NULL) {
+                       r->m = NULL;
+               } else {
+                       r->m = nalloc(z);
+                       if (s1->m == NULL)
+                               memzero(r->m, x);
+                       else
+                               memcpy(r->m, s1->m, x);
+                       if (s2->m == NULL)
+                               memzero(&r->m[x], y);
+                       else
+                               memcpy(&r->m[x], s2->m, y);
+                       r->m[z] = 0;
+               }
+               if (n1 > 1)
+                       s1 = s1->n;
+               if (n2 > 1)
+                       s2 = s2->n;
+               if (s1 == NULL || s2 == NULL || (n1 == 1 && n2 == 1))
+                       break;
+       }
+       r->n = NULL;
+       return top;
+}
+
+extern List *varsub(List *var, List *subs) {
+       List *r, *top;
+       int n = listnel(var);
+       for (top = r = NULL; subs != NULL; subs = subs->n) {
+               int i = a2u(subs->w);
+               if (i < 1)
+                       rc_error("bad subscript");
+               if (i <= n) {
+                       List *sub = var;
+                       while (--i)
+                               sub = sub->n; /* loop until sub == var(i) */
+                       if (top == NULL)
+                               top = r = nnew(List);
+                       else
+                               r = r->n = nnew(List);
+                       r->w = sub->w;
+                       r->m = sub->m;
+               }
+       }
+       if (top != NULL)
+               r->n = NULL;
+       return top;
+}
+
+extern List *flatten(List *s) {
+       List *r;
+       size_t step;
+       char *f;
+       if (s == NULL || s->n == NULL)
+               return s;
+       r = nnew(List);
+       f = r->w = nalloc(listlen(s) + 1);
+       r->m = NULL; /* flattened lists come from variables, so no meta */
+       r->n = NULL;
+       strcpy(f, s->w);
+       f += strlen(s->w);
+       do {
+               *f++ = ' ';
+               s = s->n;
+               step = strlen(s->w);
+               memcpy(f, s->w, step);
+               f += step;
+       } while (s->n != NULL);
+       *f = '\0';
+       return r;
+}
+
+static List *count(List *l) {
+       List *s = nnew(List);
+       s->w = nprint("%d", listnel(l));
+       s->n = NULL;
+       s->m = NULL;
+       return s;
+}
+
+extern void assign(List *s1, List *s2, bool stack) {
+       List *val = s2;
+       if (s1 == NULL)
+               rc_error("null variable name");
+       if (s1->n != NULL)
+               rc_error("multi-word variable name");
+       if (*s1->w == '\0')
+               rc_error("zero-length variable name");
+       if (a2u(s1->w) != -1)
+               rc_error("numeric variable name");
+       if (strchr(s1->w, '=') != NULL)
+               rc_error("'=' in variable name");
+       if (*s1->w == '*' && s1->w[1] == '\0')
+               val = append(varlookup("0"), s2); /* preserve $0 when * is assigned explicitly */
+       if (s2 != NULL || stack) {
+               if (dashex)
+                       prettyprint_var(2, s1->w, val);
+               varassign(s1->w, val, stack);
+               alias(s1->w, varlookup(s1->w), stack);
+       } else {
+               if (dashex)
+                       prettyprint_var(2, s1->w, NULL);
+               varrm(s1->w, stack);
+       }
+}
+
+/*
+   The following two functions are by the courtesy of Paul Haahr,
+   who could not stand the incompetence of my own backquote implementation.
+*/
+
+#define BUFSIZE        ((size_t) 1000)
+
+static List *bqinput(List *ifs, int fd) {
+       char *end, *bufend, *s;
+       List *r, *top, *prev;
+       size_t remain, bufsize;
+       char isifs[256];
+       int n, state; /* a simple FSA is used to read in data */
+
+       memzero(isifs, sizeof isifs);
+       for (isifs['\0'] = TRUE; ifs != NULL; ifs = ifs->n)
+               for (s = ifs->w; *s != '\0'; s++)
+                       isifs[*(unsigned char *)s] = TRUE;
+       remain = bufsize = BUFSIZE;
+       top = r = nnew(List);
+       r->w = end = nalloc(bufsize + 1);
+       r->m = NULL;
+       state = 0;
+       prev = NULL;
+
+       while (1) {
+               if (remain == 0) { /* is the string bigger than the buffer? */
+                       size_t m = end - r->w;
+                       char *buf;
+                       while (bufsize < m + BUFSIZE)
+                               bufsize *= 2;
+                       buf = nalloc(bufsize + 1);
+                       memcpy(buf, r->w, m);
+                       r->w = buf;
+                       end = &buf[m];
+                       remain = bufsize - m;
+               }
+               if ((n = rc_read(fd, end, remain)) <= 0) {
+                       if (n == 0)
+       /* break */             break;
+                       else if (errno == EINTR)
+                               return NULL; /* interrupted, wait for subproc */
+                       else {
+                               uerror("backquote read");
+                               rc_error(NULL);
+                       }
+               }
+               remain -= n;
+               for (bufend = &end[n]; end < bufend; end++)
+                       if (state == 0) {
+                               if (!isifs[*(unsigned char *)end]) {
+                                       state = 1;
+                                       r->w = end;
+                                       r->m = NULL;
+                               }
+                       } else {
+                               if (isifs[*(unsigned char *)end]) {
+                                       state = 0;
+                                       *end = '\0';
+                                       prev = r;
+                                       r = r->n = nnew(List);
+                                       r->w = end+1;
+                                       r->m = NULL;
+                               }
+                       }
+       }
+       if (state == 1) { /* terminate last string */
+               *end = '\0';
+               r->n = NULL;
+       } else {
+               if (prev == NULL) /* no input at all? */
+                       top = NULL;
+               else
+                       prev->n = NULL; /* else terminate list */
+       }
+       return top;
+}
+
+static List *backq(Node *ifs, Node *n) {
+       int p[2], sp;
+       pid_t pid;
+       List *bq;
+       if (n == NULL)
+               return NULL;
+       if (pipe(p) < 0) {
+               uerror("pipe");
+               rc_error(NULL);
+       }
+       if ((pid = rc_fork()) == 0) {
+               mvfd(p[1], 1);
+               close(p[0]);
+               redirq = NULL;
+               walk(n, FALSE);
+               exit(getstatus());
+       }
+       close(p[1]);
+       bq = bqinput(glom(ifs), p[0]);
+       close(p[0]);
+       rc_wait4(pid, &sp, TRUE);
+       statprint(-1, sp);
+       varassign("bqstatus", word(strstatus(sp), NULL), FALSE);
+       sigchk();
+       return bq;
+}
+
+extern void qredir(Node *n) {
+       Rq *next;
+       if (redirq == NULL) {
+               next = redirq = nnew(Rq);
+       } else {
+               for (next = redirq; next->n != NULL; next = next->n)
+                       ;
+               next->n = nnew(Rq);
+               next = next->n;
+       }
+       next->r = n;
+       next->n = NULL;
+}
+
+#if HAVE_DEV_FD || HAVE_PROC_SELF_FD
+static List *mkcmdarg(Node *n) {
+       char *name;
+       List *ret = nnew(List);
+       Estack *e = nnew(Estack);
+       Edata efd;
+       int p[2];
+       if (pipe(p) < 0) {
+               uerror("pipe");
+               return NULL;
+       }
+       if (rc_fork() == 0) {
+               setsigdefaults(FALSE);
+               if (mvfd(p[n->u[0].i == rFrom], n->u[0].i == rFrom) < 0) /* stupid hack */
+                       exit(1);
+               close(p[n->u[0].i != rFrom]);
+               redirq = NULL;
+               walk(n->u[2].p, FALSE);
+               exit(getstatus());
+       }
+
+#if HAVE_DEV_FD
+       name = nprint("/dev/fd/%d", p[n->u[0].i != rFrom]);
+#else
+       name = nprint("/proc/self/fd/%d", p[n->u[0].i != rFrom]);
+#endif
+
+       efd.fd = p[n->u[0].i != rFrom];
+       except(eFd, efd, e);
+       close(p[n->u[0].i == rFrom]);
+       ret->w = name;
+       ret->m = NULL;
+       ret->n = NULL;
+       return ret;
+}
+
+#elif HAVE_FIFO
+
+#if HAVE_MKFIFO
+/* Have POSIX mkfifo(). */
+#else
+#define mkfifo(n,m) mknod(n, S_IFIFO | m, 0)
+#endif
+
+static List *mkcmdarg(Node *n) {
+       int fd;
+       char *name;
+       Edata efifo;
+       Estack *e = enew(Estack);
+       List *ret = nnew(List);
+       static int fifonumber = 0;
+
+       name = nprint("/tmp/rc%d.%d", getpid(), fifonumber++);
+       if (mkfifo(name, 0666) < 0) {
+               uerror("mkfifo");
+               return NULL;
+       }
+       if (rc_fork() == 0) {
+               setsigdefaults(FALSE);
+               fd = rc_open(name, (n->u[0].i != rFrom) ? rFrom : rCreate); /* stupid hack */
+               if (fd < 0) {
+                       uerror("open");
+                       exit(1);
+               }
+               if (mvfd(fd, (n->u[0].i == rFrom)) < 0) /* same stupid hack */
+                       exit(1);
+               redirq = NULL;
+               walk(n->u[2].p, FALSE);
+               exit(getstatus());
+       }
+       efifo.name = name;
+       except(eFifo, efifo, e);
+       ret->w = name;
+       ret->m = NULL;
+       ret->n = NULL;
+       return ret;
+}
+
+#else
+
+static List *mkcmdarg(Node *n) {
+       rc_error("command arguments are not supported");
+       return NULL;
+}
+
+#endif
+
+extern List *glom(Node *n) {
+       List *v, *head, *tail;
+       Node *words;
+       if (n == NULL)
+               return NULL;
+       switch (n->type) {
+       case nArgs:
+       case nLappend:
+               words = n->u[0].p;
+               tail = NULL;
+               while (words != NULL && (words->type == nArgs || words->type == nLappend)) {
+                       if (words->u[1].p != NULL && words->u[1].p->type != nWord)
+                               break;
+                       head = glom(words->u[1].p);
+                       if (head != NULL) {
+                               head->n = tail;
+                               tail = head;
+                       }
+                       words = words->u[0].p;
+               }
+               v = append(glom(words), tail); /* force left to right evaluation */
+               return append(v, glom(n->u[1].p));
+       case nBackq:
+               return backq(n->u[0].p, n->u[1].p);
+       case nConcat:
+               head = glom(n->u[0].p); /* force left-to-right evaluation */
+               return concat(head, glom(n->u[1].p));
+       case nDup:
+       case nRedir:
+               qredir(n);
+               return NULL;
+       case nWord:
+               return word(n->u[0].s, n->u[1].s);
+       case nNmpipe:
+               return mkcmdarg(n);
+       default:
+               /*
+                  The next four operations depend on the left-child of glom
+                  to be a variable name. Therefore the variable is looked up
+                  here.
+               */
+               if ((v = glom(n->u[0].p)) == NULL)
+                       rc_error("null variable name");
+               if (v->n != NULL)
+                       rc_error("multi-word variable name");
+               if (*v->w == '\0')
+                       rc_error("zero-length variable name");
+               v = (*v->w == '*' && v->w[1] == '\0') ? varlookup(v->w)->n : varlookup(v->w);
+               switch (n->type) {
+               default:
+                       panic("unexpected node in glom");
+                       exit(1);
+                       /* NOTREACHED */
+               case nCount:
+                       return count(v);
+               case nFlat:
+                       return flatten(v);
+               case nVar:
+                       return v;
+               case nVarsub:
+                       return varsub(v, glom(n->u[1].p));
+               }
+       }
+}
diff --git a/hash.c b/hash.c
new file mode 100644 (file)
index 0000000..5fafed2
--- /dev/null
+++ b/hash.c
@@ -0,0 +1,317 @@
+/* hash.c: hash table support for functions and variables. */
+
+/*
+   Functions and variables are cached in both internal and external
+   form for performance. Thus a variable which is never "dereferenced"
+   with a $ is passed on to rc's children untouched. This is not so
+   important for variables, but is a big win for functions, where a call
+   to yyparse() is involved.
+*/
+
+#include "rc.h"
+#include "sigmsgs.h"
+
+static bool var_exportable(char *);
+static bool fn_exportable(char *);
+static int hash(char *, int);
+static int find(char *, Htab *, int);
+static void free_fn(rc_Function *);
+
+Htab *fp;
+Htab *vp;
+static int fused, fsize, vused, vsize;
+static char **env;
+static int bozosize;
+static int envsize;
+static bool env_dirty = TRUE;
+static char *dead = "";
+
+#define HASHSIZE 64 /* rc was debugged with HASHSIZE == 2; 64 is about right for normal use */
+
+extern void inithash() {
+       Htab *fpp, *vpp;
+       int i;
+       fp = ealloc(sizeof(Htab) * HASHSIZE);
+       vp = ealloc(sizeof(Htab) * HASHSIZE);
+       fused = vused = 0;
+       fsize = vsize = HASHSIZE;
+       for (vpp = vp, fpp = fp, i = 0; i < HASHSIZE; i++, vpp++, fpp++)
+               vpp->name = fpp->name = NULL;
+}
+
+#define ADV()   {if ((c = *s++) == '\0') break;}
+
+/* hash function courtesy of paul haahr */
+
+static int hash(char *s, int size) {
+       int c, n = 0;
+       while (1) {
+               ADV();
+               n += (c << 17) ^ (c << 11) ^ (c << 5) ^ (c >> 1);
+               ADV();
+               n ^= (c << 14) + (c << 7) + (c << 4) + c;
+               ADV();
+               n ^= (~c << 11) | ((c << 3) ^ (c >> 1));
+               ADV();
+               n -= (c << 16) | (c << 9) | (c << 2) | (c & 3);
+       }
+       if (n < 0)
+               n = ~n;
+       return n & (size - 1); /* need power of 2 size */
+}
+
+static bool rehash(Htab *ht) {
+       int i, j, size;
+       int newsize, newused;
+       Htab *newhtab;
+       if (ht == fp) {
+               if (fsize > 2 * fused)
+                       return FALSE;
+               size = fsize;
+       } else {
+               if (vsize > 2 * vused)
+                       return FALSE;
+               size = vsize;
+       }
+       newsize = 2 * size;
+       newhtab = ealloc(newsize * sizeof(Htab));
+       for (i = 0; i < newsize; i++)
+               newhtab[i].name = NULL;
+       for (i = newused = 0; i < size; i++)
+               if (ht[i].name != NULL && ht[i].name != dead) {
+                       newused++;
+                       j = hash(ht[i].name, newsize);
+                       while (newhtab[j].name != NULL) {
+                               j++;
+                               j &= (newsize - 1);
+                       }
+                       newhtab[j].name = ht[i].name;
+                       newhtab[j].p = ht[i].p;
+               }
+       if (ht == fp) {
+               fused = newused;
+               fp = newhtab;
+               fsize = newsize;
+       } else {
+               vused = newused;
+               vp = newhtab;
+               vsize = newsize;
+       }
+       efree(ht);
+       return TRUE;
+}
+
+#define varfind(s) find(s, vp, vsize)
+#define fnfind(s) find(s, fp, fsize)
+
+static int find(char *s, Htab *ht, int size) {
+       int h = hash(s, size);
+       while (ht[h].name != NULL && !streq(ht[h].name, s)) {
+               h++;
+               h &= size - 1;
+       }
+       return h;
+}
+
+extern void *lookup(char *s, Htab *ht) {
+       int h = find(s, ht, ht == fp ? fsize : vsize);
+       return (ht[h].name == NULL) ? NULL : ht[h].p;
+}
+
+extern rc_Function *get_fn_place(char *s) {
+       int h = fnfind(s);
+       env_dirty = TRUE;
+       if (fp[h].name == NULL) {
+               if (rehash(fp))
+                       h = fnfind(s);
+               fused++;
+               fp[h].name = ecpy(s);
+               fp[h].p = enew(rc_Function);
+       } else
+               free_fn(fp[h].p);
+       return fp[h].p;
+}
+
+extern Variable *get_var_place(char *s, bool stack) {
+       Variable *new;
+       int h = varfind(s);
+
+       env_dirty = TRUE;
+
+       if (vp[h].name == NULL) {
+               if (rehash(vp))
+                       h = varfind(s);
+               vused++;
+               vp[h].name = ecpy(s);
+               vp[h].p = enew(Variable);
+               ((Variable *)vp[h].p)->n = NULL;
+               return vp[h].p;
+       } else {
+               if (stack) {    /* increase the stack by 1 */
+                       new = enew(Variable);
+                       new->n = vp[h].p;
+                       return vp[h].p = new;
+               } else {        /* trample the top of the stack */
+                       new = vp[h].p;
+                       efree(new->extdef);
+                       listfree(new->def);
+                       return new;
+               }
+       }
+}
+
+extern void delete_fn(char *s) {
+       int h = fnfind(s);
+       if (fp[h].name == NULL)
+               return; /* not found */
+       env_dirty = TRUE;
+       free_fn(fp[h].p);
+       efree(fp[h].p);
+       efree(fp[h].name);
+       if (fp[(h+1)&(fsize-1)].name == NULL) {
+               --fused;
+               fp[h].name = NULL;
+       } else {
+               fp[h].name = dead;
+       }
+}
+
+extern void delete_var(char *s, bool stack) {
+       int h = varfind(s);
+       Variable *v;
+       if (vp[h].name == NULL)
+               return; /* not found */
+       env_dirty = TRUE;
+       v = vp[h].p;
+       efree(v->extdef);
+       listfree(v->def);
+       if (v->n != NULL) { /* This is the top of a stack */
+               if (stack) { /* pop */
+                       vp[h].p = v->n;
+                       efree(v);
+               } else { /* else just empty */
+                       v->extdef = NULL;
+                       v->def = NULL;
+               }
+       } else { /* needs to be removed from the hash table */
+               efree(v);
+               efree(vp[h].name);
+               if (vp[(h+1)&(vsize-1)].name == NULL) {
+                       --vused;
+                       vp[h].name = NULL;
+               } else {
+                       vp[h].name = dead;
+               }
+       }
+}
+
+static void free_fn(rc_Function *f) {
+       treefree(f->def);
+       efree(f->extdef);
+}
+
+extern void initenv(char **envp) {
+       int n;
+       for (n = 0; envp[n] != NULL; n++)
+               ;
+       n++; /* one for the null terminator */
+       if (n < HASHSIZE)
+               n = HASHSIZE;
+       env = ealloc((envsize = 2 * n) * sizeof (char *));
+       for (; *envp != NULL; envp++)
+               if (strncmp(*envp, "fn_", conststrlen("fn_")) == 0) {
+                       if (!dashpee)
+                               fnassign_string(*envp);
+               } else {
+                       if (!varassign_string(*envp)) /* add to bozo env */
+                               env[bozosize++] = *envp;
+               }
+}
+
+static char *neverexport[] = {
+       "apid", "apids", "bqstatus", "cdpath", "home",
+       "ifs", "path", "pid", "status", "*"
+};
+
+/* for a few variables that have default values, we export them only
+if they've been explicitly set; maybeexport[n].flag is TRUE if this
+has occurred. */
+struct nameflag {
+       char *name;
+       bool flag;
+};
+static struct nameflag maybeexport[] = {
+       { "prompt", FALSE },
+       { "version", FALSE }
+};
+
+void set_exportable(char *s, bool b) {
+       int i;
+       for (i = 0; i < arraysize(maybeexport); ++i)
+               if (maybeexport[i].flag != b && streq(s, maybeexport[i].name))
+                       maybeexport[i].flag = b;
+}
+
+static bool var_exportable(char *s) {
+       int i;
+       for (i = 0; i < arraysize(neverexport); i++)
+               if (streq(s, neverexport[i]))
+                       return FALSE;
+       for (i = 0; i < arraysize(maybeexport); i++)
+               if (maybeexport[i].flag == FALSE && streq(s, maybeexport[i].name))
+                       return FALSE;
+       return TRUE;
+}
+
+static bool fn_exportable(char *s) {
+       int i;
+       if (strncmp(s, "sig", conststrlen("sig")) == 0) { /* small speed hack */
+               for (i = 0; i < NUMOFSIGNALS; i++)
+                       if (streq(s, signals[i].name))
+                               return FALSE;
+               if (streq(s, "sigexit"))
+                       return FALSE;
+       }
+       return TRUE;
+}
+
+extern char **makeenv() {
+       int ep, i;
+       char *v;
+       if (!env_dirty)
+               return env;
+       env_dirty = FALSE;
+       ep = bozosize;
+       if (vsize + fsize + 1 + bozosize > envsize) {
+               envsize = 2 * (bozosize + vsize + fsize + 1);
+               env = erealloc(env, envsize * sizeof(char *));
+       }
+       for (i = 0; i < vsize; i++) {
+               if (vp[i].name == NULL || vp[i].name == dead || !var_exportable(vp[i].name))
+                       continue;
+               v = varlookup_string(vp[i].name);
+               if (v != NULL)
+                       env[ep++] = v;
+       }
+       for (i = 0; i < fsize; i++) {
+               if (fp[i].name == NULL || fp[i].name == dead || !fn_exportable(fp[i].name))
+                       continue;
+               env[ep++] = fnlookup_string(fp[i].name);
+       }
+       env[ep] = NULL;
+       qsort(env, (size_t) ep, sizeof(char *), starstrcmp);
+       return env;
+}
+
+extern void whatare_all_vars(bool showfn, bool showvar) {
+       int i;
+       List *s;
+       if (showvar)
+               for (i = 0; i < vsize; i++)
+                       if (vp[i].name != NULL && (s = varlookup(vp[i].name)) != NULL)
+                               prettyprint_var(1, vp[i].name, s);
+       if (showfn)
+               for (i = 0; i < fsize; i++)
+                       if (fp[i].name != NULL && fp[i].name != dead)
+                               prettyprint_fn(1, fp[i].name, fnlookup(fp[i].name));
+}
diff --git a/heredoc.c b/heredoc.c
new file mode 100644 (file)
index 0000000..348dc84
--- /dev/null
+++ b/heredoc.c
@@ -0,0 +1,158 @@
+/* heredoc.c: heredoc slurping is done here */
+
+#include "rc.h"
+
+#include "input.h"
+
+struct Hq {
+       Node *doc;
+       char *name;
+       Hq *n;
+       bool quoted;
+} *hq;
+
+static bool dead = FALSE;
+
+/*
+ * read in a heredocument. A clever trick: skip over any partially matched end-of-file
+ * marker storing only the number of characters matched. If the whole marker is matched,
+ * return from readheredoc(). If only part of the marker is matched, copy that part into
+ * the heredocument.
+ *
+ * BUG: if the eof string contains a newline, the state can get confused, and the
+ * heredoc may continue past where it should.  on the other hand, /bin/sh seems to
+ * never get out of its readheredoc() when the heredoc string contains a newline
+ */
+
+static char *readheredoc(char *eof) {
+       int c;
+       char *t, *buf, *bufend;
+       unsigned char *s;
+       size_t bufsize;
+       t = buf = nalloc(bufsize = 512);
+       bufend = &buf[bufsize];
+       dead = FALSE;
+#define        RESIZE(extra) { \
+               char *nbuf; \
+               bufsize = bufsize * 2 + extra; \
+               nbuf = nalloc(bufsize); \
+               memcpy(nbuf, buf, (size_t) (t - buf)); \
+               t = nbuf + (t - buf); \
+               buf = nbuf; \
+               bufend = &buf[bufsize]; \
+       }
+       for (;;) {
+               nextline();
+               for (s = (unsigned char *) eof; (c = gchar()) == *s; s++)
+                       ;
+               if (*s == '\0' && (c == '\n' || c == EOF)) {
+                       *t++ = '\0';
+                       return buf;
+               }
+               if (s != (unsigned char *) eof) {
+                       size_t len = s - (unsigned char *) eof;
+                       if (t + len >= bufend)
+                               RESIZE(len);
+                       memcpy(t, eof, len);
+                       t += len;
+               }
+               for (;; c = gchar()) {
+                       if (c == EOF) {
+                               yyerror("heredoc incomplete");
+                               dead = TRUE;
+                               return NULL;
+                       }
+                       if (t + 1 >= bufend)
+                               RESIZE(0);
+                       *t++ = c;
+                       if (c == '\n')
+                               break;
+               }
+       }
+}
+
+/* parseheredoc -- turn a heredoc with variable references into a node chain */
+
+static Node *parseheredoc(char *s) {
+       int c = *s;
+       Node *result = NULL;
+       while (TRUE) {
+               Node *node;
+               switch (c) {
+               default: {
+                       char *begin = s;
+                       while ((c = *s++) != '\0' && c != '$')
+                               ;
+                       *--s = '\0';
+                       node = mk(nWord, begin, NULL);
+                       break;
+               }
+               case '$': {
+                       char *begin = ++s, *var;
+                       c = *s++;
+                       if (c == '$') {
+                               node = mk(nWord, "$", NULL);
+                               c = *s;
+                       } else {
+                               size_t len = 0;
+                               do
+                                       len++;
+                               while (!dnw[c = *(unsigned char *) s++]);
+                               if (c == '^')
+                                       c = *s;
+                               else
+                                       s--;
+                               var = nalloc(len + 1);
+                               var[len] = '\0';
+                               memcpy(var, begin, len);
+                               node = mk(nFlat, mk(nWord, var, NULL));
+                       }
+                       break;
+               }
+               case '\0':
+                       return result;
+               }
+               result = (result == NULL) ? node : mk(nConcat, result, node);
+       }
+}
+
+/* read in heredocs when yyparse hits a newline. called from yyparse */
+
+extern int heredoc(int end) {
+       Hq *here;
+       if ((here = hq) != NULL) {
+               hq = NULL;
+               if (end) {
+                       yyerror("heredoc incomplete");
+                       return FALSE;
+               }
+               do {
+                       Node *n = here->doc;
+                       char *s = readheredoc(here->name);
+                       if (dead)
+                               return FALSE;
+                       n->u[2].p = here->quoted ? mk(nWord, s, NULL, FALSE) : parseheredoc(s);
+                       n->u[0].i = rHerestring;
+               } while ((here = here->n) != NULL);
+       }
+       return TRUE;
+}
+
+/* queue pending heredocs into a queue. called from yyparse */
+
+extern int qdoc(Node *name, Node *n) {
+       Hq *new, **prev;
+       if (name->type != nWord) {
+               yyerror("eof-marker not a single literal word");
+               skiptonl();
+               return FALSE;
+       }
+       for (prev = &hq; (new = *prev) != NULL; prev = &new->n)
+               ;
+       *prev = new = nnew(Hq);
+       new->name = name->u[0].s;
+       new->quoted = name->u[2].i;
+       new->doc = n;
+       new->n = NULL;
+       return TRUE;
+}
diff --git a/history.1 b/history.1
new file mode 100644 (file)
index 0000000..0be8684
--- /dev/null
+++ b/history.1
@@ -0,0 +1,254 @@
+.\" history.1
+.\"-------
+.\" See rc.1 for man page portability notes.
+.\"-------
+.\" Dd distance to space vertically before a "display"
+.\" These are what n/troff use for interparagraph distance
+.\"-------
+.if t .nr Dd .4v
+.if n .nr Dd 1v
+.\"-------
+.\" Ds begin a display, indented .5 inches from the surrounding text.
+.\"
+.\" Note that uses of Ds and De may NOT be nested.
+.\"-------
+.de Ds
+.\" .RS \\$1
+.sp \\n(Ddu
+.in +0.5i
+.nf
+..
+.\"-------
+.\" De end a display (no trailing vertical spacing)
+.\"-------
+.de De
+.fi
+.in
+.\" .RE
+..
+.\"-------
+.\" I stole the Xf macro from the -man macros on my machine (originally
+.\" "}S", I renamed it so that it won't conflict).
+.\"-------
+.\" Set Cf to the name of the constant width font.
+.\" It will be "C" or "(CW", typically.
+.\" NOTEZ BIEN the lines defining Cf must have no trailing white space:
+.\"-------
+.if t .ds Cf C
+.if n .ds Cf R
+.\"-------
+.\" Rc - Alternate Roman and Courier
+.\"-------
+.de Rc
+.Xf R \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Ic - Alternate Italic and Courier
+.\"-------
+.de Ic
+.Xf I \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Bc - Alternate Bold and Courier
+.\"-------
+.de Bc
+.Xf B \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Cr - Alternate Courier and Roman
+.\"-------
+.de Cr
+.Xf \\*(Cf R \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Ci - Alternate Courier and Italic
+.\"-------
+.de Ci
+.Xf \\*(Cf I \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Cb - Alternate Courier and Bold
+.\"-------
+.de Cb
+.Xf \\*(Cf B \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Xf - Alternate fonts
+.\"
+.\" \$1 - first font
+.\" \$2 - second font
+.\" \$3 - desired word with embedded font changes, built up by recursion
+.\" \$4 - text for first font
+.\" \$5 - \$9 - remaining args
+.\"
+.\" Every time we are called:
+.\"
+.\" If         there is something in \$4
+.\" then       Call ourself with the fonts switched,
+.\"            with a new word made of the current word (\$3) and \$4
+.\"            rendered in the first font,
+.\"            and with the remaining args following \$4.
+.\" else       We are done recursing.  \$3 holds the desired output
+.\"            word.  We emit \$3, change to Roman font, and restore
+.\"            the point size to the default.
+.\" fi
+.\"
+.\" Use Xi to add a little bit of space after italic text.
+.\"-------
+.de Xf
+.ds Xi
+.\"-------
+.\" I used to test for the italic font both by its font position
+.\" and its name.  Now just test by its name.
+.\"
+.\" .if "\\$1"2" .if !"\\$5"" .ds Xi \^
+.\"-------
+.if "\\$1"I" .if !"\\$5"" .ds Xi \^
+.\"-------
+.\" This is my original code to deal with the recursion.
+.\" Evidently some nroffs can't deal with it.
+.\"-------
+.\" .ie !"\\$4"" \{\
+.\" .  Xf \\$2 \\$1 "\\$3\\f\\$1\\$4\\*(Xi" "\\$5" "\\$6" "\\$7" "\\$8" "\\$9"
+.\" .\}
+.\" .el \{\\$3
+.\" .  ft R    \" Restore the default font, since we don't know
+.\" .          \" what the last font change was.
+.\" .  ps 10   \" Restore the default point size, since it might
+.\" .          \" have been changed by an argument to this macro.
+.\" .\}
+.\"-------
+.\" Here is more portable (though less pretty) code to deal with
+.\" the recursion.
+.\"-------
+.if !"\\$4"" .Xf \\$2 \\$1 "\\$3\\f\\$1\\$4\\*(Xi" "\\$5" "\\$6" "\\$7" "\\$8" "\\$9"
+.if "\\$4"" \\$3\fR\s10
+..
+.TH HISTORY 1 "30 July 1991"
+.SH NAME
+\-, \-\|\-, \-p, \-\|\-p \- shell history programs
+.SH SYNOPSIS
+.B \-
+.RI [ pattern ...]
+.RI [ substitution ...]
+.SH DESCRIPTION
+This set of programs provides a crude history mechanism for the shell
+.IR rc (1).
+It is based on the v8 UNIX programs
+.IR = ,
+.IR == ,
+etc.
+.PP
+The program
+.RI `` \- ''
+runs the shell on the command it is requested to find.
+The program
+.RI `` \-\|\- ''
+edits that command first.
+The programs
+.RI `` \-p ''
+and
+.RI `` \-\|\-p ''
+are similar, except that they print the final command on their standard
+output instead of running the shell.
+.PP
+The commands work by looking for a file
+named by the environment variable
+.Cr $history ,
+and by searching for previous commands in this file.
+Old commands can be edited,
+or simply re-executed according to the rules below:
+.PP
+A command is searched for by examining the lines in
+.Cr $history
+in reverse order.
+Lines which contain a previous invocation of the history
+program itself are ignored.
+If one or more
+.I pattern
+is supplied on the command line,
+then the patterns are used as a means of
+limiting the search.
+Patterns match any substring of a previous command,
+and if more than one pattern is present then all patterns must be
+matched before a command is selected.
+.PP
+Substitutions may also be specified on the command line.
+These have the syntax:
+.Ds
+.Ic old :[:...] new
+.De
+.PP
+(Note that the
+.I old
+pattern is used as a search-limiting pattern also.)
+Substitutions happen from left to right and are repeated according to the
+number of colons specified.
+.PP
+Finally, if the program was invoked as
+.RI `` -- ''
+or
+.RI `` --p '',
+a command may be edited in a crude line-mode fashion.  The line to be
+edited is printed out, and below it the user supplies modifications to
+the command.
+.TP
+.B any character except those below
+Replaces the character above.
+.TP
+.B space or tab
+Skips over the above character(s).
+.TP
+.B #
+Deletes one character.
+.TP
+.B %
+Replaces one character with a space.
+.TP
+.B ^
+Inserts the rest of the typed line just before the character.
+.TP
+.B $
+Deletes the rest of the line from that character on, and replaces
+it with the rest of the typed line.
+.TP
+.B +
+Appends the rest of the typed line.
+.TP
+.B \-
+Backs up to a previous command satisfying the same matching
+constraints.
+.TP
+.B end of line
+If any changes have been made, the command is printed out again for
+further editing.  If no changes have been made, the command is executed
+or printed, and the program exits.
+.TP
+.B end of file
+If an end-of-file is read from the keyboard by the editor,
+it aborts with exit status 1 and does not produce any output.
+.SH EXAMPLES
+The history programs work best when their output is reinterpreted by
+the shell using an
+.Cr eval
+command.
+This can be achieved by writing a shell function to perform the
+reinterpretation:
+.Ds
+.Cr "fn - -- {"
+.Cr "  comm = \`{$0^p $*}"
+.Cr "  if (! ~ $#comm 0) {"
+.Cr "          echo $comm >[1=2]"
+.Cr "          eval $comm"
+.Cr "  }"
+.Cr "}"
+.De
+.PP
+Stuttering the `:' in a substitution allows things like:
+.Ds
+; prog 1 2 3 abc > /very/long/path/abc.out
+etc.
+- prog abc::xyz
+prog 1 2 3 xyz > /very/long/path/xyz.out
+;
+.De
diff --git a/history.c b/history.c
new file mode 100644 (file)
index 0000000..1f22f2e
--- /dev/null
+++ b/history.c
@@ -0,0 +1,347 @@
+/*
+       history.c -- primitive history mechanism
+
+       Paul Haahr & Byron Rakitzis, July 1991.
+
+       This program mimics the att v8 = and == history programs.
+       The edit() algorithm was adapted from a similar program
+       that Boyd Roberts wrote, but otherwise all the code has
+       been written from scratch.
+
+       edit() was subsequently redone by Hugh Redelmeier in order
+       to correctly deal with tab characters in the source line.
+
+       BUGS:
+       There is an implicit assumption that commands are no
+       more than 1k characters long. 
+*/
+
+#include "rc.h"
+
+#include <stdio.h>
+
+static const char id[] = "$Release: @(#)" PACKAGE " " VERSION " " RELDATE " $";
+
+#define CHUNKSIZE 65536
+
+static struct {
+       char *old, *new;
+       int reps;       /* no. of repetitions. i.e. 1 means sub twice. */
+} *replace;
+
+static char **search, *progname, *history;
+static char me;        /* typically ':' or '-' */
+static bool editit = FALSE, printit = FALSE;
+static int nreplace = 0, nsearch = 0;
+static FILE *histfile;
+
+void *ealloc(size_t n) {
+       void *p = (void *) malloc(n);
+       if (p == NULL) {
+               perror("malloc");
+               exit(1);
+       }
+       return p;
+}
+
+void *erealloc(void *p, size_t n) {
+       p = (void *) realloc(p, n);
+       if (p == NULL) {
+               perror("realloc");
+               exit(1);
+       }
+       return p;
+}
+
+static char *newstr() {
+       return ealloc((size_t)1024);
+}
+
+static char *rc_basename(char *s) {
+       char *t = strrchr(s, '/');
+       return (t == NULL) ? s : t + 1;
+}
+
+/* stupid O(n^2) substring matching routine */
+
+static char *isin(char *target, char *pattern) {
+       size_t plen = strlen(pattern);
+       size_t tlen = strlen(target);
+       for (; tlen >= plen; target++, --tlen)
+               if (strncmp(target, pattern, plen) == 0)
+                       return target;
+       return NULL;
+}
+
+/* replace the first match in the string with "new" */
+static char *sub(char *s, char *old, char *new) {
+       char *t, *u;
+
+       t = isin(s, old);
+       if (!t)
+               return s;
+       u = newstr();
+
+       *t = '\0';
+       while (*old != '\0')
+               old++, t++;
+       strcpy(u, s);
+       strcat(u, new);
+       strcat(u, t);
+       return u;
+}
+
+static char *edit(char *s) {
+       char *final, *f, *end;
+       int col;
+       bool ins;
+       
+start:
+       fprintf(stderr, "%s\n", s);     
+       f = final = newstr();
+       end = s + strlen(s);
+       col = 0;
+       ins = FALSE;
+       
+       for (;; col++) {
+               int     c = getchar();
+
+               if (c == me && col == 0) {
+                       int     peekc = getchar();
+                       if (peekc == '\n')
+                               return NULL;
+                       ungetc(peekc, stdin);
+               }
+               if (c == '\n') {
+                       if (col == 0)
+                               return s;
+                       
+                       while (s < end) /* copy remainder of string */
+                               *f++ = *s++;
+                       *f = '\0';
+                       s = final;
+                       goto start;
+               } else if (ins || s>=end) {
+                       /* col need not be accurate -- tabs need not be interpreted */
+                       *f++ = c;
+               } else {
+                       switch (c) {
+                       case '+':
+                               while (s < end)
+                                       *f++ = *s++;
+                               *f = '\0';
+                               continue;
+                       case '%':
+                               c = ' ';
+                               /* FALLTHROUGH */
+                       default:
+                               *f++ = c;
+                               break;  
+                       case EOF:
+                               exit(1);
+                               /* NOTREACHED */
+                       case ' ':
+                               if (*s == '\t') {
+                                       int     oldcol = col;
+
+                                       for (;; col++) {
+                                               int     peekc;
+
+                                               if ((col&07) == 07) {
+                                                       *f++ = '\t';    /* we spaced past a tab */
+                                                       break;
+                                               }
+                                               peekc = getchar();
+                                               if (peekc != ' ') {
+                                                       ungetc(peekc, stdin);
+                                                       if (peekc != '\n') {
+                                                               /* we spaced partially into a tab */
+                                                               do {
+                                                                       *f++ = ' ';
+                                                                       oldcol++;
+                                                               } while (oldcol <= col);
+                                                       }
+                                                       break;
+                                               }
+                                       }
+                               } else {
+                                       *f++ = *s;
+                               }
+                               break;
+                       case '#':
+                               break;
+                       case '$':
+                               end = s;        /* truncate s */
+                               continue;       /* skip incrementing s */
+                       case '^':
+                               ins = TRUE;
+                               continue;       /* skip incrementing s */
+                       case '\t':
+                               for (;; col++) {
+                                       *f = s<end? *s++ : '\t';
+                                       if (*f++ == '\t') {
+                                               col = col | 07; /* advance to before next tabstop */
+                                       }
+                                       if ((col&07) == 07)     /* stop before tabstop */
+                                               break;
+                               }
+                               continue;       /* skip incrementing s */
+                       }
+                       if (s<end && (*s!='\t' || (col&07)==07))
+                               s++;
+               }
+       }
+}
+
+static char *readhistoryfile(char **last) {
+       char *buf;
+       size_t count, size;
+       long nread;
+
+       if ((history = getenv("history")) == NULL) {
+               fprintf(stderr, "$history not set\n");
+               exit(1);
+       }
+       histfile = fopen(history, "r+");
+       if (histfile == NULL) {
+               perror(history);
+               exit(1);
+       }
+
+       size = CHUNKSIZE;
+       buf = ealloc(size);
+       buf[0] = '\0'; count = 1; /* sentinel */
+       while ((nread = fread(buf + count, sizeof (char), size - count, histfile)) > 0) {
+               count += nread;
+               if (size - count == 0)
+                       buf = erealloc(buf, size *= 4);
+       }
+       if (nread == -1) {
+               perror(history);
+               exit(1);
+       }
+       *last = buf + count;
+       return buf;
+}
+
+static char *getcommand(void) {
+       char *s, *t;
+       static char *hist = NULL, *last;
+
+       if (hist == NULL) {
+               hist = readhistoryfile(&last);
+               *--last = '\0';         /* replaces final newline */
+               ++hist; /* start beyond sentinel */
+       }
+
+again: s = last;
+       if (s < hist)
+               return NULL;
+       while (s >= hist && *s != '\n')
+               --s;
+       *s = '\0';
+       last = s++;
+
+       /*
+        * if the command contains the "me" character at the start of the line
+        * or after any of [`{|()@/] then try again
+        */
+
+       for (t = s; *t != '\0'; ++t)
+               if (*t == me) {
+                       char *u = t - 1;
+                       while (u >= s && (*u == ' ' || *u == '\t'))
+                               --u;
+                       if (u < s)
+                               goto again;
+                       switch (*u) {
+                       case '`': case '@':
+                       case '(': case ')':
+                       case '{': case '|':
+                       case '/':
+                               goto again;
+                       default:
+                               break;
+                       }
+               }
+       return s;
+}
+
+int main(int argc, char **argv) {
+       int i;
+       char *s;
+
+       s = progname = rc_basename(argv[0]);
+       me = *s++;
+       if (*s == me) {
+               s++;
+               editit = TRUE;
+       }
+       if (*s == 'p') {
+               s++;
+               printit = TRUE;
+       }
+/* Nahh...
+       if (*s != '\0') {
+               fprintf(stderr, "\"%s\": bad name for history program\n", progname);
+               exit(1);
+       }
+*/
+
+       if (argc > 1) {
+               replace = ealloc((argc - 1) * sizeof *replace);
+               search = ealloc((argc - 1) * sizeof *search);
+       }
+       for (i = 1; i < argc; i++)
+               if ((s = strchr(argv[i], ':')) == NULL)
+                       search[nsearch++] = argv[i];
+               else {
+                       *(char *)s = '\0';      /* do we confuse ps too much? */
+                       replace[nreplace].reps = 0;
+                       while(*(++s) == ':') {
+                             replace[nreplace].reps++;
+                       }
+                       replace[nreplace].old = argv[i];
+                       replace[nreplace].new = s;
+                       nreplace++;
+               }
+
+next:  s = getcommand();
+       if (s == NULL) {
+               fprintf(stderr, "command not matched\n");
+               return 1;
+       }
+       for (i = 0; i < nsearch; i++)
+               if (!isin(s, search[i]))
+                       goto next;
+       for (i = 0; i < nreplace; i++)
+               if (!isin(s, replace[i].old))
+                       goto next;
+               else {
+                       int j;
+                       for (j = 0; j <= replace[i].reps; j++)
+                             s = sub(s, replace[i].old, replace[i].new);
+               }
+       if (editit) {
+               s = edit(s);
+               if (s == NULL)
+                       goto next;
+       }
+       fseek(histfile, 0, 2); /* 2 == end of file. i.e., append command to $history */
+       fprintf(histfile, "%s\n", s);
+       fclose(histfile);
+       if (printit)
+               printf("%s\n", s);
+       else {
+               char *shell = getenv("SHELL");
+
+               if (!editit)
+                       fprintf(stderr, "%s\n", s);
+               if (shell == NULL)
+                       shell = "/bin/sh";
+               execl(shell, rc_basename(shell), "-c", s, NULL);
+               perror(shell);
+               exit(1);
+       }
+       return 0;
+}
diff --git a/input.c b/input.c
new file mode 100644 (file)
index 0000000..5737375
--- /dev/null
+++ b/input.c
@@ -0,0 +1,357 @@
+/* input.c: i/o routines for files and pseudo-files (strings) */
+
+#include "rc.h"
+
+#include <errno.h>
+
+#include "edit.h"
+#include "input.h"
+#include "jbwrap.h"
+
+/* How many characters can we unget? */
+enum { UNGETSIZE = 2 };
+
+typedef enum inputtype {
+       iFd, iString, iEdit
+} inputtype;
+
+typedef struct Input {
+       bool saved;
+       inputtype t;
+       int fd, index, read, ungetcount, lineno, last;
+       char *ibuf;
+       void *cookie;
+       int ungetbuf[UNGETSIZE];
+       int (*gchar)(void);
+} Input;
+
+#define BUFSIZE ((size_t) 256)
+
+static char *inbuf;
+static size_t istacksize, chars_out, chars_in;
+static bool save_lineno = TRUE;
+static Input *istack, *itop;
+
+int lastchar;
+
+static char *prompt, *prompt2;
+
+extern void ugchar(int c) {
+       assert(istack->ungetcount < UNGETSIZE);
+       istack->ungetbuf[istack->ungetcount++] = c;
+}
+
+extern int gchar() {
+       int c;
+
+       if (istack->ungetcount)
+               return lastchar = istack->ungetbuf[--istack->ungetcount];
+
+       while ((c = (*istack->gchar)()) == '\0')
+               pr_error("warning: null character ignored", 0);
+
+       return c;
+}
+
+
+/* get the next character from a string. */
+
+static int stringgchar() {
+       return lastchar = (inbuf[chars_out] == '\0' ? EOF : inbuf[chars_out++]);
+}
+
+
+/* write last command out to a file if interactive && $history is set */
+
+static void history() {
+       List *hist;
+       size_t a;
+
+       if (!interactive || (hist = varlookup("history")) == NULL)
+               return;
+
+       for (a = 0; a < chars_in; a++) {
+               char c = inbuf[a];
+
+               /* skip empty lines and comments */
+               if (c == '#' || c == '\n')
+                       break;
+
+               /* line matches [ \t]*[^#\n] so it's ok to write out */
+               if (c != ' ' && c != '\t') {
+                       char *name = hist->w;
+                       int fd = rc_open(name, rAppend);
+                       if (fd < 0)
+                               uerror(name);
+                       else {
+                               writeall(fd, inbuf, chars_in);
+                               close(fd);
+                       }
+                       break;
+               }
+       }
+}
+
+
+/* read a character from a file descriptor */
+
+static int fdgchar() {
+       if (chars_out >= chars_in) { /* replenish empty buffer */
+               ssize_t r;
+               do {
+                       r = rc_read(istack->fd, inbuf, BUFSIZE);
+                       sigchk();
+                       if (r == -1)
+                               switch (errno) {
+                               case EAGAIN:
+                                       if (!makeblocking(istack->fd))
+                                               panic("not O_NONBLOCK");
+                                       errno = EINTR;
+                                       break;
+                               case EIO:
+                                       if (makesamepgrp(istack->fd))
+                                               errno = EINTR;
+                                       else
+                                               errno = EIO;
+                                       break;
+                               }
+               } while (r < 0 && errno == EINTR);
+               if (r < 0) {
+                       uerror("read");
+                       rc_raise(eError);
+               }
+               chars_in = (size_t) r;
+               if (chars_in == 0)
+                       return lastchar = EOF;
+               chars_out = 0;
+               if (dashvee)
+                       writeall(2, inbuf, chars_in);
+               history();
+       }
+
+       return lastchar = inbuf[chars_out++];
+}
+
+/* read a character from a line-editing file descriptor */
+
+static int editgchar() {
+       if (chars_out >= chars_in) { /* replenish empty buffer */
+               edit_free(istack->cookie);
+               inbuf = edit_alloc(istack->cookie, &chars_in);
+               if (inbuf == NULL) {
+                       chars_in = 0;
+                       fprint(2, "exit\n");
+                       return lastchar = EOF;
+               }
+
+               chars_out = 0;
+               if (dashvee)
+                       writeall(2, inbuf, chars_in);
+               history();
+       }
+
+       return lastchar = inbuf[chars_out++];
+}
+
+void termchange(void) {
+       if (istack->t == iEdit)
+               edit_reset(istack->cookie);
+}
+
+
+/* set up the input stack, and put a "dead" input at the bottom, so that yyparse will always read eof */
+
+extern void initinput() {
+       istack = itop = ealloc(istacksize = 256 * sizeof (Input));
+       istack->ungetcount = 0;
+       ugchar(EOF);
+}
+
+/* push an input source onto the stack. set up a new input buffer, and set gchar() */
+
+static void pushcommon() {
+       size_t idiff;
+       istack->index = chars_out;
+       istack->read = chars_in;
+       istack->ibuf = inbuf;
+       istack->lineno = lineno;
+       istack->saved = save_lineno;
+       istack->last = lastchar;
+       istack++;
+       idiff = istack - itop;
+       if (idiff >= istacksize / sizeof (Input)) {
+               itop = erealloc(itop, istacksize *= 2);
+               istack = itop + idiff;
+       }
+       chars_out = 0;
+       chars_in = 0;
+       istack->ungetcount = 0;
+}
+
+extern void pushfd(int fd) {
+       pushcommon();
+       save_lineno = TRUE;
+       istack->fd = fd;
+       lineno = 1;
+       if (editing && interactive && isatty(fd)) {
+               istack->t = iEdit;
+               istack->gchar = editgchar;
+               istack->cookie = edit_begin(fd);
+       } else {
+               istack->t = iFd;
+               istack->gchar = fdgchar;
+               inbuf = ealloc(BUFSIZE);
+       }
+}
+
+extern void pushstring(char **a, bool save) {
+       pushcommon();
+       istack->t = iString;
+       save_lineno = save;
+       inbuf = mprint("%A", a);
+       istack->gchar = stringgchar;
+       if (save_lineno)
+               lineno = 1;
+       else
+               --lineno;
+}
+
+
+/* remove an input source from the stack. restore associated variables etc. */
+
+extern void popinput() {
+       if (istack->t == iEdit)
+               edit_end(istack->cookie);
+       if (istack->t == iFd || istack->t == iEdit)
+               close(istack->fd);
+       efree(inbuf);
+       --istack;
+       lastchar = istack->last;
+       inbuf = istack->ibuf;
+       chars_out = istack->index;
+       chars_in = istack->read;
+       if (save_lineno)
+               lineno = istack->lineno;
+       else
+               lineno++;
+       save_lineno = istack->saved;
+}
+
+
+/* flush input characters up to newline. Used by scanerror() */
+
+extern void skiptonl() {
+       int c;
+       if (lastchar == '\n' || lastchar == EOF)
+               return;
+       while ((c = gchar()) != '\n' && c != EOF)
+               ; /* skip to newline */
+       if (c == EOF)
+               ugchar(c);
+}
+
+
+/* the wrapper loop in rc: prompt for commands until EOF, calling yyparse and walk() */
+
+extern Node *doit(bool clobberexecit) {
+       bool eof;
+       bool execit;
+       Jbwrap j;
+       Estack e1;
+       Edata jerror;
+
+       if (dashen)
+               clobberexecit = FALSE;
+       execit = clobberexecit;
+       sigsetjmp(j.j, 1);
+       jerror.jb = &j;
+       except(eError, jerror, &e1);
+       for (eof = FALSE; !eof;) {
+               Edata block;
+               Estack e2;
+
+               block.b = newblock();
+               except(eArena, block, &e2);
+               sigchk();
+
+               if (interactive) {
+                       List *s;
+                       if (!dashen && fnlookup("prompt") != NULL) {
+                               static bool died = FALSE;
+                               static char *arglist[] = { "prompt", NULL };
+
+                               if (!died) {
+                                       died = TRUE;
+                                       funcall(arglist);
+                               }
+                               died = FALSE;
+                       }
+                       s = varlookup("prompt");
+                       if (s != NULL) {
+                               prompt = s->w;
+                               if (s->n != NULL)
+                                       prompt2 = s->n->w;
+                               else
+                                       prompt2 = "";
+                       } else {
+                               prompt = prompt2 = "";
+                       }
+                       if (istack->t == iFd)
+                               fprint(2, "%s", prompt);
+                       else if (istack->t == iEdit)
+                               edit_prompt(istack->cookie, prompt);
+               }
+               inityy();
+               if (yyparse() == 1 && execit)
+                       rc_raise(eError);
+               eof = (lastchar == EOF); /* "lastchar" can be clobbered during a walk() */
+               if (parsetree != NULL) {
+                       if (execit)
+                               walk(parsetree, TRUE);
+                       else if (dashex && dashen)
+                               fprint(2, "%T\n", parsetree);
+               }
+               unexcept(); /* eArena */
+       }
+       popinput();
+       unexcept(); /* eError */
+       return parsetree;
+}
+
+/* parse a function imported from the environment */
+
+extern Node *parseline(char *extdef) {
+       bool i = interactive;
+       char *in[2];
+       Node *fun;
+       in[0] = extdef;
+       in[1] = NULL;
+       interactive = FALSE;
+       pushstring(in, TRUE);
+       fun = doit(FALSE);
+       interactive = i;
+       return fun;
+}
+
+/* close file descriptors after a fork() */
+
+extern void closefds() {
+       Input *i;
+       for (i = istack; i != itop; --i)        /* close open scripts */
+               if (i->t == iFd && i->fd > 2) {
+                       close(i->fd);
+                       i->fd = -1;
+               }
+}
+
+/* print (or set) prompt(2) */
+
+extern void nextline() {
+       lineno++;
+       if (interactive) {
+               if (istack->t == iFd)
+                       fprint(2, "%s", prompt2);
+               else if (istack->t == iEdit)
+                       edit_prompt(istack->cookie, prompt2);
+       }
+}
diff --git a/input.h b/input.h
new file mode 100644 (file)
index 0000000..87db27b
--- /dev/null
+++ b/input.h
@@ -0,0 +1,35 @@
+/* initialize the input stack */
+extern void initinput(void);
+
+/* push an input onto the stack */
+extern void pushfd(int);
+/* the Boolean argument affects line number reporting */
+extern void pushstring(char **, bool);
+
+/* pop the stack */
+extern void popinput(void);
+
+/* get / unget the next character */
+extern int gchar(void);
+extern void ugchar(int);
+
+/* $TERM or $TERMCAP has changed */
+extern void termchange(void);
+
+/* parse a function from the environment */
+extern Node *parseline(char *);
+
+/* main parsing loop; Boolean says whether to exec also */
+extern Node *doit(bool);
+
+/* error recovery: skip to the next newline */
+extern void skiptonl(void);
+
+/* prepare for next line of input */
+extern void nextline(void);
+
+/* close all file descriptors on the stack */
+extern void closefds(void);
+
+/* the last character read */
+extern int lastchar;
diff --git a/install-sh b/install-sh
new file mode 100755 (executable)
index 0000000..377bb86
--- /dev/null
@@ -0,0 +1,527 @@
+#!/bin/sh
+# install - install a program, script, or datafile
+
+scriptversion=2011-11-20.07; # UTC
+
+# This originates from X11R5 (mit/util/scripts/install.sh), which was
+# later released in X11R6 (xc/config/util/install.sh) with the
+# following copyright and license.
+#
+# Copyright (C) 1994 X Consortium
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to
+# deal in the Software without restriction, including without limitation the
+# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+# sell copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
+# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
+# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+# Except as contained in this notice, the name of the X Consortium shall not
+# be used in advertising or otherwise to promote the sale, use or other deal-
+# ings in this Software without prior written authorization from the X Consor-
+# tium.
+#
+#
+# FSF changes to this file are in the public domain.
+#
+# Calling this script install-sh is preferred over install.sh, to prevent
+# 'make' implicit rules from creating a file called install from it
+# when there is no Makefile.
+#
+# This script is compatible with the BSD install script, but was written
+# from scratch.
+
+nl='
+'
+IFS=" ""       $nl"
+
+# set DOITPROG to echo to test this script
+
+# Don't use :- since 4.3BSD and earlier shells don't like it.
+doit=${DOITPROG-}
+if test -z "$doit"; then
+  doit_exec=exec
+else
+  doit_exec=$doit
+fi
+
+# Put in absolute file names if you don't have them in your path;
+# or use environment vars.
+
+chgrpprog=${CHGRPPROG-chgrp}
+chmodprog=${CHMODPROG-chmod}
+chownprog=${CHOWNPROG-chown}
+cmpprog=${CMPPROG-cmp}
+cpprog=${CPPROG-cp}
+mkdirprog=${MKDIRPROG-mkdir}
+mvprog=${MVPROG-mv}
+rmprog=${RMPROG-rm}
+stripprog=${STRIPPROG-strip}
+
+posix_glob='?'
+initialize_posix_glob='
+  test "$posix_glob" != "?" || {
+    if (set -f) 2>/dev/null; then
+      posix_glob=
+    else
+      posix_glob=:
+    fi
+  }
+'
+
+posix_mkdir=
+
+# Desired mode of installed file.
+mode=0755
+
+chgrpcmd=
+chmodcmd=$chmodprog
+chowncmd=
+mvcmd=$mvprog
+rmcmd="$rmprog -f"
+stripcmd=
+
+src=
+dst=
+dir_arg=
+dst_arg=
+
+copy_on_change=false
+no_target_directory=
+
+usage="\
+Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE
+   or: $0 [OPTION]... SRCFILES... DIRECTORY
+   or: $0 [OPTION]... -t DIRECTORY SRCFILES...
+   or: $0 [OPTION]... -d DIRECTORIES...
+
+In the 1st form, copy SRCFILE to DSTFILE.
+In the 2nd and 3rd, copy all SRCFILES to DIRECTORY.
+In the 4th, create DIRECTORIES.
+
+Options:
+     --help     display this help and exit.
+     --version  display version info and exit.
+
+  -c            (ignored)
+  -C            install only if different (preserve the last data modification time)
+  -d            create directories instead of installing files.
+  -g GROUP      $chgrpprog installed files to GROUP.
+  -m MODE       $chmodprog installed files to MODE.
+  -o USER       $chownprog installed files to USER.
+  -s            $stripprog installed files.
+  -t DIRECTORY  install into DIRECTORY.
+  -T            report an error if DSTFILE is a directory.
+
+Environment variables override the default commands:
+  CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG
+  RMPROG STRIPPROG
+"
+
+while test $# -ne 0; do
+  case $1 in
+    -c) ;;
+
+    -C) copy_on_change=true;;
+
+    -d) dir_arg=true;;
+
+    -g) chgrpcmd="$chgrpprog $2"
+       shift;;
+
+    --help) echo "$usage"; exit $?;;
+
+    -m) mode=$2
+       case $mode in
+         *' '* | *'    '* | *'
+'*       | *'*'* | *'?'* | *'['*)
+           echo "$0: invalid mode: $mode" >&2
+           exit 1;;
+       esac
+       shift;;
+
+    -o) chowncmd="$chownprog $2"
+       shift;;
+
+    -s) stripcmd=$stripprog;;
+
+    -t) dst_arg=$2
+       # Protect names problematic for 'test' and other utilities.
+       case $dst_arg in
+         -* | [=\(\)!]) dst_arg=./$dst_arg;;
+       esac
+       shift;;
+
+    -T) no_target_directory=true;;
+
+    --version) echo "$0 $scriptversion"; exit $?;;
+
+    --)        shift
+       break;;
+
+    -*)        echo "$0: invalid option: $1" >&2
+       exit 1;;
+
+    *)  break;;
+  esac
+  shift
+done
+
+if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then
+  # When -d is used, all remaining arguments are directories to create.
+  # When -t is used, the destination is already specified.
+  # Otherwise, the last argument is the destination.  Remove it from $@.
+  for arg
+  do
+    if test -n "$dst_arg"; then
+      # $@ is not empty: it contains at least $arg.
+      set fnord "$@" "$dst_arg"
+      shift # fnord
+    fi
+    shift # arg
+    dst_arg=$arg
+    # Protect names problematic for 'test' and other utilities.
+    case $dst_arg in
+      -* | [=\(\)!]) dst_arg=./$dst_arg;;
+    esac
+  done
+fi
+
+if test $# -eq 0; then
+  if test -z "$dir_arg"; then
+    echo "$0: no input file specified." >&2
+    exit 1
+  fi
+  # It's OK to call 'install-sh -d' without argument.
+  # This can happen when creating conditional directories.
+  exit 0
+fi
+
+if test -z "$dir_arg"; then
+  do_exit='(exit $ret); exit $ret'
+  trap "ret=129; $do_exit" 1
+  trap "ret=130; $do_exit" 2
+  trap "ret=141; $do_exit" 13
+  trap "ret=143; $do_exit" 15
+
+  # Set umask so as not to create temps with too-generous modes.
+  # However, 'strip' requires both read and write access to temps.
+  case $mode in
+    # Optimize common cases.
+    *644) cp_umask=133;;
+    *755) cp_umask=22;;
+
+    *[0-7])
+      if test -z "$stripcmd"; then
+       u_plus_rw=
+      else
+       u_plus_rw='% 200'
+      fi
+      cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;;
+    *)
+      if test -z "$stripcmd"; then
+       u_plus_rw=
+      else
+       u_plus_rw=,u+rw
+      fi
+      cp_umask=$mode$u_plus_rw;;
+  esac
+fi
+
+for src
+do
+  # Protect names problematic for 'test' and other utilities.
+  case $src in
+    -* | [=\(\)!]) src=./$src;;
+  esac
+
+  if test -n "$dir_arg"; then
+    dst=$src
+    dstdir=$dst
+    test -d "$dstdir"
+    dstdir_status=$?
+  else
+
+    # Waiting for this to be detected by the "$cpprog $src $dsttmp" command
+    # might cause directories to be created, which would be especially bad
+    # if $src (and thus $dsttmp) contains '*'.
+    if test ! -f "$src" && test ! -d "$src"; then
+      echo "$0: $src does not exist." >&2
+      exit 1
+    fi
+
+    if test -z "$dst_arg"; then
+      echo "$0: no destination specified." >&2
+      exit 1
+    fi
+    dst=$dst_arg
+
+    # If destination is a directory, append the input filename; won't work
+    # if double slashes aren't ignored.
+    if test -d "$dst"; then
+      if test -n "$no_target_directory"; then
+       echo "$0: $dst_arg: Is a directory" >&2
+       exit 1
+      fi
+      dstdir=$dst
+      dst=$dstdir/`basename "$src"`
+      dstdir_status=0
+    else
+      # Prefer dirname, but fall back on a substitute if dirname fails.
+      dstdir=`
+       (dirname "$dst") 2>/dev/null ||
+       expr X"$dst" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+            X"$dst" : 'X\(//\)[^/]' \| \
+            X"$dst" : 'X\(//\)$' \| \
+            X"$dst" : 'X\(/\)' \| . 2>/dev/null ||
+       echo X"$dst" |
+           sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+                  s//\1/
+                  q
+                }
+                /^X\(\/\/\)[^/].*/{
+                  s//\1/
+                  q
+                }
+                /^X\(\/\/\)$/{
+                  s//\1/
+                  q
+                }
+                /^X\(\/\).*/{
+                  s//\1/
+                  q
+                }
+                s/.*/./; q'
+      `
+
+      test -d "$dstdir"
+      dstdir_status=$?
+    fi
+  fi
+
+  obsolete_mkdir_used=false
+
+  if test $dstdir_status != 0; then
+    case $posix_mkdir in
+      '')
+       # Create intermediate dirs using mode 755 as modified by the umask.
+       # This is like FreeBSD 'install' as of 1997-10-28.
+       umask=`umask`
+       case $stripcmd.$umask in
+         # Optimize common cases.
+         *[2367][2367]) mkdir_umask=$umask;;
+         .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;;
+
+         *[0-7])
+           mkdir_umask=`expr $umask + 22 \
+             - $umask % 100 % 40 + $umask % 20 \
+             - $umask % 10 % 4 + $umask % 2
+           `;;
+         *) mkdir_umask=$umask,go-w;;
+       esac
+
+       # With -d, create the new directory with the user-specified mode.
+       # Otherwise, rely on $mkdir_umask.
+       if test -n "$dir_arg"; then
+         mkdir_mode=-m$mode
+       else
+         mkdir_mode=
+       fi
+
+       posix_mkdir=false
+       case $umask in
+         *[123567][0-7][0-7])
+           # POSIX mkdir -p sets u+wx bits regardless of umask, which
+           # is incompatible with FreeBSD 'install' when (umask & 300) != 0.
+           ;;
+         *)
+           tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$
+           trap 'ret=$?; rmdir "$tmpdir/d" "$tmpdir" 2>/dev/null; exit $ret' 0
+
+           if (umask $mkdir_umask &&
+               exec $mkdirprog $mkdir_mode -p -- "$tmpdir/d") >/dev/null 2>&1
+           then
+             if test -z "$dir_arg" || {
+                  # Check for POSIX incompatibilities with -m.
+                  # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or
+                  # other-writable bit of parent directory when it shouldn't.
+                  # FreeBSD 6.1 mkdir -m -p sets mode of existing directory.
+                  ls_ld_tmpdir=`ls -ld "$tmpdir"`
+                  case $ls_ld_tmpdir in
+                    d????-?r-*) different_mode=700;;
+                    d????-?--*) different_mode=755;;
+                    *) false;;
+                  esac &&
+                  $mkdirprog -m$different_mode -p -- "$tmpdir" && {
+                    ls_ld_tmpdir_1=`ls -ld "$tmpdir"`
+                    test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1"
+                  }
+                }
+             then posix_mkdir=:
+             fi
+             rmdir "$tmpdir/d" "$tmpdir"
+           else
+             # Remove any dirs left behind by ancient mkdir implementations.
+             rmdir ./$mkdir_mode ./-p ./-- 2>/dev/null
+           fi
+           trap '' 0;;
+       esac;;
+    esac
+
+    if
+      $posix_mkdir && (
+       umask $mkdir_umask &&
+       $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir"
+      )
+    then :
+    else
+
+      # The umask is ridiculous, or mkdir does not conform to POSIX,
+      # or it failed possibly due to a race condition.  Create the
+      # directory the slow way, step by step, checking for races as we go.
+
+      case $dstdir in
+       /*) prefix='/';;
+       [-=\(\)!]*) prefix='./';;
+       *)  prefix='';;
+      esac
+
+      eval "$initialize_posix_glob"
+
+      oIFS=$IFS
+      IFS=/
+      $posix_glob set -f
+      set fnord $dstdir
+      shift
+      $posix_glob set +f
+      IFS=$oIFS
+
+      prefixes=
+
+      for d
+      do
+       test X"$d" = X && continue
+
+       prefix=$prefix$d
+       if test -d "$prefix"; then
+         prefixes=
+       else
+         if $posix_mkdir; then
+           (umask=$mkdir_umask &&
+            $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break
+           # Don't fail if two instances are running concurrently.
+           test -d "$prefix" || exit 1
+         else
+           case $prefix in
+             *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;;
+             *) qprefix=$prefix;;
+           esac
+           prefixes="$prefixes '$qprefix'"
+         fi
+       fi
+       prefix=$prefix/
+      done
+
+      if test -n "$prefixes"; then
+       # Don't fail if two instances are running concurrently.
+       (umask $mkdir_umask &&
+        eval "\$doit_exec \$mkdirprog $prefixes") ||
+         test -d "$dstdir" || exit 1
+       obsolete_mkdir_used=true
+      fi
+    fi
+  fi
+
+  if test -n "$dir_arg"; then
+    { test -z "$chowncmd" || $doit $chowncmd "$dst"; } &&
+    { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } &&
+    { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false ||
+      test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1
+  else
+
+    # Make a couple of temp file names in the proper directory.
+    dsttmp=$dstdir/_inst.$$_
+    rmtmp=$dstdir/_rm.$$_
+
+    # Trap to clean up those temp files at exit.
+    trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0
+
+    # Copy the file name to the temp name.
+    (umask $cp_umask && $doit_exec $cpprog "$src" "$dsttmp") &&
+
+    # and set any options; do chmod last to preserve setuid bits.
+    #
+    # If any of these fail, we abort the whole thing.  If we want to
+    # ignore errors from any of these, just make sure not to ignore
+    # errors from the above "$doit $cpprog $src $dsttmp" command.
+    #
+    { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } &&
+    { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } &&
+    { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } &&
+    { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } &&
+
+    # If -C, don't bother to copy if it wouldn't change the file.
+    if $copy_on_change &&
+       old=`LC_ALL=C ls -dlL "$dst"    2>/dev/null` &&
+       new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` &&
+
+       eval "$initialize_posix_glob" &&
+       $posix_glob set -f &&
+       set X $old && old=:$2:$4:$5:$6 &&
+       set X $new && new=:$2:$4:$5:$6 &&
+       $posix_glob set +f &&
+
+       test "$old" = "$new" &&
+       $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1
+    then
+      rm -f "$dsttmp"
+    else
+      # Rename the file to the real destination.
+      $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null ||
+
+      # The rename failed, perhaps because mv can't rename something else
+      # to itself, or perhaps because mv is so ancient that it does not
+      # support -f.
+      {
+       # Now remove or move aside any old file at destination location.
+       # We try this two ways since rm can't unlink itself on some
+       # systems and the destination file might be busy for other
+       # reasons.  In this case, the final cleanup might fail but the new
+       # file should still install successfully.
+       {
+         test ! -f "$dst" ||
+         $doit $rmcmd -f "$dst" 2>/dev/null ||
+         { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null &&
+           { $doit $rmcmd -f "$rmtmp" 2>/dev/null; :; }
+         } ||
+         { echo "$0: cannot unlink or rename $dst" >&2
+           (exit 1); exit 1
+         }
+       } &&
+
+       # Now rename the file to the real destination.
+       $doit $mvcmd "$dsttmp" "$dst"
+      }
+    fi || exit 1
+
+    trap '' 0
+  fi
+done
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/jbwrap.h b/jbwrap.h
new file mode 100644 (file)
index 0000000..4b3ea86
--- /dev/null
+++ b/jbwrap.h
@@ -0,0 +1,23 @@
+#include <setjmp.h>
+
+/* If we have POSIX sigjmp_buf and friends, use them.  If we don't, just
+use a jmp_buf.  This probably fails on a traditional SysV machine, where
+jmp_bufs don't preserve signal masks.  I'm not worrying about this till
+someone reports it as a bug :-). */
+
+#if HAVE_SIGSETJMP
+#else
+#define sigjmp_buf jmp_buf
+#define sigsetjmp(x,y) setjmp(x)
+#define siglongjmp longjmp
+#endif /* HAVE_SIGSETJMP */
+
+
+/* Certain braindamaged environments don't define jmp_buf as an array,
+so wrap it in a structure.  Potentially, we could use configure to do
+this only where it needs to be done, but the effort is probably not
+worth it. */
+
+struct Jbwrap {
+       sigjmp_buf j;
+};
diff --git a/lex.c b/lex.c
new file mode 100644 (file)
index 0000000..92732f8
--- /dev/null
+++ b/lex.c
@@ -0,0 +1,416 @@
+/* lex.c: rc's lexical analyzer */
+
+#include "rc.h"
+
+#include "input.h"
+#include "parse.h"
+
+/*
+       Special characters (i.e., "non-word") in rc:
+               \t \n # ; & | ^ $ = ~ ` ' { } @ ! ( ) < > \
+
+       The lexical analyzer is fairly straightforward. The only really
+       unclean part concerns backslash continuation and "double
+       backslashes". A backslash followed by a newline is treated as a
+       space, otherwise backslash is not a special character (i.e.,
+       it can be part of a word).  This introduces a host of unwanted
+       special cases. In our case, \ cannot be a word character, since
+       we wish to read in all word characters in a tight loop.
+
+       Note: to save the trouble of declaring these arrays with TRUEs
+       and FALSEs, I am assuming that FALSE = 0, TRUE = 1. (and so is
+       it declared in rc.h)
+*/
+
+#define BUFSIZE ((size_t) 1000)        /*      malloc hates power of 2 buffers? */
+#define BUFMAX (8 * BUFSIZE)   /*      How big the buffer can get before we re-allocate the
+                                       space at BUFSIZE again. Premature optimization? Maybe.
+                               */
+
+typedef enum wordstates {
+       NW, RW, KW /* "nonword", "realword", "keyword" */
+} wordstates;
+
+static void getpair(int);
+
+int lineno;
+
+/* lookup table for non-word characters */
+const char nw[] = {
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
+};
+
+/* lookup table for non-word characters in variable names */
+const char dnw[] = {
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1,
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+       1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1
+};
+
+/* lookup table for quotable characters: nw + glob metachars */
+const char q[] = {
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0,
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
+};
+
+static size_t bufsize = BUFSIZE;
+static char *realbuf = NULL;
+static bool newline = FALSE;
+static bool errset = FALSE;
+static bool prerror = FALSE;
+static wordstates w = NW;
+static int fd_left, fd_right;
+
+#define checkfreecaret {if (w != NW) { w = NW; ugchar(c); return '^'; }}
+
+enum filedescriptors {
+       UNSET = -9, CLOSED = -1
+};
+
+/* does this string require quoting? */
+extern bool quotep(char *s, bool dollar) {
+       unsigned char c;
+       const char *meta;
+
+       meta = dollar ? dnw : q;
+       while ((c = *s++))
+               if (meta[c])
+                       return TRUE;
+       return FALSE;
+}
+
+extern int yylex() {
+       static bool dollar = FALSE;
+       bool saw_meta = FALSE;
+       int c;
+       size_t i;                       /* The purpose of all these local assignments is to     */
+       const char *meta;               /* allow optimizing compilers like gcc to load these    */
+       char *buf = realbuf;            /* values into registers. On a sparc this is a          */
+       YYSTYPE *y = &yylval;           /* win, in code size *and* execution time               */
+       if (errset) {
+               errset = FALSE;
+               return '\n';
+       }
+       /* rc variable-names may contain only alnum, '*' and '_', so use dnw if we are scanning one. */
+       meta = (dollar ? dnw : nw);
+       if (newline) {
+               --lineno; /* slight space optimization; nextline() always increments lineno */
+               nextline();
+               newline = FALSE;
+       }
+top:   while ((c = gchar()) == ' ' || c == '\t')
+               w = NW;
+       if (c != '(') dollar = FALSE;
+       if (c == EOF)
+               return END;
+       if (!meta[(unsigned char) c]) { /* it's a word or keyword. */
+               checkfreecaret;
+               w = RW;
+               i = 0;
+       read:   do {
+                       buf[i++] = c;
+                       if (c == '?' || c == '[' || c == '*')
+                               saw_meta = TRUE;
+                       if (i >= bufsize)
+                               buf = realbuf = erealloc(buf, bufsize *= 2);
+               } while ((c = gchar()) != EOF && !meta[(unsigned char) c]);
+               while (c == '\\') {
+                       if ((c = gchar()) == '\n') {
+                               nextline();
+                               c = ' '; /* Pretend a space was read */
+                               break;
+                       } else {
+       bs:                     if (meta != dnw) { /* all words but varnames may have a bslash */
+                                       buf[i++] = '\\';
+                                       if (i >= bufsize)
+                                               buf = realbuf = erealloc(buf, bufsize *= 2);
+                                       if (!meta[(unsigned char) c])
+                                               goto read;
+                               } else {
+                                       ugchar(c);
+                                       c = '\\';
+                                       break;
+                               }
+                       }
+               }
+               ugchar(c);
+               buf[i] = '\0';
+               w = KW;
+               if (i == 2) {
+                       if (*buf == 'i' && buf[1] == 'f') return IF;
+                       if (*buf == 'f' && buf[1] == 'n') return FN;
+                       if (*buf == 'i' && buf[1] == 'n') return IN;
+               }
+               if (streq(buf, "for")) return FOR;
+               if (streq(buf, "else")) return ELSE;
+               if (streq(buf, "switch")) return SWITCH;
+               if (streq(buf, "while")) return WHILE;
+               if (streq(buf, "case")) return CASE;
+               w = RW;
+               y->word.w = ncpy(buf);
+               if (saw_meta) {
+                       char *r, *s;
+
+                       y->word.m = nalloc(strlen(buf) + 1);
+                       for (r = buf, s = y->word.m; *r != '\0'; r++, s++)
+                               *s = (*r == '?' || *r == '[' || *r == '*');
+               } else {
+                       y->word.m = NULL;
+               }
+               y->word.q = FALSE;
+               return WORD;
+       }
+       if (c == '`' || c == '!' || c == '@' || c == '~' || c == '$' || c == '\'') {
+               checkfreecaret;
+               if (c == '!' || c == '@' || c == '~')
+                       w = KW;
+       }
+       switch (c) {
+       case '!':
+               return BANG;
+       case '@':
+               return SUBSHELL;
+       case '~':
+               return TWIDDLE;
+       case '`':
+               c = gchar();
+               if (c == '`')
+                       return BACKBACK;
+               ugchar(c);
+               return '`';
+       case '$':
+               dollar = TRUE;
+               c = gchar();
+               if (c == '#')
+                       return COUNT;
+               if (c == '^' || c == '"')
+                       return FLAT;
+               ugchar(c);
+               return '$';
+       case '\'':
+               w = RW;
+               i = 0;
+               /* double ' to quote it, like this: 'how''s it going?' */
+               while ((c = gchar()) != '\'' || (c = gchar()) == '\'') {
+                       buf[i++] = c;
+                       if (c == '\n')
+                               nextline();
+                       if (c == EOF) {
+                               w = NW;
+                               scanerror("eof in quoted string");
+                               return HUH;
+                       }
+                       if (i >= bufsize)
+                               buf = realbuf = erealloc(buf, bufsize *= 2);
+               }
+               ugchar(c);
+               buf[i] = '\0';
+               y->word.w = ncpy(buf);
+               y->word.m = NULL;
+               y->word.q = TRUE;
+               return WORD;
+       case '\\':
+               if ((c = gchar()) == '\n') {
+                       nextline();
+                       goto top; /* Pretend it was just another space. */
+               }
+               ugchar(c);
+               c = '\\';
+               checkfreecaret;
+               c = gchar();
+               i = 0;
+               goto bs;
+       case '(':
+               if (w == RW) /* SUB's happen only after real words, not keywords, so if () and while () work */
+                       c = SUB;
+               w = NW;
+               return c;
+       case '#':
+               while ((c = gchar()) != '\n') /* skip comment until newline */
+                       if (c == EOF)
+                               return END;
+               /* FALLTHROUGH */
+       case '\n':
+               lineno++;
+               newline = TRUE;
+               /* FALLTHROUGH */
+       case ';':
+       case '^':
+       case ')':
+       case '=':
+       case '{': case '}':
+               w = NW;
+               return c;
+       case '&':
+               w = NW;
+               c = gchar();
+               if (c == '&')
+                       return ANDAND;
+               ugchar(c);
+               return '&';
+       case '|':
+               w = NW;
+               c = gchar();
+               if (c == '|')
+                       return OROR;
+               getpair(c);
+               if (errset)
+                       return HUH;
+               if ((y->pipe.left = fd_left) == UNSET)
+                       y->pipe.left = 1;                               /* default to fd 1 */
+               if ((y->pipe.right = fd_right) == UNSET)
+                       y->pipe.right = 0;                              /* default to fd 0 */
+               if (y->pipe.right == CLOSED) {
+                       scanerror("expected digit after '='");          /* can't close a pipe */
+                       return HUH;
+               }
+               return PIPE;
+       case '>':
+               c = gchar();
+               if (c == '>') {
+                       c = gchar();
+                       y->redir.type = rAppend;
+               } else
+                       y->redir.type = rCreate;
+               y->redir.fd = 1;
+               goto common;
+       case '<':
+               c = gchar();
+               if (c == '<') {
+                       c = gchar();
+                       if (c == '<') {
+                               c = gchar();
+                               y->redir.type = rHerestring;
+                       } else {
+                               y->redir.type = rHeredoc;
+                       }
+               } else
+                       y->redir.type = rFrom;
+               y->redir.fd = 0;
+       common:
+               w = NW;
+               getpair(c);
+               if (errset)
+                       return HUH;
+               if (fd_right == UNSET) { /* redirection, not dup */
+                       if (fd_left != UNSET) {
+                               y->redir.fd = fd_left;
+                               return SREDIR;
+                       }
+                       return (y->redir.type == rFrom || y->redir.type == rCreate) ? REDIR : SREDIR;
+               } else { /* dup; recast yylval */
+                       y->dup.type = y->redir.type;
+                       y->dup.left = fd_left;
+                       y->dup.right = fd_right;
+                       return DUP;
+               }
+       default:
+               w = NW;
+               return c; /* don't know what it is, let yacc barf on it */
+       }
+}
+
+extern void yyerror(const char *s) {
+       char *tok;
+       if (prerror) { /* don't print "syntax error" if there's a more informative scanerror */
+               prerror = FALSE;
+               return;
+       }
+       if (!interactive) {
+               if (w != NW)
+                       tok = realbuf;
+               else if (lastchar == EOF)
+                       tok = "eof";
+               else if (lastchar == '\n')
+                       tok = "end of line";
+               else
+                       tok = nprint((lastchar < 32 || lastchar > 126) ? "(decimal %d)" : "'%c'", lastchar);
+               fprint(2, "rc: line %d: %s near %s\n", lineno - (lastchar == '\n'), s, tok);
+       } else
+               fprint(2, "rc: %s\n", s);
+}
+
+extern void scanerror(char *s) {
+       skiptonl(); /* flush up to newline */
+       yyerror(s);
+       errset = prerror = TRUE;
+}
+
+extern void inityy() {
+       newline = FALSE;
+       w = NW;
+       hq = NULL;
+       /* return memory to the system if the buffer got too large */
+       if (bufsize > BUFMAX && realbuf != NULL) {
+               efree(realbuf);
+               bufsize = BUFSIZE;
+               realbuf = ealloc(bufsize);
+       } else if (realbuf == NULL)
+               realbuf = ealloc(bufsize);
+}
+
+/*
+   Scan in a pair of integers for redirections like >[2=1]. CLOSED represents a closed file
+   descriptor (i.e., >[2=]) and UNSET represents an undesignated file descriptor (e.g.,
+   >[2] is represented as (2,UNSET).
+
+   This function makes use of unsigned compares to make range tests in one compare operation.
+*/
+
+static void getpair(int c) {
+       int n;
+       fd_left = fd_right = UNSET;
+       if (c != '[') {
+               ugchar(c);
+               return;
+       }
+       if ((unsigned int) (n = gchar() - '0') > 9) {
+               scanerror("expected digit after '['");
+               return;
+       }
+       while ((unsigned int) (c = gchar() - '0') <= 9)
+               n = n * 10 + c;
+       fd_left = n;
+       c += '0';
+       switch (c) {
+       default:
+               scanerror("expected '=' or ']' after digit");
+               return;
+       case ']':
+               return;
+       case '=':
+               if ((unsigned int) (n = gchar() - '0') > 9) {
+                       if (n != ']' - '0') {
+                               scanerror("expected digit or ']' after '='");
+                               return;
+                       }
+                       fd_right = CLOSED;
+               } else {
+                       while ((unsigned int) (c = gchar() - '0') <= 9)
+                               n = n * 10 + c;
+                       if (c != ']' - '0') {
+                               scanerror("expected ']' after digit");
+                               return;
+                       }
+                       fd_right = n;
+               }
+       }
+}
diff --git a/list.c b/list.c
new file mode 100644 (file)
index 0000000..fba6f6a
--- /dev/null
+++ b/list.c
@@ -0,0 +1,57 @@
+/* list.c: routines for manipulating the List type */
+
+#include "rc.h"
+
+/*
+   These list routines assign meta values of null to the resulting lists;
+   it is impossible to glob with the value of a variable unless this value
+   is rescanned with eval---therefore it is safe to throw away the meta-ness
+   of the list.
+*/
+
+/* free a list from malloc space */
+
+extern void listfree(List *p) {
+       while (p != NULL) {
+               List *n = p->n;
+               efree(p->w);
+               efree(p);
+               p = n;
+       }
+}
+
+/* Copy list into malloc space (for storing a variable) */
+
+extern List *listcpy(List *s, void *(*alloc)(size_t)) {
+       List *top, *r;
+       for (top = r = NULL; s != NULL; s = s->n) {
+               if (top == NULL)
+                       r = top = (*alloc)(sizeof (List));
+               else
+                       r = r->n = (*alloc)(sizeof (List));
+               r->w = (*alloc)(strlen(s->w) + 1);
+               strcpy(r->w, s->w);
+               r->m = NULL;
+       }
+       if (r != NULL)
+               r->n = NULL;
+       return top;
+}
+
+/* Length of list */
+
+extern size_t listlen(List *s) {
+       size_t size;
+       for (size = 0; s != NULL; s = s->n)
+               size += strlen(s->w) + 1;
+       return size;
+}
+
+/* Number of elements in list */
+
+extern int listnel(List *s) {
+       int nel;
+       for (nel = 0; s != NULL; s = s->n)
+               nel++;
+       return nel;
+}
diff --git a/main.c b/main.c
new file mode 100644 (file)
index 0000000..4da3014
--- /dev/null
+++ b/main.c
@@ -0,0 +1,154 @@
+/* main.c: handles initialization of rc and command line options */
+
+#include "rc.h"
+
+#include <errno.h>
+
+#include "input.h"
+
+bool dashdee, dashee, dashvee, dashex, dasheye,
+       dashen, dashpee, interactive;
+pid_t rc_pid;
+
+static bool dashEYE, dashell, dashoh, dashess;
+
+static void assigndefault(char *,...);
+static void checkfd(int, enum redirtype);
+
+extern int main(int argc, char *argv[], char *envp[]) {
+       char *dashsee[2], *dollarzero, *null[1];
+       int c;
+       initprint();
+       dashsee[0] = dashsee[1] = NULL;
+       dollarzero = argv[0];
+       rc_pid = getpid();
+       dashell = (*argv[0] == '-'); /* Unix tradition */
+       while ((c = rc_getopt(argc, argv, "c:deiIlnopsvx")) != -1)
+               switch (c) {
+               case 'c':
+                       dashsee[0] = rc_optarg;
+                       goto quitopts;
+               case 'd':
+                       dashdee = TRUE;
+                       break;
+               case 'e':
+                       dashee = TRUE;
+                       break;
+               case 'I':
+                       dashEYE = TRUE;
+                       interactive = FALSE;
+                       break;
+               case 'i':
+                       dasheye = interactive = TRUE;
+                       break;
+               case 'l':
+                       dashell = TRUE;
+                       break;
+               case 'n':
+                       dashen = TRUE;
+                       break;
+               case 'o':
+                       dashoh = TRUE;
+                       break;
+               case 'p':
+                       dashpee = TRUE;
+                       break;
+               case 's':
+                       dashess = TRUE;
+                       break;
+               case 'v':
+                       dashvee = TRUE;
+                       break;
+               case 'x':
+                       dashex = TRUE;
+                       break;
+               case '?':
+                       exit(1);
+               }
+quitopts:
+       argv += rc_optind;
+       /* use isatty() iff neither -i nor -I is set, and iff the input is not from a script or -c flags */
+       if (!dasheye && !dashEYE && dashsee[0] == NULL && (dashess || *argv == NULL))
+               interactive = isatty(0);
+       if (!dashoh) {
+               checkfd(0, rFrom);
+               checkfd(1, rCreate);
+               checkfd(2, rCreate);
+       }
+       initsignal();
+       inithash();
+       initparse();
+       assigndefault("ifs", " ", "\t", "\n", (void *)0);
+#ifdef DEFAULTPATH
+       assigndefault("path", DEFAULTPATH, (void *)0);
+#endif
+       assigndefault("pid", nprint("%d", rc_pid), (void *)0);
+       assigndefault("prompt", "; ", "", (void *)0);
+       assigndefault("version", VERSION, "$Release: @(#)" PACKAGE " " VERSION " " RELDATE " $", (void *)0);
+       initenv(envp);
+       initinput();
+       null[0] = NULL;
+       starassign(dollarzero, null, FALSE); /* assign $0 to $* */
+       inithandler();
+
+       if (dashell) {
+               char *rcrc;
+               int fd;
+
+               rcrc = concat(varlookup("home"), word("/.rcrc", NULL))->w;
+               fd = rc_open(rcrc, rFrom);
+               if (fd == -1) {
+                       if (errno != ENOENT)
+                               uerror(rcrc);
+               } else {
+                       bool push_interactive;
+
+                       pushfd(fd);
+                       push_interactive = interactive;
+                       interactive = FALSE;
+                       doit(TRUE);
+                       interactive = push_interactive;
+                       close(fd);
+               }
+       }
+
+       if (dashsee[0] != NULL || dashess) {    /* input from  -c or -s? */
+               if (*argv != NULL)
+                       starassign(dollarzero, argv, FALSE);
+               if (dashess)
+                       pushfd(0);
+               else
+                       pushstring(dashsee, TRUE);
+       } else if (*argv != NULL) {     /* else from a file? */
+               b_dot(--argv);
+               rc_exit(getstatus());
+       } else {                        /* else stdin */
+               pushfd(0);
+       }
+       dasheye = FALSE;
+       doit(TRUE);
+       rc_exit(getstatus());
+       return 0; /* Never really reached. */
+}
+
+static void assigndefault(char *name,...) {
+       va_list ap;
+       List *l;
+       char *v;
+       va_start(ap, name);
+       for (l = NULL; (v = va_arg(ap, char *)) != NULL;)
+               l = append(l, word(v, NULL));
+       varassign(name, l, FALSE);
+       set_exportable(name, FALSE);
+       if (streq(name, "path"))
+               alias(name, l, FALSE);
+       va_end(ap);
+}
+
+/* open an fd on /dev/null if it is inherited closed */
+
+static void checkfd(int fd, enum redirtype r) {
+       int new = rc_open("/dev/null", r);
+       if (new != fd && new != -1)
+               close(new);
+}
diff --git a/make.log b/make.log
new file mode 100644 (file)
index 0000000..95fbe37
--- /dev/null
+++ b/make.log
@@ -0,0 +1,91 @@
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT mksignal.o -MD -MP -MF .deps/mksignal.Tpo -c -o mksignal.o mksignal.c
+mv -f .deps/mksignal.Tpo .deps/mksignal.Po
+gcc  -Wall -g -O2   -o mksignal mksignal.o  
+./mksignal
+make  all-am
+make[1]: Entering directory '/mnt/data/Downloads/rc-1.7.4'
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT builtins.o -MD -MP -MF .deps/builtins.Tpo -c -o builtins.o builtins.c
+mv -f .deps/builtins.Tpo .deps/builtins.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT except.o -MD -MP -MF .deps/except.Tpo -c -o except.o except.c
+mv -f .deps/except.Tpo .deps/except.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT exec.o -MD -MP -MF .deps/exec.Tpo -c -o exec.o exec.c
+mv -f .deps/exec.Tpo .deps/exec.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT fn.o -MD -MP -MF .deps/fn.Tpo -c -o fn.o fn.c
+mv -f .deps/fn.Tpo .deps/fn.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT footobar.o -MD -MP -MF .deps/footobar.Tpo -c -o footobar.o footobar.c
+mv -f .deps/footobar.Tpo .deps/footobar.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT getopt.o -MD -MP -MF .deps/getopt.Tpo -c -o getopt.o getopt.c
+mv -f .deps/getopt.Tpo .deps/getopt.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT glob.o -MD -MP -MF .deps/glob.Tpo -c -o glob.o glob.c
+mv -f .deps/glob.Tpo .deps/glob.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT glom.o -MD -MP -MF .deps/glom.Tpo -c -o glom.o glom.c
+mv -f .deps/glom.Tpo .deps/glom.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT hash.o -MD -MP -MF .deps/hash.Tpo -c -o hash.o hash.c
+mv -f .deps/hash.Tpo .deps/hash.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT heredoc.o -MD -MP -MF .deps/heredoc.Tpo -c -o heredoc.o heredoc.c
+mv -f .deps/heredoc.Tpo .deps/heredoc.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT input.o -MD -MP -MF .deps/input.Tpo -c -o input.o input.c
+mv -f .deps/input.Tpo .deps/input.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT lex.o -MD -MP -MF .deps/lex.Tpo -c -o lex.o lex.c
+mv -f .deps/lex.Tpo .deps/lex.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT list.o -MD -MP -MF .deps/list.Tpo -c -o list.o list.c
+mv -f .deps/list.Tpo .deps/list.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT main.o -MD -MP -MF .deps/main.Tpo -c -o main.o main.c
+mv -f .deps/main.Tpo .deps/main.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT match.o -MD -MP -MF .deps/match.Tpo -c -o match.o match.c
+mv -f .deps/match.Tpo .deps/match.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT nalloc.o -MD -MP -MF .deps/nalloc.Tpo -c -o nalloc.o nalloc.c
+mv -f .deps/nalloc.Tpo .deps/nalloc.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT open.o -MD -MP -MF .deps/open.Tpo -c -o open.o open.c
+mv -f .deps/open.Tpo .deps/open.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT parse.o -MD -MP -MF .deps/parse.Tpo -c -o parse.o parse.c
+mv -f .deps/parse.Tpo .deps/parse.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT print.o -MD -MP -MF .deps/print.Tpo -c -o print.o print.c
+mv -f .deps/print.Tpo .deps/print.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT redir.o -MD -MP -MF .deps/redir.Tpo -c -o redir.o redir.c
+mv -f .deps/redir.Tpo .deps/redir.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT signal.o -MD -MP -MF .deps/signal.Tpo -c -o signal.o signal.c
+mv -f .deps/signal.Tpo .deps/signal.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT mkstatval.o -MD -MP -MF .deps/mkstatval.Tpo -c -o mkstatval.o mkstatval.c
+mv -f .deps/mkstatval.Tpo .deps/mkstatval.Po
+gcc  -Wall -g -O2   -o mkstatval mkstatval.o  
+./mkstatval > statval.h
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT status.o -MD -MP -MF .deps/status.Tpo -c -o status.o status.c
+mv -f .deps/status.Tpo .deps/status.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT tree.o -MD -MP -MF .deps/tree.Tpo -c -o tree.o tree.c
+mv -f .deps/tree.Tpo .deps/tree.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT utils.o -MD -MP -MF .deps/utils.Tpo -c -o utils.o utils.c
+utils.c: In function â€˜panic’:
+utils.c:40:2: warning: ignoring return value of â€˜write’, declared with attribute warn_unused_result [-Wunused-result]
+  write(2, PANICMSG, conststrlen(PANICMSG));
+  ^
+utils.c:41:2: warning: ignoring return value of â€˜write’, declared with attribute warn_unused_result [-Wunused-result]
+  write(2, s, strlen(s));
+  ^
+utils.c:42:2: warning: ignoring return value of â€˜write’, declared with attribute warn_unused_result [-Wunused-result]
+  write(2, "!\n", 2);
+  ^
+mv -f .deps/utils.Tpo .deps/utils.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT var.o -MD -MP -MF .deps/var.Tpo -c -o var.o var.c
+mv -f .deps/var.Tpo .deps/var.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT wait.o -MD -MP -MF .deps/wait.Tpo -c -o wait.o wait.c
+mv -f .deps/wait.Tpo .deps/wait.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT walk.o -MD -MP -MF .deps/walk.Tpo -c -o walk.o walk.c
+mv -f .deps/walk.Tpo .deps/walk.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT which.o -MD -MP -MF .deps/which.Tpo -c -o which.o which.c
+which.c: In function â€˜which’:
+which.c:112:4: warning: ignoring return value of â€˜getgroups’, declared with attribute warn_unused_result [-Wunused-result]
+    getgroups(ngroups, gidset);
+    ^
+mv -f .deps/which.Tpo .deps/which.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT sigmsgs.o -MD -MP -MF .deps/sigmsgs.Tpo -c -o sigmsgs.o sigmsgs.c
+mv -f .deps/sigmsgs.Tpo .deps/sigmsgs.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT edit-null.o -MD -MP -MF .deps/edit-null.Tpo -c -o edit-null.o edit-null.c
+mv -f .deps/edit-null.Tpo .deps/edit-null.Po
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT system.o -MD -MP -MF .deps/system.Tpo -c -o system.o system.c
+mv -f .deps/system.Tpo .deps/system.Po
+gcc  -Wall -g -O2   -o rc builtins.o except.o exec.o fn.o footobar.o getopt.o glob.o glom.o hash.o heredoc.o input.o lex.o list.o main.o match.o nalloc.o open.o parse.o print.o redir.o signal.o status.o tree.o utils.o var.o wait.o walk.o which.o sigmsgs.o  edit-null.o  system.o 
+gcc -DHAVE_CONFIG_H -I.     -Wall -g -O2 -MT tripping.o -MD -MP -MF .deps/tripping.Tpo -c -o tripping.o tripping.c
+mv -f .deps/tripping.Tpo .deps/tripping.Po
+gcc  -Wall -g -O2   -o tripping tripping.o  
+make[1]: Leaving directory '/mnt/data/Downloads/rc-1.7.4'
diff --git a/match.c b/match.c
new file mode 100644 (file)
index 0000000..6f87614
--- /dev/null
+++ b/match.c
@@ -0,0 +1,99 @@
+/* match.c: pattern matching routines */
+
+#include "rc.h"
+
+static int rangematch(char *, char);
+
+enum { RANGE_FAIL = -1, RANGE_ERROR = -2 };
+
+/* match() matches a single pattern against a single string. */
+
+extern bool match(char *p, char *m, char *s) {
+       int i, j;
+       if (m == NULL)
+               return streq(p, s);
+       i = 0;
+       while (1) {
+               if (p[i] == '\0')
+                       return *s == '\0';
+               else if (m[i]) {
+                       switch (p[i++]) {
+                       case '?':
+                               if (*s++ == '\0')
+                                       return FALSE;
+                               break;
+                       case '*':
+                               while (p[i] == '*' && m[i] == 1)        /* collapse multiple stars */
+                                       i++;
+                               if (p[i] == '\0')       /* star at end of pattern? */
+                                       return TRUE;
+                               while (*s != '\0')
+                                       if (match(p + i, m + i, s++))
+                                               return TRUE;
+                               return FALSE;
+                       case '[':
+                               if (*s == '\0')
+                                       return FALSE;
+                               switch (j = rangematch(p + i, *s)) {
+                               default:
+                                       i += j;
+                                       break;
+                               case RANGE_FAIL:
+                                       return FALSE;
+                               case RANGE_ERROR:
+                                       if (*s != '[')
+                                               return FALSE;
+                               }
+                               s++;
+                               break;
+                       default:
+                               panic("bad metacharacter in match");
+                               /* NOTREACHED */
+                               return FALSE; /* hush up gcc -Wall */
+                       }
+               } else if (p[i++] != *s++)
+                       return FALSE;
+       }
+}
+
+/*
+   From the ed(1) man pages (on ranges):
+
+       The `-' is treated as an ordinary character if it occurs first
+       (or first after an initial ^) or last in the string.
+
+       The right square bracket does not terminate the enclosed string
+       if it is the first character (after an initial `^', if any), in
+       the bracketed string.
+
+   rangematch() matches a single character against a class, and returns
+   an integer offset to the end of the range on success, or -1 on
+   failure.
+*/
+
+static int rangematch(char *p, char c) {
+       char *orig = p;
+       bool neg = (*p == '~');
+       bool matched = FALSE;
+       if (neg)
+               p++;
+       if (*p == ']') {
+               p++;
+               matched = (c == ']');
+       }
+       for (; *p != ']'; p++) {
+               if (*p == '\0')
+                       return RANGE_ERROR;     /* bad syntax */
+               if (p[1] == '-' && p[2] != ']') { /* check for [..-..] but ignore [..-] */
+                       if (c >= *p)
+                               matched |= (c <= p[2]);
+                       p += 2;
+               } else {
+                       matched |= (*p == c);
+               }
+       }
+       if (matched ^ neg)
+               return p - orig + 1; /* skip the right-bracket */
+       else
+               return RANGE_FAIL;
+}
diff --git a/missing b/missing
new file mode 100755 (executable)
index 0000000..db98974
--- /dev/null
+++ b/missing
@@ -0,0 +1,215 @@
+#! /bin/sh
+# Common wrapper for a few potentially missing GNU programs.
+
+scriptversion=2013-10-28.13; # UTC
+
+# Copyright (C) 1996-2013 Free Software Foundation, Inc.
+# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
+
+# 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, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+if test $# -eq 0; then
+  echo 1>&2 "Try '$0 --help' for more information"
+  exit 1
+fi
+
+case $1 in
+
+  --is-lightweight)
+    # Used by our autoconf macros to check whether the available missing
+    # script is modern enough.
+    exit 0
+    ;;
+
+  --run)
+    # Back-compat with the calling convention used by older automake.
+    shift
+    ;;
+
+  -h|--h|--he|--hel|--help)
+    echo "\
+$0 [OPTION]... PROGRAM [ARGUMENT]...
+
+Run 'PROGRAM [ARGUMENT]...', returning a proper advice when this fails due
+to PROGRAM being missing or too old.
+
+Options:
+  -h, --help      display this help and exit
+  -v, --version   output version information and exit
+
+Supported PROGRAM values:
+  aclocal   autoconf  autoheader   autom4te  automake  makeinfo
+  bison     yacc      flex         lex       help2man
+
+Version suffixes to PROGRAM as well as the prefixes 'gnu-', 'gnu', and
+'g' are ignored when checking the name.
+
+Send bug reports to <bug-automake@gnu.org>."
+    exit $?
+    ;;
+
+  -v|--v|--ve|--ver|--vers|--versi|--versio|--version)
+    echo "missing $scriptversion (GNU Automake)"
+    exit $?
+    ;;
+
+  -*)
+    echo 1>&2 "$0: unknown '$1' option"
+    echo 1>&2 "Try '$0 --help' for more information"
+    exit 1
+    ;;
+
+esac
+
+# Run the given program, remember its exit status.
+"$@"; st=$?
+
+# If it succeeded, we are done.
+test $st -eq 0 && exit 0
+
+# Also exit now if we it failed (or wasn't found), and '--version' was
+# passed; such an option is passed most likely to detect whether the
+# program is present and works.
+case $2 in --version|--help) exit $st;; esac
+
+# Exit code 63 means version mismatch.  This often happens when the user
+# tries to use an ancient version of a tool on a file that requires a
+# minimum version.
+if test $st -eq 63; then
+  msg="probably too old"
+elif test $st -eq 127; then
+  # Program was missing.
+  msg="missing on your system"
+else
+  # Program was found and executed, but failed.  Give up.
+  exit $st
+fi
+
+perl_URL=http://www.perl.org/
+flex_URL=http://flex.sourceforge.net/
+gnu_software_URL=http://www.gnu.org/software
+
+program_details ()
+{
+  case $1 in
+    aclocal|automake)
+      echo "The '$1' program is part of the GNU Automake package:"
+      echo "<$gnu_software_URL/automake>"
+      echo "It also requires GNU Autoconf, GNU m4 and Perl in order to run:"
+      echo "<$gnu_software_URL/autoconf>"
+      echo "<$gnu_software_URL/m4/>"
+      echo "<$perl_URL>"
+      ;;
+    autoconf|autom4te|autoheader)
+      echo "The '$1' program is part of the GNU Autoconf package:"
+      echo "<$gnu_software_URL/autoconf/>"
+      echo "It also requires GNU m4 and Perl in order to run:"
+      echo "<$gnu_software_URL/m4/>"
+      echo "<$perl_URL>"
+      ;;
+  esac
+}
+
+give_advice ()
+{
+  # Normalize program name to check for.
+  normalized_program=`echo "$1" | sed '
+    s/^gnu-//; t
+    s/^gnu//; t
+    s/^g//; t'`
+
+  printf '%s\n' "'$1' is $msg."
+
+  configure_deps="'configure.ac' or m4 files included by 'configure.ac'"
+  case $normalized_program in
+    autoconf*)
+      echo "You should only need it if you modified 'configure.ac',"
+      echo "or m4 files included by it."
+      program_details 'autoconf'
+      ;;
+    autoheader*)
+      echo "You should only need it if you modified 'acconfig.h' or"
+      echo "$configure_deps."
+      program_details 'autoheader'
+      ;;
+    automake*)
+      echo "You should only need it if you modified 'Makefile.am' or"
+      echo "$configure_deps."
+      program_details 'automake'
+      ;;
+    aclocal*)
+      echo "You should only need it if you modified 'acinclude.m4' or"
+      echo "$configure_deps."
+      program_details 'aclocal'
+      ;;
+   autom4te*)
+      echo "You might have modified some maintainer files that require"
+      echo "the 'autom4te' program to be rebuilt."
+      program_details 'autom4te'
+      ;;
+    bison*|yacc*)
+      echo "You should only need it if you modified a '.y' file."
+      echo "You may want to install the GNU Bison package:"
+      echo "<$gnu_software_URL/bison/>"
+      ;;
+    lex*|flex*)
+      echo "You should only need it if you modified a '.l' file."
+      echo "You may want to install the Fast Lexical Analyzer package:"
+      echo "<$flex_URL>"
+      ;;
+    help2man*)
+      echo "You should only need it if you modified a dependency" \
+           "of a man page."
+      echo "You may want to install the GNU Help2man package:"
+      echo "<$gnu_software_URL/help2man/>"
+    ;;
+    makeinfo*)
+      echo "You should only need it if you modified a '.texi' file, or"
+      echo "any other file indirectly affecting the aspect of the manual."
+      echo "You might want to install the Texinfo package:"
+      echo "<$gnu_software_URL/texinfo/>"
+      echo "The spurious makeinfo call might also be the consequence of"
+      echo "using a buggy 'make' (AIX, DU, IRIX), in which case you might"
+      echo "want to install GNU make:"
+      echo "<$gnu_software_URL/make/>"
+      ;;
+    *)
+      echo "You might have modified some files without having the proper"
+      echo "tools for further handling them.  Check the 'README' file, it"
+      echo "often tells you about the needed prerequisites for installing"
+      echo "this package.  You may also peek at any GNU archive site, in"
+      echo "case some other package contains this missing '$1' program."
+      ;;
+  esac
+}
+
+give_advice "$1" | sed -e '1s/^/WARNING: /' \
+                       -e '2,$s/^/         /' >&2
+
+# Propagate the correct exit status (expected to be 127 for a program
+# not found, 63 for a program that failed due to version mismatch).
+exit $st
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/mkinstalldirs b/mkinstalldirs
new file mode 100755 (executable)
index 0000000..55d537f
--- /dev/null
@@ -0,0 +1,162 @@
+#! /bin/sh
+# mkinstalldirs --- make directory hierarchy
+
+scriptversion=2009-04-28.21; # UTC
+
+# Original author: Noah Friedman <friedman@prep.ai.mit.edu>
+# Created: 1993-05-16
+# Public domain.
+#
+# This file is maintained in Automake, please report
+# bugs to <bug-automake@gnu.org> or send patches to
+# <automake-patches@gnu.org>.
+
+nl='
+'
+IFS=" ""       $nl"
+errstatus=0
+dirmode=
+
+usage="\
+Usage: mkinstalldirs [-h] [--help] [--version] [-m MODE] DIR ...
+
+Create each directory DIR (with mode MODE, if specified), including all
+leading file name components.
+
+Report bugs to <bug-automake@gnu.org>."
+
+# process command line arguments
+while test $# -gt 0 ; do
+  case $1 in
+    -h | --help | --h*)         # -h for help
+      echo "$usage"
+      exit $?
+      ;;
+    -m)                         # -m PERM arg
+      shift
+      test $# -eq 0 && { echo "$usage" 1>&2; exit 1; }
+      dirmode=$1
+      shift
+      ;;
+    --version)
+      echo "$0 $scriptversion"
+      exit $?
+      ;;
+    --)                         # stop option processing
+      shift
+      break
+      ;;
+    -*)                         # unknown option
+      echo "$usage" 1>&2
+      exit 1
+      ;;
+    *)                          # first non-opt arg
+      break
+      ;;
+  esac
+done
+
+for file
+do
+  if test -d "$file"; then
+    shift
+  else
+    break
+  fi
+done
+
+case $# in
+  0) exit 0 ;;
+esac
+
+# Solaris 8's mkdir -p isn't thread-safe.  If you mkdir -p a/b and
+# mkdir -p a/c at the same time, both will detect that a is missing,
+# one will create a, then the other will try to create a and die with
+# a "File exists" error.  This is a problem when calling mkinstalldirs
+# from a parallel make.  We use --version in the probe to restrict
+# ourselves to GNU mkdir, which is thread-safe.
+case $dirmode in
+  '')
+    if mkdir -p --version . >/dev/null 2>&1 && test ! -d ./--version; then
+      echo "mkdir -p -- $*"
+      exec mkdir -p -- "$@"
+    else
+      # On NextStep and OpenStep, the 'mkdir' command does not
+      # recognize any option.  It will interpret all options as
+      # directories to create, and then abort because '.' already
+      # exists.
+      test -d ./-p && rmdir ./-p
+      test -d ./--version && rmdir ./--version
+    fi
+    ;;
+  *)
+    if mkdir -m "$dirmode" -p --version . >/dev/null 2>&1 &&
+       test ! -d ./--version; then
+      echo "mkdir -m $dirmode -p -- $*"
+      exec mkdir -m "$dirmode" -p -- "$@"
+    else
+      # Clean up after NextStep and OpenStep mkdir.
+      for d in ./-m ./-p ./--version "./$dirmode";
+      do
+        test -d $d && rmdir $d
+      done
+    fi
+    ;;
+esac
+
+for file
+do
+  case $file in
+    /*) pathcomp=/ ;;
+    *)  pathcomp= ;;
+  esac
+  oIFS=$IFS
+  IFS=/
+  set fnord $file
+  shift
+  IFS=$oIFS
+
+  for d
+  do
+    test "x$d" = x && continue
+
+    pathcomp=$pathcomp$d
+    case $pathcomp in
+      -*) pathcomp=./$pathcomp ;;
+    esac
+
+    if test ! -d "$pathcomp"; then
+      echo "mkdir $pathcomp"
+
+      mkdir "$pathcomp" || lasterr=$?
+
+      if test ! -d "$pathcomp"; then
+       errstatus=$lasterr
+      else
+       if test ! -z "$dirmode"; then
+         echo "chmod $dirmode $pathcomp"
+         lasterr=
+         chmod "$dirmode" "$pathcomp" || lasterr=$?
+
+         if test ! -z "$lasterr"; then
+           errstatus=$lasterr
+         fi
+       fi
+      fi
+    fi
+
+    pathcomp=$pathcomp/
+  done
+done
+
+exit $errstatus
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/mksignal.c b/mksignal.c
new file mode 100644 (file)
index 0000000..c66ad49
--- /dev/null
@@ -0,0 +1,239 @@
+#include <signal.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#ifdef NSIG
+#define NUMSIG NSIG
+#else
+#define NUMSIG 1
+#endif
+
+struct signaming {
+    int signo;
+    const char *signame;
+    const char *sigmsg;
+};
+
+static struct signaming signamings[] = {
+#ifdef SIGABRT
+    { SIGABRT, "sigabrt",      "abort"},
+#endif
+#ifdef SIGALRM
+    { SIGALRM, "sigalrm",      "alarm clock"},
+#endif
+#ifdef SIGBREAK
+    { SIGBREAK,        "sigbreak",     "break"},
+#endif
+#ifdef SIGBUS
+    { SIGBUS,  "sigbus",       "bus error"},
+#endif
+#ifdef SIGCANCEL
+    { SIGCANCEL,       "sigcancel",    "thread cancellation"},
+#endif
+#ifdef SIGCHLD
+    { SIGCHLD, "sigchld",      "child stop or exit"},
+#endif
+#ifdef SIGCLD
+    { SIGCLD,  "sigcld",       "child stop or exit"},
+#endif
+#ifdef SIGCONT
+    { SIGCONT, "sigcont",      "continue"},
+#endif
+#ifdef SIGDIL
+    { SIGDIL,  "sigdil",       "dil signal"},
+#endif
+#ifdef SIGEMT
+    { SIGEMT,  "sigemt",       "emt instruction"},
+#endif
+#ifdef SIGFPE
+    { SIGFPE,  "sigfpe",       "floating point error"},
+#endif
+#ifdef SIGFREEZE
+    { SIGFREEZE,       "sigfreeze",    "cpr freeze"},
+#endif
+#ifdef SIGHUP
+    { SIGHUP,  "sighup",       "hangup"},
+#endif
+#ifdef SIGILL
+    { SIGILL,  "sigill",       "illegal instruction"},
+#endif
+
+/* We don't want a default message for SIGINT. */
+#ifdef SIGINT
+    { SIGINT,  "sigint",       ""},
+#endif
+
+#ifdef SIGIO
+    { SIGIO,   "sigio",        "socket i/o possible"},
+#endif
+#ifdef SIGIOT
+    { SIGIOT,  "sigiot",       "iot instruction"},
+#endif
+#ifdef SIGKILL
+    { SIGKILL, "sigkill",      "killed"},
+#endif
+#ifdef SIGLOST
+    { SIGLOST, "siglost",      "resource lost"},
+#endif
+#ifdef SIGLWP
+    { SIGLWP,  "siglwp",       "thread library signal"},
+#endif
+
+/* By default, SIGPIPEs are silent. */
+#ifdef SIGPIPE
+    { SIGPIPE, "sigpipe",      ""},
+#endif
+
+#ifdef SIGPOLL
+    { SIGPOLL, "sigpoll",      "pollable event occurred"},
+#endif
+#ifdef SIGPROF
+    { SIGPROF, "sigprof",      "profiling timer alarm"},
+#endif
+#ifdef SIGPWR
+    { SIGPWR,  "sigpwr",       "power-fail restart"},
+#endif
+#ifdef SIGQUIT
+    { SIGQUIT, "sigquit",      "quit"},
+#endif
+#ifdef SIGSEGV
+    { SIGSEGV, "sigsegv",      "segmentation violation"},
+#endif
+#ifdef SIGSTKFLT
+    { SIGSTKFLT,       "sigstkflt",    "stack fault"},
+#endif
+#ifdef SIGSTOP
+    { SIGSTOP, "sigstop",      "stopped by program"},
+#endif
+#ifdef SIGSYS
+    { SIGSYS,  "sigsys",       "invalid argument to system call"},
+#endif
+#ifdef SIGTERM
+    { SIGTERM, "sigterm",      "terminated"},
+#endif
+#ifdef SIGTHAW
+    { SIGTHAW, "sigthaw",      "cpr thaw"},
+#endif
+#ifdef SIGTRAP
+    { SIGTRAP, "sigtrap",      "trace trap"},
+#endif
+#ifdef SIGTSTP
+    { SIGTSTP, "sigtstp",      "stopped"},
+#endif
+#ifdef SIGTTIN
+    { SIGTTIN, "sigttin",      "background tty read"},
+#endif
+#ifdef SIGTTOU
+    { SIGTTOU, "sigttou",      "background tty write"},
+#endif
+#ifdef SIGURG
+    { SIGURG,  "sigurg",       "urgent condition on i/o channel"},
+#endif
+#ifdef SIGUSR1
+    { SIGUSR1, "sigusr1",      "user defined signal 1"},
+#endif
+#ifdef SIGUSR2
+    { SIGUSR2, "sigusr2",      "user defined signal 2"},
+#endif
+#ifdef SIGVTALRM
+    { SIGVTALRM,       "sigvtalrm",    "virtual timer alarm"},
+#endif
+#ifdef SIGWAITING
+    { SIGWAITING,      "sigwaiting",   "lwps blocked"},
+#endif
+#ifdef SIGWINCH
+    { SIGWINCH,        "sigwinch",     "window size change"},
+#endif
+#ifdef SIGWINDOW
+    { SIGWINDOW,       "sigwindow",    "window size change"},
+#endif
+#ifdef SIGXCPU
+    { SIGXCPU, "sigxcpu",      "exceeded cpu time limit"},
+#endif
+#ifdef SIGXFSZ
+    { SIGXFSZ, "sigxfsz",      "exceeded file size limit"},
+#endif
+#ifdef SIGSAK
+    { SIGSAK,  "sigsak",       "secure attention key"},
+#endif
+#ifdef SIGSOUND
+    { SIGSOUND,        "sigsound",     "hft sound sequence completed"},
+#endif
+#ifdef SIGRETRACT
+    { SIGRETRACT,      "sigretract",   "hft monitor mode retracted"},
+#endif
+#ifdef SIGKAP
+    { SIGKAP,  "sigkap",       "keep alive poll"},
+#endif
+#ifdef SIGGRANT
+    { SIGGRANT,        "siggrant",     "hft monitor mode granted"},
+#endif
+#ifdef SIGALRM1
+    { SIGALRM1,        "sigalrm1",     "m:n condition alarm"},
+#endif
+#ifdef SIGVIRT
+    { SIGVIRT, "sigvirt",      "virtual time alarm"},
+#endif
+#ifdef SIGPRE
+    { SIGPRE,  "sigpre",       "programming error"},
+#endif
+#ifdef SIGMIGRATE
+    { SIGMIGRATE,      "sigmigrate",   "migrate process"},
+#endif
+#ifdef SIGDANGER
+    { SIGDANGER,       "sigdanger",    "system crash imminent"},
+#endif
+#ifdef SIGMSG
+    { SIGMSG,  "sigmsg",       "hft input data pending"},
+#endif
+#ifdef SIGINFO
+    { SIGINFO, "siginfo",      "information request"},
+#endif
+    { 0, 0, 0}
+};
+
+static void barf(const char *msg) {
+    fprintf(stderr, "mksignals: %s\n", msg);
+    exit(1);
+}
+
+int main(void) {
+    int maxsig = NUMSIG-1;
+    int s;
+    struct signaming *snp;
+    FILE *outf;
+
+    for (snp = signamings; snp->signo; ++snp)
+       if (snp->signo > maxsig)
+           maxsig = snp->signo;
+
+    outf = fopen("sigmsgs.h", "w");
+    if (!outf) barf("could not open sigmsgs.h for writing");
+    fprintf(outf, "typedef struct {\n");
+    fprintf(outf, "\tchar *name, *msg;\n");
+    fprintf(outf, "} Sigmsgs;\n");
+    fprintf(outf, "extern Sigmsgs signals[];\n");
+    fprintf(outf, "#define NUMOFSIGNALS %d\n", maxsig+1);
+    if (fclose(outf) == EOF)  barf("could not fclose sigmsgs.h after writing");
+
+    outf = fopen("sigmsgs.c", "w");
+    if (!outf) barf("could not open sigmsgs.c for writing");
+    fprintf(outf, "#include \"sigmsgs.h\"\n\n");
+    fprintf(outf, "Sigmsgs signals[] = {\n");
+    fprintf(outf, "\t{\"\",\t\"\"},\n");
+
+    /* yes, we could avoid the quadratic searching with an aux array. fap. */
+    for (s = 1; s <= maxsig; ++s) {
+        for (snp = signamings; snp->signo && snp->signo != s; ++snp)
+           /* */;
+       if (snp->signo)
+           fprintf(outf, "\t{\"%s\",\t\"%s\"},\n",
+                   snp->signame, snp->sigmsg);
+       else
+           fprintf(outf, "\t{\"sigunknown%d\",\t\"unknown signal %d\"},\n",
+                   s, s);
+    }
+    fprintf(outf, "};\n");
+    if (fclose(outf) == EOF) barf("could not fclose sigmsgs.c after writing");
+    return 0;
+}
diff --git a/mkstatval.c b/mkstatval.c
new file mode 100644 (file)
index 0000000..c74ac46
--- /dev/null
@@ -0,0 +1,26 @@
+#include <stdio.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+
+int main(void) {
+       int cstatus, pstatus;
+       pid_t pid;
+       
+       for (cstatus = 0; cstatus < 2; ++cstatus) {
+               switch (pid = fork()) {
+               case -1:
+                       perror("fork");
+                       return 1;
+               case 0:
+                       _exit(cstatus);
+               default:
+                       if (wait(&pstatus) != pid) {
+                               perror("wait");
+                               return 1;
+                       }
+                       printf("#define STATUS%d %d\n", cstatus, pstatus);
+               }
+       }
+       return 0;
+}
diff --git a/nalloc.c b/nalloc.c
new file mode 100644 (file)
index 0000000..0144b48
--- /dev/null
+++ b/nalloc.c
@@ -0,0 +1,139 @@
+/* nalloc.c: a simple single-arena allocator for command-line-lifetime allocation */
+#include "rc.h"
+
+static struct Block {
+       size_t used, size;
+       char *mem;
+       Block *n;
+} *fl, *ul;
+
+/* alignto() works only with power of 2 blocks and assumes 2's complement arithmetic */
+#define alignto(m, n)   ((m + n - 1) & ~(n - 1))
+#define BLOCKSIZE ((size_t) 4096)
+
+/* Allocate a block from the free list or malloc one if none in the fl fit */
+
+static void getblock(size_t n) {
+       Block *r, *p;
+       for (r = fl, p = NULL; r != NULL; p = r, r = r->n)
+               if (n <= r->size)
+                       break;  /* look for a block which fits the request */
+       if (r != NULL) {        /* if one is found, take it off the free list */        
+               if (p != NULL)
+                       p->n = r->n;
+               else
+                       fl = r->n;
+       } else {                /* else allocate a new block */
+               r = enew(Block);
+               r->mem = ealloc(r->size = alignto(n, BLOCKSIZE));
+       }
+       r->used = 0;
+       r->n = ul;
+       ul = r;
+}
+
+/*
+   A fast single-arena allocator. Looks at the current block, and if
+   there is not enough room, it goes to getblock() for more. "ul"
+   stands for "used list", and the head of the list is the current
+   block. "ulp" is a register cache for "ul"; this routine is hacked
+   for speed. (sigh, optimizing RISC compilers still can't cache the
+   address of a global in a register)
+*/
+
+extern void *nalloc(size_t n) {
+       size_t base;
+       Block *ulp;
+        n = alignto(n, sizeof(align_t));
+       ulp = ul;
+       if (ulp != NULL && n + (base = ulp->used) < ulp->size) {
+               ulp->used = base + n;
+               return &ulp->mem[base];
+       } else {
+               getblock(n); 
+               assert(ul->used == 0);
+               (ulp = ul)->used = n;
+               return &ulp->mem[0];
+       }
+}
+
+/*
+   Frees memory from nalloc space by putting it on the free list.
+   Returns free blocks to the system, retaining at least MAXMEM bytes
+   worth of blocks for nalloc.
+*/
+
+#define MAXMEM 500000
+
+extern void nfree() {
+       size_t count;
+       Block *r;
+       if (ul == NULL)
+               return;
+       for (r = ul; r->n != NULL; r = r->n)
+               ;       /* get to end of used list */
+       r->n = fl;      /* tack free list onto it */
+       fl = ul;        /* and make it the free list */
+       ul = NULL;      /* finally, zero out the used list */
+       for (r = fl, count = r->size; r->n != NULL; r = r->n, count += r->size) {
+               if (count >= MAXMEM) {
+                       Block *tmp = r;
+                       r = r->n;
+                       tmp->n = NULL;          /* terminate the free list */
+                       while (r != NULL) {     /* free memory off the tail of the free list */
+                               tmp = r->n;
+                               efree(r->mem);
+                               efree(r);
+                               r = tmp;
+                       }
+               return;
+               }
+       }
+}
+
+/*
+   "Allocates" a new arena by zeroing out the old one. Up to the
+   calling routine to keep the old value of the block around.
+*/
+
+extern Block *newblock() {
+       Block *old = ul;
+       ul = NULL;
+       return old;
+}
+
+/* "Restores" an arena to its saved value. */
+
+extern void restoreblock(Block *old) {
+       nfree();
+       ul = old;
+}
+
+/* generic memory allocation functions */
+
+extern void *ealloc(size_t n) {
+       void *p;
+
+       assert(n);
+       p = malloc(n);
+       if (p == NULL) {
+               uerror("malloc");
+               rc_exit(1);
+       }
+       return p;
+}
+
+extern void *erealloc(void *p, size_t n) {
+       if (p == NULL)          /* erealloc() has POSIX realloc() semantics */
+               return ealloc(n);
+       if ((p = realloc(p, n)) == NULL) {
+               uerror("realloc");
+               rc_exit(1);
+       }
+       return p;
+}
+
+extern void efree(void *p) {
+       if (p != NULL)
+               free(p);
+}
diff --git a/open.c b/open.c
new file mode 100644 (file)
index 0000000..60555b0
--- /dev/null
+++ b/open.c
@@ -0,0 +1,63 @@
+/* open.c: to insulate <fcntl.h> from the rest of rc. */
+
+#include "rc.h"
+#include <fcntl.h>
+
+/*
+   Opens a file with the necessary flags. Assumes the following
+   declaration for redirtype:
+
+       enum redirtype {
+               rFrom, rCreate, rAppend, rHeredoc, rHerestring
+       };
+*/
+
+static const int mode_masks[] = {
+       /* rFrom */     O_RDONLY,
+       /* rCreate */   O_TRUNC | O_CREAT | O_WRONLY,
+       /* rAppend */   O_APPEND | O_CREAT | O_WRONLY
+};
+
+extern int rc_open(const char *name, redirtype m) {
+       if ((unsigned) m >= arraysize(mode_masks))
+               panic("bad mode passed to rc_open");
+       return open(name, mode_masks[m], 0666);
+}
+
+/* make a file descriptor blocking. return value indicates whether
+the desciptor was previously set to non-blocking. */
+
+extern bool makeblocking(int fd) {
+       int flags;
+
+       if ((flags = fcntl(fd, F_GETFL)) == -1) {
+               uerror("fcntl");
+               rc_error(NULL);
+       }
+       if (! (flags & O_NONBLOCK))
+               return FALSE;
+       flags &= ~O_NONBLOCK;
+       if (fcntl(fd, F_SETFL, (long) flags) == -1) {
+               uerror("fcntl");
+               rc_error(NULL);
+       }
+       return TRUE;
+}
+
+/* make a file descriptor the same pgrp as us.  Returns TRUE if
+it changes anything. */
+
+extern bool makesamepgrp(int fd) {
+       pid_t grp;
+
+       grp = getpgrp();
+
+       if (tcgetpgrp(fd) == grp)
+               return FALSE;
+
+       if (tcsetpgrp(fd, grp) < 0) {
+               uerror("tcsetgrp");
+               return FALSE;
+       }
+       return TRUE;
+}
diff --git a/parse.c b/parse.c
new file mode 100644 (file)
index 0000000..1275ab5
--- /dev/null
+++ b/parse.c
@@ -0,0 +1,1117 @@
+#ifndef lint
+static char const 
+yyrcsid[] = "$FreeBSD: src/usr.bin/yacc/skeleton.c,v 1.28 2000/01/17 02:04:06 bde Exp $";
+#endif
+#include "rc.h"
+#include <stdlib.h>
+#define YYBYACC 1
+#define YYMAJOR 1
+#define YYMINOR 9
+#define YYLEX yylex()
+#define YYEMPTY -1
+#define yyclearin (yychar=(YYEMPTY))
+#define yyerrok (yyerrflag=0)
+#define YYRECOVERING() (yyerrflag!=0)
+static int yygrowstack();
+#define YYPREFIX "yy"
+#line 8 "parse.y"
+
+static Node *star, *nolist;
+Node *parsetree;       /* not using yylval because bison declares it as an auto */
+#line 26 "parse.y"
+typedef union {
+       struct Node *node;
+       struct Redir redir;
+       struct Pipe pipe;
+       struct Dup dup;
+       struct Word word;
+       char *keyword;
+} YYSTYPE;
+#line 31 "y.tab.c"
+#define YYERRCODE 256
+#define ANDAND 257
+#define BACKBACK 258
+#define BANG 259
+#define CASE 260
+#define COUNT 261
+#define DUP 262
+#define ELSE 263
+#define END 264
+#define FLAT 265
+#define FN 266
+#define FOR 267
+#define IF 268
+#define IN 269
+#define OROR 270
+#define PIPE 271
+#define REDIR 272
+#define SREDIR 273
+#define SUB 274
+#define SUBSHELL 275
+#define SWITCH 276
+#define TWIDDLE 277
+#define WHILE 278
+#define WORD 279
+#define HUH 280
+const short yylhs[] = {                                        -1,
+    0,    0,   22,   22,    8,    8,   13,   13,    3,    3,
+    9,    9,    4,   15,    2,   11,   11,   16,   16,   16,
+    5,    5,    6,    6,    6,   19,   19,    7,    7,    7,
+    7,    7,    7,    7,    7,    7,    7,    7,    7,    7,
+    7,    7,    7,    7,    7,   24,   24,   18,   18,   18,
+   12,   12,   17,   17,   20,   20,   10,   10,   10,   10,
+   10,   10,   10,   10,   10,   10,   10,    1,    1,    1,
+    1,    1,    1,    1,    1,    1,    1,    1,   21,   21,
+   14,   14,   14,   23,   23,
+};
+const short yylen[] = {                                         2,
+    2,    2,    1,    1,    2,    2,    1,    2,    1,    2,
+    1,    2,    3,    3,    3,    0,    2,    1,    2,    2,
+    3,    3,    1,    2,    2,    1,    4,    0,    1,    2,
+    4,    8,    6,    4,    8,    4,    4,    4,    4,    2,
+    2,    3,    3,    3,    2,    0,    1,    1,    2,    2,
+    1,    3,    1,    1,    1,    3,    2,    5,    2,    2,
+    2,    2,    3,    3,    3,    2,    1,    1,    1,    1,
+    1,    1,    1,    1,    1,    1,    1,    1,    0,    2,
+    0,    2,    2,    0,    2,
+};
+const short yydefred[] = {                                      0,
+    0,    0,    0,    0,   18,    0,   79,    0,    0,    0,
+    0,    0,    0,    0,    0,   67,    0,    0,   81,    0,
+    0,    0,    0,    0,    0,   51,    0,    0,    0,    0,
+    3,    4,    2,   77,   75,   74,   73,   68,   71,   69,
+    0,   78,   72,   76,   70,   54,   53,   55,    0,   47,
+    0,   59,   60,    0,    0,    0,   84,   66,    0,    0,
+    0,    0,    0,   84,    0,    0,    0,   11,    0,    0,
+   62,   61,    0,    0,   30,    0,   84,   84,   84,    5,
+    6,    8,    0,    0,    1,    0,   50,    0,    0,   63,
+   64,    0,   44,    0,    0,    0,    0,    0,    0,    0,
+    0,   79,   13,   12,   10,   65,   82,    0,   17,    0,
+    0,    0,    0,   52,   56,   79,   84,   14,   85,    0,
+    0,   31,   84,    0,    0,    0,    0,    0,   39,    0,
+    0,   84,    0,   58,   84,    0,    0,    0,    0,    0,
+   79,    0,    0,    0,    0,    0,    0,   24,   35,   25,
+   22,   21,
+};
+const short yydgoto[] = {                                      21,
+   46,   22,   66,   23,  142,  143,   67,   68,   69,   47,
+   75,   27,   28,   70,   57,   29,   48,   30,  122,   94,
+   54,   33,   97,   51,
+};
+const short yysindex[] = {                                    874,
+   24, 1001,  -82, 1001,    0, 1001,    0,  -27,  -26,  900,
+ 1001,  -82,  -20,  -82,  -26,    0, 1001, 1134,    0,  900,
+    0, 1134, -203,  -30, 1134,    0,  -55,   24, 1134,  826,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+  -66,    0,    0,    0,    0,    0,    0,    0,  849,    0,
+ 1134,    0,    0,  900, 1001, 1134,    0,    0,  -52,  -52,
+ 1134, 1001, 1001,    0, -212,  -58,  154,    0, 1134,  426,
+    0,    0, -196, 1001,    0, -203,    0,    0,    0,    0,
+    0,    0, 1001, 1001,    0, -196,    0,  -52, 1001,    0,
+    0, -196,    0,  -52,  -38,   36,  502, -196,  -36,  -52,
+  502,    0,    0,    0,    0,    0,    0,  -52,    0,  502,
+  502,  502,  -52,    0,    0,    0,    0,    0,    0,  -97,
+ -234,    0,    0, 1001, -234,  922, -196, -196,    0,  944,
+  502,    0,   -9,    0,    0, -234,  502,  967,  502, -234,
+    0,  967,  -45,  154,  967, -234,  448,    0,    0,    0,
+    0,    0,
+};
+const short yyrindex[] = {                                    134,
+    0,    0,  356,    0,    0,    0,    0,    0,    0,    0,
+    0,  356,    0, 1024,    0,    0,    0,  571,    0,    0,
+    0,  487,  529,   54,  134,    0,   62,    0,  487,  548,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+  487,    0,    0,  712,    0,  142,    0,    0,   14,   38,
+  487,    0,    0,    0,  -10,    0,  -32,    0,  744,    0,
+    0,    0,  749,    0,    0,  529,    0,    0,    0,    0,
+    0,    0,    0,    0,    0,  763,    0,   86,    0,    0,
+    0,  779,    0,  110,    0,    0,  -34,  788,    0,  380,
+  -34,    0,    0,    0,    0,    0,    0,  470,    0,  -34,
+  -34,  -34,  404,    0,    0,    0,    0,    0,    0,  529,
+    6,    0,    0,  724,   30,    0,  805,  813,    0,    0,
+  -34,    0,    0,    0,    0,  119,  -34,  571,  -34,  187,
+    0,  571,    0,  -44,  571,  396,    0,    0,    0,    0,
+    0,    0,
+};
+const short yygindex[] = {                                      0,
+    0,    0,  -23,   12,    0, -104, 1319,    2, -127, 1307,
+    7,    0,   57,    0,   70,  -13,   84,    0,    0,  420,
+  -81,   59,  369,   31,
+};
+#define YYTABLESIZE 1464
+const short yytable[] = {                                      57,
+  119,   25,  117,   28,  123,   83,   28,   81,    9,   76,
+  145,   50,   55,   56,  145,   26,   87,  145,  124,   62,
+  126,   58,   77,   19,   28,   57,   25,   57,   80,   57,
+   57,   71,   96,   32,  130,   78,   79,  148,   84,   34,
+  150,   89,   61,   26,   63,  105,   26,   20,   57,   19,
+   57,   19,   58,   19,   19,   89,   18,   89,    5,  147,
+   90,  102,   76,    7,   26,   93,  103,   34,   74,   11,
+   34,   48,   19,   20,   79,   20,  118,   20,   20,  149,
+   23,   82,  109,   57,   64,   57,   85,   52,   34,   53,
+   28,    0,    9,    0,    0,   49,   20,   48,    0,   48,
+   65,   48,   48,   72,    0,    0,   76,    0,  120,   19,
+    0,    0,   57,  138,   57,    0,    0,    0,    0,   80,
+   48,   49,    0,   49,    0,   49,   49,    0,   33,    0,
+   26,    0,   91,   20,    0,    0,   19,    0,   19,    0,
+    0,    0,    0,   28,   49,   80,    0,   80,    0,   80,
+   80,   28,    0,    0,   34,    0,   33,   48,    0,   33,
+   20,    0,   20,  104,    5,  132,    0,  114,   80,    0,
+    0,   28,  115,    0,   74,   11,    0,   33,    0,   28,
+    0,   49,   28,    0,    0,    0,   48,    0,    0,    0,
+    0,   81,   28,    0,    0,    0,   27,    0,    0,    0,
+   28,    0,    0,    0,    0,   80,    0,    0,    0,    0,
+   49,    0,   80,    0,    0,    0,    0,    0,    0,    0,
+    0,    0,   28,    0,   27,    0,   77,   27,    0,   28,
+  116,    0,   80,    0,   80,   28,   28,    0,    0,   78,
+   79,    0,    0,   33,    0,   27,   57,   57,   57,   57,
+   57,   57,   57,   57,   57,   57,   57,   57,   57,   57,
+   57,   57,   57,    0,   57,   57,   57,   57,   57,   26,
+   19,   19,   19,   19,   19,   19,   19,   19,   19,   19,
+   19,   19,   19,   19,   19,   19,   19,   31,   19,   19,
+   19,   19,   19,   34,   20,   20,   20,   20,   20,   20,
+   20,   20,   20,   20,   20,   20,   20,   20,   20,   20,
+   20,   27,   20,   20,   20,   20,   20,    7,   48,   48,
+   48,   48,   48,   48,   48,   48,   48,   48,   48,   48,
+   48,   48,   48,   48,   48,    0,   48,   48,   48,   48,
+   48,    0,   49,   49,   49,   49,   49,   49,   49,   49,
+   49,   49,   49,   49,   49,   49,   49,   49,   49,    0,
+   49,   49,   49,   49,   49,   46,   80,   80,   80,   80,
+   80,    0,   80,   80,   80,   80,   80,   80,   80,   80,
+   80,   80,   33,    0,   80,   80,   80,   80,   80,   79,
+   28,   46,    0,   46,    0,   46,   46,   28,   28,    0,
+    0,    0,    0,   28,   28,   32,    0,    0,    0,    0,
+   77,   28,   28,   15,   46,   79,    0,   79,    0,   79,
+   79,   49,    0,   78,   79,    0,    0,    0,    0,   59,
+   60,    0,  101,   32,    0,  107,   32,    0,   79,   15,
+    0,   15,    0,   15,   15,  110,  111,  112,    0,   88,
+   27,   46,    0,    0,   32,    0,    0,  151,    0,    0,
+    0,   17,   15,    0,    0,   19,  106,    0,    0,    0,
+    0,    0,    0,    0,   95,   79,    0,    0,   46,   83,
+   46,   99,  100,   17,    0,  131,    0,   19,    0,  108,
+    0,  133,    0,   59,    0,    0,   28,    0,    0,   15,
+  137,    0,  113,  139,   79,   83,  152,    0,    0,   83,
+   83,  119,    0,    0,    0,    0,    0,    0,    0,    0,
+   32,   20,    0,    0,   28,    0,   15,   28,   15,    0,
+    0,    0,    0,    0,    0,    0,    0,   17,   16,    0,
+    0,   19,    0,   20,    0,   28,    0,    0,    0,    0,
+    0,    0,    0,    0,    0,    0,    0,   29,    0,    0,
+    0,    0,    0,    0,    0,   83,   16,    0,    0,   16,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+   28,    0,    0,    0,    0,   29,    0,   16,   29,    0,
+    0,    0,    0,    0,    0,    0,    0,   20,    0,    0,
+    0,    0,    0,    0,    0,    0,   29,    0,   28,    0,
+    0,   28,   46,   46,   46,    0,   46,   46,    0,   46,
+   46,   46,   46,   46,   18,   46,   46,   46,   46,   28,
+   46,   46,   46,   46,   46,    0,   79,   79,   79,   79,
+   79,    0,   79,   79,   79,   79,   79,   79,   79,   79,
+   79,   79,    0,   16,   79,   79,   79,   79,   79,   32,
+   15,   15,   15,    0,   15,   15,    0,   15,   15,   15,
+   15,   15,   29,   15,   15,   15,   15,    0,   15,   15,
+   15,   15,   15,    2,   34,   35,    4,    0,   36,    0,
+    6,   37,   38,   39,   40,   28,    0,   41,    0,    0,
+   42,   43,   44,   45,   16,    2,   34,   35,    4,    0,
+   36,    0,    6,   37,   38,   39,   40,    0,    0,   41,
+    0,   45,   42,   43,   44,   45,   16,   83,   83,   83,
+   83,    0,   83,   36,   83,   83,   83,   83,   83,    0,
+    0,   83,    0,   28,   83,   83,   83,   83,   83,   45,
+   28,    0,   45,   28,    0,    0,   28,   28,   41,    2,
+    3,   36,    4,    5,   36,    0,    6,    7,    8,    9,
+   45,    0,   40,   10,   11,    0,   12,   13,   14,   15,
+   16,   28,   36,    0,   28,   16,   41,    0,   42,   41,
+    0,    0,   16,    0,    0,    0,    0,   43,   16,   16,
+   40,    0,   28,   40,   29,    0,    0,   41,    0,    0,
+    0,   29,    0,    0,   37,    0,   42,   29,   29,   42,
+    0,   40,   38,    0,    0,   43,    0,   28,   43,    0,
+    0,    0,    0,    0,    0,    0,   45,   42,    0,    0,
+   28,   28,   37,    0,    0,   37,   43,    0,   36,    0,
+   38,    0,    0,   38,    0,    0,    0,    0,    0,    0,
+    0,   17,    0,   37,    0,   19,    0,    0,   28,    0,
+    0,   38,    0,   41,    0,    0,    0,    0,    0,    0,
+    0,    0,    0,    0,   17,    0,    0,   40,   19,    0,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+    0,    0,    0,   42,    0,    0,    0,    0,    0,   17,
+    0,    0,   43,   19,    0,    0,    0,    0,    0,    0,
+    0,   20,    0,    0,    0,    0,    0,    0,    0,   37,
+    0,    0,    0,    0,    0,   17,    0,   38,    0,   19,
+    0,    0,   89,    0,   20,    0,    0,    0,    0,    0,
+    0,    0,    0,    0,    0,    0,    0,   17,    0,    0,
+    0,   19,  134,    0,    0,    0,    0,    0,   45,   20,
+    0,   18,    0,    0,    0,   45,    0,    0,    0,   17,
+   36,   45,   45,   19,  135,    0,    0,   36,    0,    0,
+    0,    0,    0,   36,   36,   20,   18,    0,    0,    0,
+   28,    0,   17,    0,    0,   41,   19,    0,    0,    0,
+    0,    0,   41,   28,   28,    0,    0,   20,   41,   40,
+    0,    0,   18,    0,    0,    0,   40,    0,    0,    0,
+    0,    0,   40,    0,    0,   42,   17,    0,    0,   20,
+   19,    0,   42,    0,   43,    0,    0,    0,   42,    0,
+    0,   43,    0,    0,    0,    0,    0,   43,    0,   46,
+    0,   37,   20,   46,    0,    0,    0,    0,   37,   38,
+    0,    0,    0,    0,   37,    0,   38,    0,    0,    0,
+    0,    0,   38,    2,   34,   35,    4,    5,   36,   18,
+    6,   37,   38,   39,   40,    0,   20,   10,   11,    0,
+   42,   43,   44,   45,   16,    0,    2,   34,   35,    4,
+    0,   36,    0,    6,   37,   38,   39,   40,    0,   46,
+   41,    0,    0,   42,   43,   44,   45,   16,    0,    1,
+    0,    2,    3,    0,    4,    5,    0,    0,    6,    7,
+    8,    9,    0,    0,    0,   10,   11,    0,   12,   13,
+   14,   15,   16,    0,    0,    0,    0,    2,   34,   35,
+    4,    0,   36,    0,    6,   37,   38,   39,   40,   17,
+    0,   41,    0,   19,   42,   43,   44,   45,   16,    2,
+   34,   35,    4,    0,   36,    0,    6,   37,   38,   39,
+   40,    0,    0,   41,    0,    0,   42,   43,   44,   45,
+   16,    2,   34,   35,    4,    0,   36,    0,    6,   37,
+   38,   39,   40,    0,    0,   41,    0,    0,   42,   43,
+   44,   45,   16,    0,    2,    3,  141,    4,    5,   20,
+    0,    6,    7,    8,    9,    0,    0,    0,   10,   11,
+    0,   12,   13,   14,   15,   16,    0,    0,    0,    0,
+    0,    0,    0,    0,    0,    0,   18,    0,    2,   34,
+   35,    4,    0,   36,    0,    6,   37,   38,   39,   40,
+    0,    0,   41,    0,    0,   42,   43,   44,   45,   16,
+    0,   46,   46,   46,   46,    0,   46,    0,   46,   46,
+   46,   46,   46,    0,    0,   46,    0,    0,   46,   46,
+   46,   46,   46,    0,    0,    0,   26,    0,    0,    0,
+    0,    0,    0,    0,    0,    0,    0,    0,   24,    0,
+    0,    0,    0,    0,   26,    0,    0,    0,   26,    0,
+    0,   26,    0,    0,    0,   26,    0,    0,    0,    0,
+   73,    0,    0,   24,    0,    0,    0,   86,    0,    0,
+    0,    0,    0,    0,    0,    0,    0,   26,    0,    0,
+    0,    0,   26,    0,    0,    0,    0,   26,    0,   92,
+    0,    0,    0,    0,    0,   26,    0,    0,    0,   98,
+    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
+    0,    2,    3,    0,    4,    5,    0,    0,    6,    7,
+    8,    9,    0,   26,    0,   10,   11,   26,   12,   13,
+   14,   15,   16,    0,    0,  121,   26,   26,   26,  125,
+    0,    0,    0,    0,    0,    0,    0,    0,  127,  128,
+  129,    0,    0,    0,    0,    0,    0,   26,    0,    0,
+    0,    0,    0,   26,   26,   26,    0,    0,   26,  136,
+    0,   26,    0,    0,    0,  140,  144,  146,    0,    0,
+  144,    0,    0,  144,
+};
+const short yycheck[] = {                                      10,
+   10,    0,   41,   38,   41,   61,   41,   38,   41,   23,
+  138,   94,   40,   40,  142,   10,   30,  145,  100,   40,
+  102,   10,  257,   10,   59,   36,   25,   38,   59,   40,
+   41,   20,   56,   10,  116,  270,  271,  142,   94,   10,
+  145,   94,   12,   38,   14,   69,   41,   10,   59,   36,
+   61,   38,   41,   40,   41,   94,  123,   94,  262,  141,
+   49,  274,   76,   10,   59,   54,  125,   38,  272,  273,
+   41,   10,   59,   36,  271,   38,   41,   40,   41,  125,
+  125,   25,   76,   94,   15,   96,   28,    4,   59,    6,
+  125,   -1,  125,   -1,   -1,   10,   59,   36,   -1,   38,
+   17,   40,   41,   20,   -1,   -1,  120,   -1,   97,   96,
+   -1,   -1,  123,  123,  125,   -1,   -1,   -1,   -1,   10,
+   59,   36,   -1,   38,   -1,   40,   41,   -1,   10,   -1,
+  125,   -1,   49,   96,   -1,   -1,  123,   -1,  125,   -1,
+   -1,   -1,   -1,   10,   59,   36,   -1,   38,   -1,   40,
+   41,   10,   -1,   -1,  125,   -1,   38,   96,   -1,   41,
+  123,   -1,  125,   10,  262,  263,   -1,   84,   59,   -1,
+   -1,   38,   89,   -1,  272,  273,   -1,   59,   -1,   38,
+   -1,   96,   41,   -1,   -1,   -1,  125,   -1,   -1,   -1,
+   -1,   38,   59,   -1,   -1,   -1,   10,   -1,   -1,   -1,
+   59,   -1,   -1,   -1,   -1,   96,   -1,   -1,   -1,   -1,
+  125,   -1,   59,   -1,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,   -1,  257,   -1,   38,   -1,  257,   41,   -1,  264,
+  269,   -1,  123,   -1,  125,  270,  271,   -1,   -1,  270,
+  271,   -1,   -1,  125,   -1,   59,  257,  258,  259,  260,
+  261,  262,  263,  264,  265,  266,  267,  268,  269,  270,
+  271,  272,  273,   -1,  275,  276,  277,  278,  279,  264,
+  257,  258,  259,  260,  261,  262,  263,  264,  265,  266,
+  267,  268,  269,  270,  271,  272,  273,  264,  275,  276,
+  277,  278,  279,  264,  257,  258,  259,  260,  261,  262,
+  263,  264,  265,  266,  267,  268,  269,  270,  271,  272,
+  273,  125,  275,  276,  277,  278,  279,  264,  257,  258,
+  259,  260,  261,  262,  263,  264,  265,  266,  267,  268,
+  269,  270,  271,  272,  273,   -1,  275,  276,  277,  278,
+  279,   -1,  257,  258,  259,  260,  261,  262,  263,  264,
+  265,  266,  267,  268,  269,  270,  271,  272,  273,   -1,
+  275,  276,  277,  278,  279,   10,  257,  258,  259,  260,
+  261,   -1,  263,  264,  265,  266,  267,  268,  269,  270,
+  271,  272,  264,   -1,  275,  276,  277,  278,  279,   10,
+  257,   36,   -1,   38,   -1,   40,   41,  264,  257,   -1,
+   -1,   -1,   -1,  270,  271,   10,   -1,   -1,   -1,   -1,
+  257,  270,  271,   10,   59,   36,   -1,   38,   -1,   40,
+   41,    2,   -1,  270,  271,   -1,   -1,   -1,   -1,   10,
+   11,   -1,   64,   38,   -1,   10,   41,   -1,   59,   36,
+   -1,   38,   -1,   40,   41,   77,   78,   79,   -1,   30,
+  264,   96,   -1,   -1,   59,   -1,   -1,   10,   -1,   -1,
+   -1,   36,   59,   -1,   -1,   40,   41,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   55,   96,   -1,   -1,  123,   10,
+  125,   62,   63,   36,   -1,  117,   -1,   40,   -1,   70,
+   -1,  123,   -1,   74,   -1,   -1,   10,   -1,   -1,   96,
+  132,   -1,   83,  135,  125,   36,   59,   -1,   -1,   40,
+   41,   10,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,
+  125,   96,   -1,   -1,   38,   -1,  123,   41,  125,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   36,   10,   -1,
+   -1,   40,   -1,   96,   -1,   59,   -1,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   10,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   96,   38,   -1,   -1,   41,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,
+   10,   -1,   -1,   -1,   -1,   38,   -1,   59,   41,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   96,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   59,   -1,   38,   -1,
+   -1,  125,  257,  258,  259,   -1,  261,  262,   -1,  264,
+  265,  266,  267,  268,  123,  270,  271,  272,  273,   59,
+  275,  276,  277,  278,  279,   -1,  257,  258,  259,  260,
+  261,   -1,  263,  264,  265,  266,  267,  268,  269,  270,
+  271,  272,   -1,  125,  275,  276,  277,  278,  279,  264,
+  257,  258,  259,   -1,  261,  262,   -1,  264,  265,  266,
+  267,  268,  125,  270,  271,  272,  273,   -1,  275,  276,
+  277,  278,  279,  258,  259,  260,  261,   -1,  263,   -1,
+  265,  266,  267,  268,  269,  125,   -1,  272,   -1,   -1,
+  275,  276,  277,  278,  279,  258,  259,  260,  261,   -1,
+  263,   -1,  265,  266,  267,  268,  269,   -1,   -1,  272,
+   -1,   10,  275,  276,  277,  278,  279,  258,  259,  260,
+  261,   -1,  263,   10,  265,  266,  267,  268,  269,   -1,
+   -1,  272,   -1,  257,  275,  276,  277,  278,  279,   38,
+  264,   -1,   41,   10,   -1,   -1,  270,  271,   10,  258,
+  259,   38,  261,  262,   41,   -1,  265,  266,  267,  268,
+   59,   -1,   10,  272,  273,   -1,  275,  276,  277,  278,
+  279,   38,   59,   -1,   41,  257,   38,   -1,   10,   41,
+   -1,   -1,  264,   -1,   -1,   -1,   -1,   10,  270,  271,
+   38,   -1,   59,   41,  257,   -1,   -1,   59,   -1,   -1,
+   -1,  264,   -1,   -1,   10,   -1,   38,  270,  271,   41,
+   -1,   59,   10,   -1,   -1,   38,   -1,  257,   41,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,  125,   59,   -1,   -1,
+  270,  271,   38,   -1,   -1,   41,   59,   -1,  125,   -1,
+   38,   -1,   -1,   41,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,   36,   -1,   59,   -1,   40,   -1,   -1,  125,   -1,
+   -1,   59,   -1,  125,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   36,   -1,   -1,  125,   40,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,   -1,   -1,  125,   -1,   -1,   -1,   -1,   -1,   36,
+   -1,   -1,  125,   40,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,   96,   -1,   -1,   -1,   -1,   -1,   -1,   -1,  125,
+   -1,   -1,   -1,   -1,   -1,   36,   -1,  125,   -1,   40,
+   -1,   -1,   94,   -1,   96,   -1,   -1,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   36,   -1,   -1,
+   -1,   40,   41,   -1,   -1,   -1,   -1,   -1,  257,   96,
+   -1,  123,   -1,   -1,   -1,  264,   -1,   -1,   -1,   36,
+  257,  270,  271,   40,   41,   -1,   -1,  264,   -1,   -1,
+   -1,   -1,   -1,  270,  271,   96,  123,   -1,   -1,   -1,
+  257,   -1,   36,   -1,   -1,  257,   40,   -1,   -1,   -1,
+   -1,   -1,  264,  270,  271,   -1,   -1,   96,  270,  257,
+   -1,   -1,  123,   -1,   -1,   -1,  264,   -1,   -1,   -1,
+   -1,   -1,  270,   -1,   -1,  257,   36,   -1,   -1,   96,
+   40,   -1,  264,   -1,  257,   -1,   -1,   -1,  270,   -1,
+   -1,  264,   -1,   -1,   -1,   -1,   -1,  270,   -1,   36,
+   -1,  257,   96,   40,   -1,   -1,   -1,   -1,  264,  257,
+   -1,   -1,   -1,   -1,  270,   -1,  264,   -1,   -1,   -1,
+   -1,   -1,  270,  258,  259,  260,  261,  262,  263,  123,
+  265,  266,  267,  268,  269,   -1,   96,  272,  273,   -1,
+  275,  276,  277,  278,  279,   -1,  258,  259,  260,  261,
+   -1,  263,   -1,  265,  266,  267,  268,  269,   -1,   96,
+  272,   -1,   -1,  275,  276,  277,  278,  279,   -1,  256,
+   -1,  258,  259,   -1,  261,  262,   -1,   -1,  265,  266,
+  267,  268,   -1,   -1,   -1,  272,  273,   -1,  275,  276,
+  277,  278,  279,   -1,   -1,   -1,   -1,  258,  259,  260,
+  261,   -1,  263,   -1,  265,  266,  267,  268,  269,   36,
+   -1,  272,   -1,   40,  275,  276,  277,  278,  279,  258,
+  259,  260,  261,   -1,  263,   -1,  265,  266,  267,  268,
+  269,   -1,   -1,  272,   -1,   -1,  275,  276,  277,  278,
+  279,  258,  259,  260,  261,   -1,  263,   -1,  265,  266,
+  267,  268,  269,   -1,   -1,  272,   -1,   -1,  275,  276,
+  277,  278,  279,   -1,  258,  259,  260,  261,  262,   96,
+   -1,  265,  266,  267,  268,   -1,   -1,   -1,  272,  273,
+   -1,  275,  276,  277,  278,  279,   -1,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,  123,   -1,  258,  259,
+  260,  261,   -1,  263,   -1,  265,  266,  267,  268,  269,
+   -1,   -1,  272,   -1,   -1,  275,  276,  277,  278,  279,
+   -1,  258,  259,  260,  261,   -1,  263,   -1,  265,  266,
+  267,  268,  269,   -1,   -1,  272,   -1,   -1,  275,  276,
+  277,  278,  279,   -1,   -1,   -1,    0,   -1,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,    0,   -1,
+   -1,   -1,   -1,   -1,   18,   -1,   -1,   -1,   22,   -1,
+   -1,   25,   -1,   -1,   -1,   29,   -1,   -1,   -1,   -1,
+   22,   -1,   -1,   25,   -1,   -1,   -1,   29,   -1,   -1,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   51,   -1,   -1,
+   -1,   -1,   56,   -1,   -1,   -1,   -1,   61,   -1,   51,
+   -1,   -1,   -1,   -1,   -1,   69,   -1,   -1,   -1,   61,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,
+   -1,  258,  259,   -1,  261,  262,   -1,   -1,  265,  266,
+  267,  268,   -1,   97,   -1,  272,  273,  101,  275,  276,
+  277,  278,  279,   -1,   -1,   97,  110,  111,  112,  101,
+   -1,   -1,   -1,   -1,   -1,   -1,   -1,   -1,  110,  111,
+  112,   -1,   -1,   -1,   -1,   -1,   -1,  131,   -1,   -1,
+   -1,   -1,   -1,  137,  138,  139,   -1,   -1,  142,  131,
+   -1,  145,   -1,   -1,   -1,  137,  138,  139,   -1,   -1,
+  142,   -1,   -1,  145,
+};
+#define YYFINAL 21
+#ifndef YYDEBUG
+#define YYDEBUG 0
+#endif
+#define YYMAXTOKEN 280
+#if YYDEBUG
+const char * const yyname[] = {
+"end-of-file",0,0,0,0,0,0,0,0,0,"'\\n'",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+0,0,0,0,0,"'$'",0,"'&'",0,"'('","')'",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,"';'",0,
+"'='",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,"'^'",0,
+"'`'",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,"'{'",0,"'}'",0,0,0,0,
+0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+0,0,0,0,0,0,0,"ANDAND","BACKBACK","BANG","CASE","COUNT","DUP","ELSE","END",
+"FLAT","FN","FOR","IF","IN","OROR","PIPE","REDIR","SREDIR","SUB","SUBSHELL",
+"SWITCH","TWIDDLE","WHILE","WORD","HUH",
+};
+const char * const yyrule[] = {
+"$accept : rc",
+"rc : line end",
+"rc : error end",
+"end : END",
+"end : '\\n'",
+"cmdsa : cmd ';'",
+"cmdsa : cmd '&'",
+"line : cmd",
+"line : cmdsa line",
+"body : cmd",
+"body : cmdsan body",
+"cmdsan : cmdsa",
+"cmdsan : cmd '\\n'",
+"brace : '{' body '}'",
+"paren : '(' body ')'",
+"assign : first '=' word",
+"epilog :",
+"epilog : redir epilog",
+"redir : DUP",
+"redir : REDIR word",
+"redir : SREDIR word",
+"case : CASE words ';'",
+"case : CASE words '\\n'",
+"cbody : cmd",
+"cbody : case cbody",
+"cbody : cmdsan cbody",
+"iftail : cmd",
+"iftail : brace ELSE optnl cmd",
+"cmd :",
+"cmd : simple",
+"cmd : brace epilog",
+"cmd : IF paren optnl iftail",
+"cmd : FOR '(' word IN words ')' optnl cmd",
+"cmd : FOR '(' word ')' optnl cmd",
+"cmd : WHILE paren optnl cmd",
+"cmd : SWITCH '(' word ')' optnl '{' cbody '}'",
+"cmd : TWIDDLE optcaret word words",
+"cmd : cmd ANDAND optnl cmd",
+"cmd : cmd OROR optnl cmd",
+"cmd : cmd PIPE optnl cmd",
+"cmd : redir cmd",
+"cmd : assign cmd",
+"cmd : BANG optcaret cmd",
+"cmd : SUBSHELL optcaret cmd",
+"cmd : FN words brace",
+"cmd : FN words",
+"optcaret :",
+"optcaret : '^'",
+"simple : first",
+"simple : simple word",
+"simple : simple redir",
+"first : comword",
+"first : first '^' sword",
+"sword : comword",
+"sword : keyword",
+"word : sword",
+"word : word '^' sword",
+"comword : '$' sword",
+"comword : '$' sword SUB words ')'",
+"comword : COUNT sword",
+"comword : FLAT sword",
+"comword : '`' sword",
+"comword : '`' brace",
+"comword : BACKBACK word brace",
+"comword : BACKBACK word sword",
+"comword : '(' nlwords ')'",
+"comword : REDIR brace",
+"comword : WORD",
+"keyword : FOR",
+"keyword : IN",
+"keyword : WHILE",
+"keyword : IF",
+"keyword : SWITCH",
+"keyword : FN",
+"keyword : ELSE",
+"keyword : CASE",
+"keyword : TWIDDLE",
+"keyword : BANG",
+"keyword : SUBSHELL",
+"words :",
+"words : words word",
+"nlwords :",
+"nlwords : nlwords '\\n'",
+"nlwords : nlwords word",
+"optnl :",
+"optnl : optnl '\\n'",
+};
+#endif
+#if YYDEBUG
+#include <stdio.h>
+#endif
+#ifdef YYSTACKSIZE
+#undef YYMAXDEPTH
+#define YYMAXDEPTH YYSTACKSIZE
+#else
+#ifdef YYMAXDEPTH
+#define YYSTACKSIZE YYMAXDEPTH
+#else
+#define YYSTACKSIZE 10000
+#define YYMAXDEPTH 10000
+#endif
+#endif
+#define YYINITSTACKSIZE 200
+int yydebug;
+int yynerrs;
+int yyerrflag;
+int yychar;
+short *yyssp;
+YYSTYPE *yyvsp;
+YYSTYPE yyval;
+YYSTYPE yylval;
+short *yyss;
+short *yysslim;
+YYSTYPE *yyvs;
+int yystacksize;
+#line 167 "parse.y"
+
+void initparse() {
+       star = treecpy(mk(nVar, mk(nWord,"*", NULL, FALSE)), ealloc);
+       nolist = treecpy(mk(nVar, mk(nWord,"ifs", NULL, FALSE)), ealloc);
+}
+
+#line 583 "y.tab.c"
+/* allocate initial stack or double stack size, up to YYMAXDEPTH */
+static int yygrowstack()
+{
+    int newsize, i;
+    short *newss;
+    YYSTYPE *newvs;
+
+    if ((newsize = yystacksize) == 0)
+        newsize = YYINITSTACKSIZE;
+    else if (newsize >= YYMAXDEPTH)
+        return -1;
+    else if ((newsize *= 2) > YYMAXDEPTH)
+        newsize = YYMAXDEPTH;
+    i = yyssp - yyss;
+    newss = yyss ? (short *)realloc(yyss, newsize * sizeof *newss) :
+      (short *)malloc(newsize * sizeof *newss);
+    if (newss == NULL)
+        return -1;
+    yyss = newss;
+    yyssp = newss + i;
+    newvs = yyvs ? (YYSTYPE *)realloc(yyvs, newsize * sizeof *newvs) :
+      (YYSTYPE *)malloc(newsize * sizeof *newvs);
+    if (newvs == NULL)
+        return -1;
+    yyvs = newvs;
+    yyvsp = newvs + i;
+    yystacksize = newsize;
+    yysslim = yyss + newsize - 1;
+    return 0;
+}
+
+#define YYABORT goto yyabort
+#define YYREJECT goto yyabort
+#define YYACCEPT goto yyaccept
+#define YYERROR goto yyerrlab
+
+#ifndef YYPARSE_PARAM
+#if defined(__cplusplus) || __STDC__
+#define YYPARSE_PARAM_ARG void
+#define YYPARSE_PARAM_DECL
+#else  /* ! ANSI-C/C++ */
+#define YYPARSE_PARAM_ARG
+#define YYPARSE_PARAM_DECL
+#endif /* ANSI-C/C++ */
+#else  /* YYPARSE_PARAM */
+#ifndef YYPARSE_PARAM_TYPE
+#define YYPARSE_PARAM_TYPE void *
+#endif
+#if defined(__cplusplus) || __STDC__
+#define YYPARSE_PARAM_ARG YYPARSE_PARAM_TYPE YYPARSE_PARAM
+#define YYPARSE_PARAM_DECL
+#else  /* ! ANSI-C/C++ */
+#define YYPARSE_PARAM_ARG YYPARSE_PARAM
+#define YYPARSE_PARAM_DECL YYPARSE_PARAM_TYPE YYPARSE_PARAM;
+#endif /* ANSI-C/C++ */
+#endif /* ! YYPARSE_PARAM */
+
+int
+yyparse (YYPARSE_PARAM_ARG)
+    YYPARSE_PARAM_DECL
+{
+    register int yym, yyn, yystate;
+#if YYDEBUG
+    register const char *yys;
+
+    if ((yys = getenv("YYDEBUG")))
+    {
+        yyn = *yys;
+        if (yyn >= '0' && yyn <= '9')
+            yydebug = yyn - '0';
+    }
+#endif
+
+    yynerrs = 0;
+    yyerrflag = 0;
+    yychar = (-1);
+
+    if (yyss == NULL && yygrowstack()) goto yyoverflow;
+    yyssp = yyss;
+    yyvsp = yyvs;
+    *yyssp = yystate = 0;
+
+yyloop:
+    if ((yyn = yydefred[yystate])) goto yyreduce;
+    if (yychar < 0)
+    {
+        if ((yychar = yylex()) < 0) yychar = 0;
+#if YYDEBUG
+        if (yydebug)
+        {
+            yys = 0;
+            if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
+            if (!yys) yys = "illegal-symbol";
+            printf("%sdebug: state %d, reading %d (%s)\n",
+                    YYPREFIX, yystate, yychar, yys);
+        }
+#endif
+    }
+    if ((yyn = yysindex[yystate]) && (yyn += yychar) >= 0 &&
+            yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
+    {
+#if YYDEBUG
+        if (yydebug)
+            printf("%sdebug: state %d, shifting to state %d\n",
+                    YYPREFIX, yystate, yytable[yyn]);
+#endif
+        if (yyssp >= yysslim && yygrowstack())
+        {
+            goto yyoverflow;
+        }
+        *++yyssp = yystate = yytable[yyn];
+        *++yyvsp = yylval;
+        yychar = (-1);
+        if (yyerrflag > 0)  --yyerrflag;
+        goto yyloop;
+    }
+    if ((yyn = yyrindex[yystate]) && (yyn += yychar) >= 0 &&
+            yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
+    {
+        yyn = yytable[yyn];
+        goto yyreduce;
+    }
+    if (yyerrflag) goto yyinrecovery;
+#if defined(lint) || defined(__GNUC__)
+    goto yynewerror;
+#endif
+yynewerror:
+    yyerror("syntax error");
+#if defined(lint) || defined(__GNUC__)
+    goto yyerrlab;
+#endif
+yyerrlab:
+    ++yynerrs;
+yyinrecovery:
+    if (yyerrflag < 3)
+    {
+        yyerrflag = 3;
+        for (;;)
+        {
+            if ((yyn = yysindex[*yyssp]) && (yyn += YYERRCODE) >= 0 &&
+                    yyn <= YYTABLESIZE && yycheck[yyn] == YYERRCODE)
+            {
+#if YYDEBUG
+                if (yydebug)
+                    printf("%sdebug: state %d, error recovery shifting\
+ to state %d\n", YYPREFIX, *yyssp, yytable[yyn]);
+#endif
+                if (yyssp >= yysslim && yygrowstack())
+                {
+                    goto yyoverflow;
+                }
+                *++yyssp = yystate = yytable[yyn];
+                *++yyvsp = yylval;
+                goto yyloop;
+            }
+            else
+            {
+#if YYDEBUG
+                if (yydebug)
+                    printf("%sdebug: error recovery discarding state %d\n",
+                            YYPREFIX, *yyssp);
+#endif
+                if (yyssp <= yyss) goto yyabort;
+                --yyssp;
+                --yyvsp;
+            }
+        }
+    }
+    else
+    {
+        if (yychar == 0) goto yyabort;
+#if YYDEBUG
+        if (yydebug)
+        {
+            yys = 0;
+            if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
+            if (!yys) yys = "illegal-symbol";
+            printf("%sdebug: state %d, error recovery discards token %d (%s)\n",
+                    YYPREFIX, yystate, yychar, yys);
+        }
+#endif
+        yychar = (-1);
+        goto yyloop;
+    }
+yyreduce:
+#if YYDEBUG
+    if (yydebug)
+        printf("%sdebug: state %d, reducing by rule %d (%s)\n",
+                YYPREFIX, yystate, yyn, yyrule[yyn]);
+#endif
+    yym = yylen[yyn];
+    yyval = yyvsp[1-yym];
+    switch (yyn)
+    {
+case 1:
+#line 47 "parse.y"
+{ parsetree = yyvsp[-1].node; YYACCEPT; }
+break;
+case 2:
+#line 48 "parse.y"
+{ yyerrok; parsetree = NULL; YYABORT; }
+break;
+case 3:
+#line 51 "parse.y"
+{ if (!heredoc(1)) YYABORT; }
+break;
+case 4:
+#line 52 "parse.y"
+{ if (!heredoc(0)) YYABORT; }
+break;
+case 6:
+#line 56 "parse.y"
+{ yyval.node = (yyvsp[-1].node != NULL ? mk(nNowait,yyvsp[-1].node) : yyvsp[-1].node); }
+break;
+case 8:
+#line 60 "parse.y"
+{ yyval.node = (yyvsp[-1].node != NULL ? mk(nBody,yyvsp[-1].node,yyvsp[0].node) : yyvsp[0].node); }
+break;
+case 10:
+#line 64 "parse.y"
+{ yyval.node = (yyvsp[-1].node == NULL ? yyvsp[0].node : yyvsp[0].node == NULL ? yyvsp[-1].node : mk(nBody,yyvsp[-1].node,yyvsp[0].node)); }
+break;
+case 12:
+#line 67 "parse.y"
+{ yyval.node = yyvsp[-1].node; if (!heredoc(0)) YYABORT; }
+break;
+case 13:
+#line 69 "parse.y"
+{ yyval.node = yyvsp[-1].node; }
+break;
+case 14:
+#line 71 "parse.y"
+{ yyval.node = yyvsp[-1].node; }
+break;
+case 15:
+#line 73 "parse.y"
+{ yyval.node = mk(nAssign,yyvsp[-2].node,yyvsp[0].node); }
+break;
+case 16:
+#line 75 "parse.y"
+{ yyval.node = NULL; }
+break;
+case 17:
+#line 76 "parse.y"
+{ yyval.node = mk(nEpilog,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 18:
+#line 79 "parse.y"
+{ yyval.node = mk(nDup,yyvsp[0].dup.type,yyvsp[0].dup.left,yyvsp[0].dup.right); }
+break;
+case 19:
+#line 80 "parse.y"
+{ yyval.node = mk(nRedir,yyvsp[-1].redir.type,yyvsp[-1].redir.fd,yyvsp[0].node);
+                                 if (yyvsp[-1].redir.type == rHeredoc && !qdoc(yyvsp[0].node, yyval.node)) YYABORT; /* queue heredocs up */
+                               }
+break;
+case 20:
+#line 83 "parse.y"
+{ yyval.node = mk(nRedir,yyvsp[-1].redir.type,yyvsp[-1].redir.fd,yyvsp[0].node);
+                                 if (yyvsp[-1].redir.type == rHeredoc && !qdoc(yyvsp[0].node, yyval.node)) YYABORT; /* queue heredocs up */
+                               }
+break;
+case 21:
+#line 87 "parse.y"
+{ yyval.node = mk(nCase, yyvsp[-1].node); }
+break;
+case 22:
+#line 88 "parse.y"
+{ yyval.node = mk(nCase, yyvsp[-1].node); }
+break;
+case 23:
+#line 90 "parse.y"
+{ yyval.node = mk(nCbody, yyvsp[0].node, NULL); }
+break;
+case 24:
+#line 91 "parse.y"
+{ yyval.node = mk(nCbody, yyvsp[-1].node, yyvsp[0].node); }
+break;
+case 25:
+#line 92 "parse.y"
+{ yyval.node = mk(nCbody, yyvsp[-1].node, yyvsp[0].node); }
+break;
+case 27:
+#line 95 "parse.y"
+{ yyval.node = mk(nElse,yyvsp[-3].node,yyvsp[0].node); }
+break;
+case 28:
+#line 97 "parse.y"
+{ yyval.node = NULL; }
+break;
+case 30:
+#line 99 "parse.y"
+{ yyval.node = mk(nBrace,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 31:
+#line 100 "parse.y"
+{ yyval.node = mk(nIf,yyvsp[-2].node,yyvsp[0].node); }
+break;
+case 32:
+#line 101 "parse.y"
+{ yyval.node = mk(nForin,yyvsp[-5].node,yyvsp[-3].node,yyvsp[0].node); }
+break;
+case 33:
+#line 102 "parse.y"
+{ yyval.node = mk(nForin,yyvsp[-3].node,star,yyvsp[0].node); }
+break;
+case 34:
+#line 103 "parse.y"
+{ yyval.node = mk(nWhile,yyvsp[-2].node,yyvsp[0].node); }
+break;
+case 35:
+#line 104 "parse.y"
+{ yyval.node = mk(nSwitch,yyvsp[-5].node,yyvsp[-1].node); }
+break;
+case 36:
+#line 105 "parse.y"
+{ yyval.node = mk(nMatch,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 37:
+#line 106 "parse.y"
+{ yyval.node = mk(nAndalso,yyvsp[-3].node,yyvsp[0].node); }
+break;
+case 38:
+#line 107 "parse.y"
+{ yyval.node = mk(nOrelse,yyvsp[-3].node,yyvsp[0].node); }
+break;
+case 39:
+#line 108 "parse.y"
+{ yyval.node = mk(nPipe,yyvsp[-2].pipe.left,yyvsp[-2].pipe.right,yyvsp[-3].node,yyvsp[0].node); }
+break;
+case 40:
+#line 109 "parse.y"
+{ yyval.node = (yyvsp[0].node != NULL ? mk(nPre,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); }
+break;
+case 41:
+#line 110 "parse.y"
+{ yyval.node = (yyvsp[0].node != NULL ? mk(nPre,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); }
+break;
+case 42:
+#line 111 "parse.y"
+{ yyval.node = mk(nBang,yyvsp[0].node); }
+break;
+case 43:
+#line 112 "parse.y"
+{ yyval.node = mk(nSubshell,yyvsp[0].node); }
+break;
+case 44:
+#line 113 "parse.y"
+{ yyval.node = mk(nNewfn,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 45:
+#line 114 "parse.y"
+{ yyval.node = mk(nRmfn,yyvsp[0].node); }
+break;
+case 49:
+#line 120 "parse.y"
+{ yyval.node = (yyvsp[0].node != NULL ? mk(nArgs,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); }
+break;
+case 50:
+#line 121 "parse.y"
+{ yyval.node = mk(nArgs,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 52:
+#line 124 "parse.y"
+{ yyval.node = mk(nConcat,yyvsp[-2].node,yyvsp[0].node); }
+break;
+case 54:
+#line 127 "parse.y"
+{ yyval.node = mk(nWord, yyvsp[0].keyword, NULL, FALSE); }
+break;
+case 56:
+#line 130 "parse.y"
+{ yyval.node = mk(nConcat,yyvsp[-2].node,yyvsp[0].node); }
+break;
+case 57:
+#line 132 "parse.y"
+{ yyval.node = mk(nVar,yyvsp[0].node); }
+break;
+case 58:
+#line 133 "parse.y"
+{ yyval.node = mk(nVarsub,yyvsp[-3].node,yyvsp[-1].node); }
+break;
+case 59:
+#line 134 "parse.y"
+{ yyval.node = mk(nCount,yyvsp[0].node); }
+break;
+case 60:
+#line 135 "parse.y"
+{ yyval.node = mk(nFlat, yyvsp[0].node); }
+break;
+case 61:
+#line 136 "parse.y"
+{ yyval.node = mk(nBackq,nolist,yyvsp[0].node); }
+break;
+case 62:
+#line 137 "parse.y"
+{ yyval.node = mk(nBackq,nolist,yyvsp[0].node); }
+break;
+case 63:
+#line 138 "parse.y"
+{ yyval.node = mk(nBackq,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 64:
+#line 139 "parse.y"
+{ yyval.node = mk(nBackq,yyvsp[-1].node,yyvsp[0].node); }
+break;
+case 65:
+#line 140 "parse.y"
+{ yyval.node = yyvsp[-1].node; }
+break;
+case 66:
+#line 141 "parse.y"
+{ yyval.node = mk(nNmpipe,yyvsp[-1].redir.type,yyvsp[-1].redir.fd,yyvsp[0].node); }
+break;
+case 67:
+#line 142 "parse.y"
+{ yyval.node = mk(nWord, yyvsp[0].word.w, yyvsp[0].word.m, yyvsp[0].word.q); }
+break;
+case 68:
+#line 144 "parse.y"
+{ yyval.keyword = "for"; }
+break;
+case 69:
+#line 145 "parse.y"
+{ yyval.keyword = "in"; }
+break;
+case 70:
+#line 146 "parse.y"
+{ yyval.keyword = "while"; }
+break;
+case 71:
+#line 147 "parse.y"
+{ yyval.keyword = "if"; }
+break;
+case 72:
+#line 148 "parse.y"
+{ yyval.keyword = "switch"; }
+break;
+case 73:
+#line 149 "parse.y"
+{ yyval.keyword = "fn"; }
+break;
+case 74:
+#line 150 "parse.y"
+{ yyval.keyword = "else"; }
+break;
+case 75:
+#line 151 "parse.y"
+{ yyval.keyword = "case"; }
+break;
+case 76:
+#line 152 "parse.y"
+{ yyval.keyword = "~"; }
+break;
+case 77:
+#line 153 "parse.y"
+{ yyval.keyword = "!"; }
+break;
+case 78:
+#line 154 "parse.y"
+{ yyval.keyword = "@"; }
+break;
+case 79:
+#line 156 "parse.y"
+{ yyval.node = NULL; }
+break;
+case 80:
+#line 157 "parse.y"
+{ yyval.node = (yyvsp[-1].node != NULL ? (yyvsp[0].node != NULL ? mk(nLappend,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node) : yyvsp[0].node); }
+break;
+case 81:
+#line 159 "parse.y"
+{ yyval.node = NULL; }
+break;
+case 83:
+#line 161 "parse.y"
+{ yyval.node = (yyvsp[-1].node != NULL ? (yyvsp[0].node != NULL ? mk(nLappend,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node) : yyvsp[0].node); }
+break;
+#line 1062 "y.tab.c"
+    }
+    yyssp -= yym;
+    yystate = *yyssp;
+    yyvsp -= yym;
+    yym = yylhs[yyn];
+    if (yystate == 0 && yym == 0)
+    {
+#if YYDEBUG
+        if (yydebug)
+            printf("%sdebug: after reduction, shifting from state 0 to\
+ state %d\n", YYPREFIX, YYFINAL);
+#endif
+        yystate = YYFINAL;
+        *++yyssp = YYFINAL;
+        *++yyvsp = yyval;
+        if (yychar < 0)
+        {
+            if ((yychar = yylex()) < 0) yychar = 0;
+#if YYDEBUG
+            if (yydebug)
+            {
+                yys = 0;
+                if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
+                if (!yys) yys = "illegal-symbol";
+                printf("%sdebug: state %d, reading %d (%s)\n",
+                        YYPREFIX, YYFINAL, yychar, yys);
+            }
+#endif
+        }
+        if (yychar == 0) goto yyaccept;
+        goto yyloop;
+    }
+    if ((yyn = yygindex[yym]) && (yyn += yystate) >= 0 &&
+            yyn <= YYTABLESIZE && yycheck[yyn] == yystate)
+        yystate = yytable[yyn];
+    else
+        yystate = yydgoto[yym];
+#if YYDEBUG
+    if (yydebug)
+        printf("%sdebug: after reduction, shifting from state %d \
+to state %d\n", YYPREFIX, *yyssp, yystate);
+#endif
+    if (yyssp >= yysslim && yygrowstack())
+    {
+        goto yyoverflow;
+    }
+    *++yyssp = yystate;
+    *++yyvsp = yyval;
+    goto yyloop;
+yyoverflow:
+    yyerror("yacc stack overflow");
+yyabort:
+    return (1);
+yyaccept:
+    return (0);
+}
diff --git a/parse.h b/parse.h
new file mode 100644 (file)
index 0000000..c193710
--- /dev/null
+++ b/parse.h
@@ -0,0 +1,37 @@
+#ifndef YYERRCODE
+#define YYERRCODE 256
+#endif
+
+#define ANDAND 257
+#define BACKBACK 258
+#define BANG 259
+#define CASE 260
+#define COUNT 261
+#define DUP 262
+#define ELSE 263
+#define END 264
+#define FLAT 265
+#define FN 266
+#define FOR 267
+#define IF 268
+#define IN 269
+#define OROR 270
+#define PIPE 271
+#define REDIR 272
+#define SREDIR 273
+#define SUB 274
+#define SUBSHELL 275
+#define SWITCH 276
+#define TWIDDLE 277
+#define WHILE 278
+#define WORD 279
+#define HUH 280
+typedef union {
+       struct Node *node;
+       struct Redir redir;
+       struct Pipe pipe;
+       struct Dup dup;
+       struct Word word;
+       char *keyword;
+} YYSTYPE;
+extern YYSTYPE yylval;
diff --git a/parse.y b/parse.y
new file mode 100644 (file)
index 0000000..8be65bb
--- /dev/null
+++ b/parse.y
@@ -0,0 +1,174 @@
+/* parse.y */
+
+/*
+ * Adapted from rc grammar, v10 manuals, volume 2.
+ */
+
+%{
+/* note that this actually needs to appear before any system header
+   files are included; byacc likes to throw in <stdlib.h> first. */
+#include "rc.h"
+
+static Node *star, *nolist;
+Node *parsetree;       /* not using yylval because bison declares it as an auto */
+%}
+
+%token ANDAND BACKBACK BANG CASE COUNT DUP ELSE END FLAT FN FOR IF IN
+%token OROR PIPE REDIR SREDIR SUB SUBSHELL SWITCH TWIDDLE WHILE WORD HUH
+
+%left WHILE ')' ELSE
+%left ANDAND OROR '\n'
+%left BANG SUBSHELL
+%left PIPE
+%right '$' 
+%left SUB
+/*
+*/
+
+%union {
+       struct Node *node;
+       struct Redir redir;
+       struct Pipe pipe;
+       struct Dup dup;
+       struct Word word;
+       char *keyword;
+}
+
+%type <redir> REDIR SREDIR
+%type <pipe> PIPE
+%type <dup> DUP
+%type <word> WORD
+%type <keyword> keyword
+%type <node> assign body brace case cbody cmd cmdsa cmdsan comword epilog
+            first line nlwords paren redir sword simple iftail word words
+
+%start rc
+
+%%
+
+rc     : line end              { parsetree = $1; YYACCEPT; }
+       | error end             { yyerrok; parsetree = NULL; YYABORT; }
+
+/* an rc line may end in end-of-file as well as newline, e.g., rc -c 'ls' */
+end    : END   /* EOF */       { if (!heredoc(1)) YYABORT; } /* flag error if there is a heredoc in the queue */
+       | '\n'                  { if (!heredoc(0)) YYABORT; } /* get heredoc on \n */
+
+/* a cmdsa is a command followed by ampersand or newline (used in "line" and "body") */
+cmdsa  : cmd ';'
+       | cmd '&'               { $$ = ($1 != NULL ? mk(nNowait,$1) : $1); }
+
+/* a line is a single command, or a command terminated by ; or & followed by a line (recursive) */
+line   : cmd
+       | cmdsa line            { $$ = ($1 != NULL ? mk(nBody,$1,$2) : $2); }
+
+/* a body is like a line, only commands may also be terminated by newline */
+body   : cmd
+       | cmdsan body           { $$ = ($1 == NULL ? $2 : $2 == NULL ? $1 : mk(nBody,$1,$2)); }
+
+cmdsan : cmdsa
+       | cmd '\n'              { $$ = $1; if (!heredoc(0)) YYABORT; } /* get h.d. on \n */
+
+brace  : '{' body '}'          { $$ = $2; }
+
+paren  : '(' body ')'          { $$ = $2; }
+
+assign : first '=' word        { $$ = mk(nAssign,$1,$3); }
+
+epilog :                       { $$ = NULL; }
+       | redir epilog          { $$ = mk(nEpilog,$1,$2); }
+
+/* a redirection is a dup (e.g., >[1=2]) or a file redirection. (e.g., > /dev/null) */
+redir  : DUP                   { $$ = mk(nDup,$1.type,$1.left,$1.right); }
+       | REDIR word            { $$ = mk(nRedir,$1.type,$1.fd,$2);
+                                 if ($1.type == rHeredoc && !qdoc($2, $$)) YYABORT; /* queue heredocs up */
+                               }
+       | SREDIR word           { $$ = mk(nRedir,$1.type,$1.fd,$2);
+                                 if ($1.type == rHeredoc && !qdoc($2, $$)) YYABORT; /* queue heredocs up */
+                               }
+
+case   : CASE words ';'                        { $$ = mk(nCase, $2); }
+       | CASE words '\n'                       { $$ = mk(nCase, $2); }
+
+cbody  : cmd                                   { $$ = mk(nCbody, $1, NULL); }
+       | case cbody                            { $$ = mk(nCbody, $1, $2); }
+       | cmdsan cbody                          { $$ = mk(nCbody, $1, $2); }
+
+iftail : cmd           %prec ELSE
+       | brace ELSE optnl cmd                  { $$ = mk(nElse,$1,$4); }
+
+cmd    : /* empty */   %prec WHILE             { $$ = NULL; }
+       | simple
+       | brace epilog                          { $$ = mk(nBrace,$1,$2); }
+       | IF paren optnl iftail                 { $$ = mk(nIf,$2,$4); }
+       | FOR '(' word IN words ')' optnl cmd   { $$ = mk(nForin,$3,$5,$8); }
+       | FOR '(' word ')' optnl cmd            { $$ = mk(nForin,$3,star,$6); }
+       | WHILE paren optnl cmd                 { $$ = mk(nWhile,$2,$4); }
+       | SWITCH '(' word ')' optnl '{' cbody '}' { $$ = mk(nSwitch,$3,$7); }
+       | TWIDDLE optcaret word words           { $$ = mk(nMatch,$3,$4); }
+       | cmd ANDAND optnl cmd                  { $$ = mk(nAndalso,$1,$4); }
+       | cmd OROR optnl cmd                    { $$ = mk(nOrelse,$1,$4); }
+       | cmd PIPE optnl cmd                    { $$ = mk(nPipe,$2.left,$2.right,$1,$4); }
+       | redir cmd     %prec BANG              { $$ = ($2 != NULL ? mk(nPre,$1,$2) : $1); }
+       | assign cmd    %prec BANG              { $$ = ($2 != NULL ? mk(nPre,$1,$2) : $1); }
+       | BANG optcaret cmd                     { $$ = mk(nBang,$3); }
+       | SUBSHELL optcaret cmd                 { $$ = mk(nSubshell,$3); }
+       | FN words brace                        { $$ = mk(nNewfn,$2,$3); }
+       | FN words                              { $$ = mk(nRmfn,$2); }
+
+optcaret : /* empty */
+       | '^'
+
+simple : first
+       | simple word                   { $$ = ($2 != NULL ? mk(nArgs,$1,$2) : $1); }
+       | simple redir                  { $$ = mk(nArgs,$1,$2); }
+
+first  : comword
+       | first '^' sword               { $$ = mk(nConcat,$1,$3); }
+
+sword  : comword
+       | keyword                       { $$ = mk(nWord, $1, NULL, FALSE); }
+
+word   : sword
+       | word '^' sword                { $$ = mk(nConcat,$1,$3); }
+
+comword        : '$' sword                     { $$ = mk(nVar,$2); }
+       | '$' sword SUB words ')'       { $$ = mk(nVarsub,$2,$4); }
+       | COUNT sword                   { $$ = mk(nCount,$2); }
+       | FLAT sword                    { $$ = mk(nFlat, $2); }
+       | '`' sword                     { $$ = mk(nBackq,nolist,$2); }
+       | '`' brace                     { $$ = mk(nBackq,nolist,$2); }
+       | BACKBACK word brace           { $$ = mk(nBackq,$2,$3); }
+       | BACKBACK word sword           { $$ = mk(nBackq,$2,$3); }
+       | '(' nlwords ')'               { $$ = $2; }
+       | REDIR brace                   { $$ = mk(nNmpipe,$1.type,$1.fd,$2); }
+       | WORD                          { $$ = mk(nWord, $1.w, $1.m, $1.q); }
+
+keyword        : FOR           { $$ = "for"; }
+       | IN            { $$ = "in"; }
+       | WHILE         { $$ = "while"; }
+       | IF            { $$ = "if"; }
+       | SWITCH        { $$ = "switch"; }
+       | FN            { $$ = "fn"; }
+       | ELSE          { $$ = "else"; }
+       | CASE          { $$ = "case"; }
+       | TWIDDLE       { $$ = "~"; }
+       | BANG          { $$ = "!"; }
+       | SUBSHELL      { $$ = "@"; }
+
+words  :               { $$ = NULL; }
+       | words word    { $$ = ($1 != NULL ? ($2 != NULL ? mk(nLappend,$1,$2) : $1) : $2); }
+
+nlwords :              { $$ = NULL; }
+       | nlwords '\n'
+       | nlwords word  { $$ = ($1 != NULL ? ($2 != NULL ? mk(nLappend,$1,$2) : $1) : $2); }
+
+optnl  : /* empty */
+       | optnl '\n'
+
+%%
+
+void initparse() {
+       star = treecpy(mk(nVar, mk(nWord,"*", NULL, FALSE)), ealloc);
+       nolist = treecpy(mk(nVar, mk(nWord,"ifs", NULL, FALSE)), ealloc);
+}
+
diff --git a/print.c b/print.c
new file mode 100644 (file)
index 0000000..2a30b5c
--- /dev/null
+++ b/print.c
@@ -0,0 +1,381 @@
+/* print.c -- formatted printing routines (Paul Haahr, 12/91) */
+
+#include "rc.h"
+#include <setjmp.h>
+
+#define        PRINT_ALLOCSIZE ((size_t)64)
+#define        SPRINT_BUFSIZ   ((size_t)1024)
+
+#define        MAXCONV 256
+
+/*
+ * conversion functions
+ *     true return -> flag changes only, not a conversion
+ */
+
+#define Flag(name, flag) \
+static bool name(Format *format, int ignore) { \
+       format->flags |= flag; \
+       return TRUE; \
+}
+
+Flag(uconv,    FMT_unsigned)
+Flag(rc_lconv, FMT_long)
+
+#if HAVE_QUAD_T
+Flag(qconv,    FMT_quad)
+#endif
+
+Flag(altconv,  FMT_altform)
+Flag(leftconv, FMT_leftside)
+Flag(dotconv,  FMT_f2set)
+
+static bool digitconv(Format *format, int c) {
+       if (format->flags & FMT_f2set)
+               format->f2 = 10 * format->f2 + c - '0';
+       else {
+               format->flags |= FMT_f1set;
+               format->f1 = 10 * format->f1 + c - '0';
+       }
+       return TRUE;
+}
+
+static bool zeroconv(Format *format, int ignore) {
+       if (format->flags & (FMT_f1set | FMT_f2set))
+               return digitconv(format, '0');
+       format->flags |= FMT_zeropad;
+       return TRUE;
+}
+
+static void pad(Format *format, size_t len, int c) {
+       while (len-- != 0)
+               fmtputc(format, c);
+}
+
+static bool sconv(Format *format, int ignore) {
+       char *s = va_arg(format->args, char *);
+       if ((format->flags & FMT_f1set) == 0)
+               fmtcat(format, s);
+       else {
+               size_t len = strlen(s), width = format->f1 - len;
+               if (format->flags & FMT_leftside) {
+                       fmtappend(format, s, len);
+                       pad(format, width, ' ');
+               } else {
+                       pad(format, width, ' ');
+                       fmtappend(format, s, len);
+               }
+       }
+       return FALSE;
+}
+
+static char *rc_utoa(unsigned long u, char *t, unsigned int radix, const char *digit) {
+       if (u >= radix) {
+               t = rc_utoa(u / radix, t, radix, digit);
+               u %= radix;
+       }
+       *t++ = digit[u];
+       return t;
+}
+
+static void intconv(Format *format, unsigned int radix, int upper, const char *altform) {
+       static const char * const table[] = {
+               "0123456789abcdefghijklmnopqrstuvwxyz",
+               "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ",
+       };
+       char padchar;
+       size_t len, pre, zeroes, padding, width;
+       long n, flags;
+       unsigned long u;
+       char number[64], prefix[20];
+
+       if (radix > 36)
+               return;
+
+       flags = format->flags;
+
+#if HAVE_QUAD_T
+       if (flags & FMT_quad)
+               n = va_arg(format->args, quad_t);
+       else
+#endif
+
+       if (flags & FMT_long)
+               n = va_arg(format->args, long);
+       else
+               n = va_arg(format->args, int);
+
+       pre = 0;
+       if ((flags & FMT_unsigned) || n >= 0)
+               u = n;
+       else {
+               prefix[pre++] = '-';
+               u = -n;
+       }
+
+       if (flags & FMT_altform)
+               while (*altform != '\0')
+                       prefix[pre++] = *altform++;
+
+       len = rc_utoa(u, number, radix, table[upper]) - number;
+       if ((flags & FMT_f2set) && (size_t) format->f2 > len)
+               zeroes = format->f2 - len;
+       else
+               zeroes = 0;
+
+       width = pre + zeroes + len;
+       if ((flags & FMT_f1set) && (size_t) format->f1 > width) {
+               padding = format->f1 - width;
+       } else
+               padding = 0;
+
+       padchar = ' ';
+       if (padding > 0 && flags & FMT_zeropad) {
+               padchar = '0';
+               if ((flags & FMT_leftside) == 0) {
+                       zeroes += padding;
+                       padding = 0;
+               }
+       }
+
+
+       if ((flags & FMT_leftside) == 0)
+               pad(format, padding, padchar);
+       fmtappend(format, prefix, pre);
+       pad(format, zeroes, '0');
+       fmtappend(format, number, len);
+       if (flags & FMT_leftside)
+               pad(format, padding, padchar);
+}
+
+static bool cconv(Format *format, int ignore) {
+       fmtputc(format, va_arg(format->args, int));
+       return FALSE;
+}
+
+static bool dconv(Format *format, int ignore) {
+       intconv(format, 10, 0, "");
+       return FALSE;
+}
+
+static bool oconv(Format *format, int ignore) {
+       intconv(format, 8, 0, "0");
+       return FALSE;
+}
+
+static bool xconv(Format *format, int ignore) {
+       intconv(format, 16, 0, "0x");
+       return FALSE;
+}
+
+static bool pctconv(Format *format, int ignore) {
+       fmtputc(format, '%');
+       return FALSE;
+}
+
+static bool badconv(Format *ignore, int ign0re) {
+       panic("bad conversion character in printfmt");
+       /* NOTREACHED */
+       return FALSE; /* hush up gcc -Wall */
+}
+
+
+/*
+ * conversion table management
+ */
+
+static Conv fmttab[MAXCONV];
+
+static void inittab(void) {
+       int i;
+       for (i = 0; i < MAXCONV; i++)
+               fmttab[i] = badconv;
+
+       fmttab['s'] = sconv;
+       fmttab['c'] = cconv;
+       fmttab['d'] = dconv;
+       fmttab['o'] = oconv;
+       fmttab['x'] = xconv;
+       fmttab['%'] = pctconv;
+
+       fmttab['u'] = uconv;
+       fmttab['l'] = rc_lconv;
+       fmttab['#'] = altconv;
+       fmttab['-'] = leftconv;
+       fmttab['.'] = dotconv;
+
+#if HAVE_QUAD_T
+       fmttab['q'] = qconv;
+#endif
+
+       fmttab['0'] = zeroconv;
+       for (i = '1'; i <= '9'; i++)
+               fmttab[i] = digitconv;
+}
+
+extern bool (*fmtinstall(int c, bool (*f)(Format *, int)))(Format *, int) {
+/*Conv fmtinstall(int c, Conv f) {*/
+       Conv oldf;
+       if (fmttab[0] == NULL)
+               inittab();
+       c &= MAXCONV - 1;
+       oldf = fmttab[c];
+       if (f != NULL)
+               fmttab[c] = f;
+       return oldf;
+}
+
+
+/*
+ * functions for inserting strings in the format buffer
+ */
+
+extern void fmtappend(Format *format, const char *s, size_t len) {
+       while (format->buf + len > format->bufend) {
+               size_t split = format->bufend - format->buf;
+               memcpy(format->buf, s, split);
+               format->buf += split;
+               s += split;
+               len -= split;
+               (*format->grow)(format, len);
+       }
+       memcpy(format->buf, s, len);
+       format->buf += len;
+}
+
+extern void fmtcat(Format *format, const char *s) {
+       fmtappend(format, s, strlen(s));
+}
+
+/*
+ * printfmt -- the driver routine
+ */
+
+extern int printfmt(Format *format, const char *fmt) {
+       unsigned const char *s = (unsigned const char *) fmt;
+
+       if (fmttab[0] == NULL)
+               inittab();
+
+       for (;;) {
+               int c = *s++;
+               switch (c) {
+               case '%':
+                       format->flags = format->f1 = format->f2 = 0;
+                       do
+                               c = *s++;
+                       while ((*fmttab[c])(format, c));
+                       break;
+               case '\0':
+                       return format->buf - format->bufbegin + format->flushed;
+               default:
+                       fmtputc(format, c);
+                       break;
+               }
+       }
+}
+
+
+/*
+ * the public entry points
+ */
+
+extern int fmtprint(Format *format, const char *fmt,...) {
+       int n = -format->flushed;
+       va_list ap, saveargs;
+
+       va_start(ap, fmt);
+       va_copy(saveargs, format->args);
+       va_copy(format->args, ap);
+       n += printfmt(format, fmt);
+       va_end(format->args);
+       va_copy(format->args, saveargs);
+
+       return n + format->flushed;
+}
+
+static void fprint_flush(Format *format, size_t ignore) {
+       size_t n = format->buf - format->bufbegin;
+       char *buf = format->bufbegin;
+
+       format->flushed += n;
+       format->buf = format->bufbegin;
+       writeall(format->u.n, buf, n);
+}
+
+extern int fprint(int fd, const char *fmt,...) {
+       char buf[1024];
+       Format format;
+       va_list ap;
+
+       format.buf      = buf;
+       format.bufbegin = buf;
+       format.bufend   = buf + sizeof buf;
+       format.grow     = fprint_flush;
+       format.flushed  = 0;
+       format.u.n      = fd;
+
+       va_start(ap, fmt);
+       va_copy(format.args, ap);
+       printfmt(&format, fmt);
+       va_end(format.args);
+
+       fprint_flush(&format, 0);
+       return format.flushed;
+}
+
+static void memprint_grow(Format *format, size_t more) {
+       char *buf;
+       size_t len = format->bufend - format->bufbegin + 1;
+       size_t used = format->buf - format->bufbegin;
+
+       len = (len >= more)
+               ? len * 2
+               : ((len + more) + PRINT_ALLOCSIZE) &~ (PRINT_ALLOCSIZE - 1);
+       if (format->u.n)
+               buf = erealloc(format->bufbegin, len);
+       else {
+               buf = nalloc(len);
+               memcpy(buf, format->bufbegin, used);
+       }
+       format->buf = buf + used;
+       format->bufbegin = buf;
+       format->bufend = buf + len - 1;
+}
+
+static char *memprint(Format *format, const char *fmt, char *buf, size_t len) {
+       format->buf      = buf;
+       format->bufbegin = buf;
+       format->bufend   = buf + len - 1;
+       format->grow     = memprint_grow;
+       format->flushed  = 0;
+       printfmt(format, fmt);
+       *format->buf = '\0';
+       return format->bufbegin;
+}
+
+extern char *mprint(const char *fmt,...) {
+       Format format;
+       char *result;
+       va_list ap;
+
+       format.u.n = 1;
+       va_start(ap, fmt);
+       va_copy(format.args, ap);
+       result = memprint(&format, fmt, ealloc(PRINT_ALLOCSIZE), PRINT_ALLOCSIZE);
+       va_end(format.args);
+       return result;
+}
+
+extern char *nprint(const char *fmt,...) {
+       Format format;
+       char *result;
+       va_list ap;
+
+       format.u.n = 0;
+       va_start(ap, fmt);
+       va_copy(format.args, ap);
+       result = memprint(&format, fmt, nalloc(PRINT_ALLOCSIZE), PRINT_ALLOCSIZE);
+       va_end(format.args);
+       return result;
+}
diff --git a/proto.h b/proto.h
new file mode 100644 (file)
index 0000000..4a2d74a
--- /dev/null
+++ b/proto.h
@@ -0,0 +1,100 @@
+/*
+  The idea of this file is to include prototypes for all external
+  functions that rc uses, either by including the appropriate header
+  file, or---for older systems---declaring the functions directly.
+*/
+
+#if HAVE_SYS_TYPES_H
+#include <sys/types.h>
+#endif
+
+#include <signal.h>
+
+#if HAVE_QUAD_T
+typedef quad_t align_t;
+#else
+typedef long align_t;
+#endif
+
+/*
+  We need <stdarg.h>.  If you really need to build rc on a system which
+  doesn't have it, please contact the maintainer.
+*/
+
+#include <stdarg.h>
+
+/* C 99 specifies a va_copy() macro to be used for copying
+objects of type va_list. If this doesn't exist, hope that simple
+assignment works. */
+#ifndef va_copy
+#define va_copy(x,y) (x)=(y)
+#endif
+
+#if STDC_HEADERS
+
+#include <stdlib.h>
+#include <string.h>
+
+#else /* STDC_HEADERS */
+
+/* fake string.h */
+extern int strncmp(const char *, const char *, size_t);
+extern int strcmp(const char *, const char *);
+extern size_t strlen(const char *);
+extern char *strchr(const char *, int);
+extern char *strrchr(const char *, int);
+extern char *strcpy(char *, const char *);
+extern char *strncpy(char *, const char *, size_t);
+extern char *strcat(char *, const char *);
+extern char *strncat(char *, const char *, size_t);
+extern void *memcpy(void *, const void *, size_t);
+extern void *memset(void *, int, size_t);
+
+/* fake stdlib.h */
+extern void exit(int);
+extern void free(void *);
+extern void *malloc(size_t);
+extern void *realloc(void *, size_t);
+extern void qsort(void *, size_t, size_t, int (*)(const void *, const void *));
+
+#endif /* STDC_HEADERS */
+
+#if HAVE_STRERROR
+/* Smells like POSIX. */
+#else
+/* Assume BSD-style sys_errlist[]. */
+extern int sys_nerr;
+extern char *sys_errlist[];
+#define strerror(x) ((0 <= (x)) && (errno < (x)) ? sys_errlist[x] : (char *)0)
+#endif
+
+#if HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
+#if HAVE_SETPGRP
+
+#if SETPGRP_VOID
+/* Smells like POSIX: should all be ok. */
+#else
+/* Old BSD: fake it. */
+#define setpgid(pid, pgrp) setpgrp(pid, pgrp)
+#include <sys/ioctl.h>
+#define tcgetpgrp(fd) ioctl((fd), TIOCGPGRP)
+#define tcsetpgrp(fd, pgrp) ioctl((fd), TIOCSPGRP, &(pgrp))
+#endif
+
+#else /* HAVE_SETPGRP */
+
+/* Nothing doing. */
+#define setpgid()
+#define tcgetpgrp()
+#define tcsetpgrp()
+
+#endif /*HAVE_SETPGRP */
+
+
+/* fake errno.h for mips (which doesn't declare errno in errno.h!?!?) */
+#ifdef host_mips
+extern int errno;
+#endif
diff --git a/rc.1 b/rc.1
new file mode 100644 (file)
index 0000000..4fecb87
--- /dev/null
+++ b/rc.1
@@ -0,0 +1,2163 @@
+.\" rc.1
+.\"-------
+.\" Man page portability notes
+.\"
+.\" These are some notes on conventions to maintain for greatest
+.\" portability of this man page to various other versions of
+.\" nroff.
+.\"
+.\" When you want a \ to appear in the output, use \e in the man page.
+.\" (NOTE this comes up in the rc grammar, where to print out '\n' the
+.\" man page must contain '\en'.)
+.\"
+.\" Evidently not all versions of nroff allow the omission of the
+.\" terminal " on a macro argument.  Thus what could be written
+.\"
+.\" .Cr "exec >[2] err.out
+.\"
+.\" in true nroffs must be written
+.\"
+.\" .Cr "exec >[2] err.out"
+.\"
+.\" instead.
+.\"
+.\" Use symbolic font names (e.g. R, I, B) instead of the standard
+.\" font positions 1, 2, 3.  Note that for Xf to work the standard
+.\" font names must be single characters.
+.\"
+.\" Not all man macros have the RS and RE requests (I altered the Ds
+.\" and De macros and the calls to Ds accordingly).
+.\"
+.\" Thanks to Michael Haardt (u31b3hs@cip-s01.informatik.rwth-aachen.de)
+.\" for pointing out these problems.
+.\"
+.\" Note that sentences should end at the end of a line.  nroff and
+.\" troff will supply the correct inter-sentence spacing, but only if
+.\" the sentences end at the end of a line.  Explicit spaces, if given,
+.\" are apparently honored and the normal inter-sentence spacing is
+.\" suppressed.
+.\"
+.\" DaviD W. Sanderson
+.\"-------
+.\" Dd distance to space vertically before a "display"
+.\" These are what n/troff use for inter-paragraph distance
+.\"-------
+.if t .nr Dd .4v
+.if n .nr Dd 1v
+.\"-------
+.\" Ds begin a display, indented .5 inches from the surrounding text.
+.\"
+.\" Note that uses of Ds and De may NOT be nested.
+.\"-------
+.de Ds
+.\" .RS \\$1
+.sp \\n(Ddu
+.in +0.5i
+.nf
+..
+.\"-------
+.\" De end a display (no trailing vertical spacing)
+.\"-------
+.de De
+.fi
+.in
+.\" .RE
+..
+.\"-------
+.\" I stole the Xf macro from the -man macros on my machine (originally
+.\" "}S", I renamed it so that it won't conflict).
+.\"-------
+.\" Set Cf to the name of the constant width font.
+.\" It will be "C" or "(CW", typically.
+.\" NOTEZ BIEN the lines defining Cf must have no trailing white space:
+.\"-------
+.if t .ds Cf C
+.if n .ds Cf R
+.\"-------
+.\" Rc - Alternate Roman and Courier
+.\"-------
+.de Rc
+.Xf R \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Ic - Alternate Italic and Courier
+.\"-------
+.de Ic
+.Xf I \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Bc - Alternate Bold and Courier
+.\"-------
+.de Bc
+.Xf B \\*(Cf \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Cr - Alternate Courier and Roman
+.\"-------
+.de Cr
+.Xf \\*(Cf R \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Ci - Alternate Courier and Italic
+.\"-------
+.de Ci
+.Xf \\*(Cf I \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Cb - Alternate Courier and Bold
+.\"-------
+.de Cb
+.Xf \\*(Cf B \& "\\$1" "\\$2" "\\$3" "\\$4" "\\$5" "\\$6"
+..
+.\"-------
+.\" Xf - Alternate fonts
+.\"
+.\" \$1 - first font
+.\" \$2 - second font
+.\" \$3 - desired word with embedded font changes, built up by recursion
+.\" \$4 - text for first font
+.\" \$5 - \$9 - remaining args
+.\"
+.\" Every time we are called:
+.\"
+.\" If         there is something in \$4
+.\" then       Call ourself with the fonts switched,
+.\"            with a new word made of the current word (\$3) and \$4
+.\"            rendered in the first font,
+.\"            and with the remaining args following \$4.
+.\" else       We are done recursing.  \$3 holds the desired output
+.\"            word.  We emit \$3, change to Roman font, and restore
+.\"            the point size to the default.
+.\" fi
+.\"
+.\" Use Xi to add a little bit of space after italic text.
+.\"-------
+.de Xf
+.ds Xi
+.\"-------
+.\" I used to test for the italic font both by its font position
+.\" and its name.  Now just test by its name.
+.\"
+.\" .if "\\$1"2" .if !"\\$5"" .ds Xi \^
+.\"-------
+.if "\\$1"I" .if !"\\$5"" .ds Xi \^
+.\"-------
+.\" This is my original code to deal with the recursion.
+.\" Evidently some nroffs can't deal with it.
+.\"-------
+.\" .ie !"\\$4"" \{\
+.\" .  Xf \\$2 \\$1 "\\$3\\f\\$1\\$4\\*(Xi" "\\$5" "\\$6" "\\$7" "\\$8" "\\$9"
+.\" .\}
+.\" .el \{\\$3
+.\" .  ft R    \" Restore the default font, since we don't know
+.\" .          \" what the last font change was.
+.\" .  ps 10   \" Restore the default point size, since it might
+.\" .          \" have been changed by an argument to this macro.
+.\" .\}
+.\"-------
+.\" Here is more portable (though less pretty) code to deal with
+.\" the recursion.
+.\"-------
+.if !"\\$4"" .Xf \\$2 \\$1 "\\$3\\f\\$1\\$4\\*(Xi" "\\$5" "\\$6" "\\$7" "\\$8" "\\$9"
+.if "\\$4"" \\$3\fR\s10
+..
+.TH RC 1 "2015-05-13"
+.SH NAME
+rc \- shell
+.SH SYNOPSIS
+.B rc
+.RB [ \-deiIlnopsvx ]
+.RB [ \-c
+.IR command ]
+.RI [ arguments ]
+.SH DESCRIPTION
+.I rc
+is a command interpreter and programming language similar to
+.IR sh (1).
+It is based on the AT&T Plan 9 shell of the same name.
+The shell offers a C-like syntax (much more so than the C shell),
+and a powerful mechanism for manipulating variables.
+It is reasonably small and reasonably fast,
+especially when compared to contemporary shells.
+Its use is intended to be interactive,
+but the language lends itself well to scripts.
+.SH OPTIONS
+.TP
+.Cr \-c
+If
+.Cr \-c
+is present, commands are executed from the immediately following
+argument.
+Any further arguments to
+.I rc
+are placed in
+.Cr $* .
+Thus:
+.Ds
+.Cr "rc -c 'echo $*' 1 2 3"
+.De
+.TP
+\&
+prints out
+.Ds
+.Cr "1 2 3"
+.De
+.TP
+.Cr \-d
+This flag causes
+.I rc
+not to ignore
+.Cr SIGQUIT
+or
+.Cr SIGTERM .
+Thus
+.I rc
+can be made to dump core if sent
+.Cr SIGQUIT .
+This flag is only useful for debugging
+.IR rc .
+.TP
+.Cr \-e
+If the
+.Cr \-e
+flag is present, then
+.I rc
+will exit if the exit status of a command is false (nonzero).
+.I rc
+will not exit, however, if a conditional fails, e.g., an
+.Cr if()
+command.
+.TP
+.Cr \-i
+If the
+.Cr \-i
+flag is present or if the input to
+.I rc
+is from a terminal (as determined by
+.IR isatty (3))
+then
+.I rc
+will be in
+.I interactive
+mode.
+That is, a prompt (from
+.Cr $prompt(1)\^ )
+will be printed before an input line is taken, and
+.I rc
+will ignore
+.Cr SIGINT .
+.TP
+.Cr \-I
+If the
+.Cr \-I
+flag is present, or if the input to
+.I rc
+is not from a terminal, then
+.I rc
+will not be in interactive mode.
+No prompts will be printed, and
+.Cr SIGINT
+will cause
+.I rc
+to exit.
+.TP
+.Cr \-l
+If the
+.Cr \-l
+flag is present, or if
+.IR rc 's
+.Cr argv[0][0]
+is a dash
+.Rc ( \- ),
+then
+.I rc
+will behave as a login shell.
+That is, it will run commands from
+.Cr $home/.rcrc ,
+if this file exists, before reading any other input.
+.TP
+.Cr \-n
+This flag causes
+.I rc
+to read its input and parse it, but not to execute any commands.
+This is useful for syntax checking on scripts.
+If used in combination with the
+.Cr \-x
+flag,
+.I rc
+will print each command as it is parsed in a form similar to the one
+used for exporting functions into the environment.
+.TP
+.Cr \-o
+This flag prevents the usual practice of trying to open
+.Cr /dev/null
+on file descriptors 0, 1, and 2, if any of those descriptors
+are inherited closed.
+.TP
+.Cr \-p
+This flag prevents
+.I rc
+from initializing shell functions from the environment.
+This allows
+.I rc
+to run in a protected mode, whereby it becomes more difficult for
+an
+.I rc
+script to be subverted by placing false commands in the environment.
+(Note that the presence of this flag does
+.I not
+mean that it is safe to run setuid
+.I rc
+scripts; the usual caveats about the setuid bit still apply.)
+.TP
+.Cr \-s
+This flag causes
+.I rc
+to read from standard input.
+Any arguments are placed in
+.Cr $* .
+.TP
+.Cr \-v
+This flag causes
+.I rc
+to echo its input
+to standard error as it is read.
+.TP
+.Cr \-x
+This flag causes
+.I rc
+to print every command on standard error before it is executed.
+It can be useful for debugging
+.I rc
+scripts.
+.PP
+.SH COMMANDS
+A simple command is a sequence of words, separated by white space
+(space and tab) characters that ends with a newline, semicolon
+.Rc ( ; ),
+or ampersand
+.Rc ( & ).
+The first word of a command is the name of that command.
+If the name begins with
+.Cr / ,
+.Cr ./ ,
+or
+.Cr ../ ,
+then the name is used as an absolute path
+name referring to an executable file.
+Otherwise, the name of the command is looked up in a table
+of shell functions, builtin commands,
+or as a file in the directories named by
+.Cr $path .
+.SS "Background Tasks"
+A command ending with
+.Cr &
+is run in the background; that is,
+the shell returns immediately rather than waiting for the command to
+complete.
+Background commands have
+.Cr /dev/null
+connected to their standard input unless an explicit redirection for
+standard input is used.
+.SS "Subshells"
+A command prefixed with an at-sign
+.Rc ( @ )
+is executed in a subshell.
+This insulates the parent shell from the effects
+of state changing operations such as a
+.B cd
+or a variable assignment.
+For example:
+.Ds
+.Cr "@ {cd ..; make}"
+.De
+.PP
+will run
+.IR make (1)
+in the parent directory
+.Rc ( .. ),
+but leaves the shell running in the current directory.
+.SS "Line continuation"
+A long logical line may be continued over several physical lines by
+terminating each line (except the last) with a backslash
+.Rc ( \e ).
+The backslash-newline sequence is treated as a space.
+A backslash is not otherwise special to
+.IR rc .
+(In addition,
+inside quotes a backslash loses its special meaning
+even when it is followed by a newline.)
+.SS Quoting
+.IR rc
+interprets several characters specially; special characters
+automatically terminate words.
+The following characters are special:
+.Ds
+.Cr "# ; & | ^ $ = \` ' { } ( ) < >"
+.De
+.PP
+The single quote
+.Rc ( ' )
+prevents special treatment of any character other than itself.
+All characters, including control characters, newlines,
+and backslashes between two quote characters are treated as an
+uninterpreted string.
+A quote character itself may be quoted by placing two quotes in a row.
+The minimal sequence needed to enter the quote character is
+.Cr '''' .
+The empty string is represented by
+.Cr '' .
+Thus:
+.Ds
+.Cr "echo 'What''s the plan, Stan?'"
+.De
+.PP
+prints out
+.Ds
+.Cr "What's the plan, Stan?"
+.De
+.PP
+The number sign
+.Rc ( # )
+begins a comment in
+.IR rc .
+All characters up to but not including the next newline are ignored.
+Note that backslash continuation does not work inside a comment,
+i.e.,
+the backslash is ignored along with everything else.
+.SS Grouping
+Zero or more commands may be grouped within braces
+.Rc (`` { ''
+and
+.Rc `` } ''),
+and are then treated as one command.
+Braces do not otherwise define scope;
+they are used only for command grouping.
+In particular, be wary of the command:
+.Ds
+.Cr "for (i) {"
+.Cr "    command"
+.Cr "} | command"
+.De
+.PP
+Since pipe binds tighter than
+.Cr for ,
+this command does not perform what the user expects it to.
+Instead, enclose the whole
+.Cr for
+statement in braces:
+.Ds
+.Cr "{for (i) command} | command"
+.De
+.PP
+Fortunately,
+.IR rc 's
+grammar is simple enough that a (confident) user can
+understand it by examining the skeletal
+.IR yacc (1)
+grammar
+at the end of this man page (see the section entitled
+.BR GRAMMAR ).
+.SS "Input and output"
+.PP
+The standard output may be redirected to a file with
+.Ds
+.Cr "command > file"
+.De
+.PP
+and the standard input may be taken from a file with
+.Ds
+.Cr "command < file"
+.De
+.PP
+Redirections can appear anywhere in the line: the word
+following the redirection symbol is the filename and must be
+quoted if it contains spaces or other special characters.
+These are all equivalent.
+.Ds
+.Cr "echo 1 2 3 > foo"
+.Cr "> foo echo 1 2 3"
+.Cr "echo 1 2 > foo 3"
+.De
+.PP
+File descriptors other than 0 and 1 may be specified also.
+For example, to redirect standard error to a file, use:
+.Ds
+.Cr "command >[2] file"
+.De
+.PP
+In order to duplicate a file descriptor, use
+.Ci >[ n = m ]\fR.
+Thus to redirect both standard output and standard error
+to the same file, use
+.Ds
+.Cr "command > file >[2=1]"
+.De
+.PP
+As in
+.IR sh ,
+redirections are processed from left to right.
+Thus this sequence
+.Ds
+.Cr "command >[2=1] > file"
+.De
+.PP
+is usually a mistake.
+It first duplicates standard error to standard
+output; then redirects standard output to a file, leaving standard error
+wherever standard output originally was.
+.PP
+To close a file descriptor that may be open, use
+.Ci >[ n =]\fR.
+For example, to
+close file descriptor 7:
+.Ds
+.Cr "command >[7=]"
+.De
+.PP
+Note that no spaces may appear in these constructs:
+.Ds
+.Cr "command > [2] file"
+.De
+.PP
+would send the output of the command to a file named
+.Cr [2] ,
+with the intended filename appearing in the command's argument list.
+.PP
+In order to place the output of a command at the end of an already
+existing file, use:
+.Ds
+.Cr "command >> file"
+.De
+.PP
+If the file does not exist, then it is created.
+.PP
+``Here documents'' are supported as in
+.I sh
+with the use of
+.Ds
+.Cr "command << 'eof-marker'"
+.De
+.PP
+Subsequent lines form the standard input of
+the command, till a line containing just the
+marker, in this case
+.Cr eof-marker ,
+is encountered.
+.PP
+If the end-of-file marker is enclosed in quotes,
+then no variable substitution occurs inside the here document.
+Otherwise, every variable is substituted
+by its space-separated-list value (see
+.BR "Flat Lists" ,
+below),
+and if a
+.Cr ^
+character follows a variable name, it is deleted.
+This allows the unambiguous use of variables adjacent to text, as in
+.Ds
+.Cr $variable^follow
+.De
+.PP
+To include a literal
+.Cr $
+in a here document when an unquoted end-of-file marker is being used,
+enter it as
+.Cr $$ .
+.PP
+Additionally,
+.I rc
+supports ``here strings'', which are like here documents,
+except that input is taken directly from a string on the command line.
+Their use is illustrated here:
+.Ds
+.Cr "cat <<< 'this is a here string' | wc"
+.De
+.PP
+(This feature enables
+.I rc
+to export functions using here documents into the environment;
+the author does not expect users to find this feature useful.)
+.SS Pipes
+Two or more commands may be combined in a pipeline by placing the
+vertical bar
+.Rc ( \||\| )
+between them.
+The standard output (file descriptor 1)
+of the command on the left is tied to the standard input (file
+descriptor 0) of the command on the right.
+The notation
+.Ci |[ n = m ]
+indicates that file descriptor
+.I n
+of the left process is connected to
+file descriptor
+.I m
+of the right process.
+.Ci |[ n ]
+is a shorthand for
+.Ci |[ n =0]\fR.
+As an example, to pipe the standard error of a command to
+.IR wc (1),
+use:
+.Ds
+.Cr "command |[2] wc"
+.De
+.PP
+As with file redirections, no spaces may occur in the construct specifying
+numbered file descriptors.
+.PP
+The exit status of a pipeline is considered true if and only if every
+command in the pipeline exits true.
+.SS "Commands as Arguments"
+Some commands, like
+.IR cmp (1)
+or
+.IR diff (1),
+take their arguments on the command
+line, and do not read input from standard input.
+It is convenient
+sometimes to build nonlinear pipelines so that a command like
+.I cmp
+can read the output of two other commands at once.
+.I rc
+does it like this:
+.Ds
+.Cr "cmp <{command} <{command}"
+.De
+.PP
+compares the output of the two commands in braces.
+Note: since this form of
+redirection is implemented with some kind of pipe, and since one cannot
+.IR lseek (2)
+on a pipe, commands that use
+.IR lseek (2)
+will hang.
+For example, some versions of
+.IR diff (1)
+use
+.IR lseek (2)
+on their inputs.
+.PP
+Data can be sent down a pipe to several commands using
+.IR tee (1)
+and the output version of this notation:
+.Ds
+.Cr "echo hi there | tee >{sed 's/^/p1 /'} >{sed 's/^/p2 /'}"
+.De
+.SH "CONTROL STRUCTURES"
+The following may be used for control flow in
+.IR rc :
+.SS "If-Else Statements"
+.PD 0
+.sp
+.Ci "if (" test ") {"
+.br
+.I  "    cmd"
+.br
+.TP
+.Ci "} else " cmd
+The
+.I test
+is executed, and if its return status is zero, the first
+command is executed, otherwise the second is.
+Braces are not mandatory around the commands.
+However, an
+.Cr else
+statement is valid only if it
+follows a close-brace on the same line.
+Otherwise, the
+.Cr if
+is taken to be a simple-if:
+.Ds
+.Cr "if (test)"
+.Cr "    command"
+.De
+.PD
+.SS "While and For Loops"
+.TP
+.Ci "while (" test ) " cmd"
+.I rc
+executes the
+.I test
+and performs the command as long as the
+.I test
+is true.
+.TP
+.Ci "for (" var " in " list ) " cmd"
+.I rc
+sets
+.I var
+to each element of
+.I list
+(which may contain variables and backquote substitutions) and runs
+.IR cmd .
+If
+.Rc `` in
+.IR list ''
+is omitted, then
+.I rc
+will set
+.I var
+to each element of
+.Cr $* .
+For example:
+.Ds
+.Cr "for (i in \`{ls -F | grep '\e*$' | sed 's/\e*$//'}) { commands }"
+.De
+.TP
+\&
+will set
+.Cr $i
+to the name of each file in the current directory that is
+executable.
+.SS "Switch"
+.TP
+.Ci "switch (" list ") { case" " ..." " }"
+.I rc
+looks inside the braces after a
+.Cr switch
+for statements beginning with the word
+.Cr case .
+If any of the patterns following
+.Cr case
+match the list supplied to
+.Cr switch ,
+then the commands up until the next
+.Cr case
+statement are executed.
+The metacharacters
+.Cr "*" ,
+.Cr [
+or
+.Cr ?
+should not be quoted;
+matching is performed only against the strings in
+.IR list ,
+not against file names.
+(Matching for case statements is the same as for the
+.Cr ~
+command.)
+.SS "Logical Operators"
+There are a number of operators in
+.I rc
+which depend on the exit status of a command.
+.Ds
+.Cr "command && command"
+.De
+.PP
+executes the first command and then executes the second command if and only if
+the first command exits with a zero exit status (``true'' in Unix).
+.Ds
+.Cr "command || command"
+.De
+.PP
+executes the first command and then executes the second command if and only if
+the first command exits with a nonzero exit status (``false'' in Unix).
+.Ds
+.Cr "! command"
+.De
+.PP
+negates the exit status of a command.
+.SH "PATTERN MATCHING"
+There are two forms of pattern matching in
+.IR rc .
+One is traditional shell globbing.
+This occurs in matching for file names in argument lists:
+.Ds
+.Cr "command argument argument ..."
+.De
+.PP
+When the characters
+.Cr "*" ,
+.Cr [
+or
+.Cr ?
+occur in an argument or command,
+.I rc
+looks at the
+argument as a pattern for matching against files.
+(Contrary to the behavior other shells exhibit,
+.I rc
+will only perform pattern matching if a metacharacter occurs unquoted and
+literally in the input.
+Thus,
+.Ds
+.Cr "foo='*'"
+.Cr "echo $foo"
+.De
+.PP
+will always echo just a star.
+In order for non-literal metacharacters to be expanded, an
+.Cr eval
+statement must be used in order to rescan the input.)
+Pattern matching occurs according to the following rules: a
+.Cr *
+matches any number (including zero) of
+characters.
+A
+.Cr ?
+matches any single character, and a
+.Cr [
+followed by a
+number of characters followed by a
+.Cr ]
+matches a single character in that
+class.
+The rules for character class matching are the same as those for
+.IR ed (1),
+with the exception that character class negation is achieved
+with the tilde
+.Rc ( ~ ),
+not the caret
+.Rc ( ^ ),
+since the caret already means
+something else in
+.IR rc .
+.PP
+.I rc
+also matches patterns against strings with the
+.Cr ~
+command:
+.Ds
+.Cr "~ subject pattern pattern ..."
+.De
+.PP
+.Cr ~
+sets
+.Cr $status
+to zero if and only if a supplied pattern matches any
+single element of the subject list.
+Thus
+.Ds
+.Cr "~ foo f*"
+.De
+.PP
+sets status to zero, while
+.Ds
+.Cr "~ (bar baz) f*"
+.De
+.PP
+sets status to one.
+The null list is matched by the null list, so
+.Ds
+.Cr "~ $foo ()"
+.De
+.PP
+checks to see whether
+.Cr $foo
+is empty or not.
+This may also be achieved
+by the test
+.Ds
+.Cr "~ $#foo 0"
+.De
+.PP
+Note that inside a
+.Cr ~
+command
+.I rc
+does not match patterns against file
+names, so it is not necessary to quote the characters
+.Cr "*" ,
+.Cr [
+and
+.Cr "?" .
+However,
+.I rc
+does expand the subject against filenames if it contains
+metacharacters.
+Thus, the command
+.Ds
+.Cr "~ * ?"
+.De
+.PP
+returns true if any of the files in the current directory have a
+single-character name.
+If the
+.Cr ~
+command is given a list as its first
+argument, then a successful match against any of the elements of that
+list will cause
+.Cr ~
+to return true.
+For example:
+.Ds
+.Cr "~ (foo goo zoo) z*"
+.De
+.PP
+is true.
+.SH "LISTS AND VARIABLES"
+The primary data structure in
+.IR rc
+is the list, which is a sequence of words.
+Parentheses are used to group lists.
+The empty list is represented by
+.Cr "()" .
+Lists have no hierarchical structure;
+a list inside another list is expanded so the
+outer list contains all the elements of the inner list.
+Thus, the following are all equivalent
+.Ds
+.Cr "one two three"
+
+.Cr "(one two three)"
+
+.Cr "((one) () ((two three)))"
+.De
+.PP
+Note that the null string,
+.Cr "''" ,
+and the null list,
+.Cr "()" ,
+are two very different things.
+Assigning the null string to a variable is a valid operation, but it
+does not remove its definition.
+.Ds
+.Cr "null = '' empty = () echo $#null $#empty"
+.De
+.PP
+produces the output
+.Ds
+.Cr "1 0"
+.De
+.SS "List Concatenation"
+Two lists may be joined by the concatenation operator
+.Rc ( ^ ).
+Concatenation works according to the following rules:
+if the two lists have the same number of elements,
+then concatenation is pairwise:
+.Ds
+.Cr "echo (a\- b\- c\-)^(1 2 3)"
+.De
+.PP
+produces the output
+.Ds
+.Cr "a\-1 b\-2 c\-3"
+.De
+.PP
+Otherwise, at least one of the lists must have a single element,
+and then the concatenation is distributive:
+.Ds
+.Cr "cc \-^(O g c) (malloc alloca)^.c"
+.De
+.PP
+has the effect of performing the command
+.Ds
+.Cr "cc \-O \-g \-c malloc.c alloca.c"
+.De
+.PP
+A single word is a list of length one, so
+.Ds
+.Cr "echo foo^bar"
+.De
+.PP
+produces the output
+.Ds
+.Cr foobar
+.De
+.SS "Free Carets"
+.I rc
+inserts carets (concatenation operators) for free in certain situations,
+in order to save some typing on the user's behalf.
+For
+example, the above example could also be typed in as:
+.Ds
+.Cr "opts=(O g c) files=(malloc alloca) cc \-$opts $files.c"
+.De
+.PP
+.I rc
+takes care to insert a free-caret between the
+.Rc `` \- ''
+and
+.Cr "$opts" ,
+as well
+as between
+.Cr $files
+and
+.Cr ".c" .
+The rule for free carets is as follows:  if
+a word or keyword is immediately
+followed by another word, keyword, dollar-sign or
+backquote, then
+.I rc
+inserts a caret between them.
+.SS "Variables"
+A list may be assigned to a variable, using the notation:
+.Ds
+.Ic var " = " list
+.De
+.PP
+The special variable
+.Cr *
+may also be assigned to using this notation;
+.I rc
+has no
+.B set
+builtin.
+.PP
+Any non-empty sequence of characters, except a sequence including only
+digits, may be used as a variable name.
+Any character except
+.Cr =
+may be used, but special characters must be quoted.
+All user-defined variables are exported into the environment.
+.PP
+The value of a variable is referenced with the dollar
+.Rc ( $ )
+operator:
+.Ds
+.Ci $ var
+.De
+.PP
+Any variable which has not been assigned a value returns the null list,
+.Cr "()" ,
+when referenced.
+Multiple references are allowed:
+.Ds
+.Cr "a = foo"
+.Cr "b = a"
+.Cr "echo $ $ b"
+.De
+.PP
+prints
+.Ds
+.Cr foo
+.De
+.PP
+A variable's definition may also be removed by
+assigning the null list to a variable:
+.Ds
+.Ic var =()
+.De
+.PP
+For ``free careting'' to work correctly,
+.I rc
+must make certain assumptions
+about what characters may appear in a variable name.
+.I rc
+assumes that a variable name consists only of alphanumeric characters,
+underscore
+.Rc ( \|_\| )
+and star
+.Rc ( * ).
+To reference a variable with other
+characters in its name, quote the variable name.
+Thus:
+.Ds
+.Cr "echo $'we$Ird:Variab!le'"
+.De
+.SS "Local Variables"
+Any number of variable assignments may be made local to a single
+command by typing:
+.Ds
+.Cr "a=foo b=bar ... command"
+.De
+.PP
+The command may be a compound command, so for example:
+.Ds
+.Cr "path=. ifs=() {"
+.Cr "    " ...
+.Cr }
+.De
+.PP
+sets
+.Cr path
+to
+.Cr .
+and removes
+.Cr ifs
+for the duration of one long compound command.
+.SS "Variable Subscripts"
+Variables may be subscripted with the notation
+.Ds
+.Ci $var( n )
+.De
+.PP
+where
+.I n
+is a list of integers (origin 1).
+The opening parenthesis must immediately follow the variable name.
+The list of subscripts need not be in order or even unique.
+Thus,
+.Ds
+.Cr "a=(one two three)"
+.Cr "echo $a(3 3 3)"
+.De
+.PP
+prints
+.Ds
+.Cr "three three three"
+.De
+.PP
+If
+.I n
+references a nonexistent element, then
+.Ci $var( n )
+returns the null list.
+The notation
+.Ci "$" n\fR,
+where
+.I n
+is an integer, is a shorthand for
+.Ci $*( n )\fR.
+Thus,
+.IR rc 's
+arguments may be referred to as
+.Cr "$1" ,
+.Cr "$2" ,
+and so on.
+.PP
+Note also that the list of subscripts may be given by any of
+.IR rc 's
+list operations:
+.Ds
+.Cr "$var(\`{awk 'BEGIN{for(i=1;i<=10;i++)print i;exit; }'})"
+.De
+.PP
+returns the first 10 elements of
+.Cr $var .
+.PP
+To count the number of elements in a variable, use
+.Ds
+.Cr $#var
+.De
+.PP
+This returns a single-element list, with the number of elements in
+.Cr $var .
+.SS "Flat Lists"
+In order to create a single-element list from a multi-element list,
+with the components space-separated, use the dollar-caret
+.Rc ( $^ )
+operator:
+.Ds
+.Cr $^var
+.De
+.PP
+This is useful when the normal list concatenation rules need to be
+bypassed.
+For example, to append a single period at the end of
+.Cr $path ,
+use:
+.Ds
+.Cr "echo $^path."
+.De
+.PP
+For compability with the Plan 9 rc,
+.Ds
+.Cr $"var
+.De
+.PP
+is accepted as a synonym for dollar-caret.
+.SS "Backquote Substitution"
+A list may be formed from the output of a command by using backquote
+substitution:
+.Ds
+.Cr "\`{ command }"
+.De
+.PP
+returns a list formed from the standard output of the command in braces.
+.Cr $ifs
+is used to split the output into list elements.
+By default,
+.Cr $ifs
+has the value space-tab-newline.
+The braces may be omitted if the command is a single word.
+Thus
+.Cr \`ls
+may be used instead of
+.Cr "\`{ls}" .
+This last feature is useful when defining functions that expand
+to useful argument lists.
+A frequent use is:
+.Ds
+.Cr "fn src { echo *.[chy] }"
+.De
+.PP
+followed by
+.Ds
+.Cr "wc \`src"
+.De
+.PP
+(This will print out a word-count of all C source files in the current
+directory.)
+.PP
+In order to override the value of
+.Cr $ifs
+for a single backquote
+substitution, use:
+.Ds
+.Cr "\`\` (ifs-list) { command }"
+.De
+.PP
+.Cr $ifs
+will be temporarily ignored and the command's output will be split as specified by
+the list following the double backquote.
+For example:
+.Ds
+.Cr "\`\` ($nl :) {cat /etc/passwd}"
+.De
+.PP
+splits up
+.Cr /etc/passwd
+into fields, assuming that
+.Cr $nl
+contains a newline
+as its value.
+.SH "SPECIAL VARIABLES"
+Several variables are known to
+.I rc
+and are treated specially.
+In the following list, ``default'' indicates that
+.I rc
+gives the variable a default value on startup; ``no-export'' indicates
+that the variable is never exported; and ``read-only'' indicates that
+an attempt to set the variable will silently have no effect.
+.PP
+Also, ``alias'' means that the variable is aliased to the same name in
+capitals.
+For example, an assignment to
+.Cr $cdpath
+causes an automatic assignment to
+.Cr $CDPATH ,
+and vice-versa.
+If
+.Cr $CDPATH
+is set when
+.I rc
+is started, its value is imported into
+.Cr $cdpath .
+.Cr $cdpath
+and
+.Cr $path
+are
+.I rc
+lists;
+.Cr $CDPATH
+and
+.Cr $PATH
+are colon-separated lists.
+Only the names spelt in capitals are exported into the environment.
+.TP
+.Cr * " (no-export)"
+The argument list of
+.IR rc .
+.Cr "$1, $2,"
+etc. are the same as
+.Cr $*(1) ,
+.Cr $*(2) ,
+etc.
+.TP
+.Cr 0 " (default no-export)"
+The variable
+.Cr $0
+holds the value of
+.Cr argv[0]
+with which
+.I rc
+was invoked.
+Additionally,
+.Cr $0
+is set to the name of a function for the duration of
+the execution of that function, and
+.Cr $0
+is also set to the name of the
+file being interpreted for the duration of a
+.Cr .
+command.
+.Cr $0
+is not an element of
+.Cr $* ,
+and is never treated as one.
+.TP
+.Cr apid " (no-export)"
+The process ID of the last process started in the background.
+.TP
+.Cr apids " (no-export read-only)"
+A list whose elements are the process IDs of all background processes
+which are still alive, or which have died and have not been waited for
+yet.
+.TP
+.Cr bqstatus " (no-export)"
+The exit status of the
+.I rc
+forked to execute the most recent backquote substitution.  Note that, unlike
+.Cr $status ,
+.Cr $bqstatus
+is always a single element list (see
+.BR "EXIT STATUS"
+below).  For example:
+.Ds
+.Cr "echo foo |grep bar; whatis status"
+.De
+.TP
+\&
+prints
+.Ds
+.Cr "status=(0 1)"
+.De
+.TP
+\&
+whereas
+.Ds
+.Cr "x=`{echo foo |grep bar}; whatis bqstatus"
+.De
+.TP
+\&
+prints
+.Ds
+.Cr "bqstatus=1"
+.De
+.TP
+.Cr cdpath " (alias)"
+A list of directories to search for the target of a
+.B cd
+command.
+The empty string stands for the current directory.
+Note that if the
+.Cr $cdpath
+variable does not contain the current directory, then the current
+directory will not be searched; this allows directory searching to
+begin in a directory other than the current directory.
+.TP
+.Cr history
+.Cr $history
+contains the name of a file to which commands are appended as
+.I rc
+reads them.
+This facilitates the use of a stand-alone history program
+(such as
+.IR history (1))
+which parses the contents of the history file and presents them to
+.I rc
+for reinterpretation.
+If
+.Cr $history
+is not set, then
+.I rc
+does not append commands to any file.
+.TP
+.Cr home " (alias)"
+The default directory for the builtin
+.B cd
+command, and the directory in which
+.I rc
+looks to find its initialization file,
+.Cr .rcrc ,
+if
+.I rc
+has been started up as a login shell.
+.TP
+.Cr ifs " (default)"
+The internal field separator, used for splitting up the output of
+backquote commands for digestion as a list.  On startup,
+.I rc
+assigns the list containing the characters space, tab, and newline to
+.Cr $ifs .
+.TP
+.Cr path " (alias)"
+This is a list of directories to search in for commands.
+The empty string stands for the current directory.
+If neither
+.Cr $PATH
+nor
+.Cr $path
+is set at startup time,
+.Cr $path
+assumes a default value suitable for your system.
+This is typically
+.Cr "(/usr/local/bin /usr/bin /usr/ucb /bin .)"
+.TP
+.Cr pid " (default no-export)"
+On startup,
+.Cr $pid
+is initialized to the numeric process ID of the currently running
+.IR rc .
+.TP
+.Cr prompt " (default)"
+This variable holds the two prompts (in list form, of course) that
+.I rc
+prints.
+.Cr $prompt(1)
+is printed before each command is read, and
+.Cr $prompt(2)
+is printed when input is expected to continue on the next
+line.
+.I rc
+sets
+.Cr $prompt
+to
+.Cr "('; ' '')"
+by default.
+The reason for this is that it enables an
+.I rc
+user to grab commands from previous lines using a
+mouse, and to present them to
+.I rc
+for re-interpretation; the semicolon
+prompt is simply ignored by
+.IR rc .
+The null
+.Cr $prompt(2)
+also has its
+justification:  an
+.I rc
+script, when typed interactively, will not leave
+.Cr $prompt(2) 's
+on the screen,
+and can therefore be grabbed by a mouse and placed
+directly into a file for use as a shell script, without further editing
+being necessary.
+.TP
+.Cr prompt " (function)"
+If this function is defined, then it gets executed every time
+.I rc
+is about to print
+.Cr "$prompt(1)" .
+.TP
+.Cr status " (no-export read-only)"
+The exit status of the last command.
+If the command exited with a numeric value, that number is the status.
+If the command died with a signal, the status is the name of that signal;
+if a core file was created, the string
+.Rc `` +core ''
+is appended.
+The value of
+.Cr $status
+for a pipeline is a list, with one entry, as above, for each process
+in the pipeline.
+For example, the command
+.Ds
+.Cr "ls | wc"
+.De
+.TP
+\&
+usually sets
+.Cr $status
+to
+.Cr "(0 0)" .
+.TP
+.Cr version " (default)"
+On startup, the first element of this list variable is initialized to
+a string which identifies this version of
+.IR rc .
+The second element is initialized to a string which can be found by
+.IR ident (1)
+and the
+.I what
+command of 
+.IR sccs (1).
+.SH FUNCTIONS
+.I rc
+functions are identical to
+.I rc
+scripts, except that they are stored
+in memory and are automatically exported into the environment.
+A shell function is declared as:
+.Ds
+.Cr "fn name { commands }"
+.De
+.PP
+.I rc
+scans the definition until the close-brace, so the function can
+span more than one line.
+The function definition may be removed by typing
+.Ds
+.Cr "fn name"
+.De
+.PP
+(One or more names may be specified.
+With an accompanying definition, all names receive the same definition.
+This is sometimes useful
+for assigning the same signal handler to many signals.
+Without a definition, all named functions are deleted.)
+When a function is executed,
+.Cr $*
+is set to the arguments to that
+function for the duration of the command.
+Thus a reasonable definition for
+.Cr "l" ,
+a shorthand for
+.IR ls (1),
+could be:
+.Ds
+.Cr "fn l { ls -FC $* }"
+.De
+.PP
+but not
+.Ds
+.Cr "fn l { ls -FC } # WRONG"
+.De
+.SH "INTERRUPTS AND SIGNALS"
+.I rc
+recognizes a number of signals, and allows the user to define shell
+functions which act as signal handlers.
+.I rc
+by default traps
+.Cr SIGINT
+when it is in interactive mode.
+.Cr SIGQUIT
+and
+.Cr SIGTERM
+are ignored, unless
+.I rc
+has been invoked with the
+.Cr \-d
+flag.
+However, user-defined signal handlers may be written for these and
+all other signals.
+The way to define a signal handler is to
+write a function by the name of the signal in lower case.
+Thus:
+.Ds
+.Cr "fn sighup { echo hangup; rm /tmp/rc$pid.*; exit }"
+.De
+.PP
+In addition to Unix signals,
+.I rc
+recognizes the artificial signal
+.Cr SIGEXIT
+which occurs as
+.I rc
+is about to exit.
+.PP
+In order to remove a signal handler's definition,
+remove it as though it were a regular function.
+For example:
+.Ds
+.Cr "fn sigint"
+.De
+.PP
+returns the handler of
+.Cr SIGINT
+to the default value.
+In order to ignore a signal, set the signal handler's value to
+.Cr "{}" .
+Thus:
+.Ds
+.Cr "fn sigint {}"
+.De
+.PP
+causes
+.Cr SIGINT
+to be ignored by the shell.
+Only signals that are being ignored are passed on to programs run by
+.IR rc ;
+signal functions are not exported.
+.PP
+On System V-based Unix systems,
+.I rc
+will not allow you to trap
+.Cr SIGCLD .
+.SH "BUILTIN COMMANDS"
+Builtin commands execute in the context of the shell, but otherwise
+behave exactly like other commands.
+Although
+.BR ! ,
+.B ~
+and
+.B @
+are not strictly speaking builtin commands,
+they can usually be used as such.
+.TP
+\&\fB.\fR [\fB\-i\fR] \fIfile \fR[\fIarg ...\fR]
+Reads
+.I file
+as input to
+.IR rc
+and executes its contents.
+With a
+.Cr \-i
+flag, input is interactive.
+Thus from within a shell script,
+.Ds
+.Cr ". \-i /dev/tty"
+.De
+.TP
+\&
+does the ``right thing''.
+.TP
+.B break
+Breaks from the innermost
+.Cr for
+or
+.Cr while ,
+as in C.
+It is an error to invoke
+.B break
+outside of a loop.
+(Note that there is no
+.B break
+keyword between commands in
+.Cr switch
+statements, unlike C.)
+.TP
+\fBbuiltin \fIcommand \fR[\fIarg ...\fR]
+Executes the command ignoring any function definition of the
+same name.
+This command is present to allow functions with the
+same names as builtins to use the underlying builtin or binary.
+For example:
+.Ds
+.Cr "fn ls { builtin ls -FC $* }"
+.De
+.TP
+\&
+is a reasonable way to pass a default set of arguments to
+.Cr ls (1),
+whereas
+.Ds
+.Cr "fn ls { ls -FC $* } # WRONG"
+.De
+.TP
+\&
+is a non-terminating recursion, which will cause
+.Cr rc
+to exhaust its stack space and (eventually) terminate if it is executed.
+.TP
+\fBcd \fR[\fIdirectory\fR]
+Changes the current directory to
+.IR directory .
+The variable
+.Cr $cdpath
+is searched for possible locations of
+.IR directory ,
+analogous to the searching of
+.Cr $path
+for executable files.
+With no argument,
+.B cd
+changes the current directory to
+.Cr "$home" .
+.TP
+\fBecho \fR[\fB\-n\fR] [\fB\-\|\-\fR] [\fIarg ...\fR]
+Prints its arguments to standard output, terminated by a newline.
+Arguments are separated by spaces.
+If the first argument is
+.Cr "\-n"
+no final newline is printed.
+If the first argument is
+.Cr "\-\|\-" ,
+then all other arguments are echoed literally.
+This is used for echoing a literal
+.Cr "\-n" .
+.TP
+\fBeval \fR[\fIlist\fR]
+Concatenates the elements of
+.I list
+with spaces and feeds the resulting string to
+.I rc
+for re-scanning.
+This is the only time input is rescanned in
+.IR rc .
+.TP
+\fBexec \fR[\fIarg ...\fR]
+Replaces
+.I rc
+with the given command.
+If the exec contains only redirections,
+then these redirections apply to the current shell
+and the shell does not exit.
+For example,
+.Ds
+.Cr "exec >[2] err.out"
+.De
+.TP
+\&
+places further output to standard error in the file
+.IR err.out .
+.TP
+\fBexit \fR[\fIstatus\fR]
+Cause the current shell to exit with the given exit
+.IR status .
+If no argument is given, the current value of
+.Cr $status
+is used.
+.TP
+\fBlimit \fR[\fB\-h\fR] [\fIresource \fR[\fIvalue\fR]]
+Similar to the
+.IR csh (1)
+.B limit
+builtin, this command operates upon the
+BSD-style resource limits of a process.
+The
+.Cr \-h
+flag displays/alters the hard
+limits.
+The resources which can be shown or altered are
+.BR cputime ,
+.BR filesize ,
+.BR datasize ,
+.BR stacksize ,
+.BR coredumpsize ,
+.BR memoryuse ,
+and, where supported,
+.BR descriptors ,
+.BR memoryuse ,
+.BR memoryrss ,
+.BR maxproc ,
+.BR memorylocked ,
+and
+.BR filelocks .
+For example:
+.Ds
+.Cr "limit coredumpsize 0"
+.De
+.TP
+\&
+disables core dumps.
+To set a soft limit equal to the hard limit:
+.Ds
+.Cr "limit `{limit -h datasize}"
+.De
+.TP
+.B newpgrp
+Puts
+.I rc
+into a new process group.
+This builtin is useful for making
+.I rc
+behave like a job-control shell in a hostile environment.
+One example is the NeXT Terminal program, which implicitly assumes
+that each shell it forks will put itself into a new process group.
+.TP
+\fBreturn \fR[\fIn\fR]
+Returns from the current function, with status
+.IR n ,
+where
+.IR n
+is a valid exit status, or a list of them.
+Thus it is legal to have
+.Ds
+.Cr "return (sigpipe 1 2 3)"
+.De
+.TP
+\&
+(This is commonly used to allow a function to return with the exit status
+of a previously executed pipeline of commands.)
+If
+.IR n
+is omitted, then
+.Cr $status
+is left unchanged.
+It is an error to invoke
+.B return
+when not inside a function.
+.TP
+\fBshift \fR[\fIn\fR]
+Deletes
+.I n
+elements from the beginning of
+.Cr $*
+and shifts the other
+elements down by
+.IR n .
+.I n
+defaults to 1.
+.TP
+\fBumask \fR[\fImask\fR]
+Sets the current umask (see
+.IR umask (2))
+to the octal
+.IR mask .
+If no argument is present, the current mask value is printed.
+.TP
+\fBwait \fR[\fIpid\fR]
+Waits for process with the specified
+.IR pid ,
+which must have been started by
+.IR rc ,
+to exit.
+If no
+.I pid
+is specified,
+.I rc
+waits for all its child processes to exit.
+.TP
+\fBwhatis \fR[\fB\-b\fR] \fR[\fB\-f\fR] \fR[\fB\-p\fR] \fR[\fB\-s\fR] \fR[\fB\-v\fR] [\fB\-\|\-\fR] [\fIname ...\fR]
+Prints a definition of the named objects.
+For builtins,
+.Cr builtin
+.I foo
+is printed; for functions, including signal handlers, their definitions
+are printed; for executable files, path names are printed; and for
+variables, their values are printed.
+The flags restrict output to builtins, functions, executable
+programs, signal handlers, and variables, respectively.
+If no
+.IR name s
+are specified,
+.I rc
+lists all objects of that type.
+(This is not permitted for
+.Cr \-p .)
+Without arguments,
+.Cr whatis
+is equivalent to
+.Cr "whatis -fv" ,
+and prints the values of all shell variables and functions.
+.TP
+\&
+Note that
+.B whatis
+output is suitable for input to
+.IR rc ;
+by saving the output of
+.B whatis
+in a file, it should be possible to recreate the state of
+.I rc
+by sourcing this file with a
+.Cr .
+command.
+Another note:
+.Cr "whatis -s > file"
+cannot be used to store the state of
+.IR rc 's
+signal handlers in a file, because builtins with redirections
+are run in a subshell, and
+.I rc
+always restores signal handlers to their default value after a
+.Cr fork() .
+.TP
+\&
+Since
+.B whatis
+uses
+.IR getopt (3)
+to parse its arguments, you can use the special argument
+.Cr "\-\|\-"
+to terminate its flags.
+This allows you to use names beginning with a dash, such as
+the
+.IR history (1)
+commands.
+For example,
+.Ds
+.Cr "whatis \-\|\- \-p"
+.De
+.SH EXAMPLES
+The
+.B shift
+builtin only shifts
+.Cr "$*" .
+This function can shift any variable (except
+.Cr "$lshift" ).
+.Ds
+.Cr "fn lshift { lshift=$*; *=$$1; shift $lshift(2); $lshift(1)=$* }"
+.De
+.PP
+With this definition in place,
+.Ds
+.Cr "walrus = (shoes ships sealing-wax cabbages kings)"
+.Cr "lshift walrus 3"
+.Cr "whatis walrus"
+.De
+.PP
+prints
+.Ds
+.Cr "walrus=(cabbages kings)"
+.De
+.PP
+The
+.Cr $^var
+operator flattens a list by separating each element with a space.
+This function allows the separator to be an arbitrary string.
+.Ds
+.Cr "fn lflat {"
+.Cr "  lflat=$*; *=$$1"
+.Cr "  while () {"
+.Cr "    echo -n $1; shift"
+.Cr "    ~ $#* 0 && break"
+.Cr "    echo -n $lflat(2)"
+.Cr "}"
+.De
+.PP
+With this definition in place,
+.Ds
+.Cr "hops=(uunet mcvax ukc tlg)"
+.Cr "lflat hops !"
+.De
+.PP
+prints (with no final newline)
+.Ds
+.Cr uunet!mcvax!ukc!tlg
+.De
+.SH "EXIT STATUS"
+The exit status of
+.I rc
+is normally the same as that of the last command executed.
+If the
+last command was a pipeline,
+.I rc
+exits
+.Cr 0
+if every command in the pipeline did; otherwise it exits
+.Cr 1 .
+.PP
+.I rc
+can be made to exit with a particular status using the
+.B exit
+builtin.
+.SH GRAMMAR
+Here is
+.IR rc 's
+grammar, edited to remove semantic actions.
+.Ds
+.ft \*(Cf
+%term ANDAND BACKBACK BANG CASE COUNT DUP ELSE END FLAT FN FOR IF IN
+%term OROR PIPE REDIR SUB SUBSHELL SWITCH TWIDDLE WHILE WORD HUH
+
+%left WHILE ')' ELSE
+%left ANDAND OROR '\en'
+%left BANG SUBSHELL
+%left PIPE
+%right '$'
+%left SUB
+
+%start rc
+
+%%
+
+rc: line end
+       | error end
+
+end: END /* EOF */ | '\en'
+
+cmdsa: cmd ';' | cmd '&'
+
+line: cmd | cmdsa line
+
+body: cmd | cmdsan body
+
+cmdsan: cmdsa | cmd '\en'
+
+brace: '{' body '}'
+
+paren: '(' body ')'
+
+assign: first '=' word
+
+epilog: /* empty */ | redir epilog
+
+redir: DUP | REDIR word
+
+case: CASE words ';' | CASE words '\en'
+
+cbody: cmd | case cbody | cmdsan cbody
+
+iftail: cmd    %prec ELSE
+       | brace ELSE optnl cmd
+
+cmd    : /* empty */   %prec WHILE
+       | simple
+       | brace epilog
+       | IF paren optnl iftail
+       | FOR '(' word IN words ')' optnl cmd
+       | FOR '(' word ')' optnl cmd
+       | WHILE paren optnl cmd 
+       | SWITCH '(' word ')' optnl '{' cbody '}'
+       | TWIDDLE optcaret word words
+       | cmd ANDAND optnl cmd
+       | cmd OROR optnl cmd
+       | cmd PIPE optnl cmd
+       | redir cmd     %prec BANG
+       | assign cmd    %prec BANG
+       | BANG optcaret cmd
+       | SUBSHELL optcaret cmd
+       | FN words brace
+       | FN words
+
+optcaret: /* empty */ | '^'
+
+simple: first | simple word | simple redir
+
+first: comword | first '^' sword
+
+sword: comword | keyword
+
+word: sword | word '^' sword
+
+comword: '$' sword
+       | '$' sword SUB words ')'
+       | COUNT sword
+       | FLAT sword
+       | '`' sword
+       | '`' brace
+       | BACKBACK word brace | BACKBACK word sword
+       | '(' words ')'
+       | REDIR brace
+       | WORD
+
+keyword: FOR | IN | WHILE | IF | SWITCH
+       | FN | ELSE | CASE | TWIDDLE | BANG | SUBSHELL
+
+words: /* empty */ | words word
+
+optnl: /* empty */ | optnl '\en'
+.ft R
+.De
+.SH FILES
+.Cr $HOME/.rcrc ,
+.Cr /tmp/rc* ,
+.Cr /dev/null
+.SH CREDITS
+.I rc
+was written by Byron Rakitzis, with valuable help
+from Paul Haahr, Hugh Redelmeier and David Sanderson.
+The design of this shell was copied from the
+.I rc
+that Tom Duff wrote at Bell Labs.
+.SH BUGS
+There is a compile-time limit on the number of
+.Cr ;
+separated commands in a line: usually 500.
+This is sometimes a problem for automatically generated scripts:
+substituting the newline character for
+.Cr ;
+avoids the limit.
+.PP
+On modern systems that support
+.Cr /dev/fd
+or
+.Cr /proc/self/fd ,
+.Cr <{foo}
+style redirection is implemented that way.
+However, on older systems it is implemented with named pipes.
+Allegedly, it is sometimes possible to foil
+.I rc
+into removing the FIFO it places in
+.Cr /tmp
+prematurely, or it is even possible to cause
+.I rc
+to hang.
+(The current maintainer has never seen this, but then he
+doesn't use systems which lack
+.Cr /dev/fd
+any more.
+If anybody can reproduce this problem, please let the maintainer know.)
+.PP
+The
+.B echo
+command does not need to be a builtin.  It is one for reasons of
+performance and portability (of
+.I rc
+scripts).
+.PP
+There should be a way to avoid exporting a variable.
+.PP
+Extra parentheses around a
+.Cr ~
+expression or a
+.Cr !
+expression are a syntax error.
+Thus, this code is illegal.
+.Ds
+.Cr "while ((~ $1 -*) && (! ~ $1 --)) { ..."
+.De
+.TP
+The redundant inner parentheses must be omitted.
+.PP
+Variable subscripting cannot be used in here documents.
+.PP
+The
+.Cr limit
+builtin silently ignores extra arguments.
+.PP
+Backquote substitution never produces empty strings - multiple
+consecutive occurrences of the separator are treated the same as a
+single occurrence.
+.Ds
+.Cr "ifs=! { x = `{echo -n a!!b}; whatis x }"
+.Cr "x=(a b) # NOT x=(a '' b)"
+.PP
+Bug reports should be mailed to
+.Cr "<toby@paccrat.org>" .
+.SH INCOMPATIBILITIES
+Here is a list of features which distinguish this incarnation of
+.I rc
+from the one described in the Bell Labs manual pages:
+.PP
+The Tenth Edition
+.I rc
+does not have the
+.B else
+keyword.
+Instead,
+.B if
+is optionally followed by
+an
+.B "if not"
+clause which is executed
+if the preceding
+.B if
+test does not succeed.
+.PP
+Backquotes are slightly different in Tenth Edition
+.IR rc :
+a backquote must always be followed by a left-brace.
+This restriction is not present for single-word commands in this
+.IR rc .
+.PP
+For
+.Cr .
+.IR file ,
+the Tenth Edition
+.IR rc
+searches
+.Cr $path
+for
+.IR file .
+This
+.I rc
+does not, since it is not considered useful.
+.PP
+The list flattening operator,
+.Cr $^foo ,
+is spelt
+.Cr "$""foo"
+in those versions of the Bell Labs
+.IR rc
+which have it.
+.PP
+The following are all new with this version of
+.IR rc :
+The
+.Cr \-n
+flag,
+here strings (they facilitate exporting of functions
+with here documents into the environment),
+the
+.B return
+and
+.B break
+keywords,
+the
+.B echo
+builtin,
+the
+.Cr bqstatus
+and
+.Cr version
+variables,
+the support for the GNU
+.IR readline (3)
+library,
+and the support for the
+.Cr prompt
+function.
+This
+.I rc
+also sets
+.Cr $0
+to the name of a function being executed/file
+being sourced.
+.SH "SEE ALSO"
+``rc \(em A Shell for Plan 9 and UNIX Systems'',
+Unix Research System,
+Tenth Edition,
+Volume 2. (Saunders College Publishing)
+.PP
+.Cr http://static.tobold.org/rc/rc-duff.html ,
+an updated version of the above paper.
+.PP
+.IR history (1)
diff --git a/rc.h b/rc.h
new file mode 100644 (file)
index 0000000..2912e60
--- /dev/null
+++ b/rc.h
@@ -0,0 +1,394 @@
+#undef NDEBUG
+#include "config.h"
+#include "proto.h"
+
+#include <assert.h>
+
+#define RC "rc: "
+
+/* datatypes */
+
+#define ENV_SEP '\001'
+#define ENV_ESC '\002'
+
+/* braindamaged IBM header files #define true and false */
+#undef FALSE
+#undef TRUE
+
+typedef void builtin_t(char **);
+typedef struct Block Block;
+typedef struct Dup Dup;
+typedef struct Estack Estack;
+typedef struct rc_Function rc_Function;
+typedef struct Hq Hq;
+typedef struct Htab Htab;
+typedef struct Jbwrap Jbwrap;
+typedef struct List List;
+typedef struct Node Node;
+typedef struct Pipe Pipe;
+typedef struct Redir Redir;
+typedef struct Rq Rq;
+typedef struct Variable Variable;
+typedef struct Word Word;
+typedef struct Format Format;
+typedef union Edata Edata;
+
+typedef enum nodetype {
+       nAndalso, nAssign, nBackq, nBang, nBody, nCbody, nNowait, nBrace,
+       nConcat, nCount, nElse, nFlat, nDup, nEpilog, nNewfn, nForin, nIf,
+       nOrelse, nPipe, nPre, nRedir, nRmfn, nArgs, nSubshell, nCase,
+       nSwitch, nMatch, nVar, nVarsub, nWhile, nWord, nLappend, nNmpipe
+} nodetype;
+
+typedef enum ecodes {
+       eError, eBreak, eReturn, eVarstack, eArena, eFifo, eFd
+} ecodes;
+
+typedef enum bool {
+       FALSE, TRUE
+} bool;
+
+typedef enum redirtype {
+       rFrom, rCreate, rAppend, rHeredoc, rHerestring
+} redirtype;
+
+typedef bool (*Conv)(Format *, int);
+
+union Edata {
+       Jbwrap *jb;
+       Block *b;
+       char *name;
+       int fd;
+};
+
+struct Estack {
+       ecodes e;
+       bool interactive;
+       Edata data;
+       Estack *prev;
+};
+
+struct List {
+       char *w, *m;
+       List *n;
+};
+
+struct Node {
+       nodetype type;
+       union {
+               char *s;
+               int i;
+               Node *p;
+       } u[4];
+};
+
+struct Pipe {
+       int left, right;
+};
+
+struct Dup {
+       redirtype type;
+       int left, right;
+};
+
+struct Redir {
+       redirtype type;
+       int fd;
+};
+
+struct Word {
+       char *w, *m;
+       bool q;
+};
+
+struct Rq {
+       Node *r;
+       struct Rq *n;
+};
+
+struct rc_Function {
+       Node *def;
+       char *extdef;
+};
+
+struct Variable {
+       List *def;
+       char *extdef;
+       Variable *n;
+};
+
+struct Htab {
+       char *name;
+       void *p;
+};
+
+struct Format {
+       /* for the formatting routines */
+       va_list args;
+       long flags, f1, f2;
+       /* for the buffer maintenance routines */
+       char *buf, *bufbegin, *bufend;
+       int flushed;
+       void (*grow)(Format *, size_t);
+       union { int n; void *p; } u;
+};
+
+/* Format->flags values */
+enum {
+       FMT_quad        = 1,            /* %q */
+       FMT_long        = 2,            /* %l */
+       FMT_unsigned    = 8,            /* %u */
+       FMT_zeropad     = 16,           /* %0 */
+       FMT_leftside    = 32,           /* %- */
+       FMT_altform     = 64,           /* %# */
+       FMT_f1set       = 128,          /* %<n> */
+       FMT_f2set       = 256           /* %.<n> */
+};
+
+/* macros */
+#define EOF (-1)
+#ifndef NULL
+#define NULL 0
+#endif
+#define a2u(x) n2u(x, 10)
+#define o2u(x) n2u(x, 8)
+#define arraysize(a) ((int)(sizeof(a)/sizeof(*a)))
+#define memzero(s, n) memset(s, 0, n)
+#define enew(x) ((x *) ealloc(sizeof(x)))
+#define ecpy(x) strcpy((char *) ealloc(strlen(x) + 1), x)
+#define lookup_fn(s) ((rc_Function *) lookup(s, fp))
+#define lookup_var(s) ((Variable *) lookup(s, vp))
+#define nnew(x) ((x *) nalloc(sizeof(x)))
+#define ncpy(x) (strcpy((char *) nalloc(strlen(x) + 1), x))
+#ifndef offsetof
+#define offsetof(t, m) ((size_t) (((char *) &((t *) 0)->m) - (char *)0))
+#endif
+#define streq(x, y) (*(x) == *(y) && strcmp(x, y) == 0)
+#define conststrlen(x) (sizeof (x) - 1)
+
+/* rc prototypes */
+
+/* main.c */
+extern Rq *redirq;
+extern bool dashdee, dashee, dashvee, dashex, dasheye, dashen, dashpee, interactive;
+extern pid_t rc_pid;
+extern int lineno;
+
+/* builtins.c */
+extern builtin_t *isbuiltin(char *);
+extern void b_exec(char **), funcall(char **), b_dot(char **), b_builtin(char **);
+extern char *which(char *, bool);
+
+/* except.c */
+extern bool nl_on_intr;
+extern bool outstanding_cmdarg(void);
+extern void pop_cmdarg(bool);
+extern void rc_raise(ecodes);
+extern void except(ecodes, Edata, Estack *);
+extern void unexcept(void);
+extern void rc_error(char *);
+extern void sigint(int);
+
+/* exec.c */
+extern void exec(List *, bool);
+
+#if HASH_BANG
+#define rc_execve execve
+#else
+/* execve.c */
+extern int my_execve(char *, char **, char **);
+#endif
+
+/* footobar.c */
+extern char **list2array(List *, bool);
+extern char *get_name(char *);
+extern List *parse_var(char *);
+extern Node *parse_fn(char *);
+extern void initprint(void);
+extern void rc_exit(int); /* here for odd reasons; user-defined signal handlers are kept in fn.c */
+
+/* getopt.c */
+extern int rc_getopt(int, char **, char *);
+
+extern int rc_optind, rc_opterr, rc_optopt;
+extern char *rc_optarg;
+
+/* glob.c */
+extern bool lmatch(List *, List *);
+extern List *glob(List *);
+
+/* glom.c */
+extern void assign(List *, List *, bool);
+extern void qredir(Node *);
+extern List *append(List *, List*);
+extern List *flatten(List *);
+extern List *glom(Node *);
+extern List *concat(List *, List *);
+extern List *varsub(List *, List *);
+extern List *word(char *, char *);
+
+/* hash.c */
+extern Htab *fp, *vp;
+extern void *lookup(char *, Htab *);
+extern rc_Function *get_fn_place(char *);
+extern List *varlookup(char *);
+extern Node *fnlookup(char *);
+extern Variable *get_var_place(char *, bool);
+extern bool varassign_string(char *);
+extern char **makeenv(void);
+extern char *fnlookup_string(char *);
+extern char *varlookup_string(char *);
+extern void alias(char *, List *, bool);
+extern void starassign(char *, char **, bool);
+extern void delete_fn(char *);
+extern void delete_var(char *, bool);
+extern void fnassign(char *, Node *);
+extern void fnassign_string(char *);
+extern void fnrm(char *);
+extern void initenv(char **);
+extern void inithash(void);
+extern void set_exportable(char *, bool);
+extern void setsigdefaults(bool);
+extern void inithandler(void);
+extern void varassign(char *, List *, bool);
+extern void varrm(char *, bool);
+extern void whatare_all_vars(bool, bool);
+extern void whatare_all_signals(void);
+extern void prettyprint_var(int, char *, List *);
+extern void prettyprint_fn(int, char *, Node *);
+
+/* heredoc.c */
+extern int heredoc(int);
+extern int qdoc(Node *, Node *);
+extern Hq *hq;
+
+/* lex.c */
+extern bool quotep(char *, bool);
+extern int yylex(void);
+extern void inityy(void);
+extern void yyerror(const char *);
+extern void scanerror(char *);
+extern const char nw[], dnw[];
+
+/* list.c */
+extern void listfree(List *);
+extern List *listcpy(List *, void *(*)(size_t));
+extern size_t listlen(List *);
+extern int listnel(List *);
+
+/* match.c */
+extern bool match(char *, char *, char *);
+
+/* alloc.c */
+extern void *ealloc(size_t);
+extern void *erealloc(void *, size_t);
+extern void efree(void *);
+extern Block *newblock(void);
+extern void *nalloc(size_t);
+extern void nfree(void);
+extern void restoreblock(Block *);
+
+/* open.c */
+extern int rc_open(const char *, redirtype);
+extern bool makeblocking(int);
+extern bool makesamepgrp(int);
+
+/* print.c */
+/*
+   The following prototype should be:
+extern Conv fmtinstall(int, Conv);
+   but this freaks out SGI's compiler under IRIX3.3.2
+*/
+extern bool (*fmtinstall(int, bool (*)(Format *, int)))(Format *, int);
+extern int printfmt(Format *, const char *);
+extern int fmtprint(Format *, const char *,...);
+extern void fmtappend(Format *, const char *, size_t);
+extern void fmtcat(Format *, const char *);
+extern int fprint(int fd, const char *fmt,...);
+extern char *mprint(const char *fmt,...);
+extern char *nprint(const char *fmt,...);
+/*
+   the following macro should by rights be coded as an expression, not
+   a statement, but certain compilers (notably DEC) have trouble with
+   void expressions inside the ?: operator. (sheesh, give me a break!)
+*/
+#define        fmtputc(f, c) {\
+       if ((f)->buf >= (f)->bufend)\
+               (*(f)->grow)((f), (size_t)1);\
+       *(f)->buf++ = (c);\
+}
+
+/* parse.c (parse.y) */
+extern Node *parsetree;
+extern int yyparse(void);
+extern void initparse(void);
+
+/* readline */
+extern volatile sig_atomic_t rl_active;
+extern struct Jbwrap rl_buf;
+
+/* redir.c */
+extern void doredirs(void);
+
+
+/* signal.c */
+extern void initsignal(void);
+extern void catcher(int);
+extern void sigchk(void);
+extern void (*rc_signal(int, void (*)(int)))(int);
+extern void (*sys_signal(int, void (*)(int)))(int);
+extern void (*sighandlers[])(int);
+
+
+/* status.c */
+extern int istrue(void);
+extern int getstatus(void);
+extern void set(bool);
+extern void setstatus(pid_t, int);
+extern List *sgetstatus(void);
+extern void setpipestatus(int [], int);
+extern void statprint(pid_t, int);
+extern void ssetstatus(char **);
+extern char *strstatus(int s);
+
+
+/* system.c or system-bsd.c */
+extern void writeall(int, char *, size_t);
+
+#if HAVE_RESTARTABLE_SYSCALLS
+extern int rc_read(int, char *, size_t);
+extern pid_t rc_wait(int *);
+extern Jbwrap slowbuf;
+extern volatile sig_atomic_t slow;
+
+#else /* HAVE_RESTARTABLE_SYSCALLS */
+
+#define rc_read read
+#define rc_wait wait
+#endif /* HAVE_RESTARTABLE_SYSCALLS */
+
+
+/* tree.c */
+extern Node *mk(int /*nodetype*/,...);
+extern Node *treecpy(Node *, void *(*)(size_t));
+extern void treefree(Node *);
+
+/* utils.c */
+extern bool isabsolute(char *);
+extern int n2u(char *, unsigned int);
+extern int mvfd(int, int);
+extern int starstrcmp(const void *, const void *);
+extern void pr_error(char *, int);
+extern void panic(char *);
+extern void uerror(char *);
+
+/* wait.c */
+extern pid_t rc_fork(void);
+extern pid_t rc_wait4(pid_t, int *, bool);
+extern List *sgetapids(void);
+extern void waitforall(void);
+extern bool forked;
+
+/* walk.c */
+extern bool walk(Node *, bool);
+extern bool cond;
diff --git a/redir.c b/redir.c
new file mode 100644 (file)
index 0000000..b582341
--- /dev/null
+++ b/redir.c
@@ -0,0 +1,77 @@
+/* redir.c: code for opening files and piping heredocs after fork but before exec. */
+
+#include "rc.h"
+
+/*
+   Walk the redirection queue, and open files and dup2 to them. Also,
+   here-documents are treated here by dumping them down a pipe. (this
+   should make here-documents fast on systems with lots of memory which
+   do pipes right. Under sh, a file is copied to /tmp, and then read
+   out of /tmp again. I'm interested in knowing how much faster, say,
+   shar runs when unpacking when invoked with rc instead of sh. On my
+   sun4/280, it runs in about 60-75% of the time of sh for unpacking
+   the rc source distribution.)
+*/
+
+extern void doredirs() {
+       List *fname;
+       int fd, p[2];
+       Rq *r;
+       for (r = redirq; r != NULL; r = r->n) {
+               switch(r->r->type) {
+               default:
+                       panic("unexpected node in doredirs");
+                       /* NOTREACHED */
+               case nRedir:
+                       if (r->r->u[0].i == rHerestring) {
+                               fname = flatten(glom(r->r->u[2].p)); /* fname is really a string */
+                               if (pipe(p) < 0) {
+                                       uerror("pipe");
+                                       rc_error(NULL);
+                               }
+                               if (rc_fork() == 0) { /* child writes to pipe */
+                                       setsigdefaults(FALSE);
+                                       close(p[0]);
+                                       if (fname != NULL)
+                                               writeall(p[1], fname->w, strlen(fname->w));
+                                       exit(0);
+                               } else {
+                                       close(p[1]);
+                                       if (mvfd(p[0], r->r->u[1].i) < 0)
+                                               rc_error(NULL);
+                               }
+                       } else {
+                               fname = glob(glom(r->r->u[2].p));
+                               if (fname == NULL)
+                                       rc_error("null filename in redirection");
+                               if (fname->n != NULL)
+                                       rc_error("multi-word filename in redirection");
+                               switch (r->r->u[0].i) {
+                               default:
+                                       panic("unexpected node in doredirs");
+                                       /* NOTREACHED */
+                               case rCreate: case rAppend: case rFrom:
+                                       fd = rc_open(fname->w, r->r->u[0].i);
+                                       break;
+                               }
+                               if (fd < 0) {
+                                       uerror(fname->w);
+                                       rc_error(NULL);
+                               }
+                               if (mvfd(fd, r->r->u[1].i) < 0)
+                                       rc_error(NULL);
+                       }
+                       break;
+               case nDup:
+                       if (r->r->u[2].i == -1)
+                               close(r->r->u[1].i);
+                       else if (r->r->u[2].i != r->r->u[1].i) {
+                               if (dup2(r->r->u[2].i, r->r->u[1].i) < 0) {
+                                       uerror("dup2");
+                                       rc_error(NULL);
+                               }
+                       }
+               }
+       }
+       redirq = NULL;
+}
diff --git a/rlimit.h b/rlimit.h
new file mode 100644 (file)
index 0000000..a3dbe8d
--- /dev/null
+++ b/rlimit.h
@@ -0,0 +1,53 @@
+/* What a mess.  This file attempts to straighten everything out. */
+
+#if HAVE_SETRLIMIT
+
+#if HAVE_SYS_RESOURCE_H
+#include <sys/time.h>
+#if RLIMIT_NEEDS_KERNEL
+#define _KERNEL
+#endif
+#include <sys/resource.h>
+#if RLIMIT_NEEDS_KERNEL
+#undef _KERNEL
+#endif
+#else
+#include <sys/times.h>
+#endif
+
+#if HAVE_LIMITS_H
+#include <limits.h>
+#endif
+
+#ifndef HAVE_RLIM_T
+#if RLIM_T_IS_QUAD_T
+typedef quad_t rlim_t;
+#else
+typedef long rlim_t;
+#endif
+#endif
+
+#if HAVE_QUAD_T
+#define RLIM_CONV quad_t
+#define RLIM_FMT "%s \t%qd%s\n"
+#else
+#define RLIM_CONV long
+#define RLIM_FMT "%s \t%ld%s\n"
+#endif
+
+#if defined(RLIMIT_OFILE) && !defined (RLIMIT_NOFILE)
+#define RLIMIT_NOFILE RLIMIT_OFILE
+#endif
+
+struct Suffix {
+       const struct Suffix *next;
+       long amount;
+       char *name;
+};
+
+struct Limit {
+       char *name;
+       int flag;
+       const struct Suffix *suffix;
+};
+#endif /* HAVE_SETRLIMIT */
diff --git a/signal.c b/signal.c
new file mode 100644 (file)
index 0000000..037be1d
--- /dev/null
+++ b/signal.c
@@ -0,0 +1,106 @@
+/* signal.c: a Hugh-approved signal handler. */
+
+#include "rc.h"
+
+#include <signal.h>
+#include <setjmp.h>
+
+#include "sigmsgs.h"
+#include "jbwrap.h"
+
+#if HAVE_SIGACTION
+void (*sys_signal(int signum, void (*handler)(int)))(int) {
+       struct sigaction new, old;
+
+       new.sa_handler = handler;
+       new.sa_flags = 0; /* clear SA_RESTART */
+       sigfillset(&new.sa_mask);
+       sigaction(signum, &new, &old);
+       return old.sa_handler;
+}
+#else
+void (*sys_signal(int signum, void (*handler)(int)))(int) {
+       return signal(signum, handler);
+}
+#endif
+
+void (*sighandlers[NUMOFSIGNALS])(int);
+
+static volatile sig_atomic_t sigcount, caught[NUMOFSIGNALS];
+
+extern void catcher(int s) {
+       if (caught[s] == 0) {
+               sigcount++;
+               caught[s] = 1;
+       }
+       sys_signal(s, catcher);
+
+#if HAVE_RESTARTABLE_SYSCALLS
+       if (slow) {
+               siglongjmp(slowbuf.j, s);
+       }
+#endif
+}
+
+extern void sigchk() {
+       void (*h)(int);
+       int s, i;
+
+       if (sigcount == 0)
+               return; /* ho hum; life as usual */
+       if (forked)
+               exit(1); /* exit unconditionally on a signal in a child process */
+       for (i = 0, s = -1; i < NUMOFSIGNALS; i++)
+               if (caught[i] != 0) {
+                       s = i;
+                       --sigcount;
+                       caught[s] = 0;
+                       break;
+               }
+       if (s == -1)
+               panic("all-zero sig vector with nonzero sigcount");
+       if ((h = sighandlers[s]) == SIG_DFL)
+               panic("caught signal set to SIG_DFL");
+       if (h == SIG_IGN)
+               panic("caught signal set to SIG_IGN");
+       (*h)(s);
+}
+
+extern void (*rc_signal(int s, void (*h)(int)))(int) {
+       void (*old)(int);
+       sigchk();
+       old = sighandlers[s];
+       sighandlers[s] = h;
+       if (h == SIG_DFL || h == SIG_IGN)
+               sys_signal(s, h);
+       else
+               sys_signal(s, catcher);
+       return old;
+}
+
+extern void initsignal() {
+       void (*h)(int);
+       int i;
+
+#if HAVE_SYSV_SIGCLD
+       /* Ensure that SIGCLD is not SIG_IGN.  Solaris's rshd does this.  :-( */
+       h = sys_signal(SIGCLD, SIG_IGN);
+       if (h != SIG_IGN && h != SIG_ERR)
+               sys_signal(SIGCLD, h);
+       else
+               sys_signal(SIGCLD, SIG_DFL);
+#endif
+
+       for (i = 1; i < NUMOFSIGNALS; i++) {
+#ifdef SIGKILL
+               if (i == SIGKILL) continue;
+#endif
+#ifdef SIGSTOP
+               if (i == SIGSTOP) continue;
+#endif
+               h = sys_signal(i, SIG_IGN);
+               if (h != SIG_IGN && h != SIG_ERR)
+                       sys_signal(i, h);
+               sighandlers[i] = h;
+       }
+}
diff --git a/stat.h b/stat.h
new file mode 100644 (file)
index 0000000..5f87a69
--- /dev/null
+++ b/stat.h
@@ -0,0 +1,6 @@
+#include <sys/stat.h>
+
+#if HAVE_LSTAT
+#else
+#define lstat(name, buf) (stat((name), (buf)))
+#endif
diff --git a/status.c b/status.c
new file mode 100644 (file)
index 0000000..5b37aa5
--- /dev/null
+++ b/status.c
@@ -0,0 +1,151 @@
+/* status.c: functions for printing fancy status messages in rc */
+
+#include "rc.h"
+#include "sigmsgs.h"
+#include "statval.h"
+#include "wait.h"
+
+/* status == the wait() value of the last command in the pipeline, or the last command */
+
+static int statuses[512];
+static int pipelength = 1;
+
+/*
+   Test to see if rc's status is true. According to td, status is true
+   if and only if every pipe-member has an exit status of zero.
+*/
+
+extern int istrue() {
+       int i;
+       for (i = 0; i < pipelength; i++)
+               if (statuses[i] != 0)
+                       return FALSE;
+       return TRUE;
+}
+
+/*
+   Return the status as an integer. A status which has low-bits set is
+   a signal number, whereas a status with high bits set is a value set
+   from exit(). The presence of a signal just sets status to 1. Also,
+   a pipeline with nonzero exit statuses in it just sets status to 1.
+*/
+
+extern int getstatus() {
+       int s;
+       if (pipelength > 1)
+               return !istrue();
+       s = statuses[0];
+       if (WIFSIGNALED(s))
+               return 1;
+       return WEXITSTATUS(s);
+}
+
+extern void set(bool code) {
+       setstatus(-1, code ? STATUS0 : STATUS1);
+}
+
+/* take a pipeline and store the exit statuses. Check to see whether any of the children dumped core */
+
+extern void setpipestatus(int stats[], int num) {
+       int i;
+       for (i = 0; i < (pipelength = num); i++) {
+               statprint(-1, stats[i]);
+               statuses[i] = stats[i];
+       }
+}
+
+/* set a simple status, as opposed to a pipeline */
+
+extern void setstatus(pid_t pid, int i) {
+       pipelength = 1;
+       statuses[0] = i;
+       statprint(pid, i);
+}
+
+/* print a message if termination was with a signal, and if the child dumped core. exit on error if -e is set */
+
+extern void statprint(pid_t pid, int i) {
+       if (WIFSIGNALED(i)) {
+               int t = WTERMSIG(i);
+               char *msg = ((t > 0) && (t < NUMOFSIGNALS) ? signals[WTERMSIG(i)].msg : "");
+               if (pid != -1)
+                       fprint(2, "%ld: ", (long)pid);
+               if (myWIFDUMPED(i)) {
+                       if (*msg == '\0')
+                               fprint(2, "core dumped\n");
+                       else
+                               fprint(2, "%s--core dumped\n", msg);
+               } else if (*msg != '\0')
+                       fprint(2, "%s\n", msg);
+       }
+       if (i != 0 && dashee && !cond)
+               rc_exit(getstatus());
+}
+
+/* prepare a list to be passed back. Used whenever $status is dereferenced */
+
+extern List *sgetstatus() {
+       List *r = NULL;
+       int i;
+
+       for (i = 0; i < pipelength; i++) {
+               List *q = nnew(List);
+               q->w = strstatus(statuses[i]);
+               q->m = NULL;
+               q->n = r;
+               r = q;
+       }
+
+       return r;
+}
+
+/* return status as a string (used above and for bqstatus) */
+
+extern char *strstatus(int s) {
+       if (WIFSIGNALED(s)) {
+               int t = WTERMSIG(s);
+               const char *core = myWIFDUMPED(s) ? "+core" : "";
+               if ((t > 0) && (t < NUMOFSIGNALS) && *signals[t].name != '\0')
+                       return nprint("%s%s", signals[t].name, core);
+               else
+                       return nprint("-%d%s", t, core); /* unknown signals are negated */
+       } else
+               return nprint("%d", WEXITSTATUS(s));
+}
+
+extern void ssetstatus(char **av) {
+       int i, j, k, l;
+       bool found;
+       for (l = 0; av[l] != NULL; l++)
+               ; /* count up array length */
+       --l;
+       for (i = 0; av[i] != NULL; i++) {
+               j = a2u(av[i]);
+               if (j >= 0) {
+                       statuses[l - i] = j << 8;
+                       continue;
+               }
+               found = FALSE;
+               for (k = 0; k < NUMOFSIGNALS; k++) {
+                       if (streq(signals[k].name, av[i])) {
+                               statuses[l - i] = k;
+                               found = TRUE;
+                               break;
+                       } 
+                       else {
+                               size_t len = strlen(signals[k].name);
+                               if (strncmp(signals[k].name, av[i], len) == 0 && streq(av[i] + len, "+core")) {
+                                       statuses[l - i] = k + 0x80;
+                                       found = TRUE;
+                                       break;
+                               }
+                       }
+               }
+               if (!found) {
+                       fprint(2, "bad status\n");
+                       set(FALSE);
+                       return;
+               }
+       }
+       pipelength = i;
+}
diff --git a/system-bsd.c b/system-bsd.c
new file mode 100644 (file)
index 0000000..f081e1a
--- /dev/null
@@ -0,0 +1,61 @@
+/* signal-safe read and write (for BSD slow devices). writeall() also
+allows partial writes */
+
+#include "rc.h"
+
+#include <errno.h>
+
+#include "jbwrap.h"
+#include "wait.h"
+
+Jbwrap slowbuf;
+volatile sig_atomic_t slow;
+
+static char *safe_buf;
+static size_t safe_remain;
+
+extern void writeall(int fd, char *buf, size_t remain) {
+       int i;
+
+       safe_buf = buf;
+       safe_remain = remain;
+       for (i = 0; safe_remain > 0; buf += i, safe_remain -= i) {
+               if (sigsetjmp(slowbuf.j, 1) == 0) {
+                       slow = TRUE;
+                       if ((i = write(fd, safe_buf, safe_remain)) <= 0)
+                               break; /* abort silently on errors in write() */
+               } else
+                       break;
+       }
+       slow = FALSE;
+       sigchk();
+}
+
+extern int rc_read(int fd, char *buf, size_t n) {
+       ssize_t r;
+
+       if (sigsetjmp(slowbuf.j, 1) == 0) {
+               slow = TRUE;
+               r = read(fd, buf, n);
+       } else {
+               errno = EINTR;
+               r = -1;
+       }
+       slow = FALSE;
+
+       return r;
+}
+
+static int r = -1;
+extern pid_t rc_wait(int *stat) {
+       if (sigsetjmp(slowbuf.j, 1) == 0) {
+               slow = TRUE;
+               r = wait(stat);
+       } else {
+               errno = EINTR;
+               r = -1;
+       }
+       slow = FALSE;
+
+       return r;
+}
diff --git a/system.c b/system.c
new file mode 100644 (file)
index 0000000..edc0e0f
--- /dev/null
+++ b/system.c
@@ -0,0 +1,10 @@
+#include "rc.h"
+
+extern void writeall(int fd, char *buf, size_t remain) {
+       int i;
+
+       for (i = 0; remain > 0; buf += i, remain -= i)
+               if ((i = write(fd, buf, remain)) <= 0)
+                       break; /* abort silently on errors in write() */
+       sigchk();
+}
diff --git a/tree.c b/tree.c
new file mode 100644 (file)
index 0000000..60b42e3
--- /dev/null
+++ b/tree.c
@@ -0,0 +1,174 @@
+/* tree.c: functions for manipulating parse-trees. (create, copy, delete) */
+
+#include "rc.h"
+
+/* make a new node, pass it back to yyparse. Used to generate the parsetree. */
+
+extern Node *mk(int /*nodetype*/ t,...) {
+       va_list ap;
+       Node *n;
+       va_start(ap, t);
+       switch (t) {
+       default:
+               panic("unexpected node in mk");
+               /* NOTREACHED */
+       case nDup:
+               n = nalloc(offsetof(Node, u[3]));
+               n->u[0].i = va_arg(ap, int);
+               n->u[1].i = va_arg(ap, int);
+               n->u[2].i = va_arg(ap, int);
+               break;
+       case nWord:
+               n = nalloc(offsetof(Node, u[3]));
+               n->u[0].s = va_arg(ap, char *);
+               n->u[1].s = va_arg(ap, char *);
+               n->u[2].i = va_arg(ap, int);
+               break;
+       case nBang: case nNowait:
+       case nCount: case nFlat: case nRmfn: case nSubshell:
+       case nVar: case nCase:
+               n = nalloc(offsetof(Node, u[1]));
+               n->u[0].p = va_arg(ap, Node *);
+               break;
+       case nAndalso: case nAssign: case nBackq: case nBody: case nBrace: case nConcat:
+       case nElse: case nEpilog: case nIf: case nNewfn: case nCbody:
+       case nOrelse: case nPre: case nArgs: case nSwitch:
+       case nMatch: case nVarsub: case nWhile: case nLappend:
+               n = nalloc(offsetof(Node, u[2]));
+               n->u[0].p = va_arg(ap, Node *);
+               n->u[1].p = va_arg(ap, Node *);
+               break;
+       case nForin:
+               n = nalloc(offsetof(Node, u[3]));
+               n->u[0].p = va_arg(ap, Node *);
+               n->u[1].p = va_arg(ap, Node *);
+               n->u[2].p = va_arg(ap, Node *);
+               break;
+       case nPipe:
+               n = nalloc(offsetof(Node, u[4]));
+               n->u[0].i = va_arg(ap, int);
+               n->u[1].i = va_arg(ap, int);
+               n->u[2].p = va_arg(ap, Node *);
+               n->u[3].p = va_arg(ap, Node *);
+               break;
+       case nRedir:
+       case nNmpipe:
+               n = nalloc(offsetof(Node, u[3]));
+               n->u[0].i = va_arg(ap, int);
+               n->u[1].i = va_arg(ap, int);
+               n->u[2].p = va_arg(ap, Node *);
+               break;
+       }
+       n->type = t;
+       va_end(ap);
+       return n;
+}
+
+/* copy a tree to malloc space. Used when storing the definition of a function */
+
+extern Node *treecpy(Node *s, void *(*alloc)(size_t)) {
+       Node *n;
+       if (s == NULL)
+               return NULL;
+       switch (s->type) {
+       default:
+               panic("unexpected node in treecpy");
+               /* NOTREACHED */
+       case nDup:
+               n = (*alloc)(offsetof(Node, u[3]));
+               n->u[0].i = s->u[0].i;
+               n->u[1].i = s->u[1].i;
+               n->u[2].i = s->u[2].i;
+               break;
+       case nWord:
+               n = (*alloc)(offsetof(Node, u[3]));
+               n->u[0].s = strcpy((char *) (*alloc)(strlen(s->u[0].s) + 1), s->u[0].s);
+               if (s->u[1].s != NULL) {
+                       size_t i = strlen(s->u[0].s);
+                       n->u[1].s = (*alloc)(i);
+                       memcpy(n->u[1].s, s->u[1].s, i);
+               } else
+                       n->u[1].s = NULL;
+               n->u[2].i = s->u[2].i;
+               break;
+       case nBang: case nNowait: case nCase:
+       case nCount: case nFlat: case nRmfn: case nSubshell: case nVar:
+               n = (*alloc)(offsetof(Node, u[1]));
+               n->u[0].p = treecpy(s->u[0].p, alloc);
+               break;
+       case nAndalso: case nAssign: case nBackq: case nBody: case nBrace: case nConcat:
+       case nElse: case nEpilog: case nIf: case nNewfn: case nCbody:
+       case nOrelse: case nPre: case nArgs: case nSwitch:
+       case nMatch: case nVarsub: case nWhile: case nLappend:
+               n = (*alloc)(offsetof(Node, u[2]));
+               n->u[0].p = treecpy(s->u[0].p, alloc);
+               n->u[1].p = treecpy(s->u[1].p, alloc);
+               break;
+       case nForin:
+               n = (*alloc)(offsetof(Node, u[3]));
+               n->u[0].p = treecpy(s->u[0].p, alloc);
+               n->u[1].p = treecpy(s->u[1].p, alloc);
+               n->u[2].p = treecpy(s->u[2].p, alloc);
+               break;
+       case nPipe:
+               n = (*alloc)(offsetof(Node, u[4]));
+               n->u[0].i = s->u[0].i;
+               n->u[1].i = s->u[1].i;
+               n->u[2].p = treecpy(s->u[2].p, alloc);
+               n->u[3].p = treecpy(s->u[3].p, alloc);
+               break;
+       case nRedir:
+       case nNmpipe:
+               n = (*alloc)(offsetof(Node, u[3]));
+               n->u[0].i = s->u[0].i;
+               n->u[1].i = s->u[1].i;
+               n->u[2].p = treecpy(s->u[2].p, alloc);
+               break;
+       }
+       n->type = s->type;
+       return n;
+}
+
+/* free a function definition that is no longer needed */
+
+extern void treefree(Node *s) {
+       if (s == NULL)
+               return;
+       switch (s->type) {
+       default:
+               panic("unexpected node in treefree");
+               /* NOTREACHED */
+       case nDup:
+               break;
+       case nWord:
+               efree(s->u[0].s);
+               efree(s->u[1].s);
+               break;
+       case nBang: case nNowait:
+       case nCount: case nFlat: case nRmfn:
+       case nSubshell: case nVar: case nCase:
+               treefree(s->u[0].p);
+               break;
+       case nAndalso: case nAssign: case nBackq: case nBody: case nBrace: case nConcat:
+       case nElse: case nEpilog: case nIf: case nNewfn:
+       case nOrelse: case nPre: case nArgs: case nCbody:
+       case nSwitch: case nMatch:  case nVarsub: case nWhile:
+       case nLappend:
+               treefree(s->u[1].p);
+               treefree(s->u[0].p);
+               break;
+       case nForin:
+               treefree(s->u[2].p);
+               treefree(s->u[1].p);
+               treefree(s->u[0].p);
+               break;
+       case nPipe:
+               treefree(s->u[2].p);
+               treefree(s->u[3].p);
+               break;
+       case nRedir:
+       case nNmpipe:
+               treefree(s->u[2].p);
+       }
+       efree(s);
+}
diff --git a/trip.rc b/trip.rc
new file mode 100644 (file)
index 0000000..c811347
--- /dev/null
+++ b/trip.rc
@@ -0,0 +1,599 @@
+# trip.rc -- take a tour of rc
+# Invoke as "path-to-new-rc < trip.rc"
+
+rc=$0
+echo tripping $rc $version
+
+tmpdir=''
+fn fail {
+       echo >[1=2] trip took a wrong turn: $*
+       rm -rf $tmpdir
+       fn sigexit
+       exit 1
+}
+fn expect {
+       echo >[1=2] -n expect $^*^': '
+}
+fn submatch {
+       if (!~ $#* 3)
+               fail incorrect invocation of submatch
+       prompt=$nl if (!~ `` $nl {$rc -ic $1>[2=1]} $2)
+               fail $3
+}
+fn sigexit sigint sigquit sigsegv
+fn sigexit {
+       echo trip complete
+}
+tmpdir=`{ mktemp -d -t rc-trip.XXXXXX }
+tmp=$tmpdir/tmp
+nl='
+'
+
+#
+# rc -c
+#
+
+if ($rc -c >[2]/dev/null) fail 'rc -c didn''t report a bad exit status'
+x=`{$rc -c 'echo $0 $2 $#*' a b c d e f}
+if (false) {                                   # WARNING: this differs from sh
+       if (!~ $x(1) a) fail rc -c reports '$0' incorrectly as $x(1)
+       if (!~ $x(2) c) fail rc -c reports '$2' incorrectly as $x(2)
+       if (!~ $x(3) 5) fail rc -c reports '$#' incorrectly as $x(3)
+} else {
+       if (!~ $x(1) $rc) fail rc -c reports '$0' incorrectly as $x(1)
+       if (!~ $x(2) b) fail rc -c reports '$2' incorrectly as $x(2)
+       if (!~ $x(3) 6) fail rc -c reports '$#' incorrectly as $x(3)
+}
+
+#
+# umask
+#
+
+umask 0
+> $tmp
+x=`{ls -l $tmp}
+if (!~ $x(1) -rw-rw-rw-*) fail umask 0 produced incorrect result: $x(1)
+rm -f $tmp
+umask 027
+> $tmp
+y=`{ls -l $tmp}
+if (!~ $y(1) -rw-r-----*) fail umask 027 produced incorrect file: $y(1)
+rm -f $tmp
+if (!~ `umask 027) fail umask reported bad value: `umask
+
+submatch 'umask bad' 'bad umask' 'bad umask'
+submatch 'umask -027' 'bad umask' 'bad umask'
+submatch 'umask 999999' 'bad umask' 'bad umask'
+submatch 'umask hi there' 'rc: too many arguments to umask' 'umask arg count'
+
+if (!~ `umask 027) fail bad umask changed umask value to `umask
+
+#
+# redirections
+#
+
+fn bytes { for (i) x=`{wc -c $i} echo $x(1) }
+echo foo > foo > bar
+if (!~ `{bytes foo} 0) fail double redirection created non-empty empty file
+if (!~ `{bytes bar} 4) fail double redirection created wrong sized file: `{bytes bar}
+rm -f foo bar
+echo -n >1 >[2]2 >[1=2] foo
+x = `` '' {cat 1}
+if (!~ $#x 0) fail dup created non-empty empty file: `` '' {cat 1}
+if (!~ `` '' {cat 2} foo) fail dup put wrong contents in file : `` '' {cat 2}
+rm -f 1 2
+
+expect error from cat, closing stdin
+cat >[0=]
+
+submatch 'cat>(1 2 3)' 'rc: multi-word filename in redirection' 'redirection error'
+submatch 'cat>()' 'rc: null filename in redirection' 'redirection error'
+
+#
+# blow the input stack
+#
+
+if (!~ hi `{
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval eval eval \
+eval eval eval eval eval eval eval eval eval eval eval echo hi
+})
+       fail huge eval
+
+#
+# heredocs and herestrings
+#
+
+bigfile=$tmpdir/big.$pid
+od $rc | sed 5000q > $bigfile
+abc=(this is a)
+x=()
+result='this is a heredoc
+this is an heredoc
+'
+if (!~ `` '' {<<[5] EOF cat <[0=5]} $result) fail unquoted heredoc
+$abc heredoc$x
+$abc^n $x^here$x^doc
+EOF
+{if (!~ `` $nl cat '   ') fail quoted heredoc} << ' '
+       
+
+<<<[9] ``''{cat $bigfile} \
+{
+       if(!~ ``''{cat <[0=9]}``'' cat)fail large herestrings
+} < \
+$bigfile
+
+rm -f $bigfile
+
+if (!~ `{cat<<eof
+$$
+eof
+} '$')
+       fail quoting '$' in heredoc
+
+submatch 'cat<<eof' 'rc: heredoc incomplete' 'incomplete heredoc'
+submatch 'cat<<eof
+' 'rc: heredoc incomplete' 'incomplete heredoc'
+
+submatch 'cat<<(eof eof)' 'rc: eof-marker not a single literal word' 'bad heredoc marker'
+
+#
+# lexical analysis
+#
+
+expect warning
+./tripping 0 > $tmp
+$rc $tmp
+rm -f $tmp
+
+echo here_is_a_really_long_word.It_has_got_to_be_longer_than_1000_characters_for_the_lexical_analyzers_buffer_to_overflow_but_that_should_not_be_too_difficult_to_do.Let_me_start_writing_some_Lewis_Carroll.Twas_brillig_and_the_slithy_toves,Did_gyre_and_gimble_in_the_wabe.All_mimsy_were_the_borogoves,And_the_mome-raths_outgrabe.Beware_the_Jabberwock_my_son,The_jaws_that_bite,the_claws_that_catch.Beware_the_Jub-jub_bird,and_shun_The_frumious_Bandersnatch.He_took_his_vorpal_sword_in_hand,Long_time_the_manxome_foe_he_sought,So_rested_he_by_the_Tumtum_tree,And_stood_awhile_in_thought.And_as_in_uffish_thought_he_stood,The_Jabberwock,with_eyes_of_flame,Came_whiffling_through_the_tulgey_wood,And_burbled_as_it_came.One_two,one_two.And_through_and_through_The_vorpal_blade_went_snicker-snack.He_left_it_dead_and_with_its_head,He_went_galumphing_back.And_hast_thou_slain_the_Jabberwock?Come_to_my_arms,my_beamish_boy,Oh_frabjous_day.Callooh_callay.He_chortled_in_his_joy.Twas_brillig,and_the_slithy_toves,Did_gyre_and_gimble_in_the_wabe,All_mimsy_were_the_borogoves,And_the_mome-raths_outgrabe. > $tmpdir/$pid.lw
+
+echo 'here_is_a_really_long_word.It_has_got_to_be_longer_than_1000_characters_for_the_lexical_analyzers_buffer_to_overflow_but_that_should_not_be_too_difficult_to_do.Let_me_start_writing_some_Lewis_Carroll.Twas_brillig_and_the_slithy_toves,Did_gyre_and_gimble_in_the_wabe.All_mimsy_were_the_borogoves,And_the_mome-raths_outgrabe.Beware_the_Jabberwock_my_son,The_jaws_that_bite,the_claws_that_catch.Beware_the_Jub-jub_bird,and_shun_The_frumious_Bandersnatch.He_took_his_vorpal_sword_in_hand,Long_time_the_manxome_foe_he_sought,So_rested_he_by_the_Tumtum_tree,And_stood_awhile_in_thought.And_as_in_uffish_thought_he_stood,The_Jabberwock,with_eyes_of_flame,Came_whiffling_through_the_tulgey_wood,And_burbled_as_it_came.One_two,one_two.And_through_and_through_The_vorpal_blade_went_snicker-snack.He_left_it_dead_and_with_its_head,He_went_galumphing_back.And_hast_thou_slain_the_Jabberwock?Come_to_my_arms,my_beamish_boy,Oh_frabjous_day.Callooh_callay.He_chortled_in_his_joy.Twas_brillig,and_the_slithy_toves,Did_gyre_and_gimble_in_the_wabe,All_mimsy_were_the_borogoves,And_the_mome-raths_outgrabe.' > $tmpdir/$pid.lq
+
+if (!~ ``(){cat $tmpdir/$pid.lw} ``(){cat $tmpdir/$pid.lq})
+       fail expected long string and long word to be identical
+if (! x=`{wc -c $tmpdir/$pid.lw} ~ $x(1) 1088)
+       fail expected long word to be 1088 bytes
+if (! x=`{wc -c $tmpdir/$pid.lq} ~ $x(1) 1088)
+       fail expected long quote to be 1088 bytes
+
+rm $tmpdir/$pid.lw
+rm $tmpdir/$pid.lq
+
+submatch 'echo hi |[2' 'rc: expected ''='' or '']'' after digit' 'scan error'
+submatch 'echo hi |[92=]' 'rc: expected digit after ''=''' 'scan error'
+submatch 'echo hi |[a]' 'rc: expected digit after ''[''' 'scan error'
+submatch 'echo hi |[2-' 'rc: expected ''='' or '']'' after digit' 'scan error'
+submatch 'echo hi |[2=99a]' 'rc: expected '']'' after digit' 'scan error'
+submatch 'echo hi |[2=a99]' 'rc: expected digit or '']'' after ''=''' 'scan error'
+submatch 'echo ''hi' 'rc: eof in quoted string' 'scan error'
+
+ifs='' {
+       if (!~ 'h i' `{echo -n h\
+i})
+               fail backslash-newline to space conversion
+       if (!~ $rc^\rc `{echo -n $rc\rc})
+               fail backslash after variable name did not terminate variable name scan
+       if (!~ $rc^' rc' `{echo -n $rc\
+rc})
+               fail backslash-newline after variable name space conversion
+       if (!~ 'h\i' `{echo -n h\i})
+               fail backslash in the middle of word
+       if (!~ 'h \ i' `{echo -n h \ i})
+               fail free-standing backslash
+}
+
+if (! $rc -c '# eof in comment')
+       fail eof in comment exited with nonzero status
+
+# test the syntax error printer
+
+prompt='' if (!~ `` $nl {$rc -cif>[2=1]} 'rc: line 1: '*' error near if')
+       fail print syntax error
+
+prompt='' if (!~ `` $nl {$rc -icif>[2=1]} *' error')
+       fail print syntax error
+
+#
+# builtins
+#
+
+fn foo {
+       return sigfpe
+}
+
+foo
+if (!~ $status sigfpe)
+       fail return builtin did not return sigfpe
+
+fn foo # test deleting of function
+fn bar {
+       for (i in 1 2 3 4 5)
+               if (~ $i 3)
+                       return
+}
+
+bar
+if (!~ $i 3)
+       fail return inside loop inside function failed
+
+submatch return 'rc: return outside of function' 'return outside of function'
+submatch 'break 1' 'rc: too many arguments to break' 'break arg count'
+submatch break 'rc: break outside of loop' 'break outside of loop'
+
+for (i in 1 2 3 4 5)
+       if (~ $i 2)
+               break
+if (!~ $i 2)
+       fail break out of loop
+
+submatch 'wait foo' 'rc: `foo'' is a bad number' 'bogus argument to wait'
+
+if (~ `{echo -n} ?)
+       fail echo -n
+if (!~ `` '' {echo --} $nl)
+       fail echo --
+
+pwd=`/bin/pwd cdpath=/ { # some local assignments
+       home=/tmp cd
+       if (!~ `/bin/pwd `{sh -c 'cd /tmp; /bin/pwd'})
+               fail could not cd to '$home'
+
+       cdpath=/ cd tmp
+       if (!~ `/bin/pwd `{sh -c 'cd /tmp; /bin/pwd'})
+               fail could not cd to /tmp
+
+       cd $pwd
+       if (!~ `/bin/pwd `{sh -c 'cd $pwd; /bin/pwd'})
+               fail could not cd to current directory!
+}
+
+# Test that cd to a directory found via cdpath produces output
+# when interactive.
+submatch 'cdpath=/ cd tmp' /tmp 'cdpath produced wrong output'
+
+*=(1 2 3 4 5) {
+       expect bad number
+       shift foo
+       expect arg count
+       shift 1 2 3
+       expect shift overflow
+       shift 123
+       shift 3
+       if (!~ $#* 2)
+               fail shift 3 of '(1 2 3 4 5)' failed
+       shift
+       if (!~ $* 5)
+               fail shift failed to shift left-to-right
+}
+
+false
+eval && fail null eval reset '$status'
+
+if (!~ `{rm=(); fn rm; path=(. /bin); whatis rm} /bin/rm)
+       fail rm isn''''t in bin!?
+
+expect list of signal handlers
+whatis -s
+
+expect list of variables and functions
+whatis
+
+submatch 'whatis -x' 'whatis: bad option: -x' 'bad option to whatis'
+
+submatch 'whatis /frobnatz' '/frobnatz not found' 'search for /frobnatz'
+
+if (~ `{whatis limit >[2]/dev/null} builtin) {
+       limit coredumpsize 0
+       if (!~ `{limit coredumpsize} 0*)
+               fail failed to set coredumpsize to zero
+       if (!~ `` () {limit coredumpsize} `` () {limit|grep coredumpsize})
+               fail limit limit
+       submatch 'limit foo' 'no such limit' 'bad limit'
+}
+
+fn cd
+
+submatch 'cd a b c' 'rc: too many arguments to cd' 'cd arg count'
+$rc -c 'cdpath=() cd /frobnatz' >[2]/dev/null && fail 'cd to /frobnatz succeeded!?'
+submatch 'cdpath='''' cd frobnatz' 'couldn''t cd to frobnatz' 'cd to frobnatz succeeded!?'
+
+'if'=keyword {
+       {whatis if | fgrep '''if''=keyword' >/dev/null} || fail whatis of keyword is not quoted
+}
+
+#
+# wait
+#
+
+submatch 'wait 1 2 3' 'rc: too many arguments to wait' 'wait arg count'
+$rc -c 'wait 1' >[2]/dev/null && fail wait 1
+
+sleep 3&
+expect $apid
+echo $apids
+wait
+
+if (~ `` '' {wait} ?)
+       fail waiting for nothing
+
+#
+# matching
+#
+touch $tmpdir/abc.$pid $tmpdir/bbc.$pid
+mkdir $tmpdir/dir.$pid $tmpdir/dip.$pid
+touch $tmpdir/dir.$pid/^(a b c) $tmpdir/dip.$pid/^(a b c)
+
+if (!~ 123 [~x]?[0-9])
+       fail match
+if (!~ () *)
+       fail match of null list with '*'
+if (~ () *v*)
+       fail match of null list with '*v*' succeeded
+if (!~ (foo bar zar) *****z*****)
+       fail match of list by one pattern failed
+if (~ (foo bar zar) *c*)
+       fail bad match
+if (!~ [aaa [aaa)
+       fail bad rangematch
+if (!~ ']' []])
+       fail match right bracket
+if (~ x [y])
+       fail rangematch out of range
+if (~ x x?)
+       fail too many characters in pattern
+
+sh -c 'test -f /////$tmpdir//////a?c.'^$pid || fail glob with many slashes
+if (!~ /////$tmpdir//////a*.$pid /////$tmpdir//////a?c.$pid)
+       fail glob with many slashes
+if (!~ ////$tmpdir////di?.$pid////* ////$tmpdir////dir.$pid////*b*)
+       fail glob with more slashes
+if (! @{cd $tmpdir; ~ *.$pid/a d*/*})
+       fail glob in current directory
+if (!~ $tmpdir/?bc.$pid $tmpdir/bbc.$pid)
+       fail match of bbc.$pid against '('abc.$pid bbc.$pid')'
+
+rm $tmpdir/abc.$pid $tmpdir/bbc.$pid
+rm -rf $tmpdir/dir.$pid $tmpdir/dip.$pid
+
+#
+# signals
+#
+fn sigint {eval}
+kill -2 $pid
+fn sigint
+
+#
+# path searching
+#
+$rc -c /frobnatz >[2]/dev/null && fail 'search error'
+
+touch $tmpdir/noexec.$pid
+chmod a-x $tmpdir/noexec.$pid
+$rc -c $tmpdir/noexec.$pid >[2]/dev/null && fail $tmpdir/noexec.$pid is found!?
+rm $tmpdir/noexec.$pid
+
+submatch 'path='''' frobnatz' 'rc: cannot find `frobnatz''' 'search error'
+
+{path=() /bin/sh -c 'exit 0'} || fail abs pathname with path set to null
+
+#
+# options
+#
+
+# this test is meaningless; not really a trip
+expect prompt, echo hi
+home=/frobnatz $rc -nolpeivdxc 'echo hi'
+if (!~ `` $nl {$rc -c>[2=1]} *': option requires an argument -- c')
+       fail getopt on -c
+if (!~ `` $nl {$rc -q>[2=1]} *': bad option: -q')
+       fail getopt on -q (bogus option)
+if (!~ `{echo '#echo' | $rc -v |[2] sed 's/#//'} echo)
+       fail rc -v
+
+#
+# dot
+#
+
+if (~ `` '' . ?*)
+       fail null dot
+if (~ `` '' {. -i} ?*)
+       fail null dot -i
+
+cat > $tmpdir/dot.$pid << eof
+echo hi
+eof
+
+prompt=';' if (!~ `` '' {. -i $tmpdir/dot.$pid>[2=1]} ';hi'^$nl';')
+       fail dot -i
+submatch .' '$tmpdir/dot.$pid hi dot
+
+rm $tmpdir/dot.$pid
+
+$rc -c '. /frobnatz' >[2]/dev/null && fail 'dot of a nonexistent file'
+
+#
+# stdin
+#
+if (!~ `{echo echo hi | $rc} hi)
+       fail piping stdin to rc
+
+#
+# functions, variables & environment
+#
+fn --- {for(i)a|[2=3]b>>c<<<e&f>[2=1]}
+
+if (whatis printenv >/dev/null>[2=1]) {
+       printenv=printenv
+} else if (whatis env >/dev/null>[2=1]) {
+       printenv=env
+} else
+       printenv=()
+
+if (~ $#printenv 1 && !~ `` $nl {$printenv | grep fn___2d__2d__2d} 'fn___2d__2d__2d={for(i in $*)a|[2=3]b >>c <<<e&f >[2=1]}')
+       fail protect_env
+
+fn --- {replace}
+~ `{whatis -- ---} *replace* || fail replace a function definition
+fn ---
+whatis -- --- >[2]/dev/null && fail function deletion
+foo=bar *=bar
+foo=nest *=nest {
+       ~ $foo nest || fail local assignment
+       ~ $* nest || fail local assignment to '$*'
+       foo=()
+       *=()
+       ~ $foo () || fail local deletion
+       ~ $* () || fail local deletion to '$*'
+}
+~ $foo bar || fail restore of global after local group
+~ $* bar || fail restore of '$*' after local group
+~ `{exec>[2=1];$rc -xc 'foo=()'} 'foo=()' || fail -x echo of variable deletion
+
+fn_ff='{' prompt='' if (!~ `` $nl {$rc -cff>[2=1]} 'rc: line 1: '*' error near eof')
+       fail 'bogus function in environment'
+
+#
+# statuses
+#
+~ `{$rc -ec 'sleep 10&kill -9 $apid;wait'>[2=1]} killed ||
+       fail status diagnostic
+
+$rc -c 'exit 0 sigfpe' && fail exit of bad pipeline is true
+
+submatch 'exit foo' 'bad status' 'exit diagnostic'
+
+#
+# control structures
+#
+if (!~ `{false || echo hi} hi)
+       fail '||'
+if (!~ `{true && echo hi} hi)
+       fail '&&'
+if (~ `{true || echo hi} hi)
+       fail '||'
+if (~ `{false && echo hi} hi)
+       fail '&&'
+
+while (false)
+       fail false while
+while (true) {
+       break
+       fail break in while
+}
+
+switch (foo) {
+       case bar
+               fail matched bar in switch
+       case foo
+               eval
+       case *
+               fail match foo in switch
+}
+
+switch (nothing) {
+       case bar
+               fail matched bar in switch
+       case *
+               i=frobnatz
+}
+
+~ $i frobnatz || fail match '*' in switch
+
+submatch '()=()' 'rc: null variable name' 'assignment diagnostic'
+submatch 'fn () {eval}' 'rc: null function name' 'assigning null function name'
+
+#
+# prompt
+#
+fn prompt {echo hi}
+prompt=() if (!~ `{$rc -i /dev/null>[2]/dev/null} hi) fail fn prompt
+fn prompt
+
+#
+# history
+#
+history=$tmpdir/hist.$pid prompt='' echo 'history=()' | $rc -i
+
+if (!~ `{cat $tmpdir/hist.$pid} 'history=()')
+       fail output to history file
+
+history=$tmpdir/hist.$pid prompt='' echo 'history=()' | $rc -i
+
+if (!~ `` () {cat $tmpdir/hist.$pid} 'history=()
+history=()
+')
+       fail append to history file
+
+rm $tmpdir/hist.$pid
+
+if (!~ `{history=/frobnatz/foo prompt='' echo eval | $rc -i >[2=1]} ?*)
+       fail accessing bad history file
+
+#
+# regression
+#
+
+expect date
+{ date & wait } |cat
+
+# Making rc's input non-blocking should have no untoward side effects.
+x=`{ { sleep 1; echo echo foo } | { ./tripping n; $rc >[2=1] } }
+if (!~ foo $x)
+       fail input file descriptor nonblocking
+
+# `rc -s' reads from stdin, but should not imply `-i'
+expect foo bar qux
+$rc -s foo bar qux <<'eof'
+echo $*
+eof
+
+# Believe it or not, I broke root directory globbing in rc-1.6b1.
+x=/*
+~ '/*' $^x && fail root directory globbing
+
+# fn sigexit should be cleared in children
+
+x = ()
+expect rc: cannot find '`nonesuch'''
+x = `{true | nonesuch}; if (~ $x trip) fail sigexit in children
+x = `{ < /dev/null wc |grep xxx }; if (~ $x trip) fail sigexit in children
+x = `{{ wc | wc } < /dev/null }; if (~ $x trip) fail sigexit in children
+
+# core dumps in glob.c
+~ () '*' && fail globber problem
+~ () '**' && fail globber problem
+
+# check for ctrl-a bug
+x=`{./tripping a}
+~ `{$rc -c 'echo $x'} $x || fail ctrl-a bug detected
+
+# check for hilarious quoting bug introduced while fixing ctrl-a
+x=('#' '#' '#')
+eval z^`{whatis -v x}
+~ $#zx 3 || fail hilarious quoting bug
+
+# parens bypass quote detector bug
+fn x {echo x.y $(x.y)}
+~ ``''{whatis -f x} 'fn x {echo x.y $(x^.y)}
+' || fail sneaky parens bug
+
+# before rc-1.7.1, certain glob patterns could fail on broken symlinks
+mkdir $tmpdir/qux
+ln -s /frobnatz $tmpdir/qux/foo
+x=$tmpdir/qux/foo*
+~ $x $tmpdir/qux/foo || { rm -rf $tmpdir/qux; fail broken symlink globbing }
+x=$tmpdir/qux*/foo
+~ $x $tmpdir/qux/foo || { rm -rf $tmpdir/qux; fail broken symlink globbing }
+
+rm -rf $tmpdir
diff --git a/tripping.c b/tripping.c
new file mode 100644 (file)
index 0000000..23b2972
--- /dev/null
@@ -0,0 +1,45 @@
+/* This is an auxiliary test program for rc.  */
+
+#include "config.h"
+
+#include <fcntl.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+static void out0(void) {
+       putchar('t'); putchar('r');
+       putchar('\0');
+       putchar('u'); putchar('e');
+       putchar('\n');
+}
+
+static void ctrl_a(void) {
+       puts("a\001ab\002b");
+}
+
+static void makenonblock(void) {
+       int flags;
+
+       if ((flags = fcntl(0, F_GETFL)) == -1)
+               perror("fcntl 1");
+       flags |= O_NONBLOCK;
+       if (fcntl(0, F_SETFL, (long) flags) == -1)
+               perror("fcntl 2");
+}
+
+int main(int argc, char **argv) {
+       switch(argv[1][0]) {
+       case '0':
+               out0();
+               break;
+       case 'a':
+               ctrl_a();
+               break;
+       case 'n':
+               makenonblock();
+               break;
+       }
+       return 0;
+}
diff --git a/utils.c b/utils.c
new file mode 100644 (file)
index 0000000..482f7a7
--- /dev/null
+++ b/utils.c
@@ -0,0 +1,81 @@
+/* utils.c: functions of general utility */
+
+#include "rc.h"
+
+#include <errno.h>
+#include <setjmp.h>
+
+#include "jbwrap.h"
+
+/* print error with line number on noninteractive shells (i.e., scripts) */
+
+extern void pr_error(char *s, int offset) {
+       if (s != NULL) {
+               if (interactive)
+                       fprint(2, RC "%s\n", s);
+               else
+                       fprint(2, RC "line %d: %s\n", lineno + offset, s);
+       }
+}
+
+/* our perror */
+
+extern void uerror(char *s) {
+       char *err;
+
+       err = strerror(errno);
+       if (!err) err = "unknown error";
+
+       if (s)
+               fprint(2, RC "%s: %s\n", s, err);
+       else
+               fprint(2, RC "%s\n", err);
+}
+
+/* Die horribly. This should never get called. Please let me know if it does. */
+
+#define PANICMSG "rc panic: "
+
+extern void panic(char *s) {
+       write(2, PANICMSG, conststrlen(PANICMSG));
+       write(2, s, strlen(s));
+       write(2, "!\n", 2);
+       exit(1);
+}
+
+/* ascii -> unsigned conversion routines. -1 indicates conversion error. */
+
+extern int n2u(char *s, unsigned int base) {
+       unsigned int i;
+       for (i = 0; *s != '\0'; s++) {
+               unsigned int j = (unsigned int) *s - '0';
+               if (j >= base) /* small hack with unsigned ints -- one compare for range test */
+                       return -1;
+               i = i * base + j;
+       }
+       return (int) i;
+}
+
+/* The last word in portable ANSI: a strcmp wrapper for qsort */
+
+extern int starstrcmp(const void *s1, const void *s2) {
+       return strcmp(*(char * const *)s1, *(char * const *)s2);
+}
+
+/* tests to see if pathname begins with "/", "./", or "../" */
+
+extern bool isabsolute(char *path) {
+       return path[0] == '/' || (path[0] == '.' && (path[1] == '/' || (path[1] == '.' && path[2] == '/')));
+}
+
+
+/* duplicate a fd and close the old one only if necessary */
+
+extern int mvfd(int i, int j) {
+       if (i != j) {
+               int s = dup2(i, j);
+               close(i);
+               return s;
+       }
+       return 0;
+}
diff --git a/var.c b/var.c
new file mode 100644 (file)
index 0000000..2fa7c35
--- /dev/null
+++ b/var.c
@@ -0,0 +1,225 @@
+/* var.c: provide "public" functions for adding and removing variables from the symbol table */
+
+#include "rc.h"
+
+#include "input.h"
+
+static void colonassign(char *, List *, bool);
+static void listassign(char *, List *, bool);
+static int hasalias(char *);
+
+static char *const aliases[] = {
+       "home", "HOME", "path", "PATH", "cdpath", "CDPATH"
+};
+
+/* assign a variable in List form to a name, stacking if appropriate */
+
+extern void varassign(char *name, List *def, bool stack) {
+       Variable *new;
+       List *newdef = listcpy(def, ealloc); /* important to do the listcpy first; get_var_place() frees old values */
+       new = get_var_place(name, stack);
+       new->def = newdef;
+       new->extdef = NULL;
+       set_exportable(name, TRUE);
+       if (streq(name, "TERM") || streq(name, "TERMCAP"))
+               termchange();
+}
+
+/* assign a variable in string form. Check to see if it is aliased (e.g., PATH and path) */
+
+extern bool varassign_string(char *extdef) {
+       static bool aliasset[arraysize(aliases)] = {
+               FALSE, FALSE, FALSE, FALSE, FALSE, FALSE
+       };
+       char *name = get_name(extdef);
+       Variable *new;
+       int i;
+       if (name == NULL)
+               return FALSE; /* add it to bozo env */
+       if ((i = hasalias(name)) != -1) {
+               aliasset[i] = TRUE;
+               i ^= 1;                         /* set i to the "opposite" case subscript and */
+               if (i&1 && aliasset[i])         /* don't alias variables that are already set in upper case */
+                       return TRUE;
+       }
+       new = get_var_place(name, FALSE);
+       new->def = NULL;
+       new->extdef = ealloc(strlen(extdef) + 1);
+       strcpy(new->extdef, extdef);
+       if (i != -1)
+               alias(name, varlookup(name), FALSE);
+       set_exportable(name, TRUE);
+       return TRUE;
+}
+
+/*
+   Return a List based on a name lookup. If the list is in external (string) form,
+   convert it to internal (List) form. Treat $n (n is an integer) specially as $*(n).
+   Also check to see if $status is being dereferenced. (we lazily evaluate the List
+   associated with $status)
+*/
+
+extern List *varlookup(char *name) {
+       Variable *look;
+       List *ret, *l;
+       int sub;
+       if (streq(name, "apids"))
+               return sgetapids();
+       if (streq(name, "status"))
+               return sgetstatus();
+       if (*name != '\0' && (sub = a2u(name)) != -1) { /* handle $1, $2, etc. */
+               for (l = varlookup("*"); l != NULL && sub != 0; --sub)
+                       l = l->n;
+               if (l == NULL)
+                       return NULL;
+               ret = nnew(List);
+               ret->w = l->w;
+               ret->m = NULL;
+               ret->n = NULL;
+               return ret;
+       }
+       look = lookup_var(name);
+       if (look == NULL)
+               return NULL; /* not found */
+       if (look->def != NULL)
+               return look->def;
+       if (look->extdef == NULL)
+               return NULL; /* variable was set to null, e.g., a=() echo foo */
+       ret = parse_var(look->extdef);
+       if (ret == NULL) {
+               look->extdef = NULL;
+               return NULL;
+       }
+       return look->def = ret;
+}
+
+/* lookup a variable in external (string) form, converting if necessary. Used by makeenv() */
+
+extern char *varlookup_string(char *name) {
+       Variable *look;
+       look = lookup_var(name);
+       if (look == NULL)
+               return NULL;
+       if (look->extdef != NULL)
+               return look->extdef;
+       if (look->def == NULL)
+               return NULL;
+       return look->extdef = mprint("%F=%W", name, look->def);
+}
+
+/* remove a variable from the symtab. "stack" determines whether a level of scoping is popped or not */
+
+extern void varrm(char *name, bool stack) {
+       int i = hasalias(name);
+       if (streq(name, "*") && !stack) { /* when assigning () to $*, we want to preserve $0 */
+               varassign("*", varlookup("0"), FALSE);
+               return;
+       }
+       delete_var(name, stack);
+       if (i != -1)
+               delete_var(aliases[i^1], stack);
+}
+
+/* assign a value (List) to a variable, using array "a" as input. Used to assign $* */
+
+extern void starassign(char *dollarzero, char **a, bool stack) {
+       List *s, *var;
+       var = nnew(List);
+       var->w = dollarzero;
+       if (*a == NULL) {
+               var->n = NULL;
+               varassign("*", var, stack);
+               return;
+       }
+       var->n = s = nnew(List);
+       while (1) {
+               s->w = *a++;
+               if (*a == NULL) {
+                       s->n = NULL;
+                       break;
+               } else
+                       s = s->n = nnew(List);
+       }
+       varassign("*", var, stack);
+}
+
+/* (ugly name, huh?) assign a colon-separated value to a variable (e.g., PATH) from a List (e.g., path) */
+
+static void colonassign(char *name, List *def, bool stack) {
+       List dud;
+       if (def == NULL) {
+               varassign(name, NULL, stack);
+               return;
+       }
+       dud.w = nprint("%-L", def, ":");
+       dud.n = NULL;
+       varassign(name, &dud, stack);
+}
+
+/* assign a List variable (e.g., path) from a colon-separated string (e.g., PATH) */
+
+static void listassign(char *name, List *def, bool stack) {
+       List *val, *r;
+       char *v, *w;
+       if (def == NULL) {
+               varassign(name, NULL, stack);
+               return;
+       }
+       v = def->w;
+       r = val = nnew(List);
+       while ((w = strchr(v, ':')) != NULL) {
+               *w = '\0';
+               r->w = ncpy(v);
+               *w = ':';
+               v = w + 1;
+               r = r->n = nnew(List);
+       }
+       r->w = ncpy(v);
+       r->n = NULL;
+       varassign(name, val, stack);
+}
+
+/* check to see if a particular variable is aliased; return -1 on failure, or the index */
+
+static int hasalias(char *name) {
+       int i;
+       for (i = 0; i < arraysize(aliases); i++)
+               if (streq(name, aliases[i]))
+                       return i;
+       return -1;
+}
+
+/* alias a variable to its lowercase equivalent. function pointers are used to specify the conversion function */
+
+extern void alias(char *name, List *s, bool stack) {
+       static void (*vectors[])(char *, List *, bool) = {
+               varassign, varassign, colonassign, listassign, colonassign, listassign
+       };
+       int i = hasalias(name);
+       if (i != -1)
+               (*vectors[i])(aliases[i^1], s, stack); /* xor hack to reverse case of alias entry */
+}
+
+extern void prettyprint_var(int fd, char *name, List *s) {
+       int i;
+       static const char * const keywords[] = {
+               "if", "in", "fn", "for", "else", "switch", "while", "case"
+       };
+       if (s == NULL) {
+               fprint(fd, "%S=()\n", name);
+               return;
+       }
+       if (streq(name, "*")) {
+               s = s->n;
+               if (s == NULL)
+                       return; /* Don't print $0, and if $* is not set, skip it */
+       }
+       for (i = 0; i < arraysize(keywords); i++)
+               if (streq(keywords[i], name)) {
+                       fprint(fd, "%#S=", name);
+                       goto value;
+               }
+       fprint(fd, "%S=", name);
+value:
+       fprint(fd, s->n == NULL ? "%L\n" : "(%L)\n", s, " ");
+}
diff --git a/wait.c b/wait.c
new file mode 100644 (file)
index 0000000..1ab8533
--- /dev/null
+++ b/wait.c
@@ -0,0 +1,128 @@
+#include "rc.h"
+
+#include <errno.h>
+
+#include "wait.h"
+
+bool forked = FALSE;
+
+typedef struct Pid Pid;
+
+static struct Pid {
+       pid_t pid;
+       int stat;
+       bool alive;
+       Pid *n;
+} *plist = NULL;
+
+extern pid_t rc_fork() {
+       Pid *new;
+       struct Pid *p, *q;
+       pid_t pid = fork();
+
+       switch (pid) {
+       case -1:
+               uerror("fork");
+               rc_error(NULL);
+               /* NOTREACHED */
+       case 0:
+               forked = TRUE;
+               sigchk();
+               p = plist; q = 0;
+               while (p) {
+                       if (q) efree(q);
+                       q = p;
+                       p = p->n;
+               }
+               if (q) efree(q);
+               plist = 0;
+               return 0;
+       default:
+               new = enew(Pid);
+               new->pid = pid;
+               new->alive = TRUE;
+               new->n = plist;
+               plist = new;
+               return pid;
+       }
+}
+
+extern pid_t rc_wait4(pid_t pid, int *stat, bool nointr) {
+       Pid *r, *prev;
+
+       /* Find the child on the list. */
+       for (r = plist, prev = NULL; r != NULL; prev = r, r = r->n)
+               if (r->pid == pid)
+                       break;
+
+       /* Uh-oh, not there. */
+       if (r == NULL) {
+               errno = ECHILD; /* no children */
+               uerror("wait");
+               *stat = 0x100; /* exit(1) */
+               return -1;
+       }
+
+       /* If it's still alive, wait() for it. */
+       while (r->alive) {
+               int ret;
+               Pid *q;
+
+               ret = rc_wait(stat);
+
+               if (ret < 0) {
+                       if (errno == ECHILD)
+                               panic("lost child");
+                       if (nointr)
+                               continue;
+                       else
+                               return ret;
+               }
+
+               for (q = plist; q != NULL; q = q->n)
+                       if (q->pid == ret) {
+                               q->alive = FALSE;
+                               q->stat = *stat;
+                               break;
+                       }
+       }
+       *stat = r->stat;
+       if (prev == NULL)
+               plist = r->n; /* remove element from head of list */
+       else
+               prev->n = r->n;
+       efree(r);
+       return pid;
+}
+
+extern List *sgetapids() {
+       List *r;
+       Pid *p;
+       for (r = NULL, p = plist; p != NULL; p = p->n) {
+               List *q;
+               if (!p->alive)
+                       continue;
+               q = nnew(List);
+               q->w = nprint("%d", p->pid);
+               q->m = NULL;
+               q->n = r;
+               r = q;
+       }
+       return r;
+}
+
+extern void waitforall() {
+       int stat;
+
+       while (plist != NULL) {
+               pid_t pid = rc_wait4(plist->pid, &stat, FALSE);
+               if (pid > 0)
+                       setstatus(pid, stat);
+               else {
+                       set(FALSE);
+                       if (errno == EINTR)
+                               return;
+               }
+               sigchk();
+       }
+}
diff --git a/wait.h b/wait.h
new file mode 100644 (file)
index 0000000..e54ae45
--- /dev/null
+++ b/wait.h
@@ -0,0 +1,23 @@
+#if HAVE_SYS_WAIT_H
+#include <sys/wait.h>
+#endif
+
+/* Fake the POSIX wait() macros if we don't have them. */
+#ifndef WIFEXITED
+#define WIFEXITED(s) (((s) & 0xFF) == 0)
+#endif
+#ifndef WEXITSTATUS
+#define WEXITSTATUS(s) (((unsigned)(s) >> 8) && 0xFF)
+#endif
+#ifndef WIFSIGNALED
+#define WIFSIGNALED(s) (((s) & 0xFF) != 0)
+#endif
+#ifndef WTERMSIG
+#define WTERMSIG(s) ((s) & 0x7F)
+#endif
+
+/* These don't exist in POSIX. */
+#define myWIFDUMPED(s) (((s) & 0x80) != 0)
+
+
+
diff --git a/walk.c b/walk.c
new file mode 100644 (file)
index 0000000..984a68c
--- /dev/null
+++ b/walk.c
@@ -0,0 +1,365 @@
+/* walk.c: walks the parse tree. */
+
+#include "rc.h"
+
+#include <signal.h>
+#include <setjmp.h>
+
+#include "jbwrap.h"
+
+/*
+   global which indicates whether rc is executing a test;
+   used by rc -e so that if (false) does not exit.
+*/
+bool cond = FALSE;
+
+static bool haspreredir(Node *);
+static bool isallpre(Node *);
+static bool dofork(bool);
+static void dopipe(Node *);
+
+/* Tail-recursive version of walk() */
+
+#define WALK(x, y) { n = x; parent = y; goto top; }
+
+/* walk the parse-tree. "obvious". */
+
+extern bool walk(Node *n, bool parent) {
+top:   sigchk();
+       if (n == NULL) {
+               if (!parent)
+                       exit(0);
+               set(TRUE);
+               return TRUE;
+       }
+       switch (n->type) {
+       case nArgs: case nBackq: case nConcat: case nCount:
+       case nFlat: case nLappend: case nRedir: case nVar:
+       case nVarsub: case nWord:
+               exec(glob(glom(n)), parent);    /* simple command */
+               break;
+       case nBody:
+               walk(n->u[0].p, TRUE);
+               WALK(n->u[1].p, parent);
+               /* WALK doesn't fall through */
+       case nNowait: {
+               int pid;
+               if ((pid = rc_fork()) == 0) {
+#if defined(RC_JOB) && defined(SIGTTOU) && defined(SIGTTIN) && defined(SIGTSTP)
+                       setsigdefaults(FALSE);
+                       rc_signal(SIGTTOU, SIG_IGN);    /* Berkeleyized version: put it in a new pgroup. */
+                       rc_signal(SIGTTIN, SIG_IGN);
+                       rc_signal(SIGTSTP, SIG_IGN);
+                       setpgid(0, getpid());
+#else
+                       setsigdefaults(TRUE);           /* ignore SIGINT, SIGQUIT, SIGTERM */
+#endif
+                       mvfd(rc_open("/dev/null", rFrom), 0);
+                       walk(n->u[0].p, FALSE);
+                       exit(getstatus());
+               }
+               if (interactive)
+                       fprint(2, "%d\n", pid);
+               varassign("apid", word(nprint("%d", pid), NULL), FALSE);
+               redirq = NULL; /* kill pre-redir queue */
+               break;
+       }
+       case nAndalso: {
+               bool oldcond = cond;
+               cond = TRUE;
+               if (walk(n->u[0].p, TRUE)) {
+                       cond = oldcond;
+                       WALK(n->u[1].p, parent);
+               } else
+                       cond = oldcond;
+               break;
+       }
+       case nOrelse: {
+               bool oldcond = cond;
+               cond = TRUE;
+               if (!walk(n->u[0].p, TRUE)) {
+                       cond = oldcond;
+                       WALK(n->u[1].p, parent);
+               } else
+                       cond = oldcond;
+               break;
+       }
+       case nBang:
+               set(!walk(n->u[0].p, TRUE));
+               break;
+       case nIf: {
+               bool oldcond = cond;
+               Node *true_cmd = n->u[1].p, *false_cmd = NULL;
+               if (true_cmd != NULL && true_cmd->type == nElse) {
+                       false_cmd = true_cmd->u[1].p;
+                       true_cmd = true_cmd->u[0].p;
+               }
+               cond = TRUE;
+               if (!walk(n->u[0].p, TRUE))
+                       true_cmd = false_cmd; /* run the else clause */
+               cond = oldcond;
+               WALK(true_cmd, parent);
+       }
+       case nWhile: {
+               Jbwrap j;
+               Edata jbreak;
+               Estack e1, e2;
+               bool testtrue, oldcond = cond;
+               cond = TRUE;
+               if (!walk(n->u[0].p, TRUE)) { /* prevent spurious breaks inside test */
+                       cond = oldcond;
+                       break;
+               }
+               if (sigsetjmp(j.j, 1))
+                       break;
+               jbreak.jb = &j;
+               except(eBreak, jbreak, &e1);
+               do {
+                       Edata block;
+                       block.b = newblock();
+                       cond = oldcond;
+                       except(eArena, block, &e2);
+                       walk(n->u[1].p, TRUE);
+                       testtrue = walk(n->u[0].p, TRUE);
+                       unexcept(); /* eArena */
+                       cond = TRUE;
+               } while (testtrue);
+               cond = oldcond;
+               unexcept(); /* eBreak */
+               break;
+       }
+       case nForin: {
+               List *l, *var = glom(n->u[0].p);
+               Jbwrap j;
+               Estack e1, e2;
+               Edata jbreak;
+               if (sigsetjmp(j.j, 1))
+                       break;
+               jbreak.jb = &j;
+               except(eBreak, jbreak, &e1);
+               for (l = listcpy(glob(glom(n->u[1].p)), nalloc); l != NULL; l = l->n) {
+                       Edata block;
+                       assign(var, word(l->w, NULL), FALSE);
+                       block.b = newblock();
+                       except(eArena, block, &e2);
+                       walk(n->u[2].p, TRUE);
+                       unexcept(); /* eArena */
+               }
+               unexcept(); /* eBreak */
+               break;
+       }
+       case nSubshell:
+               if (dofork(TRUE)) {
+                       setsigdefaults(FALSE);
+                       walk(n->u[0].p, FALSE);
+                       rc_exit(getstatus());
+               }
+               break;
+       case nAssign:
+               if (n->u[0].p == NULL)
+                       rc_error("null variable name");
+               assign(glom(n->u[0].p), glob(glom(n->u[1].p)), FALSE);
+               set(TRUE);
+               break;
+       case nPipe:
+               dopipe(n);
+               break;
+       case nNewfn: {
+               List *l = glom(n->u[0].p);
+               if (l == NULL)
+                       rc_error("null function name");
+               while (l != NULL) {
+                       if (dashex)
+                               prettyprint_fn(2, l->w, n->u[1].p);
+                       fnassign(l->w, n->u[1].p);
+                       l = l->n;
+               }
+               set(TRUE);
+               break;
+       }
+       case nRmfn: {
+               List *l = glom(n->u[0].p);
+               while (l != NULL) {
+                       if (dashex)
+                               fprint(2, "fn %S\n", l->w);
+                       fnrm(l->w);
+                       l = l->n;
+               }
+               set(TRUE);
+               break;
+       }
+       case nDup:
+               redirq = NULL;
+               break; /* Null command */
+       case nMatch: {
+               List *a = glob(glom(n->u[0].p)), *b = glom(n->u[1].p);
+               if (dashex)
+                       fprint(2, (a != NULL && a->n != NULL) ? "~ (%L) %L\n" : "~ %L %L\n", a, " ", b, " ");
+               set(lmatch(a, b));
+               break;
+       }
+       case nSwitch: {
+               List *v = glom(n->u[0].p);
+               while (1) {
+                       do {
+                               n = n->u[1].p;
+                               if (n == NULL)
+                                       return istrue();
+                       } while (n->u[0].p == NULL || n->u[0].p->type != nCase);
+                       if (lmatch(v, glom(n->u[0].p->u[0].p))) {
+                               for (n = n->u[1].p; n != NULL && (n->u[0].p == NULL || n->u[0].p->type != nCase); n = n->u[1].p)
+                                       walk(n->u[0].p, TRUE);
+                               break;
+                       }
+               }
+               break;
+       }
+       case nPre: {
+               List *v;
+               if (n->u[0].p->type == nRedir || n->u[0].p->type == nDup) {
+                       if (redirq == NULL && !dofork(parent)) /* subshell on first preredir */
+                               break;
+                       setsigdefaults(FALSE);
+                       qredir(n->u[0].p);
+                       if (!haspreredir(n->u[1].p))
+                               doredirs(); /* no more preredirs, empty queue */
+                       walk(n->u[1].p, FALSE);
+                       rc_exit(getstatus());
+                       /* NOTREACHED */
+               } else if (n->u[0].p->type == nAssign) {
+                       if (isallpre(n->u[1].p)) {
+                               walk(n->u[0].p, TRUE);
+                               WALK(n->u[1].p, parent);
+                       } else {
+                               Estack e;
+                               Edata var;
+                               v = glom(n->u[0].p->u[0].p);
+                               assign(v, glob(glom(n->u[0].p->u[1].p)), TRUE);
+                               var.name = v->w;
+                               except(eVarstack, var, &e);
+                               walk(n->u[1].p, parent);
+                               varrm(v->w, TRUE);
+                               unexcept(); /* eVarstack */
+                       }
+               } else
+                       panic("unexpected node in preredir section of walk");
+               break;
+       }
+       case nBrace:
+               if (n->u[1].p == NULL) {
+                       WALK(n->u[0].p, parent);
+               } else if (dofork(parent)) {
+                       setsigdefaults(FALSE);
+                       walk(n->u[1].p, TRUE); /* Do redirections */
+                       redirq = NULL;   /* Reset redirection queue */
+                       walk(n->u[0].p, FALSE); /* Do commands */
+                       rc_exit(getstatus());
+                       /* NOTREACHED */
+               }
+               break;
+       case nEpilog:
+               qredir(n->u[0].p);
+               if (n->u[1].p != NULL) {
+                       WALK(n->u[1].p, parent); /* Do more redirections. */
+               } else {
+                       doredirs();     /* Okay, we hit the bottom. */
+               }
+               break;
+       case nNmpipe:
+               rc_error("named pipes cannot be executed as commands");
+               /* NOTREACHED */
+       default:
+               panic("unknown node in walk");
+               /* NOTREACHED */
+       }
+       return istrue();
+}
+
+/* checks to see whether there are any pre-redirections left in the tree */
+
+static bool haspreredir(Node *n) {
+       while (n != NULL && n->type == nPre) {
+               if (n->u[0].p->type == nDup || n->u[0].p->type == nRedir)
+                       return TRUE;
+               n = n->u[1].p;
+       }
+       return FALSE;
+}
+
+/* checks to see whether a subtree is all pre-command directives, i.e., assignments and redirs only */
+
+static bool isallpre(Node *n) {
+       while (n != NULL && n->type == nPre)
+               n = n->u[1].p;
+       return n == NULL || n->type == nRedir || n->type == nAssign || n->type == nDup;
+}
+
+/*
+   A code-saver. Forks, child returns (for further processing in walk()), and the parent
+   waits for the child to finish, setting $status appropriately.
+*/
+
+static bool dofork(bool parent) {
+       int pid, sp;
+
+       if (!parent || (pid = rc_fork()) == 0)
+               return TRUE;
+       redirq = NULL; /* clear out the pre-redirection queue in the parent */
+       rc_wait4(pid, &sp, TRUE);
+       setstatus(-1, sp);
+       sigchk();
+       return FALSE;
+}
+
+static void dopipe(Node *n) {
+       int i, j, sp, pid, fd_prev, fd_out, pids[512], stats[512], p[2];
+       bool intr;
+       Node *r;
+
+       fd_prev = fd_out = 1;
+       for (r = n, i = 0; r != NULL && r->type == nPipe; r = r->u[2].p, i++) {
+               if (i > 500) /* the only hard-wired limit in rc? */
+                       rc_error("pipe too long");
+               if (pipe(p) < 0) {
+                       uerror("pipe");
+                       rc_error(NULL);
+               }
+               if ((pid = rc_fork()) == 0) {
+                       setsigdefaults(FALSE);
+                       redirq = NULL; /* clear preredir queue */
+                       mvfd(p[0], r->u[1].i);
+                       if (fd_prev != 1)
+                               mvfd(fd_prev, fd_out);
+                       close(p[1]);
+                       walk(r->u[3].p, FALSE);
+                       exit(getstatus());
+               }
+               if (fd_prev != 1)
+                       close(fd_prev); /* parent must close all pipe fd's */
+               pids[i] = pid;
+               fd_prev = p[1];
+               fd_out = r->u[0].i;
+               close(p[0]);
+       }
+       if ((pid = rc_fork()) == 0) {
+               setsigdefaults(FALSE);
+               mvfd(fd_prev, fd_out);
+               walk(r, FALSE);
+               exit(getstatus());
+               /* NOTREACHED */
+       }
+       redirq = NULL; /* clear preredir queue */
+       close(fd_prev);
+       pids[i++] = pid;
+
+       /* collect statuses */
+
+       intr = FALSE;
+       for (j = 0; j < i; j++) {
+               rc_wait4(pids[j], &sp, TRUE);
+               stats[j] = sp;
+               intr |= (sp == SIGINT);
+       }
+       setpipestatus(stats, i);
+       sigchk();
+}
diff --git a/which.c b/which.c
new file mode 100644 (file)
index 0000000..798d7b0
--- /dev/null
+++ b/which.c
@@ -0,0 +1,142 @@
+/* which.c: check to see if a file is executable.
+
+   This function was originally written with Maarten Litmaath's which.c as
+   a template, but was changed in order to accommodate the possibility of
+   rc's running setuid or the possibility of executing files not in the
+   primary group. Much of this file has been re-vamped by Paul Haahr.
+   I re-re-vamped the functions that Paul supplied to correct minor bugs
+   and to strip out unneeded functionality.
+*/
+
+#include "rc.h"
+
+#include <ctype.h>
+#include <errno.h>
+#include <sys/stat.h>
+
+#include "getgroups.h"
+
+#define X_USR 0100
+#define X_GRP 0010
+#define X_OTH 0001
+#define X_ALL (X_USR|X_GRP|X_OTH)
+
+static bool initialized = FALSE;
+static uid_t uid;
+static gid_t gid;
+
+#if HAVE_GETGROUPS
+static int ngroups;
+static GETGROUPS_T *gidset;
+
+/* determine whether gid lies in gidset */
+
+static int ingidset(gid_t g) {
+       int i;
+       for (i = 0; i < ngroups; ++i)
+               if (g == gidset[i])
+                       return 1;
+       return 0;
+}
+#else
+#define ingidset(g) (FALSE)
+#endif
+
+/*
+   A home-grown access/stat. Does the right thing for group-executable files.
+   Returns a bool instead of this -1 nonsense.
+*/
+
+static bool rc_access(char *path, bool verbose) {
+       struct stat st;
+       int mask;
+       if (stat(path, &st) != 0) {
+               if (verbose) /* verbose flag only set for absolute pathname */
+                       uerror(path);
+               return FALSE;
+       }
+       if (uid == 0)
+               mask = X_ALL;
+       else if (uid == st.st_uid)
+               mask = X_USR;
+       else if (gid == st.st_gid || ingidset(st.st_gid))
+               mask = X_GRP;
+       else
+               mask = X_OTH;
+       if (((st.st_mode & S_IFMT) == S_IFREG) && (st.st_mode & mask))
+               return TRUE;
+       errno = EACCES;
+       if (verbose)
+               uerror(path);
+       return FALSE;
+}
+
+/* replace non-printing characters with question marks in a freshly
+ * allocated string */
+static char *protect(char *in) {
+       int l = strlen(in);
+       char *out = ealloc(l + 1);
+       int i;
+
+       for (i = 0; i < l; ++i)
+               out[i] = isprint(in[i]) ? in[i] : '?';
+       out[i] = '\0';
+       return out;
+}
+                   
+/* return a full pathname by searching $path, and by checking the status of the file */
+
+extern char *which(char *name, bool verbose) {
+       static char *test = NULL;
+       static size_t testlen = 0;
+       List *path;
+       int len;
+       if (name == NULL)       /* no filename? can happen with "> foo" as a command */
+               return NULL;
+       if (!initialized) {
+               initialized = TRUE;
+               uid = geteuid();
+               gid = getegid();
+#if HAVE_GETGROUPS
+#if HAVE_POSIX_GETGROUPS
+               ngroups = getgroups(0, (GETGROUPS_T *)0);
+               if (ngroups < 0) {
+                       uerror("getgroups");
+                       rc_exit(1);
+               }
+#else
+               ngroups = NGROUPS;
+#endif
+               if (ngroups) {  
+                       gidset = ealloc(ngroups * sizeof(GETGROUPS_T));
+                       getgroups(ngroups, gidset);
+               }
+#endif
+       }
+       if (isabsolute(name)) /* absolute pathname? */
+               return rc_access(name, verbose) ? name : NULL;
+       len = strlen(name);
+       for (path = varlookup("path"); path != NULL; path = path->n) {
+               size_t need = strlen(path->w) + len + 2; /* one for null terminator, one for the '/' */
+               if (testlen < need) {
+                       efree(test);
+                       test = ealloc(testlen = need);
+               }
+               if (*path->w == '\0') {
+                       strcpy(test, name);
+               } else {
+                       strcpy(test, path->w);
+                       if (!streq(test, "/")) /* "//" is special to POSIX */
+                               strcat(test, "/");
+                       strcat(test, name);
+               }
+               if (rc_access(test, FALSE))
+                       return test;
+       }
+       if (verbose) {
+               char *n = protect(name);
+               fprint(2, RC "cannot find `%s'\n", n);
+               efree(n);
+       }
+       return NULL;
+}