From e11c7df86144bed383ac6bbeaecc3017d18b37db Mon Sep 17 00:00:00 2001 From: Toby Goodwin Date: Mon, 11 Jan 1999 10:55:18 +0000 Subject: beta: rc-1.5b4 --- AUTHORS | 34 + CHANGES | 278 ------ COPYING | 26 + COPYRIGHT | 26 - ChangeLog | 531 +++++++++++ INSTALL | 167 ++++ Makefile.am | 69 ++ Makefile.in | 80 -- NEWS | 50 ++ README | 191 +--- acconfig.h | 80 ++ acinclude.m4 | 206 +++++ addon.c | 33 +- addon.h | 49 +- builtins.c | 15 +- config.h-dist | 204 +++++ config.h.in | 44 - configure | 2541 ----------------------------------------------------- configure.ac | 200 +++++ configure.in | 287 ------ cpp | 38 - except.c | 4 +- exec.c | 16 +- execve.c | 6 +- fn.c | 19 +- footobar.c | 10 +- getgroups.h | 10 + getopt.c | 73 +- glob.c | 3 +- glom.c | 17 +- group.h | 9 - hash.c | 10 +- history.1 | 243 +++++ history.c | 339 +++++++ history/history.1 | 234 ----- history/history.c | 341 ------- input.c | 99 ++- install-sh | 250 ------ jbwrap.h | 22 +- lex.c | 12 +- main.c | 10 +- mksignal | 76 -- mksignal.c | 238 +++++ nalloc.c | 7 +- open.c | 22 +- parse.y | 4 +- print.c | 141 +-- proto.h | 70 +- rc.1 | 61 +- rc.h | 114 ++- rlimit.h | 36 +- signal.c | 53 +- status.c | 23 +- system-bsd.c | 60 ++ system.c | 10 + trip.rc | Bin 14684 -> 15120 bytes tripping.c | 33 + utils.c | 42 +- var.c | 8 +- version.c | 1 - version.c.in | 1 + wait.c | 94 +- wait.h | 23 + walk.c | 5 +- which.c | 26 +- y.tab.c | 1070 ---------------------- y.tab.h | 33 - 67 files changed, 3104 insertions(+), 6023 deletions(-) create mode 100644 AUTHORS delete mode 100644 CHANGES create mode 100644 COPYING delete mode 100644 COPYRIGHT create mode 100644 ChangeLog create mode 100644 INSTALL create mode 100644 Makefile.am delete mode 100644 Makefile.in create mode 100644 NEWS create mode 100644 acconfig.h create mode 100644 acinclude.m4 create mode 100644 config.h-dist delete mode 100644 config.h.in delete mode 100755 configure create mode 100644 configure.ac delete mode 100644 configure.in delete mode 100644 cpp create mode 100644 getgroups.h delete mode 100644 group.h create mode 100644 history.1 create mode 100644 history.c delete mode 100644 history/history.1 delete mode 100644 history/history.c delete mode 100755 install-sh delete mode 100755 mksignal create mode 100644 mksignal.c create mode 100644 system-bsd.c create mode 100644 system.c create mode 100644 tripping.c delete mode 100644 version.c create mode 100644 version.c.in create mode 100644 wait.h delete mode 100644 y.tab.c delete mode 100644 y.tab.h diff --git a/AUTHORS b/AUTHORS new file mode 100644 index 0000000..4075191 --- /dev/null +++ b/AUTHORS @@ -0,0 +1,34 @@ +The current maintainer of rc is Tim Goodwin . Please +send all bug reports to him. + +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. + +Tim would like to thank these people for their contributions since he +took over maintenance of rc. Arvid Requate, Bengt Kleberg, Brynjulv +Hauksson, Byron Rakitzis, Chris Siebenmann, David Swasey, Gert-Jan Vons, +Ian Lance Taylor, Jeremy Fitzhardinge, Marc Moorcroft, Mark K Gardner, +Raymond Venneker, Rich $alz, Rob Savoye, Scott Schwartz, Stefan Dalibor, +Tom Culliton, Tom Tromey, Vincent Broman. diff --git a/CHANGES b/CHANGES deleted file mode 100644 index 0543c11..0000000 --- a/CHANGES +++ /dev/null @@ -1,278 +0,0 @@ -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. diff --git a/COPYING b/COPYING new file mode 100644 index 0000000..8ce4998 --- /dev/null +++ b/COPYING @@ -0,0 +1,26 @@ +/* + * Copyright 1991, 1999 Byron Rakitzis. All rights reserved. + * + * This software is not subject to any license of the American Telephone + * and Telegraph Company or of the Regents of the University of California. + * + * Permission is granted to anyone to use this software for any purpose on + * any computer system, and to alter it and redistribute it freely, subject + * to the following restrictions: + * + * 1. The author is not responsible for the consequences of use of this + * software, no matter how awful, even if they arise from flaws in it. + * + * 2. The origin of this software must not be misrepresented, either by + * explicit claim or by omission. Since few users ever read sources, + * credits must appear in the documentation. + * + * 3. Altered versions must be plainly marked as such, and must not be + * misrepresented as being the original software. Since few users + * ever read sources, credits must appear in the documentation. + * + * 4. This notice may not be removed or altered. + * + * [this copyright notice is adapted from Henry Spencer's + * "awf" copyright notice.] + */ diff --git a/COPYRIGHT b/COPYRIGHT deleted file mode 100644 index 279f66c..0000000 --- a/COPYRIGHT +++ /dev/null @@ -1,26 +0,0 @@ -/* - * Copyright 1991 Byron Rakitzis. All rights reserved. - * - * This software is not subject to any license of the American Telephone - * and Telegraph Company or of the Regents of the University of California. - * - * Permission is granted to anyone to use this software for any purpose on - * any computer system, and to alter it and redistribute it freely, subject - * to the following restrictions: - * - * 1. The author is not responsible for the consequences of use of this - * software, no matter how awful, even if they arise from flaws in it. - * - * 2. The origin of this software must not be misrepresented, either by - * explicit claim or by omission. Since few users ever read sources, - * credits must appear in the documentation. - * - * 3. Altered versions must be plainly marked as such, and must not be - * misrepresented as being the original software. Since few users - * ever read sources, credits must appear in the documentation. - * - * 4. This notice may not be removed or altered. - * - * [this copyright notice is adapted from Henry Spencer's - * "awf" copyright notice.] - */ diff --git a/ChangeLog b/ChangeLog new file mode 100644 index 0000000..d997a6d --- /dev/null +++ b/ChangeLog @@ -0,0 +1,531 @@ +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 + to say that it is void. Fix this by defining our own + RC_FUNC_SETPGRP for now. + + Bug: 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 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: 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 before . + +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 . + +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. diff --git a/INSTALL b/INSTALL new file mode 100644 index 0000000..f99c34e --- /dev/null +++ b/INSTALL @@ -0,0 +1,167 @@ +COMPILING + +rc uses GNU autoconf and automake. The following commands are all you +need to configure, build, test, and install rc. + + $ sh configure + $ make + $ make trip + # make install + +This will build rc in the source directory (see below for details on how +to build rc in a different directory). + +BUILD AND CONFIGURATION OPTIONS + +There are lots of options you can give to configure to modify rc's +behaviour. You can also select a command line history library to +link against---see the README file for details of where to find these +libraries. For a summary of all options, run `sh configure --help'. + +You can specify Makefile variables by setting the corresponding +environment variables. For example, you might want to set `CC=cc', to +prevent configure looking for gcc, or set an initial value for `LIBS', +as in the example below. It is a good idea to specify static linking +(unless you are linking against a dynamic readline library)---if you are +using gcc, you can do this by setting `CFLAGS=-static'. + +Here are the configure options you may want to use, in approximately +descending order of usefulness. + + --with-editline + + This option tells rc to use the editline package (see the README file + for details) to provide EMACS style command line editing and history. + If the editline library is not installed in a standard place, you can + tell configure where to find it by setting the environment variable + LIBS. For example, the maintainer builds rc by copying libedit.a into + the rc build directory and then running this configure command. + + LIBS=-L. sh ../rc-1.5b3/configure --with-editline + + --with-vrl + + This option tells rc to use the vrl package (see the README file for + details) to provide EMACS style command line editing and history. As + for `--with-editline', you may need to set the environment variable + LIBS appropriately. + + --with-readline + + This option tells rc to use the GNU readline package, which is similar + to editline or vrl, but has many more features. The readline package + is over 6 times the size of editline (whether you count lines of code, + or the library itself). As for editline, you can set the environment + variable LIBS if your readline library is not installed in a standard + place. + + LIBS=-L/usr/gnu/lib sh configure --with-readline + + --with-history + + Use this option if you want to build and install the programs that + support a crude history mechanism. + +You can't use more than one of `--with-editline', `--with-vrl', and +`--with-readline' at the same time. If you have any of these you +probably don't want to bother with `--with-history'. + + --prefix /path + + By default, `prefix' is /usr/local, which means that `make install' + installs rc (and possibly the history programs) in /usr/local/bin, and + man pages in /usr/local/man/man1. Use this option to change where + `make install' puts things. + + --disable-builtin-echo + + By default, the `echo' command is builtin to rc for reasons of + efficiency and portability (of rc scripts). It is the only builtin + which is not essential, and purists may wish to omit it. Note that + `make trip' will fail if you disable builtin echo and your system's + `echo' does not understand `-n' to suppress newline. + + --with-addon + --with-addon=foo.c + + On the other hand, non-purists may wish to add extra builtin commands. + An example is included in the files addon.c and addon.h, which will + only be built if you specify `--with-addon'. If your addons are + in another file, you can specify that instead (but beware that the + interface file is still addon.h). + + --disable-def-interp + --enable-def-interp=/bin/foo + + By default, a program that fails with "Exec format error" is handed to + /bin/sh. This does the Right Thing for scripts that start with `:' to + indicate that they are sh scripts. You can disable this behaviour + entirely, or specify a different default interpreter. + + --disable-def-path + --enable-def-path "/usr/local/bin","/usr/bin" + + By default, if rc is started with no PATH, it uses a default path. + The default path is constructed at configure time, and consists + of each of the following directories that exist, in order. + + /usr/local/bin /usr/bin /usr/ucb /bin . + + You can disable this, or specify a different default path. Note that + the quote marks (") must be seen by configure; unless you are already + using rc, you will probably need to quote them to your shell. + + --disable-job + + By default, rc puts backgrounded processes into a new process group, + as though it were a job control shell (it isn't). This is usually + needed to work around bugs in application programs which install + signal handlers for the keyboard signals without checking whether the + signal was being ignored. This option disables the default behaviour, + making rc behave like a traditional sh. You are unlikely to want this + option on any Unix system. + + --disable-protect-env + + By default, rc encodes special characters in environment variables. + This is necessary on all known Unix systems to prevent sh either + dying or discarding the variables. This option disables the default + behaviour. You are unlikely to want this option on any Unix system. + +After you've built rc, I recommend that you run it through a test script +to gain some confidence that all is working well. Type `make trip' to +do this. This will produce some output, and should end with "trip is +complete". If the trip instead ends with "trip took a wrong turn..." +please contact the maintainer. + +BUILDING IN ANOTHER DIRECTORY + +If you have a suitable `make', you can build rc in a different directory +from where the sources are held. This is particularly useful if you +are building rc for multiple architectures. All you need do is specify +the path to the configure script in the first step. Suitable `make's +include GNU, HP-UX, and SunOS, but not Irix, nor Ultrix, nor UnixWare. + +COMPILATION WARNINGS + +If your C compiler is gcc, the option `-Wall' is turned on. This may +produce a few warnings. + +Warnings about "implicit declaration" of system functions may occur if +your system's include files are deficient---they are usually harmless. + +There is a warning about "variable `n' might be clobbered" in walk.c. +I'm not sure how serious this warning is, nor how to eliminate it. + +On some systems there are warnings about "passing arg 2 of `getgroups' +from incompatible pointer type" in which.c. I believe this is due to an +incorrect declaration of `getgroups()' in those systems' header files. + +Any other warnings should be reported to the maintainer. + +OLD C + +rc needs an ISO C (89) compiler, or at least one that has a reasonable +understanding of function prototypes, `', `void', and +`volatile'. If you really need to compile rc with an ancient C +compiler, please contact the maintainer. diff --git a/Makefile.am b/Makefile.am new file mode 100644 index 0000000..6433f0c --- /dev/null +++ b/Makefile.am @@ -0,0 +1,69 @@ +## Process this file with automake to produce Makefile.in + +if AMC_ADDON +ADDON = @ADDON@ +endif + +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_READLINE +READLINE = readline.o +endif + +if AMC_RESTART +SYSTEM = system-bsd.o +else +SYSTEM = system.o +endif + +bin_PROGRAMS = rc +noinst_PROGRAMS = mksignal 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 execve.c readline.c system.c system-bsd.c + +rc_DEPENDENCIES = sigmsgs.o $(ADDON) $(EXECVE) $(READLINE) $(SYSTEM) +rc_LDADD = sigmsgs.o $(ADDON) $(EXECVE) $(READLINE) $(SYSTEM) + +noinst_HEADERS = getgroups.h jbwrap.h parse.h proto.h rc.h rlimit.h wait.h + +BUILT_SOURCES = sigmsgs.c + +EXTRA_DIST = EXAMPLES RELDATE addon.c addon.h history.1 parse.y rc.1 trip.rc + +sigmsgs.c sigmsgs.h: mksignal + ./mksignal + +CONFIGURE_DEPENDENCIES = RELDATE + +# 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 + +trip: rc tripping + ./rc -p < $(srcdir)/trip.rc + +install-exec-hook: +if AMC_HISTORY + $(LN) history - ;\ + $(INSTALL_PROGRAM) - $(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 deleted file mode 100644 index ed89d84..0000000 --- a/Makefile.in +++ /dev/null @@ -1,80 +0,0 @@ -# Makefile.in for rc. - -SHELL=/bin/sh - -bindir=@bindir@ -exec_prefix=@exec_prefix@ -mandir=@mandir@ -prefix=@prefix@ - -CC=@CC@ -CFLAGS=@CFLAGS@ -LDFLAGS=@CFLAGS@ -LIBS=@LIBS@ - -INSTALL=@INSTALL@ -INSTALL_DATA=@INSTALL_DATA@ -INSTALL_PROGRAM=@INSTALL_PROGRAM@ -LN=@LN@ -YACC=@YACC@ - -HISTORY=@HISTORY@ - -OBJS=@ADDON@ builtins.o except.o exec.o @EXECVE@ 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 print.o redir.o sigmsgs.o signal.o status.o tree.o \ - utils.o var.o version.o wait.o walk.o which.o y.tab.o - -all: rc $(HISTORY) - -rc: $(OBJS) - $(CC) -o $@ $(OBJS) $(LDFLAGS) $(LIBS) - -sigmsgs.c: mksignal - sh mksignal @SIGNAL_H@ - -y.tab.c: parse.y - $(YACC) -d parse.y - -trip: rc - ./rc -p < trip.rc - -clean: force - rm -f rc $(HISTORY) - *.o *.tab.* sigmsgs.* config.cache config.log - -cleaner: clean - rm -f config.status config.h Makefile - -cleanest: cleaner - rm -f configure - -history: force - cd history; make CC="$(CC)" $(HISTORYMAKEFLAGS) - -install: all - $(INSTALL_PROGRAM) rc $(bindir) - $(INSTALL_DATA) rc.1 $(mandir)/man1/rc.1 - case "x$(HISTORY)" in \ - x) \ - ;; \ - *) \ - $(LN) $(HISTORY) - ;\ - $(INSTALL_PROGRAM) - $(bindir) ;\ - $(LN) $(bindir)/- $(bindir)/-- ;\ - $(LN) $(bindir)/- $(bindir)/-p ;\ - $(LN) $(bindir)/- $(bindir)/--p ;\ - $(INSTALL_DATA) history/history.1 $(mandir)/man1/history.1 \ - ;; \ - esac - -force: - -# dependencies: - -$(OBJS): config.h proto.h rc.h -sigmsgs.h: sigmsgs.c -lex.o y.tab.o: y.tab.c - -builtins.o except.o exec.o input.o signal.o utils.o wait.o walk.o: jbwrap.h -builtins.o: rlimit.h -builtins.o fn.o hash.o signal.o status.o: sigmsgs.h diff --git a/NEWS b/NEWS new file mode 100644 index 0000000..ec827a6 --- /dev/null +++ b/NEWS @@ -0,0 +1,50 @@ +Since rc-1.5b2 was released, many fixes have been made to the +autoconfiguration code, some of them critical. One problem (which I +introduced) was found in minutes with ElectricFence: I had spent several +hours failing to find it with other tools. + +Two bugs in rc itself, one of them trivial, were fixed. + +rc now uses GNU automake. Although I feel that automake is sticking +plaster to mend a broken leg, it has made my job as maintainer easier. +(Errm, apart from tracking down bugs in automake itself, and Perl, that +is.) For people building rc, it's now possible (depending on your +flavour of `make') to build in a separate directory from the source. + +Creeping featurism: rc now has a `-V' switch to report its version +number. + +The detection of signal names has been completely revised. Vincent +Broman suggested this, and contributed mksignal.c. + +The interaction with readline has been redone, principally to work +around bugs in the readline library. Tom Culliton persuaded me of +the need for this, and his patches to an earlier version of rc became +readline.c. + +I rewrote addon.[ch] to provide a more useful example of adding extra +builtins. + +The rc build system no longer considers running `yacc': parse.y is for +information only. The supplied y.tab.[ch] were built with Berkeley +`yacc', and lightly edited to remove a few gcc warnings. This idea was +suggested by Gert-Jan Vons. + +Binaries of rc-1.5b4 are typically a few kilobytes smaller than 1.5b2. +I believe this is due to improved autoconfiguration: we are now much +more careful only to include code that will be used. + +Support for vrl (another lightweight "readline"-style library) was +added. + +rc can now deal with a bogus application that sets its stdin to +non-blocking mode. + +See ChangeLog for more details. + +What happened to rc-1.5b3? There were a couple of releases to people +who'd found bugs in rc-1.5b2 that were called b3. To avoid any +possibility of confusion, I have named this beta release rc-1.5b4. + +Tim Goodwin +1999-01-11 diff --git a/README b/README index 30e9f9a..f750d18 100644 --- a/README +++ b/README @@ -1,136 +1,18 @@ -This is release 1.5b2 of rc. +This is a snapshot release of rc-1.5. The file RELDATE identifies the +date of the snapshot. -Read COPYRIGHT for copying information. All files are +See COPYING for copying information. All files are - Copyright 1991, 1997 Byron Rakitzis. + Copyright 1991, 1999 Byron Rakitzis. -COMPILING +See INSTALL for build and installation information. -rc was written in portable ANSI C. If you don't have an ANSI compiler -like gcc or something close (e.g., sgi's cc) read further down on -how to convert rc's source to old C. - -The following commands are all you need to configure, build, -test, and install rc. - - $ sh configure - $ make - $ make trip - # make install - -There are lots of options you can give to configure to modify rc's -behaviour. You can also select a command line history library to link -against. For a summary of all options, run `sh configure --help'. - -You can specify Makefile variables by setting the corresponding -environment variables. For example, you might want to set `CC=cc', to -prevent configure looking for gcc, or set an initial value for `LIBS', -as in the example below. - -Here are the configure options you may want to use, in approximately -descending order of usefulness. - - --with-editline - - This option tells rc to use Simmule Turner's and Rich $alz's editline - package, which you can get from the following location. This is - essentially a lightweight version of GNU readline, providing EMACS - style command line editing and history. - - ftp://ftp.pipex.net/people/tim/editline.tar.gz - - If the editline library is not installed in a standard place, you - can tell configure where to find it by setting the environment - variable LIBS. For example, the maintainer builds rc by copying - libedit.a into the rc directory and then running this configure - command. - - LIBS=-L. sh configure --with-editline - - --with-readline - - This option tells rc to use the GNU readline package, which is similar - to editline, but has many more features. The readline package is over - 6 times the size of editline (whether you count lines of code, or the - library itself). You probably need to tell the compiler to link with - the termcap library if you're using readline. For example, here is - the configure command the maintainer uses to build rc with readline. - - LIBS=-ltermcap sh configure --with-readline - - --enable-history - - Use this option if you want to build and install the programs that - support a crude history mechanism. - -You can't use `--with-editline' and `--with-readline' together, of course, -and if you have either of those you probably don't want to bother with -`--enable-history'. - - --prefix=/path - - By default, `prefix' is /usr/local, which means that `make install' - installs rc (and possibly the history programs) in /usr/local/bin, and - man pages in /usr/local/man/man1. Use this option to change where - `make install' puts things. - - --disable-builtin-echo - - By default, the `echo' command is builtin to rc for efficiency reasons. - It is the only builtin which is not essential, and purists may wish - to omit it. - - --disable-def-interp - --enable-def-interp=/bin/foo - - By default, a program that fails with "Exec format error" is handed to - /bin/sh. This does the Right Thing for scripts that start with `:' to - indicate that they are sh scripts. You can disable this behaviour - entirely, or specify a different default interpreter. - - --disable-def-path - --enable-def-path="/usr/local/bin","/usr/bin" - - By default, if rc is started with no PATH, it uses a default path. - The default path is constructed at configure time, and consists - of each of the following directories that exist, in order. - - /usr/local/bin /usr/bin /usr/ucb /bin . - - You can disable this, or specify a different default path. Note - that the quote marks (") must be seen by configure; you will - probably need to quote them to your shell. (Not if it's already - rc, but then you will need to quote the `='.) - - --disable-job - - By default, rc puts backgrounded processes into a new process group, - as though it were a job control shell (it isn't). This is usually - needed to work around bugs in application programs which install - signal handlers for the keyboard signals without checking whether the - signal was being ignored. This option disables the default behaviour, - making rc behave like a traditional sh. You are unlikely to want this - option on any Unix system. - - --disable-protect-env - - By default, rc encodes special characters in environment variables. - This is necessary on all known Unix systems to prevent sh either - dying or discarding the variables. This option disables the default - behaviour. You are unlikely to want this option on any Unix system. - -After you've built rc, you may wish to run it through a test script -to see that everything is ok. Type `make trip' for this. This will -produce some output, and end with "trip is complete". If the trip ends -with "trip took a wrong turn..." please contact the maintainer. (If -you've built in either of the command line history libraries, the trip -will fail near the end with `trip took a wrong turn: dot -i'.) BUGS -Send bug reports to ( after -1997-07-27). If a core dump is generated, sending a backtrace will -help a great deal. You can get a backtrace like this. +Send bug reports to . 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 @@ -140,58 +22,19 @@ help a great deal. You can get a backtrace like this. 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 "INCOMPATABILITIES" 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, +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. -YACC - -The yacc that Sun ships with SunOS 4.1.1 calls malloc() to allocate -space for the state stack, and requires a call to YYACCEPT or YYABORT to -free this memory. This means that if rc takes an interrupt while parsing -a command (say, if ^C is typed), yacc will leak away this memory. The -solution is to use a yacc which statically allocates this array, such -as the yacc in the BSD distribution. Berkeley yacc-generated y.tab.c -and y.tab.h are shipped with rc in case you cannot get hold of Berkeley -yacc. - -OLD C - -If you need to convert rc's source into K&R C, you need to run the -source through a filter called "unproto", posted in comp.sources.misc. -A sample "cpp" shell script that I used to run unproto under SunOS is -supplied with rc. - -CREDITS - -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 of 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 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. - -The current maintainer of rc is Tim Goodwin, -( after 1997-07-27). + +WWW + +More information on releases of rc can be found at this web page. + + http://www.star.le.ac.uk/~tjg/rc/ + diff --git a/acconfig.h b/acconfig.h new file mode 100644 index 0000000..8e8c0e7 --- /dev/null +++ b/acconfig.h @@ -0,0 +1,80 @@ +/* Define to a suitable ssize_t. */ +#undef ssize_t + +/* Define to a suitable sig_atomic_t. */ +#undef sig_atomic_t + +/* Define if you want rc to hand off exec errors to (e.g.) /bin/sh. */ +#undef DEFAULTINTERP + +/* Define to the default path used if $PATH is empty when rc starts. */ +#undef DEFAULTPATH + +/* Define if your kernel has SysV special SIGCLD semantics. */ +#undef HAVE_SYSV_SIGCLD + +/* Define if your kernel supports `#!' magic numbers. */ +#undef HASH_BANG + +/* Define if you have /dev/fd. */ +#undef HAVE_DEV_FD + +/* Define if you have /proc/self/fd. */ +#undef HAVE_PROC_SELF_FD + +/* Define if you have named pipes. */ +#undef HAVE_FIFO + +/* Define if quad_t is a native type. */ +#undef HAVE_QUAD_T + +/* Define if you have rlim_t. */ +#undef HAVE_RLIM_T + +/* Define if you have sigsetjmp(). */ +#undef HAVE_SIGSETJMP + +/* Define if you want rc to encode strange characters in the environment. */ +#undef PROTECT_ENV + +/* Define if you have extra builtins. */ +#undef RC_ADDON + +/* Define if you want echo as a builtin. */ +#undef RC_ECHO + +/* Define if you want rc to support broken apps, like a job control shell. */ +#undef RC_JOB + +/* Define if you want to use editline. */ +#undef EDITLINE + +/* Define if you want to use GNU readline. */ +#undef READLINE + +/* Define if you have the older readline, with rl_deprep_terminal. */ +#undef READLINE_OLD + +/* Define if RLIMIT_foo defines need _KERNEL. */ +#undef RLIMIT_NEEDS_KERNEL + +/* Define if rlim_t is quad_t. */ +#undef RLIM_T_IS_QUAD_T + +/* Define to package name. */ +#undef PACKAGE + +/* Define to version. */ +#undef VERSION + +/* Define to release date. */ +#undef RELDATE + +/* Define if you have SA_INTERRUPT (and sigaction()). */ +#undef HAVE_SA_INTERRUPT + +/* Define if you have POSIX getgroups(). */ +#undef HAVE_POSIX_GETGROUPS + +/* Define if you have va_copy(). */ +#undef HAVE_VA_COPY diff --git a/acinclude.m4 b/acinclude.m4 new file mode 100644 index 0000000..3516928 --- /dev/null +++ b/acinclude.m4 @@ -0,0 +1,206 @@ +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 +#include +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) ;; + esac +]) + + +dnl Check for va_copy() in . This is new in C 9x. +AC_DEFUN(RC_HAVE_VA_COPY, [ + AC_CACHE_CHECK(for va_copy(), rc_cv_have_va_copy, AC_EGREP_CPP(yes, [ +#include +#ifdef va_copy +yes +#endif +], rc_cv_have_va_copy=yes, rc_cv_have_va_copy=no)) + case "$rc_cv_have_va_copy" in + yes) AC_DEFINE(HAVE_VA_COPY) ;; + 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 + ], [ +sigjmp_buf e; +sigsetjmp(e, 1); + ], rc_cv_sigsetjmp=yes, rc_cv_sigsetjmp=no)) + case "$rc_cv_sigsetjmp" in + yes) AC_DEFINE(HAVE_SIGSETJMP) ;; + 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 +#include + ], [ +int f; +f = RLIMIT_DATA; + ], rc_cv_kernel_rlimit=no, [ AC_TRY_COMPILE([ +#include +#define _KERNEL +#include +#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) ;; + 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 +#if RLIMIT_NEEDS_KERNEL +#define _KERNEL +#endif +#include + ], 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) ;; + no) AC_CACHE_CHECK(for native quad_t, rc_cv_have_quad_t, + AC_TRY_COMPILE([ +#include + ], [ +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) + AC_CACHE_CHECK(if rlimit values are quad_t, rc_cv_rlim_t_is_quad_t, + AC_TRY_RUN([ +#include +#include +#include +#if RLIMIT_NEEDS_KERNEL +#define _KERNEL +#endif +#include +#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) ;; + 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) ;; + esac +]) + + +dnl Check for sigaction and SA_INTERRUPT +AC_DEFUN(RC_FUNC_SIGACTION, [ + AC_CACHE_CHECK(for sigaction and SA_INTERRUPT, rc_cv_sa_int, + AC_TRY_COMPILE([ +#include + ], [ +struct sigaction foo; +foo.sa_flags = SA_INTERRUPT; +sigaction(SIGINT, 0, 0); + ], rc_cv_sa_int=yes, rc_cv_sa_int=no + ) + ) +]) + + +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? +AC_DEFUN(RC_SYS_V_SIGCLD, [ + AC_CACHE_CHECK(for SysV SIGCLD semantics, rc_cv_sysv_sigcld, + AC_TRY_RUN([ +#include +#include +#include +#include +#include +int main(void) { + int i; + sigset(SIGCLD, SIG_IGN); + switch (fork()) { + case -1: + return 1; + case 0: + return 0; + default: + 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) ;; + 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 +#include + +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 +]) diff --git a/addon.c b/addon.c index df3fcd7..6e6c232 100644 --- a/addon.c +++ b/addon.c @@ -1,22 +1,25 @@ /* - This file contains the implementations of any locally defined - builtins. + This file is NOT BUILT by default. Together with addon.h, it + provides an example of how to add new builtins to rc. */ -#ifdef DWS - -/* - This is what DaviD Sanderson (dws@cs.wisc.edu) uses. -*/ +#include "rc.h" +#include "addon.h" -#include -#include -#include +void b_sum(char **av) { + long sum = 0; -#include "rc.h" /* for bool TRUE, FALSE */ -#include "addon.h" + while (*++av) + sum += atol(*av); + fprint(1, "%ld\n", sum); + set(TRUE); +} -#include "addon/access.c" -#include "addon/test.c" +void b_prod(char **av) { + long sum = 1; -#endif + while (*++av) + sum *= atol(*av); + fprint(1, "%ld\n", sum); + set(TRUE); +} diff --git a/addon.h b/addon.h index 25f2312..4a69375 100644 --- a/addon.h +++ b/addon.h @@ -1,38 +1,31 @@ /* - This file is the interface to the rest of rc for any locally - defined addon builtins. By default there are none. - The interface consists of the following macro. - - ADDONS A comma-separated list of pairs of function pointers - and string literals. - - The addon functions must also have proper prototypes in this file. - The builtins all have the form: - + 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); - - Builtins report their exit status using set(TRUE) or set(FALSE). - - Example: - - #define ADDONS { b_test, "test" }, - extern void b_test(char **av); -*/ -#define ADDONS /* no addons by default */ + The first argument, av[0], is the name of the builtin. The last + argument is followed by a NULL pointer. -#ifdef DWS + Builtins report their exit status using set(TRUE) or set(FALSE). -/* - This is what DaviD Sanderson (dws@cs.wisc.edu) uses. */ -#undef ADDONS -#define ADDONS { b_access, "access" },\ - { b_test, "test" },\ - { b_test, "[" }, +#if RC_ADDON + +#define ADDONS \ + { b_sum, "+" }, \ + { b_prod, "x" }, -extern void b_access(char **av); -extern void b_test(char **av); +extern void b_sum(char **av); +extern void b_prod(char **av); #endif diff --git a/builtins.c b/builtins.c index 1f9b56e..dcea06d 100644 --- a/builtins.c +++ b/builtins.c @@ -10,15 +10,14 @@ #include "rc.h" #include +#include #include #include -#include "jbwrap.h" -#include "sigmsgs.h" #include "addon.h" +#include "jbwrap.h" #include "rlimit.h" - -extern int umask(int); +#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 **), @@ -55,7 +54,9 @@ static struct { { b_wait, "wait" }, { b_whatis, "whatis" }, { b_dot, "." }, +#ifdef ADDONS ADDONS +#endif }; extern builtin_t *isbuiltin(char *s) { @@ -72,7 +73,7 @@ extern void funcall(char **av) { Jbwrap j; Estack e1, e2; Edata jreturn, star; - if (setjmp(j.j)) + if (sigsetjmp(j.j, 1)) return; starassign(*av, av+1, TRUE); jreturn.jb = &j; @@ -97,7 +98,7 @@ static void badnum(char *num) { /* a dummy command. (exec() performs "exec" simply by not forking) */ -extern void b_exec(char **av) { +extern void b_exec(char **ignore) { } #if RC_ECHO @@ -244,7 +245,7 @@ static void b_shift(char **av) { /* dud function */ -extern void b_builtin(char **av) { +extern void b_builtin(char **ignore) { } /* wait for a given process, or all outstanding processes */ diff --git a/config.h-dist b/config.h-dist new file mode 100644 index 0000000..5be81eb --- /dev/null +++ b/config.h-dist @@ -0,0 +1,204 @@ +/* Copy config.h-dist to config.h and edit config.h, don't edit this file */ + +/* + * Configuration parameters for rc. Suggested defaults are at the bottom + * of this file (you should probably look at those first to see if your + * system matches one of them; you can search for the beginning of the + * defaults section by looking for the string "#ifndef CUSTOM"). If you + * want to override the suggested defaults, define the macro CUSTOM. +#define CUSTOM + */ + +/* + * (Note that certain default settings redefine this macro) + * DEFAULTPATH the default search path that rc uses when it is started + * without either a $PATH or $path environment variable. You must pick + * something sensible for your system if you don't like the path shown + * below. + */ +#define DEFAULTPATH "/usr/ucb", "/usr/bin", "/bin", "." + +/* + * Define the macro NODIRENT if your system has but not + * . (e.g., NeXT-OS and RISCos) +#define NODIRENT + */ + +/* + * Define the macro SVSIGS if your system has System V signal semantics, + * i.e., if "slow" system calls are interrupted rather than resumed + * after returning from an interrupt handler. (If you are not sure what + * this means, see the man page for signal(2). In any case, it is probably + * safe to leave this macro undefined.) +#define SVSIGS + */ + +/* + * Define the macro NOCMDARG if you do not have /dev/fd or fifos on your + * system. You may also want to define this if you have broken fifos. +#define NOCMDARG + */ + +/* + * Define TMPDIR if you need to have rc create its fifos in a directory + * other than /tmp. For example, if you have a Sun with /tmp mounted + * as a ramdisk (type "tmpfs") then you cannot use fifos in /tmp (sigh). +#define TMPDIR "/var/tmp" + */ + +/* + * Define the macro DEVFD if your system supports /dev/fd. +#define DEVFD + */ + +/* + * Define the macro NOLIMITS if your system does not support Berkeley + * limits. +#define NOLIMITS + */ + +/* + * Define the macro NOSIGCLD if your system uses SIGCLD in the System + * V way. (e.g., sgi's Irix) +#define NOSIGCLD + */ + +/* + * Define the macro READLINE if you want rc to call GNU readline + * instead of read(2) on interactive shells. +#define READLINE + */ + +/* + * Define the macro NOEXECVE if your Unix does not interpret #! in the + * kernel, and uncomment the EXECVE variable in the Makefile. +#define NOEXECVE + */ + +/* + * If you want rc to default to some interpreter for files which don't + * have a legal #! on the first line, define the macro DEFAULTINTERP. +#define DEFAULTINTERP "/bin/sh" + */ + +/* + * If your /bin/sh (or another program you care about) rejects environment + * variables with special characters in them (such as ':' or '-'), rc can + * put out ugly variable names using [_0-9a-zA-Z] that encode the real name; + * define PROTECT_ENV for this hack. (Known offenders: every sh I have tried; + * SunOS (silently discards), NeXT (aborts with error), SGI (aborts with + * error), Ultrix (sh seems to work, sh5 aborts with error)) +#define PROTECT_ENV + */ + +/* + * Define the macro NOECHO if you wish to omit rc's echo builtin from the + * compile. +#define NOECHO + */ + +/* + * Define the NOJOB if you do *not* wish rc to perform backgrounding + * as if it were a job-control shell; that is, if you do *not* wish + * it to put a command spawned in the background into a new process + * group. Since most systems support job control and since there are + * many broken programs that do not behave correctly when backgrounded + * in a v7 non-job-control fashion, rc by default performs a job- + * control-like backgrounding. +#define NOJOB + */ + +/* Beginning of defaults section: */ + +#ifndef CUSTOM + +/* + * Suggested settings for Sun, NeXT and sgi (machines here at TAMU): + */ + +#ifdef NeXT /* Used on NextOS 2.1 */ +#define NODIRENT +#define PROTECT_ENV +#define NOCMDARG +#endif + +#ifdef sgi /* Used on Irix 3.3.[12] */ +#define SVSIGS +#define NOSIGCLD +#define PROTECT_ENV +#undef DEFAULTPATH +#define DEFAULTPATH "/usr/bsd", "/usr/sbin", "/usr/bin", "/bin", "." +#endif + +#ifdef sun /* Used on SunOS 4.1.1 */ +#define PROTECT_ENV +#undef DEFAULTPATH +#define DEFAULTPATH "/usr/ucb", "/usr/bin", "." +#endif + +/* + * Suggested settings for HP300 running 4.3BSD-utah (DWS): + */ + +#if defined(hp300) && !defined(hpux) +#define NODIRENT +#define NOCMDARG +#define DEFAULTINTERP "/bin/sh" +#define PROTECT_ENV +#endif + +/* + * Suggested settings for Ultrix + */ + +#ifdef ultrix +#define PROTECT_ENV +#define DEFAULTINTERP "/bin/sh" /* so /bin/true can work */ +#endif + +/* + * Suggested settings for RISCos 4.52 + */ + +/* + This doesn't work without interfering with other MIPS-based + systems' configuration. Please do it by hand. +*/ + +#if defined(host_mips) && defined(MIPSEB) && defined(SYSTYPE_BSD43) +#define NODIRENT +#define PROTECT_ENV +#endif + +/* + * Suggested settings for AIX + */ + +#ifdef _AIX +#define PROTECT_ENV +#endif + +/* + * Suggested settings for OSF/1 1.0 + */ + +#ifdef OSF1 +#define PROTECT_ENV +#endif + +/* + * Suggested settings for Unicos XXX + */ + +#ifdef cray +#define PROTECT_ENV +#define NOLIMITS +#define word _word +#define DEFAULTINTERP "/bin/sh" +#endif + +#endif /* CUSTOM */ + +#ifndef TMPDIR +#define TMPDIR "/tmp" +#endif diff --git a/config.h.in b/config.h.in deleted file mode 100644 index 3c8bde8..0000000 --- a/config.h.in +++ /dev/null @@ -1,44 +0,0 @@ -/* Header files */ -#undef STDC_HEADERS - -#undef HAVE_SYS_RESOURCE_H -#undef RLIMIT_NEEDS_KERNEL -#undef HAVE_SYS_TIME_H -#undef HAVE_UNISTD_H - -#undef HAVE_DIRENT_H -#undef HAVE_SYS_NDIR_H -#undef HAVE_SYS_DIR_H -#undef HAVE_NDIR_H - -/* Functions */ -#undef HAVE_GETGROUPS -#undef HAVE_SETPGRP -#undef HAVE_SETRLIMIT - -/* Types */ -#undef HAVE_GID_T -#undef HAVE_RLIM_T -#undef HAVE_QUAD_T -#undef RLIM_T_IS_QUAD_T -#undef GETGROUPS_T -#undef gid_t -#undef pid_t -#undef size_t -#undef uid_t - -/* OS features */ -#undef HASH_BANG -#undef HAVE_DEV_FD -#undef HAVE_FIFO -#undef HAVE_PROC_SELF_FD -#undef HAVE_RESTARTABLE_SYSCALLS -#undef SETPGRP_VOID - -/* rc features */ -#undef DEFAULTINTERP -#undef DEFAULTPATH -#undef RC_ECHO -#undef RC_JOB -#undef PROTECT_ENV -#undef READLINE diff --git a/configure b/configure deleted file mode 100755 index 9460c76..0000000 --- a/configure +++ /dev/null @@ -1,2541 +0,0 @@ -#! /bin/sh - -# Guess values for system-dependent variables and create Makefiles. -# Generated automatically using autoconf version 2.12 -# Copyright (C) 1992, 93, 94, 95, 96 Free Software Foundation, Inc. -# -# This configure script is free software; the Free Software Foundation -# gives unlimited permission to copy, distribute and modify it. - -# Defaults: -ac_help= -ac_default_prefix=/usr/local -# Any additions from configure.in: -ac_help="$ac_help - --disable-builtin-echo Don't include \`echo' as a builtin" -ac_help="$ac_help - --disable-job Don't do job-control-style backgrounding" -ac_help="$ac_help - --disable-protect-env Don't protect environment names" -ac_help="$ac_help - --enable-def-interp=/bin/foo - Use /bin/foo as default interpreter [/bin/sh]" -ac_help="$ac_help - --enable-def-path=\"/usr/local/bin/\",\"/usr/bin\" - Default path [All of these that exist - (/usr/local/bin /usr/bin /usr/ucb /bin .)]" -ac_help="$ac_help - --enable-history Build history subprograms" -ac_help="$ac_help - --with-addon Extra builtins, from addon.c " -ac_help="$ac_help - --with-editline Simmule Turner's line editing" -ac_help="$ac_help - --with-readline Bloated GNU line editing" - -# Initialize some variables set by options. -# The variables have the same names as the options, with -# dashes changed to underlines. -build=NONE -cache_file=./config.cache -exec_prefix=NONE -host=NONE -no_create= -nonopt=NONE -no_recursion= -prefix=NONE -program_prefix=NONE -program_suffix=NONE -program_transform_name=s,x,x, -silent= -site= -srcdir= -target=NONE -verbose= -x_includes=NONE -x_libraries=NONE -bindir='${exec_prefix}/bin' -sbindir='${exec_prefix}/sbin' -libexecdir='${exec_prefix}/libexec' -datadir='${prefix}/share' -sysconfdir='${prefix}/etc' -sharedstatedir='${prefix}/com' -localstatedir='${prefix}/var' -libdir='${exec_prefix}/lib' -includedir='${prefix}/include' -oldincludedir='/usr/include' -infodir='${prefix}/info' -mandir='${prefix}/man' - -# Initialize some other variables. -subdirs= -MFLAGS= MAKEFLAGS= -# Maximum number of lines to put in a shell here document. -ac_max_here_lines=12 - -ac_prev= -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=`echo "$ac_option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; - *) ac_optarg= ;; - esac - - # Accept the important Cygnus configure options, so we can diagnose typos. - - case "$ac_option" in - - -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 ;; - -build=* | --build=* | --buil=* | --bui=* | --bu=*) - build="$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" ;; - - -datadir | --datadir | --datadi | --datad | --data | --dat | --da) - ac_prev=datadir ;; - -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \ - | --da=*) - datadir="$ac_optarg" ;; - - -disable-* | --disable-*) - ac_feature=`echo $ac_option|sed -e 's/-*disable-//'` - # Reject names that are not valid shell variable names. - if test -n "`echo $ac_feature| sed 's/[-a-zA-Z0-9_]//g'`"; then - { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } - fi - ac_feature=`echo $ac_feature| sed 's/-/_/g'` - eval "enable_${ac_feature}=no" ;; - - -enable-* | --enable-*) - ac_feature=`echo $ac_option|sed -e 's/-*enable-//' -e 's/=.*//'` - # Reject names that are not valid shell variable names. - if test -n "`echo $ac_feature| sed 's/[-_a-zA-Z0-9]//g'`"; then - { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } - fi - ac_feature=`echo $ac_feature| sed 's/-/_/g'` - case "$ac_option" in - *=*) ;; - *) ac_optarg=yes ;; - esac - eval "enable_${ac_feature}='$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) - # 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 << EOF -Usage: configure [options] [host] -Options: [defaults in brackets after descriptions] -Configuration: - --cache-file=FILE cache test results in FILE - --help print this message - --no-create do not create output files - --quiet, --silent do not print \`checking...' messages - --version print the version of autoconf that created configure -Directory and file names: - --prefix=PREFIX install architecture-independent files in PREFIX - [$ac_default_prefix] - --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX - [same as prefix] - --bindir=DIR user executables in DIR [EPREFIX/bin] - --sbindir=DIR system admin executables in DIR [EPREFIX/sbin] - --libexecdir=DIR program executables in DIR [EPREFIX/libexec] - --datadir=DIR read-only architecture-independent data in DIR - [PREFIX/share] - --sysconfdir=DIR read-only single-machine data in DIR [PREFIX/etc] - --sharedstatedir=DIR modifiable architecture-independent data in DIR - [PREFIX/com] - --localstatedir=DIR modifiable single-machine data in DIR [PREFIX/var] - --libdir=DIR object code libraries in DIR [EPREFIX/lib] - --includedir=DIR C header files in DIR [PREFIX/include] - --oldincludedir=DIR C header files for non-gcc in DIR [/usr/include] - --infodir=DIR info documentation in DIR [PREFIX/info] - --mandir=DIR man documentation in DIR [PREFIX/man] - --srcdir=DIR find the sources in DIR [configure dir or ..] - --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 -EOF - cat << EOF -Host type: - --build=BUILD configure for building on BUILD [BUILD=HOST] - --host=HOST configure for HOST [guessed] - --target=TARGET configure for TARGET [TARGET=HOST] -Features and packages: - --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) - --enable-FEATURE[=ARG] include FEATURE [ARG=yes] - --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] - --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) - --x-includes=DIR X include files are in DIR - --x-libraries=DIR X library files are in DIR -EOF - if test -n "$ac_help"; then - echo "--enable and --with options recognized:$ac_help" - fi - exit 0 ;; - - -host | --host | --hos | --ho) - ac_prev=host ;; - -host=* | --host=* | --hos=* | --ho=*) - host="$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" ;; - - -localstatedir | --localstatedir | --localstatedi | --localstated \ - | --localstate | --localstat | --localsta | --localst \ - | --locals | --local | --loca | --loc | --lo) - ac_prev=localstatedir ;; - -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ - | --localstate=* | --localstat=* | --localsta=* | --localst=* \ - | --locals=* | --local=* | --loca=* | --loc=* | --lo=*) - 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) - 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" ;; - - -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 ;; - -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) - target="$ac_optarg" ;; - - -v | -verbose | --verbose | --verbos | --verbo | --verb) - verbose=yes ;; - - -version | --version | --versio | --versi | --vers) - echo "configure generated by autoconf version 2.12" - exit 0 ;; - - -with-* | --with-*) - ac_package=`echo $ac_option|sed -e 's/-*with-//' -e 's/=.*//'` - # Reject names that are not valid shell variable names. - if test -n "`echo $ac_package| sed 's/[-_a-zA-Z0-9]//g'`"; then - { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } - fi - ac_package=`echo $ac_package| sed 's/-/_/g'` - case "$ac_option" in - *=*) ;; - *) ac_optarg=yes ;; - esac - eval "with_${ac_package}='$ac_optarg'" ;; - - -without-* | --without-*) - ac_package=`echo $ac_option|sed -e 's/-*without-//'` - # Reject names that are not valid shell variable names. - if test -n "`echo $ac_package| sed 's/[-a-zA-Z0-9_]//g'`"; then - { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } - fi - ac_package=`echo $ac_package| sed 's/-/_/g'` - eval "with_${ac_package}=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" ;; - - -*) { echo "configure: error: $ac_option: invalid option; use --help to show usage" 1>&2; exit 1; } - ;; - - *) - if test -n "`echo $ac_option| sed 's/[-a-z0-9.]//g'`"; then - echo "configure: warning: $ac_option: invalid host type" 1>&2 - fi - if test "x$nonopt" != xNONE; then - { echo "configure: error: can only configure for one host and one target at a time" 1>&2; exit 1; } - fi - nonopt="$ac_option" - ;; - - esac -done - -if test -n "$ac_prev"; then - { echo "configure: error: missing argument to --`echo $ac_prev | sed 's/_/-/g'`" 1>&2; exit 1; } -fi - -trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 - -# File descriptor usage: -# 0 standard input -# 1 file creation -# 2 errors and warnings -# 3 some systems may open it to /dev/tty -# 4 used on the Kubota Titan -# 6 checking for... messages and results -# 5 compiler messages saved in config.log -if test "$silent" = yes; then - exec 6>/dev/null -else - exec 6>&1 -fi -exec 5>./config.log - -echo "\ -This file contains any messages produced by compilers while -running configure, to aid debugging if configure makes a mistake. -" 1>&5 - -# Strip out --no-create and --no-recursion so they do not pile up. -# Also quote any args containing shell metacharacters. -ac_configure_args= -for ac_arg -do - case "$ac_arg" in - -no-create | --no-create | --no-creat | --no-crea | --no-cre \ - | --no-cr | --no-c) ;; - -no-recursion | --no-recursion | --no-recursio | --no-recursi \ - | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) ;; - *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?]*) - ac_configure_args="$ac_configure_args '$ac_arg'" ;; - *) ac_configure_args="$ac_configure_args $ac_arg" ;; - esac -done - -# NLS nuisances. -# Only set these to C if already set. These must not be set unconditionally -# because not all systems understand e.g. LANG=C (notably SCO). -# Fixing LC_MESSAGES prevents Solaris sh from translating var values in `set'! -# Non-C LC_CTYPE values break the ctype check. -if test "${LANG+set}" = set; then LANG=C; export LANG; fi -if test "${LC_ALL+set}" = set; then LC_ALL=C; export LC_ALL; fi -if test "${LC_MESSAGES+set}" = set; then LC_MESSAGES=C; export LC_MESSAGES; fi -if test "${LC_CTYPE+set}" = set; then LC_CTYPE=C; export LC_CTYPE; fi - -# confdefs.h avoids OS command line length limits that DEFS can exceed. -rm -rf conftest* confdefs.h -# AIX cpp loses on an empty file, so make sure it contains at least a newline. -echo > confdefs.h - -# A filename unique to this package, relative to the directory that -# configure is in, which we can look for to find out if srcdir is correct. -ac_unique_file=rc.h - -# 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 its parent. - ac_prog=$0 - ac_confdir=`echo $ac_prog|sed 's%/[^/][^/]*$%%'` - test "x$ac_confdir" = "x$ac_prog" && ac_confdir=. - 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 - if test "$ac_srcdir_defaulted" = yes; then - { echo "configure: error: can not find sources in $ac_confdir or .." 1>&2; exit 1; } - else - { echo "configure: error: can not find sources in $srcdir" 1>&2; exit 1; } - fi -fi -srcdir=`echo "${srcdir}" | sed 's%\([^/]\)/*$%\1%'` - -# Prefer explicitly selected file to automatically selected ones. -if test -z "$CONFIG_SITE"; then - if test "x$prefix" != xNONE; then - CONFIG_SITE="$prefix/share/config.site $prefix/etc/config.site" - else - CONFIG_SITE="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" - fi -fi -for ac_site_file in $CONFIG_SITE; do - if test -r "$ac_site_file"; then - echo "loading site script $ac_site_file" - . "$ac_site_file" - fi -done - -if test -r "$cache_file"; then - echo "loading cache $cache_file" - . $cache_file -else - echo "creating cache $cache_file" - > $cache_file -fi - -ac_ext=c -# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. -ac_cpp='$CPP $CPPFLAGS' -ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' -ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' -cross_compiling=$ac_cv_prog_cc_cross - -if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then - # Stardent Vistra SVR4 grep lacks -e, says ghazi@caip.rutgers.edu. - if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then - ac_n= ac_c=' -' ac_t=' ' - else - ac_n=-n ac_c= ac_t= - fi -else - ac_n= ac_c='\c' ac_t= -fi - - - - - -# Extract the first word of "gcc", so it can be a program name with args. -set dummy gcc; ac_word=$2 -echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:549: checking for $ac_word" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" - for ac_dir in $PATH; do - test -z "$ac_dir" && ac_dir=. - if test -f $ac_dir/$ac_word; then - ac_cv_prog_CC="gcc" - break - fi - done - IFS="$ac_save_ifs" -fi -fi -CC="$ac_cv_prog_CC" -if test -n "$CC"; then - echo "$ac_t""$CC" 1>&6 -else - echo "$ac_t""no" 1>&6 -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 -echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:578: checking for $ac_word" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" - ac_prog_rejected=no - for ac_dir in $PATH; do - test -z "$ac_dir" && ac_dir=. - if test -f $ac_dir/$ac_word; then - if test "$ac_dir/$ac_word" = "/usr/ucb/cc"; then - ac_prog_rejected=yes - continue - fi - ac_cv_prog_CC="cc" - break - fi - done - IFS="$ac_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 $# -gt 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 - set dummy "$ac_dir/$ac_word" "$@" - shift - ac_cv_prog_CC="$@" - fi -fi -fi -fi -CC="$ac_cv_prog_CC" -if test -n "$CC"; then - echo "$ac_t""$CC" 1>&6 -else - echo "$ac_t""no" 1>&6 -fi - - test -z "$CC" && { echo "configure: error: no acceptable cc found in \$PATH" 1>&2; exit 1; } -fi - -echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 -echo "configure:626: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 - -ac_ext=c -# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. -ac_cpp='$CPP $CPPFLAGS' -ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' -ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' -cross_compiling=$ac_cv_prog_cc_cross - -cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then - ac_cv_prog_cc_works=yes - # If we can't run a trivial program, we are probably using a cross compiler. - if (./conftest; exit) 2>/dev/null; then - ac_cv_prog_cc_cross=no - else - ac_cv_prog_cc_cross=yes - fi -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - ac_cv_prog_cc_works=no -fi -rm -fr conftest* - -echo "$ac_t""$ac_cv_prog_cc_works" 1>&6 -if test $ac_cv_prog_cc_works = no; then - { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } -fi -echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 -echo "configure:660: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 -echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 -cross_compiling=$ac_cv_prog_cc_cross - -echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:665: checking whether we are using GNU C" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then - ac_cv_prog_gcc=yes -else - ac_cv_prog_gcc=no -fi -fi - -echo "$ac_t""$ac_cv_prog_gcc" 1>&6 - -if test $ac_cv_prog_gcc = yes; then - GCC=yes - ac_test_CFLAGS="${CFLAGS+set}" - ac_save_CFLAGS="$CFLAGS" - CFLAGS= - echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 -echo "configure:689: checking whether ${CC-cc} accepts -g" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - echo 'void f(){}' > conftest.c -if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then - ac_cv_prog_cc_g=yes -else - ac_cv_prog_cc_g=no -fi -rm -f conftest* - -fi - -echo "$ac_t""$ac_cv_prog_cc_g" 1>&6 - if test "$ac_test_CFLAGS" = set; then - CFLAGS="$ac_save_CFLAGS" - elif test $ac_cv_prog_cc_g = yes; then - CFLAGS="-g -O2" - else - CFLAGS="-O2" - fi -else - GCC= - test "${CFLAGS+set}" = set || CFLAGS="-g" -fi - -case "x$GCC" in -xyes) - CFLAGS="-Wall $CFLAGS" - ;; -esac - -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 - fi -done -if test -z "$ac_aux_dir"; then - { echo "configure: error: can not find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../.." 1>&2; exit 1; } -fi -ac_config_guess=$ac_aux_dir/config.guess -ac_config_sub=$ac_aux_dir/config.sub -ac_configure=$ac_aux_dir/configure # This should be Cygnus configure. - -# 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 -# AFS /usr/afsws/bin/install, which mishandles nonexistent args -# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" -# ./install, which can be erroneously created by make from ./install.sh. -echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 -echo "configure:752: checking for a BSD compatible install" >&5 -if test -z "$INSTALL"; then -if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS="${IFS}:" - for ac_dir in $PATH; do - # Account for people who put trailing slashes in PATH elements. - case "$ac_dir/" in - /|./|.//|/etc/*|/usr/sbin/*|/usr/etc/*|/sbin/*|/usr/afsws/bin/*|/usr/ucb/*) ;; - *) - # OSF1 and SCO ODT 3.0 have their own names for install. - for ac_prog in ginstall installbsd scoinst install; do - if test -f $ac_dir/$ac_prog; then - if test $ac_prog = install && - grep dspmsg $ac_dir/$ac_prog >/dev/null 2>&1; then - # AIX install. It has an incompatible calling convention. - # OSF/1 installbsd also uses dspmsg, but is usable. - : - else - ac_cv_path_install="$ac_dir/$ac_prog -c" - break 2 - fi - fi - done - ;; - esac - done - IFS="$ac_save_IFS" - -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. We don't cache a - # path for INSTALL within a source directory, because that will - # break other packages using the cache if that directory is - # removed, or if the path is relative. - INSTALL="$ac_install_sh" - fi -fi -echo "$ac_t""$INSTALL" 1>&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_DATA" && INSTALL_DATA='${INSTALL} -m 644' - -for ac_prog in 'bison -y' byacc -do -# Extract the first word of "$ac_prog", so it can be a program name with args. -set dummy $ac_prog; ac_word=$2 -echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:806: checking for $ac_word" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_YACC'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test -n "$YACC"; then - ac_cv_prog_YACC="$YACC" # Let the user override the test. -else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" - for ac_dir in $PATH; do - test -z "$ac_dir" && ac_dir=. - if test -f $ac_dir/$ac_word; then - ac_cv_prog_YACC="$ac_prog" - break - fi - done - IFS="$ac_save_ifs" -fi -fi -YACC="$ac_cv_prog_YACC" -if test -n "$YACC"; then - echo "$ac_t""$YACC" 1>&6 -else - echo "$ac_t""no" 1>&6 -fi - -test -n "$YACC" && break -done -test -n "$YACC" || YACC="yacc" - -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 -echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:840: checking for $ac_word" >&5 -if eval "test \"`echo '$''{'ac_cv_prog_LN'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test -n "$LN"; then - ac_cv_prog_LN="$LN" # Let the user override the test. -else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" - for ac_dir in $PATH; do - test -z "$ac_dir" && ac_dir=. - if test -f $ac_dir/$ac_word; then - ac_cv_prog_LN="$ac_prog" - break - fi - done - IFS="$ac_save_ifs" -fi -fi -LN="$ac_cv_prog_LN" -if test -n "$LN"; then - echo "$ac_t""$LN" 1>&6 -else - echo "$ac_t""no" 1>&6 -fi - -test -n "$LN" && break -done - - -echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 -echo "configure:870: checking how to run the C preprocessor" >&5 -# On Suns, sometimes $CPP names a directory. -if test -n "$CPP" && test -d "$CPP"; then - CPP= -fi -if test -z "$CPP"; then -if eval "test \"`echo '$''{'ac_cv_prog_CPP'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - # This must be in double quotes, not single quotes, because CPP may get - # substituted into the Makefile and "${CC-cc}" will confuse make. - CPP="${CC-cc} -E" - # On the NeXT, cc -E runs the code through the compiler's parser, - # not just through cpp. - cat > conftest.$ac_ext < -Syntax Error -EOF -ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:891: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` -if test -z "$ac_err"; then - : -else - echo "$ac_err" >&5 - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - CPP="${CC-cc} -E -traditional-cpp" - cat > conftest.$ac_ext < -Syntax Error -EOF -ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:908: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` -if test -z "$ac_err"; then - : -else - echo "$ac_err" >&5 - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - CPP=/lib/cpp -fi -rm -f conftest* -fi -rm -f conftest* - ac_cv_prog_CPP="$CPP" -fi - CPP="$ac_cv_prog_CPP" -else - ac_cv_prog_CPP="$CPP" -fi -echo "$ac_t""$CPP" 1>&6 - -for ac_hdr in sys/resource.h sys/time.h sys/types.h unistd.h -do -ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` -echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:934: checking for $ac_hdr" >&5 -if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -EOF -ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:944: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` -if test -z "$ac_err"; then - rm -rf conftest* - eval "ac_cv_header_$ac_safe=yes" -else - echo "$ac_err" >&5 - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_header_$ac_safe=no" -fi -rm -f conftest* -fi -if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then - echo "$ac_t""yes" 1>&6 - ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` - cat >> confdefs.h <&6 -fi -done - -ac_header_dirent=no -for ac_hdr in dirent.h sys/ndir.h sys/dir.h ndir.h -do -ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` -echo $ac_n "checking for $ac_hdr that defines DIR""... $ac_c" 1>&6 -echo "configure:975: checking for $ac_hdr that defines DIR" >&5 -if eval "test \"`echo '$''{'ac_cv_header_dirent_$ac_safe'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#include <$ac_hdr> -int main() { -DIR *dirp = 0; -; return 0; } -EOF -if { (eval echo configure:988: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then - rm -rf conftest* - eval "ac_cv_header_dirent_$ac_safe=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_header_dirent_$ac_safe=no" -fi -rm -f conftest* -fi -if eval "test \"`echo '$ac_cv_header_dirent_'$ac_safe`\" = yes"; then - echo "$ac_t""yes" 1>&6 - ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` - cat >> confdefs.h <&6 -fi -done -# Two versions of opendir et al. are in -ldir and -lx on SCO Xenix. -if test $ac_header_dirent = dirent.h; then -echo $ac_n "checking for opendir in -ldir""... $ac_c" 1>&6 -echo "configure:1013: checking for opendir in -ldir" >&5 -ac_lib_var=`echo dir'_'opendir | sed 'y%./+-%__p_%'` -if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - ac_save_LIBS="$LIBS" -LIBS="-ldir $LIBS" -cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=no" -fi -rm -f conftest* -LIBS="$ac_save_LIBS" - -fi -if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then - echo "$ac_t""yes" 1>&6 - LIBS="$LIBS -ldir" -else - echo "$ac_t""no" 1>&6 -fi - -else -echo $ac_n "checking for opendir in -lx""... $ac_c" 1>&6 -echo "configure:1054: checking for opendir in -lx" >&5 -ac_lib_var=`echo x'_'opendir | sed 'y%./+-%__p_%'` -if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - ac_save_LIBS="$LIBS" -LIBS="-lx $LIBS" -cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=no" -fi -rm -f conftest* -LIBS="$ac_save_LIBS" - -fi -if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then - echo "$ac_t""yes" 1>&6 - LIBS="$LIBS -lx" -else - echo "$ac_t""no" 1>&6 -fi - -fi - -echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 -echo "configure:1096: checking for ANSI C header files" >&5 -if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#include -#include -#include -EOF -ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:1109: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` -if test -z "$ac_err"; then - rm -rf conftest* - ac_cv_header_stdc=yes -else - echo "$ac_err" >&5 - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - ac_cv_header_stdc=no -fi -rm -f conftest* - -if test $ac_cv_header_stdc = yes; then - # SunOS 4.x string.h does not declare mem*, contrary to ANSI. -cat > conftest.$ac_ext < -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "memchr" >/dev/null 2>&1; then - : -else - rm -rf conftest* - 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 > conftest.$ac_ext < -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "free" >/dev/null 2>&1; then - : -else - rm -rf conftest* - 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 > conftest.$ac_ext < -#define ISLOWER(c) ('a' <= (c) && (c) <= 'z') -#define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) -#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)) exit(2); -exit (0); } - -EOF -if { (eval echo configure:1176: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - : -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - ac_cv_header_stdc=no -fi -rm -fr conftest* -fi - -fi -fi - -echo "$ac_t""$ac_cv_header_stdc" 1>&6 -if test $ac_cv_header_stdc = yes; then - cat >> confdefs.h <<\EOF -#define STDC_HEADERS 1 -EOF - -fi - - -echo $ac_n "checking for signal names in ""... $ac_c" 1>&6 -echo "configure:1201: checking for signal names in " >&5 -if eval "test \"`echo '$''{'rc_cv_sys_signal_h'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if grep SIGINT /usr/include/sys/signal.h >/dev/null 2>&1; then - rc_cv_sys_signal_h=yes - else - rc_cv_sys_signal_h=no - fi -fi - -echo "$ac_t""$rc_cv_sys_signal_h" 1>&6 - -case "x$rc_cv_sys_signal_h" in -xyes) - SIGNAL_H=/usr/include/sys/signal.h - ;; -xno) - echo $ac_n "checking for signal names in ""... $ac_c" 1>&6 -echo "configure:1220: checking for signal names in " >&5 -if eval "test \"`echo '$''{'rc_cv_asm_signal_h'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if grep SIGINT /usr/include/asm/signal.h >/dev/null 2>&1; then - rc_cv_asm_signal_h=yes - else - rc_cv_asm_signal_h=no - fi -fi - -echo "$ac_t""$rc_cv_asm_signal_h" 1>&6 - - case "x$rc_cv_asm_signal_h" in - xyes) - SIGNAL_H=/usr/include/asm/signal.h - ;; - xno) - { echo "configure: error: Can't find signal names in or " 1>&2; exit 1; } - ;; - esac - ;; -esac - - -echo $ac_n "checking for uid_t in sys/types.h""... $ac_c" 1>&6 -echo "configure:1246: checking for uid_t in sys/types.h" >&5 -if eval "test \"`echo '$''{'ac_cv_type_uid_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "uid_t" >/dev/null 2>&1; then - rm -rf conftest* - ac_cv_type_uid_t=yes -else - rm -rf conftest* - ac_cv_type_uid_t=no -fi -rm -f conftest* - -fi - -echo "$ac_t""$ac_cv_type_uid_t" 1>&6 -if test $ac_cv_type_uid_t = no; then - cat >> confdefs.h <<\EOF -#define uid_t int -EOF - - cat >> confdefs.h <<\EOF -#define gid_t int -EOF - -fi - -echo $ac_n "checking type of array argument to getgroups""... $ac_c" 1>&6 -echo "configure:1280: checking type of array argument to getgroups" >&5 -if eval "test \"`echo '$''{'ac_cv_type_getgroups'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test "$cross_compiling" = yes; then - ac_cv_type_getgroups=cross -else - cat > conftest.$ac_ext < -#define NGID 256 -#undef MAX -#define MAX(x, y) ((x) > (y) ? (x) : (y)) -main() -{ - gid_t gidset[NGID]; - int i, n; - union { gid_t gval; long 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 but getgroups modifies an array of ints. */ - exit ((n > 0 && gidset[n] != val.gval) ? 1 : 0); -} - -EOF -if { (eval echo configure:1313: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - ac_cv_type_getgroups=gid_t -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - ac_cv_type_getgroups=int -fi -rm -fr conftest* -fi - -if test $ac_cv_type_getgroups = cross; then - cat > conftest.$ac_ext < -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "getgroups.*int.*gid_t" >/dev/null 2>&1; then - rm -rf conftest* - ac_cv_type_getgroups=gid_t -else - rm -rf conftest* - ac_cv_type_getgroups=int -fi -rm -f conftest* - -fi -fi - -echo "$ac_t""$ac_cv_type_getgroups" 1>&6 -cat >> confdefs.h <&6 -echo "configure:1351: checking for pid_t" >&5 -if eval "test \"`echo '$''{'ac_cv_type_pid_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#if STDC_HEADERS -#include -#include -#endif -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "pid_t[^a-zA-Z_0-9]" >/dev/null 2>&1; then - rm -rf conftest* - ac_cv_type_pid_t=yes -else - rm -rf conftest* - ac_cv_type_pid_t=no -fi -rm -f conftest* - -fi -echo "$ac_t""$ac_cv_type_pid_t" 1>&6 -if test $ac_cv_type_pid_t = no; then - cat >> confdefs.h <<\EOF -#define pid_t int -EOF - -fi - -echo $ac_n "checking for size_t""... $ac_c" 1>&6 -echo "configure:1384: checking for size_t" >&5 -if eval "test \"`echo '$''{'ac_cv_type_size_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#if STDC_HEADERS -#include -#include -#endif -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "size_t[^a-zA-Z_0-9]" >/dev/null 2>&1; then - rm -rf conftest* - ac_cv_type_size_t=yes -else - rm -rf conftest* - ac_cv_type_size_t=no -fi -rm -f conftest* - -fi -echo "$ac_t""$ac_cv_type_size_t" 1>&6 -if test $ac_cv_type_size_t = no; then - cat >> confdefs.h <<\EOF -#define size_t unsigned -EOF - -fi - -echo $ac_n "checking for uid_t in sys/types.h""... $ac_c" 1>&6 -echo "configure:1417: checking for uid_t in sys/types.h" >&5 -if eval "test \"`echo '$''{'ac_cv_type_uid_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "uid_t" >/dev/null 2>&1; then - rm -rf conftest* - ac_cv_type_uid_t=yes -else - rm -rf conftest* - ac_cv_type_uid_t=no -fi -rm -f conftest* - -fi - -echo "$ac_t""$ac_cv_type_uid_t" 1>&6 -if test $ac_cv_type_uid_t = no; then - cat >> confdefs.h <<\EOF -#define uid_t int -EOF - - cat >> confdefs.h <<\EOF -#define gid_t int -EOF - -fi - - -for ac_func in getgroups setpgrp setrlimit -do -echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:1454: checking for $ac_func" >&5 -if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -/* Override any gcc2 internal prototype to avoid an error. */ -/* We use char because int might match the return type of a gcc2 - builtin and then its argument prototype would still apply. */ -char $ac_func(); - -int main() { - -/* 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_$ac_func) || defined (__stub___$ac_func) -choke me -#else -$ac_func(); -#endif - -; return 0; } -EOF -if { (eval echo configure:1482: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then - rm -rf conftest* - eval "ac_cv_func_$ac_func=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_func_$ac_func=no" -fi -rm -f conftest* -fi - -if eval "test \"`echo '$ac_cv_func_'$ac_func`\" = yes"; then - echo "$ac_t""yes" 1>&6 - ac_tr_func=HAVE_`echo $ac_func | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'` - cat >> confdefs.h <&6 -fi -done - - -echo $ac_n "checking whether setpgrp takes no argument""... $ac_c" 1>&6 -echo "configure:1508: checking whether setpgrp takes no argument" >&5 -if eval "test \"`echo '$''{'ac_cv_func_setpgrp_void'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test "$cross_compiling" = yes; then - { echo "configure: error: cannot check setpgrp if cross compiling" 1>&2; exit 1; } -else - cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - ac_cv_func_setpgrp_void=no -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - ac_cv_func_setpgrp_void=yes -fi -rm -fr conftest* -fi - - -fi - -echo "$ac_t""$ac_cv_func_setpgrp_void" 1>&6 -if test $ac_cv_func_setpgrp_void = yes; then - cat >> confdefs.h <<\EOF -#define SETPGRP_VOID 1 -EOF - -fi - - -echo $ac_n "checking if _KERNEL is required for RLIMIT defines""... $ac_c" 1>&6 -echo "configure:1557: checking if _KERNEL is required for RLIMIT defines" >&5 -if eval "test \"`echo '$''{'rc_cv_kernel_rlimit'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#include - -int main() { - -int f; -f = RLIMIT_DATA; - -; return 0; } -EOF -if { (eval echo configure:1575: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then - rm -rf conftest* - rc_cv_kernel_rlimit=no -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - cat > conftest.$ac_ext < -#define _KERNEL -#include -#undef _KERNEL - -int main() { - -int f; -f = RLIMIT_DATA; - -; return 0; } -EOF -if { (eval echo configure:1598: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then - rm -rf conftest* - rc_cv_kernel_rlimit=yes -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - rc_cv_kernel_rlimit=no -fi -rm -f conftest* -fi -rm -f conftest* -fi - -echo "$ac_t""$rc_cv_kernel_rlimit" 1>&6 -case "x$rc_cv_kernel_rlimit" in -xyes) - cat >> confdefs.h <<\EOF -#define RLIMIT_NEEDS_KERNEL 1 -EOF - - ;; -esac - -echo $ac_n "checking for rlim_t""... $ac_c" 1>&6 -echo "configure:1623: checking for rlim_t" >&5 -if eval "test \"`echo '$''{'rc_cv_have_rlim_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat > conftest.$ac_ext < -#if RLIMIT_NEEDS_KERNEL -#define _KERNEL -#endif -#include - -EOF -if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | - egrep "rlim_t" >/dev/null 2>&1; then - rm -rf conftest* - rc_cv_have_rlim_t=yes -else - rm -rf conftest* - rc_cv_have_rlim_t=no -fi -rm -f conftest* - -fi - -echo "$ac_t""$rc_cv_have_rlim_t" 1>&6 - -case "x$rc_cv_have_rlim_t" in -xyes) - cat >> confdefs.h <<\EOF -#define HAVE_RLIM_T 1 -EOF - - ;; -xno) - echo $ac_n "checking for native quad_t""... $ac_c" 1>&6 -echo "configure:1661: checking for native quad_t" >&5 -if eval "test \"`echo '$''{'rc_cv_have_quad_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test "$cross_compiling" = yes; then - { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } -else - cat > conftest.$ac_ext < -main() { - quad_t q; - q = 0; - exit((int) q); -} - -EOF -if { (eval echo configure:1680: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - rc_cv_have_quad_t=yes -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - rc_cv_have_quad_t=no -fi -rm -fr conftest* -fi - -fi - -echo "$ac_t""$rc_cv_have_quad_t" 1>&6 - - case "x$rc_cv_have_quad_t" in - xyes) - cat >> confdefs.h <<\EOF -#define HAVE_QUAD_T 1 -EOF - - - echo $ac_n "checking if rlimit values are quad_t""... $ac_c" 1>&6 -echo "configure:1704: checking if rlimit values are quad_t" >&5 -if eval "test \"`echo '$''{'rc_cv_rlim_t_is_quad_t'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test "$cross_compiling" = yes; then - $ac_cv_type_quad_t -else - cat > conftest.$ac_ext < -#include -#include -#if RLIMIT_NEEDS_KERNEL -#define _KERNEL -#endif -#include -#if RLIMIT_NEEDS_KERNEL -#undef _KERNEL -#endif -main(){ - struct rlimit rl; - exit(sizeof rl.rlim_cur != sizeof(quad_t)); -} - -EOF -if { (eval echo configure:1731: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - rc_cv_rlim_t_is_quad_t=yes -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - rc_cv_rlim_t_is_quad_t=no -fi -rm -fr conftest* -fi - -fi - -echo "$ac_t""$rc_cv_rlim_t_is_quad_t" 1>&6 - - case "x$rc_cv_rlim_t_is_quad_t" in - xyes) - cat >> confdefs.h <<\EOF -#define RLIM_T_IS_QUAD_T 1 -EOF - - ;; - esac - ;; - esac - ;; -esac - -echo $ac_n "checking for restartable system calls""... $ac_c" 1>&6 -echo "configure:1761: checking for restartable system calls" >&5 -if eval "test \"`echo '$''{'ac_cv_sys_restartable_syscalls'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - if test "$cross_compiling" = yes; then - { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } -else - cat > conftest.$ac_ext < -#include -ucatch (isig) { } -main () { - int i = fork (), status; - if (i == 0) { sleep (3); kill (getppid (), SIGINT); sleep (3); exit (0); } - signal (SIGINT, ucatch); - status = wait(&i); - if (status == -1) wait(&i); - exit (status == -1); -} - -EOF -if { (eval echo configure:1787: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - ac_cv_sys_restartable_syscalls=yes -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - ac_cv_sys_restartable_syscalls=no -fi -rm -fr conftest* -fi - -fi - -echo "$ac_t""$ac_cv_sys_restartable_syscalls" 1>&6 -if test $ac_cv_sys_restartable_syscalls = yes; then - cat >> confdefs.h <<\EOF -#define HAVE_RESTARTABLE_SYSCALLS 1 -EOF - -fi - - -# Pull the hash mark out of the macro call to avoid m4 problems. -ac_msg="whether #! works in shell scripts" -echo $ac_n "checking $ac_msg""... $ac_c" 1>&6 -echo "configure:1813: checking $ac_msg" >&5 -if eval "test \"`echo '$''{'ac_cv_sys_interpreter'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - echo '#! /bin/cat -exit 69 -' > conftest -chmod u+x conftest -(SHELL=/bin/sh; export SHELL; ./conftest >/dev/null) -if test $? -ne 69; then - ac_cv_sys_interpreter=yes -else - ac_cv_sys_interpreter=no -fi -rm -f conftest -fi - -echo "$ac_t""$ac_cv_sys_interpreter" 1>&6 - -case "x$ac_cv_sys_interpreter" in -xyes) - cat >> confdefs.h <<\EOF -#define HASH_BANG 1 -EOF - - EXECVE='' - ;; -xno) - EXECVE=execve.o -esac - - -echo $ac_n "checking for /dev/fd""... $ac_c" 1>&6 -echo "configure:1846: checking for /dev/fd" >&5 -if eval "test \"`echo '$''{'rc_cv_sys_dev_fd'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&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 - -echo "$ac_t""$rc_cv_sys_dev_fd" 1>&6 - -case "x$rc_cv_sys_dev_fd" in -xyes) - cat >> confdefs.h <<\EOF -#define HAVE_DEV_FD 1 -EOF - - ;; -xodd) - cat >> confdefs.h <<\EOF -#define HAVE_PROC_SELF_FD 1 -EOF - - ;; -xno) - echo $ac_n "checking for named pipes""... $ac_c" 1>&6 -echo "configure:1876: checking for named pipes" >&5 -if eval "test \"`echo '$''{'rc_cv_sys_fifo'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - cat >> confdefs.h < conftest.$ac_ext < -#include - -main() { - exit(mknod(TMPNAM, S_IFIFO | 0666, 0) != 0); -} - -EOF -if { (eval echo configure:1899: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null -then - rc_cv_sys_fifo=yes -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -fr conftest* - rc_cv_sys_fifo=no -fi -rm -fr conftest* -fi - -fi - -echo "$ac_t""$rc_cv_sys_fifo" 1>&6 - case "x$rc_cv_sys_fifo" in - xyes) - cat >> confdefs.h <<\EOF -#define HAVE_FIFO 1 -EOF - - ;; - esac -esac - -# Check whether --enable-builtin-echo or --disable-builtin-echo was given. -if test "${enable_builtin_echo+set}" = set; then - enableval="$enable_builtin_echo" - test "x$enableval" != "xno" && cat >> confdefs.h <<\EOF -#define RC_ECHO 1 -EOF - -else - cat >> confdefs.h <<\EOF -#define RC_ECHO 1 -EOF - -fi - - -# Check whether --enable-job or --disable-job was given. -if test "${enable_job+set}" = set; then - enableval="$enable_job" - test "x$enableval" != "xno" && cat >> confdefs.h <<\EOF -#define RC_JOB 1 -EOF - -else - cat >> confdefs.h <<\EOF -#define RC_JOB 1 -EOF - -fi - - -# Check whether --enable-protect-env or --disable-protect-env was given. -if test "${enable_protect_env+set}" = set; then - enableval="$enable_protect_env" - test "x$enableval" != "xno" && cat >> confdefs.h <<\EOF -#define PROTECT_ENV 1 -EOF - -else - cat >> confdefs.h <<\EOF -#define PROTECT_ENV 1 -EOF - -fi - - -# Check whether --enable-def-interp or --disable-def-interp was given. -if test "${enable_def_interp+set}" = set; then - enableval="$enable_def_interp" - - case "x$enableval" in - xno) - ;; - xyes) - cat >> confdefs.h <<\EOF -#define DEFAULTINTERP "/bin/sh" -EOF - - ;; - *) - cat >> confdefs.h <> confdefs.h <<\EOF -#define DEFAULTINTERP "/bin/sh" -EOF - -fi - - -# Check whether --enable-def-path or --disable-def-path was given. -if test "${enable_def_path+set}" = set; then - enableval="$enable_def_path" - - case "x$enableval" in - xno|xyes) - ;; - *) - cat >> confdefs.h <&6 -echo "configure:2019: checking extant directories for default path" >&5 -if eval "test \"`echo '$''{'rc_cv_def_path'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - - rc_cv_def_path='' - for i in /usr/local/bin /usr/bin /usr/ucb /bin .; do - if test -d $i; then - case "x$rc_cv_def_path" in - x) - rc_cv_def_path=\"$i\" - ;; - *) - rc_cv_def_path=$rc_cv_def_path,\"$i\" - ;; - esac - fi - done - cat >> confdefs.h <&6 - ;; -esac - -# Check whether --enable-history or --disable-history was given. -if test "${enable_history+set}" = set; then - enableval="$enable_history" - test "x$enableval" != "xno" && rc_history=yes -else - rc_history=no -fi - -case "x$rc_history" in -xyes) - HISTORY=history/history - ;; -esac - - -# Check whether --with-addon or --without-addon was given. -if test "${with_addon+set}" = set; then - withval="$with_addon" - - case "x$withval" in - xyes) - ADDON=addon.o - ;; - xno) - ADDON='' - ;; - *) - ADDON=$withval - ;; - esac - -fi - - - -# Check whether --with-editline or --without-editline was given. -if test "${with_editline+set}" = set; then - withval="$with_editline" - echo $ac_n "checking for readline in -ledit""... $ac_c" 1>&6 -echo "configure:2087: checking for readline in -ledit" >&5 -ac_lib_var=`echo edit'_'readline | sed 'y%./+-%__p_%'` -if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - ac_save_LIBS="$LIBS" -LIBS="-ledit $LIBS" -cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=no" -fi -rm -f conftest* -LIBS="$ac_save_LIBS" - -fi -if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then - echo "$ac_t""yes" 1>&6 - cat >> confdefs.h <<\EOF -#define READLINE 1 -EOF - LIBS="$LIBS -ledit" -else - echo "$ac_t""no" 1>&6 -echo "configure: warning: editline library not found" 1>&2 -fi - -fi - - -# Check whether --with-readline or --without-readline was given. -if test "${with_readline+set}" = set; then - withval="$with_readline" - echo $ac_n "checking for readline in -lreadline""... $ac_c" 1>&6 -echo "configure:2137: checking for readline in -lreadline" >&5 -ac_lib_var=`echo readline'_'readline | sed 'y%./+-%__p_%'` -if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then - echo $ac_n "(cached) $ac_c" 1>&6 -else - ac_save_LIBS="$LIBS" -LIBS="-lreadline $LIBS" -cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=yes" -else - echo "configure: failed program was:" >&5 - cat conftest.$ac_ext >&5 - rm -rf conftest* - eval "ac_cv_lib_$ac_lib_var=no" -fi -rm -f conftest* -LIBS="$ac_save_LIBS" - -fi -if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then - echo "$ac_t""yes" 1>&6 - cat >> confdefs.h <<\EOF -#define READLINE 1 -EOF - LIBS="$LIBS -lreadline -ltermcap" -else - echo "$ac_t""no" 1>&6 -echo "configure: warning: readline library not found" 1>&2 -fi - -fi - - -trap '' 1 2 15 -cat > confcache <<\EOF -# 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. It is not useful on other systems. -# If it contains results you don't want to keep, you may remove or edit it. -# -# By default, configure uses ./config.cache as the cache file, -# creating it if it does not exist already. You can give configure -# the --cache-file=FILE option to use a different cache file; that is -# what configure does when it calls configure scripts in -# subdirectories, so they share the cache. -# Giving --cache-file=/dev/null disables caching, for debugging configure. -# config.status only pays attention to the cache file if you give it the -# --recheck option to rerun configure. -# -EOF -# The following way of writing the cache mishandles newlines in values, -# but we know of no workaround that is simple, portable, and efficient. -# So, don't put newlines in cache variables' values. -# 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. -(set) 2>&1 | - case `(ac_space=' '; set) 2>&1` in - *ac_space=\ *) - # `set' does not quote correctly, so add quotes (double-quote substitution - # turns \\\\ into \\, and sed turns \\ into \). - sed -n \ - -e "s/'/'\\\\''/g" \ - -e "s/^\\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\\)=\\(.*\\)/\\1=\${\\1='\\2'}/p" - ;; - *) - # `set' quotes correctly as required by POSIX, so do not add quotes. - sed -n -e 's/^\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\)=\(.*\)/\1=${\1=\2}/p' - ;; - esac >> confcache -if cmp -s $cache_file confcache; then - : -else - if test -w $cache_file; then - echo "updating cache $cache_file" - cat confcache > $cache_file - else - echo "not updating unwritable cache $cache_file" - fi -fi -rm -f confcache - -trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 - -test "x$prefix" = xNONE && prefix=$ac_default_prefix -# Let make expand exec_prefix. -test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' - -# Any assignment to VPATH causes Sun make to only execute -# the first set of double-colon rules, so remove it if not needed. -# If there is a colon in the path, we need to keep it. -if test "x$srcdir" = x.; then - ac_vpsub='/^[ ]*VPATH[ ]*=[^:]*$/d' -fi - -trap 'rm -f $CONFIG_STATUS conftest*; exit 1' 1 2 15 - -DEFS=-DHAVE_CONFIG_H - -# Without the "./", some shells look in PATH for config.status. -: ${CONFIG_STATUS=./config.status} - -echo creating $CONFIG_STATUS -rm -f $CONFIG_STATUS -cat > $CONFIG_STATUS </dev/null | sed 1q`: -# -# $0 $ac_configure_args -# -# Compiler output produced by configure, useful for debugging -# configure, is in ./config.log if it exists. - -ac_cs_usage="Usage: $CONFIG_STATUS [--recheck] [--version] [--help]" -for ac_option -do - case "\$ac_option" in - -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) - echo "running \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion" - exec \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion ;; - -version | --version | --versio | --versi | --vers | --ver | --ve | --v) - echo "$CONFIG_STATUS generated by autoconf version 2.12" - exit 0 ;; - -help | --help | --hel | --he | --h) - echo "\$ac_cs_usage"; exit 0 ;; - *) echo "\$ac_cs_usage"; exit 1 ;; - esac -done - -ac_given_srcdir=$srcdir -ac_given_INSTALL="$INSTALL" - -trap 'rm -fr `echo "Makefile config.h" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 -EOF -cat >> $CONFIG_STATUS < conftest.subs <<\\CEOF -$ac_vpsub -$extrasub -s%@CFLAGS@%$CFLAGS%g -s%@CPPFLAGS@%$CPPFLAGS%g -s%@CXXFLAGS@%$CXXFLAGS%g -s%@DEFS@%$DEFS%g -s%@LDFLAGS@%$LDFLAGS%g -s%@LIBS@%$LIBS%g -s%@exec_prefix@%$exec_prefix%g -s%@prefix@%$prefix%g -s%@program_transform_name@%$program_transform_name%g -s%@bindir@%$bindir%g -s%@sbindir@%$sbindir%g -s%@libexecdir@%$libexecdir%g -s%@datadir@%$datadir%g -s%@sysconfdir@%$sysconfdir%g -s%@sharedstatedir@%$sharedstatedir%g -s%@localstatedir@%$localstatedir%g -s%@libdir@%$libdir%g -s%@includedir@%$includedir%g -s%@oldincludedir@%$oldincludedir%g -s%@infodir@%$infodir%g -s%@mandir@%$mandir%g -s%@CC@%$CC%g -s%@INSTALL_PROGRAM@%$INSTALL_PROGRAM%g -s%@INSTALL_DATA@%$INSTALL_DATA%g -s%@YACC@%$YACC%g -s%@LN@%$LN%g -s%@CPP@%$CPP%g -s%@SIGNAL_H@%$SIGNAL_H%g -s%@EXECVE@%$EXECVE%g -s%@HISTORY@%$HISTORY%g -s%@ADDON@%$ADDON%g - -CEOF -EOF - -cat >> $CONFIG_STATUS <<\EOF - -# Split the substitutions into bite-sized pieces for seds with -# small command number limits, like on Digital OSF/1 and HP-UX. -ac_max_sed_cmds=90 # Maximum number of lines to put in a sed script. -ac_file=1 # Number of current file. -ac_beg=1 # First line for current file. -ac_end=$ac_max_sed_cmds # Line after last line for current file. -ac_more_lines=: -ac_sed_cmds="" -while $ac_more_lines; do - if test $ac_beg -gt 1; then - sed "1,${ac_beg}d; ${ac_end}q" conftest.subs > conftest.s$ac_file - else - sed "${ac_end}q" conftest.subs > conftest.s$ac_file - fi - if test ! -s conftest.s$ac_file; then - ac_more_lines=false - rm -f conftest.s$ac_file - else - if test -z "$ac_sed_cmds"; then - ac_sed_cmds="sed -f conftest.s$ac_file" - else - ac_sed_cmds="$ac_sed_cmds | sed -f conftest.s$ac_file" - fi - ac_file=`expr $ac_file + 1` - ac_beg=$ac_end - ac_end=`expr $ac_end + $ac_max_sed_cmds` - fi -done -if test -z "$ac_sed_cmds"; then - ac_sed_cmds=cat -fi -EOF - -cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF -for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then - # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". - case "$ac_file" in - *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` - ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; - *) ac_file_in="${ac_file}.in" ;; - esac - - # Adjust a relative srcdir, top_srcdir, and INSTALL for subdirectories. - - # Remove last slash and all that follows it. Not all systems have dirname. - ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` - if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then - # The file is in a subdirectory. - test ! -d "$ac_dir" && mkdir "$ac_dir" - ac_dir_suffix="/`echo $ac_dir|sed 's%^\./%%'`" - # A "../" for each directory in $ac_dir_suffix. - ac_dots=`echo $ac_dir_suffix|sed 's%/[^/]*%../%g'` - else - ac_dir_suffix= ac_dots= - fi - - case "$ac_given_srcdir" in - .) srcdir=. - if test -z "$ac_dots"; then top_srcdir=. - else top_srcdir=`echo $ac_dots|sed 's%/$%%'`; fi ;; - /*) srcdir="$ac_given_srcdir$ac_dir_suffix"; top_srcdir="$ac_given_srcdir" ;; - *) # Relative path. - srcdir="$ac_dots$ac_given_srcdir$ac_dir_suffix" - top_srcdir="$ac_dots$ac_given_srcdir" ;; - esac - - case "$ac_given_INSTALL" in - [/$]*) INSTALL="$ac_given_INSTALL" ;; - *) INSTALL="$ac_dots$ac_given_INSTALL" ;; - esac - - echo creating "$ac_file" - rm -f "$ac_file" - configure_input="Generated automatically from `echo $ac_file_in|sed 's%.*/%%'` by configure." - case "$ac_file" in - *Makefile*) ac_comsub="1i\\ -# $configure_input" ;; - *) ac_comsub= ;; - esac - - ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` - sed -e "$ac_comsub -s%@configure_input@%$configure_input%g -s%@srcdir@%$srcdir%g -s%@top_srcdir@%$top_srcdir%g -s%@INSTALL@%$INSTALL%g -" $ac_file_inputs | (eval "$ac_sed_cmds") > $ac_file -fi; done -rm -f conftest.s* - -# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where -# NAME is the cpp macro being defined and VALUE is the value it is being given. -# -# ac_d sets the value in "#define NAME VALUE" lines. -ac_dA='s%^\([ ]*\)#\([ ]*define[ ][ ]*\)' -ac_dB='\([ ][ ]*\)[^ ]*%\1#\2' -ac_dC='\3' -ac_dD='%g' -# ac_u turns "#undef NAME" with trailing blanks into "#define NAME VALUE". -ac_uA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' -ac_uB='\([ ]\)%\1#\2define\3' -ac_uC=' ' -ac_uD='\4%g' -# ac_e turns "#undef NAME" without trailing blanks into "#define NAME VALUE". -ac_eA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' -ac_eB='$%\1#\2define\3' -ac_eC=' ' -ac_eD='%g' - -if test "${CONFIG_HEADERS+set}" != set; then -EOF -cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF -fi -for ac_file in .. $CONFIG_HEADERS; do if test "x$ac_file" != x..; then - # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". - case "$ac_file" in - *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` - ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; - *) ac_file_in="${ac_file}.in" ;; - esac - - echo creating $ac_file - - rm -f conftest.frag conftest.in conftest.out - ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` - cat $ac_file_inputs > conftest.in - -EOF - -# Transform confdefs.h into a sed script conftest.vals that substitutes -# the proper values into config.h.in to produce config.h. And first: -# Protect against being on the right side of a sed subst in config.status. -# Protect against being in an unquoted here document in config.status. -rm -f conftest.vals -cat > conftest.hdr <<\EOF -s/[\\&%]/\\&/g -s%[\\$`]%\\&%g -s%#define \([A-Za-z_][A-Za-z0-9_]*\) *\(.*\)%${ac_dA}\1${ac_dB}\1${ac_dC}\2${ac_dD}%gp -s%ac_d%ac_u%gp -s%ac_u%ac_e%gp -EOF -sed -n -f conftest.hdr confdefs.h > conftest.vals -rm -f conftest.hdr - -# This sed command replaces #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. -cat >> conftest.vals <<\EOF -s%^[ ]*#[ ]*undef[ ][ ]*[a-zA-Z_][a-zA-Z_0-9]*%/* & */% -EOF - -# Break up conftest.vals because some shells have a limit on -# the size of here documents, and old seds have small limits too. - -rm -f conftest.tail -while : -do - ac_lines=`grep -c . conftest.vals` - # grep -c gives empty output for an empty file on some AIX systems. - if test -z "$ac_lines" || test "$ac_lines" -eq 0; then break; fi - # Write a limited-size here document to conftest.frag. - echo ' cat > conftest.frag <> $CONFIG_STATUS - sed ${ac_max_here_lines}q conftest.vals >> $CONFIG_STATUS - echo 'CEOF - sed -f conftest.frag conftest.in > conftest.out - rm -f conftest.in - mv conftest.out conftest.in -' >> $CONFIG_STATUS - sed 1,${ac_max_here_lines}d conftest.vals > conftest.tail - rm -f conftest.vals - mv conftest.tail conftest.vals -done -rm -f conftest.vals - -cat >> $CONFIG_STATUS <<\EOF - rm -f conftest.frag conftest.h - echo "/* $ac_file. Generated automatically by configure. */" > conftest.h - cat conftest.in >> conftest.h - rm -f conftest.in - if cmp -s $ac_file conftest.h 2>/dev/null; then - echo "$ac_file is unchanged" - rm -f conftest.h - else - # Remove last slash and all that follows it. Not all systems have dirname. - ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` - if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then - # The file is in a subdirectory. - test ! -d "$ac_dir" && mkdir "$ac_dir" - fi - rm -f $ac_file - mv conftest.h $ac_file - fi -fi; done - -EOF -cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF - -exit 0 -EOF -chmod +x $CONFIG_STATUS -rm -fr confdefs* $ac_clean_files -test "$no_create" = yes || ${CONFIG_SHELL-/bin/sh} $CONFIG_STATUS || exit 1 - diff --git a/configure.ac b/configure.ac new file mode 100644 index 0000000..dd460aa --- /dev/null +++ b/configure.ac @@ -0,0 +1,200 @@ +dnl Get things going... +AC_INIT(rc.h) + +RELDATE=`cat $srcdir/RELDATE` +AC_DEFINE_UNQUOTED(RELDATE, "$RELDATE") + +dnl Automake stuff. +dnl Use this one for snapshots... +dnl AM_INIT_AUTOMAKE(rc, 1.5s`echo $RELDATE |sed 's/-//g'`) +dnl ...and this one for releases +AM_INIT_AUTOMAKE(rc, 1.5b4) + +AM_CONFIG_HEADER(config.h) + +dnl Anybody using name transformations? +AC_ARG_PROGRAM + +dnl Find a standard C compiler +AC_PROG_CC +AM_PROG_CC_STDC + +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_PROG_CPP +AC_PROG_INSTALL +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 setpgrp setrlimit) +RC_FUNC_GETGROUPS + +RC_FUNC_SIGSETJMP + +AC_FUNC_SETPGRP + +RC_NEED_KERNEL + +RC_TYPE_RLIM_T + +RC_TYPE_SIG_ATOMIC_T + +dnl We prefer system calls that don't restart. If we have sigaction() and +dnl SA_INTERRUPT, we'll use 'em. Otherwise, we check whether +dnl good ol' signal() produces interruptible system calls. +RC_FUNC_SIGACTION +case "$rc_cv_sa_int" in +yes) AC_DEFINE(HAVE_SA_INTERRUPT) ;; +no) AC_SYS_RESTARTABLE_SYSCALLS ;; +esac +AM_CONDITIONAL(AMC_RESTART, test "$ac_cv_sys_restartable_syscalls" = yes) + +RC_SYS_V_SIGCLD + +dnl Does the kernel handle `#! /interpreter'? +AC_SYS_INTERPRETER +case "$ac_cv_sys_interpreter" in +yes) AC_DEFINE(HASH_BANG) ;; +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) ;; +odd) AC_DEFINE(HAVE_PROC_SELF_FD) ;; +no) AC_CHECK_FUNCS(mkfifo) ;; +esac + +case "$ac_cv_func_mkfifo" in +yes) AC_DEFINE(HAVE_FIFO) ;; +no) RC_SYS_MKNOD_FIFO ;; +esac + +RC_HAVE_VA_COPY + +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), + 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), + 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), + 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") + ;; + *) + 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/ucb /bin .)]], +[ + case "$enableval" in + no|yes) ;; + *) AC_DEFINE_UNQUOTED(DEFAULTPATH, $enableval) ;; + 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/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) ;; +esac +AC_SUBST(ADDON) + + +AC_ARG_WITH(editline, [ --with-editline Simmule Turner's line editing], + AC_CHECK_LIB(edit, readline, + AC_DEFINE(EDITLINE) LIBS="$LIBS -ledit", + AC_MSG_ERROR(editline library not found))) + +AC_ARG_WITH(vrl, [ --with-vrl Gert-Jan Vons's line editing], + AC_CHECK_LIB(vrl, readline, + AC_DEFINE(EDITLINE) LIBS="$LIBS -lvrl -ltermcap", + AC_MSG_ERROR(vrl library not found), -ltermcap)) + +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. +AC_ARG_WITH(readline, [ --with-readline Bloated GNU line editing], [ + AC_CHECK_LIB(readline, readline, [ + AC_DEFINE(READLINE) + LIBS="$LIBS -lreadline -ltermcap" + AC_CHECK_LIB(readline, _rl_clean_up_for_exit, , AC_DEFINE(READLINE_OLD), -ltermcap) + ], AC_MSG_ERROR(readline library not found), -ltermcap) +]) +AM_CONDITIONAL(AMC_READLINE, test "${with_readline+set}" = set) + +dnl For some reason CPPFLAGS doesn't get propagated. +AC_SUBST(CPPFLAGS) + +AC_OUTPUT(Makefile) diff --git a/configure.in b/configure.in deleted file mode 100644 index 86a97bb..0000000 --- a/configure.in +++ /dev/null @@ -1,287 +0,0 @@ -AC_INIT(rc.h) - -AC_CONFIG_HEADER(config.h) - -AC_PROG_CC -case "x$GCC" in -xyes) - CFLAGS="-Wall $CFLAGS" - ;; -esac - -AC_PROG_INSTALL -AC_PROG_YACC -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 - -dnl Linux puts real signal names in /usr/include/asm/signal.h. -AC_CACHE_CHECK(for signal names in , rc_cv_sys_signal_h, - if grep SIGINT /usr/include/sys/signal.h >/dev/null 2>&1; then - rc_cv_sys_signal_h=yes - else - rc_cv_sys_signal_h=no - fi) - -case "x$rc_cv_sys_signal_h" in -xyes) - SIGNAL_H=/usr/include/sys/signal.h - ;; -xno) - AC_CACHE_CHECK(for signal names in , rc_cv_asm_signal_h, - if grep SIGINT /usr/include/asm/signal.h >/dev/null 2>&1; then - rc_cv_asm_signal_h=yes - else - rc_cv_asm_signal_h=no - fi) - - case "x$rc_cv_asm_signal_h" in - xyes) - SIGNAL_H=/usr/include/asm/signal.h - ;; - xno) - AC_MSG_ERROR(Can't find signal names in or ) - ;; - esac - ;; -esac -AC_SUBST(SIGNAL_H) - -AC_TYPE_GETGROUPS -AC_TYPE_PID_T -AC_TYPE_SIZE_T -AC_TYPE_UID_T - -AC_CHECK_FUNCS(getgroups setpgrp setrlimit) - -AC_FUNC_SETPGRP - -dnl HPUX needs _KERNEL defined to pick up RLIMIT_foo defines. (Why?) -AC_CACHE_CHECK(if _KERNEL is required for RLIMIT defines, rc_cv_kernel_rlimit, - AC_TRY_COMPILE([ -#include -#include - ], [ -int f; -f = RLIMIT_DATA; - ], rc_cv_kernel_rlimit=no, [ AC_TRY_COMPILE([ -#include -#define _KERNEL -#include -#undef _KERNEL - ], [ -int f; -f = RLIMIT_DATA; - ], rc_cv_kernel_rlimit=yes, rc_cv_kernel_rlimit=no)])) -case "x$rc_cv_kernel_rlimit" in -xyes) - AC_DEFINE(RLIMIT_NEEDS_KERNEL) - ;; -esac - -dnl Look for rlim_t in sys/types.h and sys/resource.h -AC_CACHE_CHECK(for rlim_t, rc_cv_have_rlim_t, - AC_EGREP_CPP(rlim_t, [ -#include -#if RLIMIT_NEEDS_KERNEL -#define _KERNEL -#endif -#include - ], rc_cv_have_rlim_t=yes, rc_cv_have_rlim_t=no)) - -case "x$rc_cv_have_rlim_t" in -xyes) - AC_DEFINE(HAVE_RLIM_T) - ;; -xno) - AC_CACHE_CHECK(for native quad_t, rc_cv_have_quad_t, - AC_TRY_RUN([ -#include -main() { - quad_t q; - q = 0; - exit((int) q); -} - ], rc_cv_have_quad_t=yes, rc_cv_have_quad_t=no)) - - case "x$rc_cv_have_quad_t" in - xyes) - AC_DEFINE(HAVE_QUAD_T) - - AC_CACHE_CHECK(if rlimit values are quad_t, rc_cv_rlim_t_is_quad_t, - AC_TRY_RUN([ -#include -#include -#include -#if RLIMIT_NEEDS_KERNEL -#define _KERNEL -#endif -#include -#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 "x$rc_cv_rlim_t_is_quad_t" in - xyes) - AC_DEFINE(RLIM_T_IS_QUAD_T) - ;; - esac - ;; - esac - ;; -esac - -AC_SYS_RESTARTABLE_SYSCALLS - -dnl Does the kernel handle `#! /interpreter'? -AC_SYS_INTERPRETER -case "x$ac_cv_sys_interpreter" in -xyes) - AC_DEFINE(HASH_BANG) - EXECVE='' - ;; -xno) - EXECVE=execve.o -esac -AC_SUBST(EXECVE) - -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) - -case "x$rc_cv_sys_dev_fd" in -xyes) - AC_DEFINE(HAVE_DEV_FD) - ;; -xodd) - AC_DEFINE(HAVE_PROC_SELF_FD) - ;; -xno) - AC_CACHE_CHECK(for named pipes, rc_cv_sys_fifo, - AC_DEFINE_UNQUOTED(TMPNAM, "/tmp/rc$$.0") - AC_TRY_RUN([ -#include -#include - -main() { - exit(mknod(TMPNAM, S_IFIFO | 0666, 0) != 0); -} - ], rc_cv_sys_fifo=yes, rc_cv_sys_fifo=no, rc_cv_sys_fifo=no)) - case "x$rc_cv_sys_fifo" in - xyes) - AC_DEFINE(HAVE_FIFO) - ;; - esac -esac - -AC_ARG_ENABLE(builtin-echo, [ --disable-builtin-echo Don't include \`echo' as a builtin], - test "x$enableval" != "xno" && AC_DEFINE(RC_ECHO), - 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), - 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), - AC_DEFINE(PROTECT_ENV)) - -AC_ARG_ENABLE(def-interp, -[ --enable-def-interp=/bin/foo - Use /bin/foo as default interpreter [/bin/sh]], -[ - case "x$enableval" in - xno) - ;; - xyes) - AC_DEFINE(DEFAULTINTERP, "/bin/sh") - ;; - *) - 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/ucb /bin .)]], -[ - case "x$enableval" in - xno|xyes) - ;; - *) - AC_DEFINE_UNQUOTED(DEFAULTPATH, $enableval) - esac -], - enable_def_path=yes) - -case "x$enable_def_path" in -xyes) - 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/ucb /bin .; do - if test -d $i; then - case "x$rc_cv_def_path" in - x) - 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_ENABLE(history, [ --enable-history Build history subprograms], - test "x$enableval" != "xno" && rc_history=yes, - rc_history=no) -case "x$rc_history" in -xyes) - HISTORY=history/history - ;; -esac -AC_SUBST(HISTORY) - -AC_ARG_WITH(addon, [ --with-addon Extra builtins, from addon.c ],[ - case "x$withval" in - xyes) - ADDON=addon.o - ;; - xno) - ADDON='' - ;; - *) - ADDON=$withval - ;; - esac - ]) -AC_SUBST(ADDON) - -AC_ARG_WITH(editline, [ --with-editline Simmule Turner's line editing], - AC_CHECK_LIB(edit, readline, - AC_DEFINE(READLINE) LIBS="$LIBS -ledit", - AC_MSG_WARN(editline library not found))) - -AC_ARG_WITH(readline, [ --with-readline Bloated GNU line editing], - AC_CHECK_LIB(readline, readline, - AC_DEFINE(READLINE) LIBS="$LIBS -lreadline -ltermcap", - AC_MSG_WARN(readline library not found))) - -AC_OUTPUT(Makefile) diff --git a/cpp b/cpp deleted file mode 100644 index e3ac656..0000000 --- a/cpp +++ /dev/null @@ -1,38 +0,0 @@ -#!/bin/sh - -# @(#) cpp.sh 1.3 92/01/15 21:53:22 - -# Unprototypeing preprocessor for pre-ANSI C compilers. On some systems, -# this script can be as simple as: -# -# /lib/cpp "$@" | unproto -# -# However, some cc(1) drivers specify output file names on the -# preprocessor command line, so this shell script must be prepared to -# intercept them. Depending on the driver program, the cpp options may -# even go before or after the file name argument(s). The script below -# tries to tackle all these cases. -# -# You may want to add -Ipath_to_stdarg.h_file, -Dvoid=, -Dvolatile=, -# and even -D__STDC__. - -## (This is what I used while testing with the SunOS C compiler. -## Also, I added "-Qpath ." to CFLAGS so that cpp would be -## run out of the current directory. --- Byron) -cpp_args="-I/u/byron/lib/sun4 -Dconst= -Dvolatile=" - -while : -do - case $1 in - "") break;; - -*) cpp_args="$cpp_args $1";; - *) cpp_args="$cpp_args $1" - case $2 in - ""|-*) ;; - *) exec 1> $2 || exit 1; shift;; - esac;; - esac - shift -done - -/lib/cpp $cpp_args | unproto diff --git a/except.c b/except.c index 241d887..af30e71 100644 --- a/except.c +++ b/except.c @@ -91,7 +91,7 @@ extern void rc_raise(ecodes e) { interactive = estack->interactive; estack = estack->prev; - longjmp(j->j, 1); + siglongjmp(j->j, 1); } } rc_exit(1); /* top of exception stack */ @@ -120,7 +120,7 @@ extern void pop_cmdarg(bool remove) { /* exception handlers */ extern void rc_error(char *s) { - pr_error(s); + pr_error(s, -1); set(FALSE); redirq = NULL; cond = FALSE; /* no longer inside conditional */ diff --git a/exec.c b/exec.c index 6a0082e..a0ba8d4 100644 --- a/exec.c +++ b/exec.c @@ -1,10 +1,9 @@ /* exec.c */ -#include #include -#include -#include "rc.h" -#include "jbwrap.h" +#include +#include "rc.h" +#include "wait.h" /* Takes an argument list and does the appropriate thing (calls a builtin, calls a function, etc.) @@ -92,11 +91,7 @@ extern void exec(List *s, bool parent) { return; rc_exit(getstatus()); } -#if HASH_BANG - execve(path, (char * const *) av, (char * const *) ev); -#else - my_execve(path, (char * const *) av, (char * const *) ev); /* bogus, huh? */ -#endif + rc_execve(path, (char * const *) av, (char * const *) ev); #ifdef DEFAULTINTERP if (errno == ENOEXEC) { @@ -105,6 +100,7 @@ extern void exec(List *s, bool parent) { execve(*av, (char * const *) av, (char * const *) ev); } #endif + uerror(*av); rc_exit(1); /* NOTREACHED */ @@ -123,7 +119,7 @@ extern void exec(List *s, bool parent) { prompt, even though there's a SIGINT in its signal vector. */ - if ((stat & 0xff) == 0) + if (WIFEXITED(stat)) nl_on_intr = FALSE; sigchk(); nl_on_intr = TRUE; diff --git a/execve.c b/execve.c index b21b30c..3fb5cc1 100644 --- a/execve.c +++ b/execve.c @@ -1,8 +1,8 @@ /* 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. + 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 @@ -10,7 +10,7 @@ #define giveupif(x) { if (x) goto fail; } -extern int my_execve(const char *path, const char **av, const char **ev) { +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 */ diff --git a/fn.c b/fn.c index 053ed89..e82e832 100644 --- a/fn.c +++ b/fn.c @@ -26,7 +26,7 @@ extern void inithandler() { null.type = nBody; null.u[0].p = null.u[1].p = NULL; for (i = 1; i < NUMOFSIGNALS; i++) -#ifndef HAVE_RESTARTABLE_SYSCALLS +#if HAVE_SYSV_SIGCLD if (i != SIGCLD) #endif if (sighandlers[i] == SIG_IGN) @@ -133,7 +133,7 @@ static void fn_handler(int s) { /* A dud signal handler for SIGQUIT and SIGTERM */ -static void dud_handler(int s) { +static void dud_handler(int ignore) { } /* @@ -143,12 +143,12 @@ static void dud_handler(int s) { extern void fnassign(char *name, Node *def) { Node *newdef = treecpy(def == NULL ? &null : def, ealloc); /* important to do the treecopy first */ - Function *new = get_fn_place(name); + rc_Function *new = get_fn_place(name); int i; new->def = newdef; new->extdef = NULL; if (strncmp(name, "sig", conststrlen("sig")) == 0) { /* slight optimization */ -#ifndef HAVE_RESTARTABLE_SYSCALLS /* System V machines treat SIGCLD very specially */ +#if HAVE_SYSV_SIGCLD /* System V machines treat SIGCLD very specially */ if (streq(name, "sigcld")) rc_error("can't trap SIGCLD"); #endif @@ -170,7 +170,7 @@ extern void fnassign(char *name, Node *def) { extern void fnassign_string(char *extdef) { char *name = get_name(extdef+3); /* +3 to skip over "fn_" */ - Function *new; + rc_Function *new; if (name == NULL) return; new = get_fn_place(name); @@ -181,7 +181,7 @@ extern void fnassign_string(char *extdef) { /* Return a function in Node form, evaluating an entry from the environment if necessary */ extern Node *fnlookup(char *name) { - Function *look = lookup_fn(name); + rc_Function *look = lookup_fn(name); Node *ret; if (look == NULL) return NULL; /* not found */ @@ -189,7 +189,7 @@ extern Node *fnlookup(char *name) { return look->def; if (look->extdef == NULL) /* function was set to null, e.g., fn foo {} */ return &null; - ret = parse_fn(name, look->extdef); + ret = parse_fn(look->extdef); if (ret == NULL) { efree(look->extdef); look->extdef = NULL; @@ -202,7 +202,7 @@ extern Node *fnlookup(char *name) { /* Return a function in string form (used by makeenv) */ extern char *fnlookup_string(char *name) { - Function *look = lookup_fn(name); + rc_Function *look = lookup_fn(name); if (look == NULL) return NULL; @@ -243,13 +243,14 @@ extern void fnrm(char *name) { extern void whatare_all_signals() { int i; for (i = 1; i < NUMOFSIGNALS; i++) - if (*signals[i].name != '\0') + 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) { diff --git a/footobar.c b/footobar.c index 27955ba..43a44d9 100644 --- a/footobar.c +++ b/footobar.c @@ -39,7 +39,7 @@ static bool Dconv(Format *f, int ignore) { /* defaultfd -- return the default fd for a given redirection operation */ -extern int defaultfd(int op) { +static int defaultfd(int op) { return (op == rCreate || op == rAppend) ? 1 : 0; } @@ -221,7 +221,7 @@ extern char *get_name(char *s) { #define skipleft(p) do --p; while (*p != '\0' && *p != '\001'); -extern List *parse_var(char *name, char *extdef) { +extern List *parse_var(char *extdef) { char *endp, *realend, *sepp; List *tailp, *new; @@ -257,7 +257,7 @@ extern List *parse_var(char *name, char *extdef) { #define PREFIX "fn x" #define PRELEN conststrlen(PREFIX) -extern Node *parse_fn(char *name, char *extdef) { +extern Node *parse_fn(char *extdef) { Node *def; char *s, old[PRELEN]; if ((s = strchr(extdef, '=')) == NULL) @@ -269,7 +269,7 @@ extern Node *parse_fn(char *name, char *extdef) { return (def == NULL || def->type != nNewfn) ? NULL : def->u[1].p; } -static bool Aconv(Format *f, int c) { +static bool Aconv(Format *f, int ignore) { char **a = va_arg(f->args, char **); if (*a != NULL) { fmtcat(f, *a); @@ -279,7 +279,7 @@ static bool Aconv(Format *f, int c) { return FALSE; } -static bool Lconv(Format *f, int c) { +static bool Lconv(Format *f, int ignore) { List *l = va_arg(f->args, List *); char *sep = va_arg(f->args, char *); char *fmt = (f->flags & FMT_leftside) ? "%s%s" : "%-S%s"; diff --git a/getgroups.h b/getgroups.h new file mode 100644 index 0000000..982dfa0 --- /dev/null +++ b/getgroups.h @@ -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 for NGROUPS. */ +#include +#endif +#endif diff --git a/getopt.c b/getopt.c index 423b84a..3c54f53 100644 --- a/getopt.c +++ b/getopt.c @@ -9,42 +9,43 @@ char *rc_optarg; extern int rc_getopt(int argc, char **argv, char *opts) { static int sp = 1; - int c; - char *cp; + 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; + 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 index 043f767..419a096 100644 --- a/glob.c +++ b/glob.c @@ -1,8 +1,7 @@ /* glob.c: rc's (ugly) globber. This code is not elegant, but it works */ -#include -#include #include "rc.h" +#include /* Lifted from autoconf documentation.*/ #if HAVE_DIRENT_H diff --git a/glom.c b/glom.c index e835ed2..ea6b432 100644 --- a/glom.c +++ b/glom.c @@ -1,10 +1,10 @@ /* glom.c: builds an argument list out of words, variables, etc. */ -#include +#include "rc.h" + #include #include #include -#include "rc.h" static List *backq(Node *, Node *); static List *bqinput(List *, int); @@ -324,6 +324,12 @@ static List *mkcmdarg(Node *n) { #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; @@ -331,9 +337,10 @@ static List *mkcmdarg(Node *n) { Estack *e = enew(Estack); List *ret = nnew(List); static int fifonumber = 0; + name = nprint("/tmp/rc%d.%d", getpid(), fifonumber++); - if (mknod(name, S_IFIFO | 0666, 0) < 0) { - uerror("mknod"); + if (mkfifo(name, 0666) < 0) { + uerror("mkfifo"); return NULL; } if (rc_fork() == 0) { @@ -360,7 +367,7 @@ static List *mkcmdarg(Node *n) { #else static List *mkcmdarg(Node *n) { - rc_error("named pipes are not supported"); + rc_error("command arguments are not supported"); return NULL; } diff --git a/group.h b/group.h deleted file mode 100644 index 8e78468..0000000 --- a/group.h +++ /dev/null @@ -1,9 +0,0 @@ -/* Solaris / `gcc -ansi' only defines NGROUPS_MAX in if -_POSIX_C_SOURCE is defined. */ -#define _POSIX_C_SOURCE 1 -#include -#undef _POSIX_C_SOURCE - -#if defined(NGROUPS) && !defined(NGROUPS_MAX) -#define NGROUPS_MAX NGROUPS -#endif diff --git a/hash.c b/hash.c index 9f75b6c..408d0f2 100644 --- a/hash.c +++ b/hash.c @@ -15,7 +15,7 @@ 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(Function *); +static void free_fn(rc_Function *); Htab *fp; Htab *vp; @@ -118,7 +118,7 @@ extern void *lookup(char *s, Htab *ht) { return (ht[h].name == NULL) ? NULL : ht[h].p; } -extern Function *get_fn_place(char *s) { +extern rc_Function *get_fn_place(char *s) { int h = fnfind(s); env_dirty = TRUE; if (fp[h].name == NULL) { @@ -126,7 +126,7 @@ extern Function *get_fn_place(char *s) { h = fnfind(s); fused++; fp[h].name = ecpy(s); - fp[h].p = enew(Function); + fp[h].p = enew(rc_Function); } else free_fn(fp[h].p); return fp[h].p; @@ -205,7 +205,7 @@ extern void delete_var(char *s, bool stack) { } } -static void free_fn(Function *f) { +static void free_fn(rc_Function *f) { treefree(f->def); efree(f->extdef); } @@ -294,7 +294,7 @@ extern void whatare_all_vars(bool showfn, bool showvar) { /* fake getenv() for readline() follows: */ -#if READLINE +#if EDITLINE || READLINE extern char *getenv(const char *name) { List *s; if (name == NULL || vp == NULL || (s = varlookup((char *) name)) == NULL) diff --git a/history.1 b/history.1 new file mode 100644 index 0000000..5530654 --- /dev/null +++ b/history.1 @@ -0,0 +1,243 @@ +.\" 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 on the first match. +.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 "}" diff --git a/history.c b/history.c new file mode 100644 index 0000000..629751d --- /dev/null +++ b/history.c @@ -0,0 +1,339 @@ +/* + 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 + +static const char id[] = "$Release: @(#)" PACKAGE " " VERSION " " RELDATE " $"; + +#define CHUNKSIZE 65536 + +static struct { + char *old, *new; +} *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); + 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 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() { + char *s, *t; + static char *hist = NULL, *last; + + if (hist == NULL) { + hist = readhistoryfile(&last); + *--last = '\0'; /* trim final newline */ + } + +again: s = last; + if (s < hist) + return NULL; + while (*--s != '\n') + if (s <= hist) { + last = hist - 1; + return hist; + } + *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].old = argv[i]; + replace[nreplace].new = s + 1; + 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 + 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/history/history.1 b/history/history.1 deleted file mode 100644 index 18ed28f..0000000 --- a/history/history.1 +++ /dev/null @@ -1,234 +0,0 @@ -.\" 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 on the first match. -.PP -Finally, 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 -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 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 "}" diff --git a/history/history.c b/history/history.c deleted file mode 100644 index e6aa29d..0000000 --- a/history/history.c +++ /dev/null @@ -1,341 +0,0 @@ -/* - 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 -#include -#include - -static char *id = "@(#) history.c 8/91"; - -#undef FALSE -#undef TRUE -typedef enum { FALSE, TRUE } bool; - -#define CHUNKSIZE 65536 - -static struct { - char *old, *new; -} *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 *fp; - -static void *ealloc(size_t n) { - void *p = (void *) malloc(n); - if (p == NULL) { - perror("malloc"); - exit(1); - } - return p; -} - -static 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 *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); - 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++) { - if ((*f++ = s 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() { - char *s, *t; - static char *hist = NULL, *last; - - if (hist == NULL) { - hist = readhistoryfile(&last); - *--last = '\0'; /* trim final newline */ - } - -again: s = last; - if (s < hist) - return NULL; - while (*--s != '\n') - if (s <= hist) { - last = hist - 1; - return hist; - } - *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 '|': - goto again; - default: - break; - } - } - return s; -} - -int main(int argc, char **argv) { - int i; - char *s; - - s = progname = 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].old = argv[i]; - replace[nreplace].new = s + 1; - 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 - s = sub(s, replace[i].old, replace[i].new); - if (editit) { - s = edit(s); - if (s == NULL) - goto next; - } - fseek(fp, 0, 2); /* 2 == end of file. i.e., append command to $history */ - fprintf(fp, "%s\n", s); - fclose(fp); - 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, basename(shell), "-c", s, NULL); - perror(shell); - exit(1); - } - return 0; -} diff --git a/input.c b/input.c index 3b60677..83bd60b 100644 --- a/input.c +++ b/input.c @@ -1,7 +1,7 @@ /* input.c: i/o routines for files and pseudo-files (strings) */ #include -#include + #include "rc.h" #include "jbwrap.h" @@ -20,13 +20,7 @@ typedef struct Input { #define BUFSIZE ((size_t) 256) -#if READLINE -extern char *readline(char *); -extern void add_history(char *); -static char *rlinebuf; -#endif - -char *prompt, *prompt2; +static char *prompt2; bool rcrc; static int dead(void); @@ -46,6 +40,10 @@ static void (*realugchar)(int); int last; +#if EDITLINE || READLINE +static char *rlinebuf, *prompt; +#endif + extern int gchar() { int c; @@ -55,7 +53,7 @@ extern int gchar() { } while ((c = (*realgchar)()) == '\0') - pr_error("warning: null character ignored"); + pr_error("warning: null character ignored", 0); return c; } @@ -68,7 +66,7 @@ static int dead() { return last = EOF; } -static void ugdead(int c) { +static void ugdead(int ignore) { return; } @@ -85,42 +83,20 @@ static int stringgchar() { return last = (inbuf[chars_out] == '\0' ? EOF : inbuf[chars_out++]); } -/* signal-safe readline wrapper */ - -#if READLINE -#ifndef HAVE_RESTARTABLE_SYSCALLS -static char *rc_readline(char *prompt) { - char *r; - interrupt_happened = FALSE; - if (!setjmp(slowbuf.j)) { - slow = TRUE; - if (!interrupt_happened) - r = readline(prompt); - else - r = NULL; - } else - r = NULL; - slow = FALSE; - if (r == NULL) - errno = EINTR; - sigchk(); - return r; -} -#else -#define rc_readline readline -#endif /* HAVE_RESTARTABLE_SYSCALLS */ -#endif /* READLINE */ - /* - read a character from a file-descriptor. If GNU readline is defined, add a newline and doctor - the buffer to look like a regular fdgchar buffer. + read a character from a file-descriptor. If GNU readline is defined, + add a newline and doctor the buffer to look like a regular fdgchar + buffer. */ static int fdgchar() { + if (chars_out >= chars_in + 2) { /* has the buffer been exhausted? if so, replenish it */ while (1) { -#if READLINE - if (interactive && istack->fd == 0) { +#if EDITLINE || READLINE + if (interactive && istack->fd == 0 && isatty(0)) { + /* The readline library doesn't handle read() returning EAGAIN. */ + makeblocking(istack->fd); rlinebuf = rc_readline(prompt); if (rlinebuf == NULL) { chars_in = 0; @@ -136,9 +112,17 @@ static int fdgchar() { } } else #endif - { - long /*ssize_t*/ r = rc_read(istack->fd, inbuf + 2, BUFSIZE); - sigchk(); + { + ssize_t r; + do { + r = rc_read(istack->fd, inbuf + 2, BUFSIZE); + sigchk(); + if (errno == EAGAIN) { + if (!makeblocking(istack->fd)) + panic("not O_NONBLOCK"); + errno = EINTR; + } + } while (r < 0 && errno == EINTR); if (r < 0) { uerror("read"); rc_exit(1); @@ -248,15 +232,17 @@ extern void flushu() { /* the wrapper loop in rc: prompt for commands until EOF, calling yyparse and walk() */ -extern Node *doit(bool execit) { +extern Node *doit(bool clobberexecit) { bool eof; + bool execit ; Jbwrap j; Estack e1, e2; Edata jerror; if (dashen) - execit = FALSE; - setjmp(j.j); + clobberexecit = FALSE; + execit = clobberexecit; + sigsetjmp(j.j, 1); jerror.jb = &j; except(eError, jerror, &e1); for (eof = FALSE; !eof;) { @@ -279,11 +265,12 @@ extern Node *doit(bool execit) { funcall(arglist); } if ((s = varlookup("prompt")) != NULL) { -#if READLINE - prompt = s->w; -#else - fprint(2, "%s", s->w); +#if EDITLINE || READLINE + if (istack->t == iFd && istack->fd == 0 && isatty(0)) + prompt = s->w; + else #endif + fprint(2, "%s", s->w); prompt2 = (s->n == NULL ? "" : s->n->w); } } @@ -361,3 +348,15 @@ extern void closefds() { i->fd = -1; } } + +extern void print_prompt2() { + lineno++; + if (interactive) { +#if EDITLINE || READLINE + if (istack->t == iFd && istack->fd == 0 && isatty(0)) + prompt = prompt2; + else +#endif + fprint(2, "%s", prompt2); + } +} diff --git a/install-sh b/install-sh deleted file mode 100755 index ebc6691..0000000 --- a/install-sh +++ /dev/null @@ -1,250 +0,0 @@ -#! /bin/sh -# -# install - install a program, script, or datafile -# This comes from X11R5 (mit/util/scripts/install.sh). -# -# Copyright 1991 by the Massachusetts Institute of Technology -# -# Permission to use, copy, modify, distribute, and sell this software and its -# documentation for any purpose is hereby granted without fee, provided that -# the above copyright notice appear in all copies and that both that -# copyright notice and this permission notice appear in supporting -# documentation, and that the name of M.I.T. not be used in advertising or -# publicity pertaining to distribution of the software without specific, -# written prior permission. M.I.T. makes no representations about the -# suitability of this software for any purpose. It is provided "as is" -# without express or implied warranty. -# -# Calling this script install-sh is preferred over install.sh, to prevent -# `make' implicit rules from creating a file called install from it -# when there is no Makefile. -# -# This script is compatible with the BSD install script, but was written -# from scratch. It can only install one file at a time, a restriction -# shared with many OS's install programs. - - -# set DOITPROG to echo to test this script - -# Don't use :- since 4.3BSD and earlier shells don't like it. -doit="${DOITPROG-}" - - -# put in absolute paths if you don't have them in your path; or use env. vars. - -mvprog="${MVPROG-mv}" -cpprog="${CPPROG-cp}" -chmodprog="${CHMODPROG-chmod}" -chownprog="${CHOWNPROG-chown}" -chgrpprog="${CHGRPPROG-chgrp}" -stripprog="${STRIPPROG-strip}" -rmprog="${RMPROG-rm}" -mkdirprog="${MKDIRPROG-mkdir}" - -transformbasename="" -transform_arg="" -instcmd="$mvprog" -chmodcmd="$chmodprog 0755" -chowncmd="" -chgrpcmd="" -stripcmd="" -rmcmd="$rmprog -f" -mvcmd="$mvprog" -src="" -dst="" -dir_arg="" - -while [ x"$1" != x ]; do - case $1 in - -c) instcmd="$cpprog" - shift - continue;; - - -d) dir_arg=true - shift - continue;; - - -m) chmodcmd="$chmodprog $2" - shift - shift - continue;; - - -o) chowncmd="$chownprog $2" - shift - shift - continue;; - - -g) chgrpcmd="$chgrpprog $2" - shift - shift - continue;; - - -s) stripcmd="$stripprog" - shift - continue;; - - -t=*) transformarg=`echo $1 | sed 's/-t=//'` - shift - continue;; - - -b=*) transformbasename=`echo $1 | sed 's/-b=//'` - shift - continue;; - - *) if [ x"$src" = x ] - then - src=$1 - else - # this colon is to work around a 386BSD /bin/sh bug - : - dst=$1 - fi - shift - continue;; - esac -done - -if [ x"$src" = x ] -then - echo "install: no input file specified" - exit 1 -else - true -fi - -if [ x"$dir_arg" != x ]; then - dst=$src - src="" - - if [ -d $dst ]; then - instcmd=: - else - instcmd=mkdir - fi -else - -# Waiting for this to be detected by the "$instcmd $src $dsttmp" command -# might cause directories to be created, which would be especially bad -# if $src (and thus $dsttmp) contains '*'. - - if [ -f $src -o -d $src ] - then - true - else - echo "install: $src does not exist" - exit 1 - fi - - if [ x"$dst" = x ] - then - echo "install: no destination specified" - exit 1 - else - true - fi - -# If destination is a directory, append the input filename; if your system -# does not like double slashes in filenames, you may need to add some logic - - if [ -d $dst ] - then - dst="$dst"/`basename $src` - else - true - fi -fi - -## this sed command emulates the dirname command -dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` - -# Make sure that the destination directory exists. -# this part is taken from Noah Friedman's mkinstalldirs script - -# Skip lots of stat calls in the usual case. -if [ ! -d "$dstdir" ]; then -defaultIFS=' -' -IFS="${IFS-${defaultIFS}}" - -oIFS="${IFS}" -# Some sh's can't handle IFS=/ for some reason. -IFS='%' -set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` -IFS="${oIFS}" - -pathcomp='' - -while [ $# -ne 0 ] ; do - pathcomp="${pathcomp}${1}" - shift - - if [ ! -d "${pathcomp}" ] ; - then - $mkdirprog "${pathcomp}" - else - true - fi - - pathcomp="${pathcomp}/" -done -fi - -if [ x"$dir_arg" != x ] -then - $doit $instcmd $dst && - - if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && - if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && - if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && - if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi -else - -# If we're going to rename the final executable, determine the name now. - - if [ x"$transformarg" = x ] - then - dstfile=`basename $dst` - else - dstfile=`basename $dst $transformbasename | - sed $transformarg`$transformbasename - fi - -# don't allow the sed command to completely eliminate the filename - - if [ x"$dstfile" = x ] - then - dstfile=`basename $dst` - else - true - fi - -# Make a temp file name in the proper directory. - - dsttmp=$dstdir/#inst.$$# - -# Move or copy the file name to the temp name - - $doit $instcmd $src $dsttmp && - - trap "rm -f ${dsttmp}" 0 && - -# and set any options; do chmod last to preserve setuid bits - -# If any of these fail, we abort the whole thing. If we want to -# ignore errors from any of these, just make sure not to ignore -# errors from the above "$doit $instcmd $src $dsttmp" command. - - if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && - if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && - if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && - if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && - -# Now rename the file to the real destination. - - $doit $rmcmd -f $dstdir/$dstfile && - $doit $mvcmd $dsttmp $dstdir/$dstfile - -fi && - - -exit 0 diff --git a/jbwrap.h b/jbwrap.h index 7d0358b..4b3ea86 100644 --- a/jbwrap.h +++ b/jbwrap.h @@ -1,9 +1,23 @@ #include -/* certain braindamaged environments don't define jmp_buf as an array, so... */ +/* 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 { - jmp_buf j; + sigjmp_buf j; }; - -extern Jbwrap slowbuf; /* for getting out of interrupts while performing slow i/o on BSD */ diff --git a/lex.c b/lex.c index a763ce4..7e35cdd 100644 --- a/lex.c +++ b/lex.c @@ -1,7 +1,7 @@ /* lex.c: rc's lexical analyzer */ #include "rc.h" -#include "y.tab.h" +#include "parse.h" /* Special characters (i.e., "non-word") in rc: @@ -336,16 +336,6 @@ extern void inityy() { realbuf = ealloc(bufsize); } -extern void print_prompt2() { - lineno++; -#if READLINE - prompt = prompt2; -#else - if (interactive) - fprint(2, "%s", prompt2); -#endif -} - /* 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., diff --git a/main.c b/main.c index 68624d7..55649fe 100644 --- a/main.c +++ b/main.c @@ -11,7 +11,9 @@ static bool dashoh; static void assigndefault(char *,...); static void checkfd(int, enum redirtype); -extern void main(int argc, char *argv[], char *envp[]) { +static const char id[] = "$Release: @(#)" PACKAGE " " VERSION " " RELDATE " $"; + +extern int main(int argc, char *argv[], char *envp[]) { char *dashsee[2], *dollarzero, *null[1]; int c; initprint(); @@ -19,7 +21,7 @@ extern void main(int argc, char *argv[], char *envp[]) { dollarzero = argv[0]; rc_pid = getpid(); dashell = (*argv[0] == '-'); /* Unix tradition */ - while ((c = rc_getopt(argc, argv, "nolpeivdxsc:")) != -1) + while ((c = rc_getopt(argc, argv, "Vnolpeivdxsc:")) != -1) switch (c) { case 'l': dashell = TRUE; @@ -54,6 +56,9 @@ extern void main(int argc, char *argv[], char *envp[]) { case 'o': dashoh = TRUE; break; + case 'V': + fprint(1, "%s\n", id); + exit(0); case '?': exit(1); } @@ -97,6 +102,7 @@ quitopts: dasheye = FALSE; doit(TRUE); rc_exit(getstatus()); + return 0; /* Never really reached. */ } static void assigndefault(char *name,...) { diff --git a/mksignal b/mksignal deleted file mode 100755 index 9902ed8..0000000 --- a/mksignal +++ /dev/null @@ -1,76 +0,0 @@ -#!/bin/sh -# generate rc's internal signal table from signal.h - -exec > sigmsgs.c - -echo '#include "sigmsgs.h"' -echo -echo 'Sigmsgs signals[] = {' - -sed ' s/\/\*[ ]*// - s/[ ]*\*\/// - s/([@*+!]) // - s/[ ]*([a-zA-Z,->& ]*)[ ]*// - s/^[ ]*\#[ ]*define/\#define/ - s/[ ]*signal$// - s/_SIG/SIG/g' $1 | -awk ' - BEGIN { - # assign to nomesg["SIGNAME"] to suppress a long message - nomesg["SIGINT"] = 1 - nomesg["SIGPIPE"] = 1 - # assign to mesg["SIGNAME"] to override a message - mesg["SIGHUP"] = "hangup" - mesg["SIGKILL"] = "killed" - mesg["SIGQUIT"] = "quit" - mesg["SIGTERM"] = "terminated" - mesg["SIGURG"] = "urgent condition on i/o channel" - mesg["SIGSTOP"] = "stop signal not from tty" - mesg["SIGTSTP"] = "stopped" - mesg["SIGCONT"] = "continue" - mesg["SIGCHLD"] = "child stop or exit" - mesg["SIGTTIN"] = "background tty read" - mesg["SIGTTOU"] = "background tty write" - # assign to ignore["SIGNAME"] to explicitly ignore a named signal - ignore["SIGMAX"] = 1 - } - $1 == "#define" && $2 == "NSIG" && $3 ~ /^[0-9]+$/ { nsig = $3 } - $1 == "#define" && $2 ~ /^SIG/ && $3 ~ /^[0-9]+$/ && sig[$3] == "" && ignore[$2] == 0 { - sig[$3] = $2 - if ($3 > max) - max = $3 - if (mesg[$2] == "" && nomesg[$2] == 0) { - str = $4 - for (i = 5; i <= NF; i++) - str = str " " $i - mesg[$2] = str - } - } - END { - if (nsig == 0) - nsig = max + 1 - printf " {!!, !!},\n" - for (i = 1; i < nsig; i++) { - if (sig[i] == "") - printf " {!!, !!},\n" - else - printf " {!%s!, !%s!},\n", sig[i], mesg[sig[i]] - } - } -' | -tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ!' 'abcdefghijklmnopqrstuvwxyz"' - -echo '};' - -exec > sigmsgs.h - -echo 'typedef struct {' -echo ' char *name, *msg;' -echo '} Sigmsgs;' -echo 'extern Sigmsgs signals[];' - -grep '^ ' sigmsgs.c | # the thing in quotes is ^ -awk ' - { sum = sum + 1; } - END { print "#define NUMOFSIGNALS", sum } -' diff --git a/mksignal.c b/mksignal.c new file mode 100644 index 0000000..5677271 --- /dev/null +++ b/mksignal.c @@ -0,0 +1,238 @@ +#include +#include + +#ifdef NSIG +#define NUMSIG NSIG +#else +#define NUMSIG 1 +#endif + +typedef struct { + int signo; + char *signame; + char *sigmsg; +} signaming; + +static 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(char *msg) { + fprintf(stderr, "mksignals: %s\n", msg); + exit(1); +} + +int main(void) { + int maxsig = NUMSIG-1; + int s; + 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/nalloc.c b/nalloc.c index a809504..25e75a1 100644 --- a/nalloc.c +++ b/nalloc.c @@ -111,8 +111,8 @@ extern void restoreblock(Block *old) { /* generic memory allocation functions */ extern void *ealloc(size_t n) { - extern void *malloc(size_t); void *p = malloc(n); + if (p == NULL) { uerror("malloc"); rc_exit(1); @@ -121,8 +121,7 @@ extern void *ealloc(size_t n) { } extern void *erealloc(void *p, size_t n) { - extern void *realloc(void *, size_t); - if (p == NULL) /* convenience feature */ + if (p == NULL) /* erealloc() has POSIX realloc() semantics */ return ealloc(n); if ((p = realloc(p, n)) == NULL) { uerror("realloc"); @@ -132,8 +131,6 @@ extern void *erealloc(void *p, size_t n) { } extern void efree(void *p) { - extern void free(void *); if (p != NULL) free(p); } - diff --git a/open.c b/open.c index 2b6ee75..bac9f2c 100644 --- a/open.c +++ b/open.c @@ -1,7 +1,7 @@ /* open.c: to insulate from the rest of rc. */ -#include #include "rc.h" +#include /* Opens a file with the necessary flags. Assumes the following @@ -23,3 +23,23 @@ extern int rc_open(const char *name, redirtype m) { 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; +} diff --git a/parse.y b/parse.y index f1f5526..b1bcf85 100644 --- a/parse.y +++ b/parse.y @@ -6,9 +6,7 @@ %{ #include "rc.h" -#ifndef lint -#define lint /* hush up gcc -Wall, leave out the dumb sccsid's. */ -#endif + static Node *star, *nolist; Node *parsetree; /* not using yylval because bison declares it as an auto */ %} diff --git a/print.c b/print.c index e0dba12..9ccccc4 100644 --- a/print.c +++ b/print.c @@ -14,14 +14,14 @@ */ #define Flag(name, flag) \ -static bool name(Format *format, int c) { \ +static bool name(Format *format, int ignore) { \ format->flags |= flag; \ return TRUE; \ } Flag(uconv, FMT_unsigned) Flag(hconv, FMT_short) -Flag(lconv, FMT_long) +Flag(rc_lconv, FMT_long) #if HAVE_QUAD_T Flag(qconv, FMT_quad) @@ -41,7 +41,7 @@ static bool digitconv(Format *format, int c) { return TRUE; } -static bool zeroconv(Format *format, int c) { +static bool zeroconv(Format *format, int ignore) { if (format->flags & (FMT_f1set | FMT_f2set)) return digitconv(format, '0'); format->flags |= FMT_zeropad; @@ -53,7 +53,7 @@ static void pad(Format *format, size_t len, int c) { fmtputc(format, c); } -static bool sconv(Format *format, int c) { +static bool sconv(Format *format, int ignore) { char *s = va_arg(format->args, char *); if ((format->flags & FMT_f1set) == 0) fmtcat(format, s); @@ -151,32 +151,32 @@ static void intconv(Format *format, unsigned int radix, int upper, const char *a pad(format, padding, padchar); } -static bool cconv(Format *format, int c) { +static bool cconv(Format *format, int ignore) { fmtputc(format, va_arg(format->args, int)); return FALSE; } -static bool dconv(Format *format, int c) { +static bool dconv(Format *format, int ignore) { intconv(format, 10, 0, ""); return FALSE; } -static bool oconv(Format *format, int c) { +static bool oconv(Format *format, int ignore) { intconv(format, 8, 0, "0"); return FALSE; } -static bool xconv(Format *format, int c) { +static bool xconv(Format *format, int ignore) { intconv(format, 16, 0, "0x"); return FALSE; } -static bool pctconv(Format *format, int c) { +static bool pctconv(Format *format, int ignore) { fmtputc(format, '%'); return FALSE; } -static bool badconv(Format *format, int c) { +static bool badconv(Format *ignore, int ign0re) { panic("bad conversion character in printfmt"); /* NOTREACHED */ return FALSE; /* hush up gcc -Wall */ @@ -203,7 +203,7 @@ static void inittab(void) { fmttab['u'] = uconv; fmttab['h'] = hconv; - fmttab['l'] = lconv; + fmttab['l'] = rc_lconv; fmttab['#'] = altconv; fmttab['-'] = leftconv; fmttab['.'] = dotconv; @@ -289,16 +289,16 @@ extern int fmtprint(Format *format, const char *fmt,...) { va_list ap, saveargs; va_start(ap, fmt); - saveargs = format->args; - format->args = ap; + va_copy(saveargs, format->args); + va_copy(format->args, ap); n += printfmt(format, fmt); va_end(format->args); - format->args = saveargs; + va_copy(format->args, saveargs); return n + format->flushed; } -static void fprint_flush(Format *format, size_t more) { +static void fprint_flush(Format *format, size_t ignore) { size_t n = format->buf - format->bufbegin; char *buf = format->bufbegin; @@ -320,7 +320,7 @@ extern int fprint(int fd, const char *fmt,...) { format.u.n = fd; va_start(ap, fmt); - format.args = ap; + va_copy(format.args, ap); printfmt(&format, fmt); va_end(format.args); @@ -331,19 +331,20 @@ extern int fprint(int fd, const char *fmt,...) { 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 { - size_t used = format->buf - format->bufbegin; buf = nalloc(len); memcpy(buf, format->bufbegin, used); } - format->buf = buf + (format->buf - format->bufbegin); + format->buf = buf + used; format->bufbegin = buf; - format->bufend = buf + len - 1; + format->bufend = buf + len - 1; } static char *memprint(Format *format, const char *fmt, char *buf, size_t len) { @@ -364,7 +365,7 @@ extern char *mprint(const char *fmt,...) { format.u.n = 1; va_start(ap, fmt); - format.args = ap; + va_copy(format.args, ap); result = memprint(&format, fmt, ealloc(PRINT_ALLOCSIZE), PRINT_ALLOCSIZE); va_end(format.args); return result; @@ -377,106 +378,8 @@ extern char *nprint(const char *fmt,...) { format.u.n = 0; va_start(ap, fmt); - format.args = ap; + va_copy(format.args, ap); result = memprint(&format, fmt, nalloc(PRINT_ALLOCSIZE), PRINT_ALLOCSIZE); va_end(format.args); return result; } - - -/* THESE ARE UNUSED IN rc */ - -#if 0 - -extern int print(const char *fmt,...) { - char buf[1024]; - Format format; - - format.buf = buf; - format.bufbegin = buf; - format.bufend = buf + sizeof buf; - format.grow = fprint_flush; - format.flushed = 0; - format.u.n = 1; - - va_start(format.args, fmt); - printfmt(&format, fmt); - va_end(format.args); - - fprint_flush(&format, 0); - return format.flushed; -} - -extern int eprint(const char *fmt,...) { - char buf[1024]; - Format format; - - format.buf = buf; - format.bufbegin = buf; - format.bufend = buf + sizeof buf; - format.grow = fprint_flush; - format.flushed = 0; - format.u.n = 2; - - va_start(format.args, fmt); - printfmt(&format, fmt); - va_end(format.args); - - fprint_flush(&format, 0); - return format.flushed; -} - -static void snprint_grow(Format *format, size_t more) { - longjmp(format->u.p, 1); -} - -extern int snprint(char *buf, int buflen, const char *fmt,...) { - int n; - jmp_buf jbuf; - Format format; - - if (setjmp(jbuf)) { - *format.buf = '\0'; - return format.buf - format.bufbegin; - } - - format.buf = buf; - format.bufbegin = buf; - format.bufend = buf + buflen - 1; - format.grow = snprint_grow; - format.flushed = 0; - format.u.p = jbuf; - - va_start(format.args, fmt); - n = printfmt(&format, fmt); - va_end(format.args); - - *format.buf = '\0'; - return n; -} - -extern int sprint(char *buf, const char *fmt,...) { - int n; - jmp_buf jbuf; - Format format; - - if (setjmp(jbuf)) { - *format.buf = '\0'; - return format.buf - format.bufbegin; - } - - format.buf = buf; - format.bufbegin = buf; - format.bufend = buf + SPRINT_BUFSIZ - 1; - format.grow = snprint_grow; - format.flushed = 0; - format.u.p = jbuf; - - va_start(format.args, fmt); - n = printfmt(&format, fmt); - va_end(format.args); - - *format.buf = '\0'; - return n; -} -#endif diff --git a/proto.h b/proto.h index 4e0fb5a..82e5cb7 100644 --- a/proto.h +++ b/proto.h @@ -1,25 +1,42 @@ +/* + 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 +#endif + +#include + #if HAVE_QUAD_T typedef quad_t align_t; #else typedef long align_t; #endif -/* If you need to change this, please let the maintainer know. */ -#ifndef SIG_ATOMIC_T -typedef int SIG_ATOMIC_T; -#endif +/* + We need . If you really need to build rc on a system which + doesn't have it, please contact the maintainer. +*/ -#if STDC_HEADERS -#include -#else -/* fake stdlib.h */ -extern void exit(int); -extern void qsort(void *, size_t, size_t, int (*)(const void *, const void *)); +#include + +/* C 9x specifies a va_copy() macro which should be used for copying +objects of type va_list. Of course, most places don't have this yet, +but where it does exist we need to use it. */ +#ifndef va_copy +#define va_copy(x,y) (x)=(y) #endif #if STDC_HEADERS + +#include #include -#else + +#else /* STDC_HEADERS */ + /* fake string.h */ extern int strncmp(const char *, const char *, size_t); extern int strcmp(const char *, const char *); @@ -32,8 +49,39 @@ 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_UNISTD_H +#include #endif +#if HAVE_SETPGRP + +#if SETPGRP_VOID +/* Smells like POSIX: should all be ok. */ +#else +/* BSD: fake it. */ +#define setpgid(pid, pgrp) setpgrp(pid, pgrp) +#define tcsetpgrp(fd, pgrp) ioctl((fd), TIOCSPGRP, &(pgrp)) +#endif + +#else /* HAVE_SETPGRP */ + +/* Nothing doing. */ +#define setpgid() +#define tcsetpgrp() + +#endif /*HAVE_SETPGRP */ + + /* fake errno.h for mips (which doesn't declare errno in errno.h!?!?) */ #ifdef host_mips extern int errno; diff --git a/rc.1 b/rc.1 index 140eb66..8353340 100644 --- a/rc.1 +++ b/rc.1 @@ -35,7 +35,7 @@ .\" troff will supply the correct intersentence spacing, but only if .\" the sentences end at the end of a line. Explicit spaces, if given, .\" are apparently honored and the normal intersentence spacing is -.\" supressed. +.\" suppressed. .\" .\" DaviD W. Sanderson .\"------- @@ -166,7 +166,7 @@ rc \- shell .SH SYNOPSIS .B rc -.RB [ \-eixvldnpo ] +.RB [ \-eixvldnpoV ] .RB [ \-c .IR command ] .RI [ arguments ] @@ -300,6 +300,11 @@ Any further arguments to .I rc are placed in .Cr $* . +.TP +.Cr \-V +This flag causes +.I rc +to print a version string to stdout, and exit immediately. .PP .SH COMMANDS A simple command is a sequence of words, separated by white space @@ -1628,19 +1633,28 @@ is specified, .I rc waits for all child processes to exit. .TP -\fBwhatis \fR[\fB\-s\fR] [\fB\-\|\-\fR] [\fIname ...\fR] +\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 variables, their values -are printed; for functions, their definitions are; and for executable -files, path names are printed. +For builtins, +.B 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 options 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 +.BR -p .) Without arguments, .B whatis -prints the values of all shell variables and functions. -With a -.Cr \-s -argument, -.B whatis -also prints out a list of available signals and their handlers (if any). +is equivalent to +.BR "whatis -fv" , +and prints the values of all shell variables and functions. +.TP +\& Note that .B whatis output is suitable for input to @@ -1788,8 +1802,16 @@ The design of this shell has been copied from the .I rc that Tom Duff wrote at Bell Labs. .SH BUGS -On systems that support -.Cr /dev/fd , +Environment variables that contain the ASCII character SOH (also known +as '\\001', or CTRL-A) will be split into lists at that character in +descendant +.IR rc +processes. +.PP +On modern systems that support +.Cr /dev/fd +or +.Cr /proc/self/fd , .Cr <{foo} style redirection is implemented that way. However, on other systems it is implemented with named pipes, @@ -1818,7 +1840,7 @@ notation for flattening should allow for using an arbitrary separating character, not just space. .PP Bug reports should be mailed to -.Cr "byron@archone.tamu.edu" . +.Cr "" . .SH INCOMPATIBILITIES Here is a list of features which distinguish this incarnation of .I rc @@ -1841,12 +1863,19 @@ a backquote must always be followed by a left-brace. This restriction is not present for single-word commands in this .IR rc . .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 option, -the list flattening operator, here strings (they facilitate exporting of functions with here documents into the environment), the diff --git a/rc.h b/rc.h index e540117..f582bd4 100644 --- a/rc.h +++ b/rc.h @@ -1,13 +1,4 @@ #include "config.h" - -#if HAVE_SYS_TYPES_H -#include -#endif - -#if HAVE_UNISTD_H -#include -#endif - #include "proto.h" /* datatypes */ @@ -16,31 +7,12 @@ #undef FALSE #undef TRUE -#include - -#if HAVE_SETPGRP - -#if SETPGRP_VOID -/* Smells like POSIX: should all be ok. */ -#else -/* BSD: fake it. */ -#define setpgid(pid, pgrp) setpgrp(pid, pgrp) -#define tcsetpgrp(fd, pgrp) ioctl((fd), TIOCSPGRP, &(pgrp)) -#endif - -#else /* HAVE_SETPGRP */ - -/* Nothing doing. */ -#define setpgid -#define tcsetpgrp - -#endif /*HAVE_SETPGRP */ typedef void builtin_t(char **); typedef struct Block Block; typedef struct Dup Dup; typedef struct Estack Estack; -typedef struct Function Function; +typedef struct rc_Function rc_Function; typedef struct Hq Hq; typedef struct Htab Htab; typedef struct Jbwrap Jbwrap; @@ -130,7 +102,7 @@ struct Rq { struct Rq *n; }; -struct Function { +struct rc_Function { Node *def; char *extdef; }; @@ -181,7 +153,7 @@ enum { #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) ((Function *) lookup(s, fp)) +#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)) @@ -194,7 +166,6 @@ enum { /* rc prototypes */ /* main.c */ -extern char *prompt, *prompt2; extern Rq *redirq; extern bool dashdee, dashee, dashvee, dashex, dashell, dasheye, dashen, dashpee, interactive; @@ -220,11 +191,18 @@ extern void sigint(int); extern void exec(List *, bool); extern void doredirs(void); +#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 *, char *); -extern Node *parse_fn(char *, 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 */ @@ -251,7 +229,7 @@ extern List *word(char *, char *); /* hash.c */ extern Htab *fp, *vp; extern void *lookup(char *, Htab *); -extern Function *get_fn_place(char *); +extern rc_Function *get_fn_place(char *); extern List *varlookup(char *); extern Node *fnlookup(char *); extern Variable *get_var_place(char *, bool); @@ -282,6 +260,7 @@ extern int heredoc(int); extern int qdoc(Node *, Node *); extern Hq *hq; + /* input.c */ extern void initinput(void); extern Node *parseline(char *); @@ -289,6 +268,7 @@ extern int gchar(void); extern void ugchar(int); extern Node *doit(bool); extern void flushu(void); +extern void print_prompt2(void); extern void pushfd(int); extern void pushstring(char **, bool); extern void popinput(void); @@ -296,12 +276,12 @@ extern void closefds(void); extern int last; extern bool rcrc; + /* lex.c */ extern int yylex(void); extern void inityy(void); extern void yyerror(const char *); extern void scanerror(char *); -extern void print_prompt2(void); extern const char nw[], dnw[]; /* list.c */ @@ -324,6 +304,7 @@ extern void restoreblock(Block *); /* open.c */ extern int rc_open(const char *, redirtype); +extern bool makeblocking(int); /* print.c */ /* @@ -350,21 +331,56 @@ extern char *nprint(const char *fmt,...); *(f)->buf++ = (c);\ } -/* y.tab.c (parse.y) */ +/* parse.c (parse.y) */ extern Node *parsetree; extern int yyparse(void); extern void initparse(void); +/* readline */ + +#if READLINE + +/* Including the real readline .h files is too complicated, so we just +declare what we actually use. */ + +extern void add_history(char *); +extern char *readline(char *); +extern int rl_clear_signals(void); +extern int rl_pending_input; +extern int rl_reset_terminal(char *); + +#if READLINE_OLD +extern void rl_clean_up_for_exit(void); +extern void rl_deprep_terminal(void); +#else +extern void _rl_clean_up_for_exit(void); +extern void (*rl_deprep_term_function)(void); +#endif + +extern char *rc_readline(char *); + +extern volatile sig_atomic_t rl_active; +extern struct Jbwrap rl_buf; +#endif + +#if EDITLINE +extern char *readline(char *); +extern void add_history(char *); +#define rc_readline readline +#endif + + /* 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 (*sighandlers[])(int); -extern volatile SIG_ATOMIC_T slow, interrupt_happened; + /* status.c */ extern int istrue(void); @@ -377,6 +393,23 @@ 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)); @@ -385,13 +418,11 @@ extern void treefree(Node *); /* utils.c */ extern bool isabsolute(char *); extern int n2u(char *, unsigned int); -extern int rc_read(int, char *, size_t); extern int mvfd(int, int); extern int starstrcmp(const void *, const void *); -extern void pr_error(char *); +extern void pr_error(char *, int); extern void panic(char *); extern void uerror(char *); -extern void writeall(int, char *, size_t); /* wait.c */ extern pid_t rc_fork(void); @@ -403,4 +434,3 @@ extern bool forked; /* walk.c */ extern bool walk(Node *, bool); extern bool cond; - diff --git a/rlimit.h b/rlimit.h index f6e179b..f3c2e3d 100644 --- a/rlimit.h +++ b/rlimit.h @@ -3,40 +3,40 @@ #if HAVE_SETRLIMIT #if HAVE_SYS_RESOURCE_H -# include -# if RLIMIT_NEEDS_KERNEL -# define _KERNEL -# endif -# include -# if RLIMIT_NEEDS_KERNEL -# undef _KERNEL -# endif +#include +#if RLIMIT_NEEDS_KERNEL +#define _KERNEL +#endif +#include +#if RLIMIT_NEEDS_KERNEL +#undef _KERNEL +#endif #else -# include +#include #endif #if HAVE_LIMITS_H -# include +#include #endif #ifndef HAVE_RLIM_T -# if RLIM_T_IS_QUAD_T +#if RLIM_T_IS_QUAD_T typedef quad_t rlim_t; -# else +#else typedef long rlim_t; -# endif +#endif #endif #if HAVE_QUAD_T -# define RLIM_CONV quad_t -# define RLIM_FMT "%s \t%qd%s\n" +#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" +#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 +#define RLIMIT_NOFILE RLIMIT_OFILE #endif #endif /* HAVE_SETRLIMIT */ diff --git a/signal.c b/signal.c index 1c3f812..1c59746 100644 --- a/signal.c +++ b/signal.c @@ -2,32 +2,51 @@ #include #include + #include "rc.h" #include "sigmsgs.h" #include "jbwrap.h" -Jbwrap slowbuf; -volatile SIG_ATOMIC_T slow, interrupt_happened; +#if HAVE_SA_INTERRUPT +static void (*sys_signal(int signum, void (*handler)(int)))(int) { + struct sigaction new, old; + + new.sa_handler = handler; + new.sa_flags = SA_INTERRUPT; + sigaction(signum, &new, &old); + return old.sa_handler; +} +#else +#define sys_signal signal +#endif + void (*sighandlers[NUMOFSIGNALS])(int); -static volatile SIG_ATOMIC_T sigcount, caught[NUMOFSIGNALS]; +static volatile sig_atomic_t sigcount, caught[NUMOFSIGNALS]; extern void catcher(int s) { if (caught[s] == 0) { sigcount++; caught[s] = 1; } - signal(s, catcher); - interrupt_happened = TRUE; -#ifndef HAVE_RESTARTABLE_SYSCALLS - if (slow) - longjmp(slowbuf.j, 1); + sys_signal(s, catcher); + +#if READLINE + if (rl_active) + siglongjmp(rl_buf.j, s); +#endif /* READLINE */ + +#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) @@ -53,11 +72,11 @@ extern void (*rc_signal(int s, void (*h)(int)))(int) { sigchk(); old = sighandlers[s]; if (h == SIG_DFL || h == SIG_IGN) { - signal(s, h); sighandlers[s] = h; + sys_signal(s, h); } else { sighandlers[s] = h; - signal(s, catcher); + sys_signal(s, catcher); } return old; } @@ -65,16 +84,18 @@ extern void (*rc_signal(int s, void (*h)(int)))(int) { extern void initsignal() { void (*h)(int); int i; + for (i = 1; i < NUMOFSIGNALS; i++) { - if ((h = signal(i, SIG_DFL)) != SIG_DFL) - signal(i, h); + h = sys_signal(i, SIG_DFL); + if (h != SIG_DFL && h != SIG_ERR) + sys_signal(i, h); sighandlers[i] = h; } -#ifdef SIGCLD +#if HAVE_SYSV_SIGCLD /* Ensure that SIGCLD is not SIG_IGN. Solaris's rshd does this. :-( */ - h = signal(SIGCLD, SIG_DFL); - if (h != SIG_IGN) - signal(SIGCLD, h); + h = sys_signal(SIGCLD, SIG_DFL); + if (h != SIG_IGN && h != SIG_ERR) + sys_signal(SIGCLD, h); #endif } diff --git a/status.c b/status.c index 428e414..b594e4b 100644 --- a/status.c +++ b/status.c @@ -2,6 +2,7 @@ #include "rc.h" #include "sigmsgs.h" +#include "wait.h" /* status == the wait() value of the last command in the pipeline, or the last command */ @@ -33,7 +34,9 @@ extern int getstatus() { if (pipelength > 1) return !istrue(); s = statuses[0]; - return (s&0xff) ? 1 : (s >> 8) & 0xff; + if (WIFSIGNALED(s)) + return 1; + return WEXITSTATUS(s); } extern void set(bool code) { @@ -61,11 +64,12 @@ extern void setstatus(pid_t pid, int 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 (i & 0xff) { - char *msg = ((i & 0x7f) < NUMOFSIGNALS ? signals[i & 0x7f].msg : ""); + 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 (i & 0x80) { + if (myWIFDUMPED(i)) { if (*msg == '\0') fprint(2, "core dumped\n"); else @@ -97,16 +101,15 @@ extern List *sgetstatus() { /* return status as a string (used above and for bqstatus) */ extern char *strstatus(int s) { - int t = s & 0x7f; - - if (t != 0) { - const char *core = (s & 0x80) ? "+core" : ""; - if (t < NUMOFSIGNALS && *signals[t].name != '\0') + 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", (s >> 8) & 0xff); + return nprint("%d", WEXITSTATUS(s)); } extern void ssetstatus(char **av) { diff --git a/system-bsd.c b/system-bsd.c new file mode 100644 index 0000000..3babaea --- /dev/null +++ b/system-bsd.c @@ -0,0 +1,60 @@ +/* signal-safe read and write (for BSD slow devices). writeall() also +allows partial writes */ + +#include + +#include "rc.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 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/trip.rc b/trip.rc index 64d660f..717b0a2 100644 Binary files a/trip.rc and b/trip.rc differ diff --git a/tripping.c b/tripping.c new file mode 100644 index 0000000..911d229 --- /dev/null +++ b/tripping.c @@ -0,0 +1,33 @@ +/* This is an auxiliary test program for rc. */ + +#include +#include + +void out0(void) { + putchar('t'); putchar('r'); + putchar('\0'); + putchar('u'); putchar('e'); + putchar('\n'); +} + +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 'n': + makenonblock(); + break; + } + return 0; +} diff --git a/utils.c b/utils.c index 71ef61b..ded0c03 100644 --- a/utils.c +++ b/utils.c @@ -7,12 +7,12 @@ /* print error with line number on noninteractive shells (i.e., scripts) */ -extern void pr_error(char *s) { +extern void pr_error(char *s, int offset) { if (s != NULL) { if (interactive) fprint(2, "%s\n", s); else - fprint(2, "line %d: %s\n", lineno - 1, s); + fprint(2, "line %d: %s\n", lineno + offset, s); } } @@ -65,44 +65,6 @@ extern bool isabsolute(char *path) { return path[0] == '/' || (path[0] == '.' && (path[1] == '/' || (path[1] == '.' && path[2] == '/'))); } -/* signal-safe read and write (for BSD slow devices). writeall also allows partial writes */ - -extern void writeall(int fd, char *buf, size_t remain) { - int i; - for (i = 0; remain > 0; buf += i, remain -= i) { - interrupt_happened = FALSE; - if (!setjmp(slowbuf.j)) { - slow = TRUE; - if (interrupt_happened) - break; - else if ((i = write(fd, buf, remain)) <= 0) - break; /* abort silently on errors in write() */ - } else - break; - slow = FALSE; - } - slow = FALSE; - sigchk(); -} - -extern int rc_read(int fd, char *buf, size_t n) { - long /*ssize_t*/ r; - interrupt_happened = FALSE; - if (!setjmp(slowbuf.j)) { - slow = TRUE; - if (!interrupt_happened) - r = read(fd, buf, n); - else - r = -2; - } else - r = -2; - slow = FALSE; - if (r == -2) { - errno = EINTR; - r = -1; - } - return r; -} /* duplicate a fd and close the old one only if necessary */ diff --git a/var.c b/var.c index b0bc60b..8ef453b 100644 --- a/var.c +++ b/var.c @@ -18,11 +18,9 @@ extern void varassign(char *name, List *def, bool stack) { new = get_var_place(name, stack); new->def = newdef; new->extdef = NULL; -#if READLINE /* need to reset readline() every time TERM or TERMCAP changes */ - if (interactive && (streq(name, "TERM") || streq(name, "TERMCAP"))) { - extern void rl_reset_terminal(char *); +#if READLINE + if (interactive && (streq(name, "TERM") || streq(name, "TERMCAP"))) rl_reset_terminal(NULL); - } #endif } @@ -85,7 +83,7 @@ extern List *varlookup(char *name) { return look->def; if (look->extdef == NULL) return NULL; /* variable was set to null, e.g., a=() echo foo */ - ret = parse_var(name, look->extdef); + ret = parse_var(look->extdef); if (ret == NULL) { look->extdef = NULL; return NULL; diff --git a/version.c b/version.c deleted file mode 100644 index 68b5dc1..0000000 --- a/version.c +++ /dev/null @@ -1 +0,0 @@ -const char id[] = "@(#)rc version 1.5b2, 1997-07-01."; diff --git a/version.c.in b/version.c.in new file mode 100644 index 0000000..967f0eb --- /dev/null +++ b/version.c.in @@ -0,0 +1 @@ +const char id[] = "@(#)@PACKAGE@ version @VERSION@, @RELDATE@."; diff --git a/wait.c b/wait.c index 171d97e..66c5097 100644 --- a/wait.c +++ b/wait.c @@ -1,15 +1,10 @@ -#include "rc.h" - #include -#include -#include -#include "jbwrap.h" +#include "rc.h" +#include "wait.h" bool forked = FALSE; -static pid_t rc_wait(int *); - typedef struct Pid Pid; static struct Pid { @@ -21,7 +16,9 @@ static struct Pid { extern pid_t rc_fork() { Pid *new; + struct Pid *p, *q; pid_t pid = fork(); + switch (pid) { case -1: uerror("fork"); @@ -30,6 +27,14 @@ extern pid_t rc_fork() { 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); @@ -43,34 +48,44 @@ extern pid_t rc_fork() { extern pid_t rc_wait4(pid_t pid, int *stat, bool nointr) { Pid *r, *prev; - int ret; - /* first look for a child which may already have exited */ -again: for (r = plist, prev = NULL; r != NULL; prev = r, r = r->n) + + /* 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 (r->alive) { - while (pid != (ret = rc_wait(stat))) { - Pid *q; - if (ret < 0) { - if (nointr) - goto again; + + /* 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; - } } - } else - *stat = r->stat; + + 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 @@ -97,33 +112,16 @@ extern List *sgetapids() { extern void waitforall() { int stat; + while (plist != NULL) { - int pid = rc_wait4(plist->pid, &stat, FALSE); + pid_t pid = rc_wait4(plist->pid, &stat, FALSE); if (pid > 0) setstatus(pid, stat); - else + else { set(FALSE); + if (errno == EINTR) + return; + } sigchk(); } } - -/* - rc_wait: a wait() wrapper that interfaces wait() w/rc signals. - Note that the signal queue is not checked in this fn; someone - may want to resume the wait() without delivering any signals. -*/ - -static pid_t rc_wait(int *stat) { - int r; - interrupt_happened = FALSE; - if (!setjmp(slowbuf.j)) { - slow = TRUE; - if (!interrupt_happened) - r = wait(stat); - else - r = -1; - } else - r = -1; - slow = FALSE; - return r; -} diff --git a/wait.h b/wait.h new file mode 100644 index 0000000..e54ae45 --- /dev/null +++ b/wait.h @@ -0,0 +1,23 @@ +#if HAVE_SYS_WAIT_H +#include +#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 index ed9f965..2f725d6 100644 --- a/walk.c +++ b/walk.c @@ -108,7 +108,7 @@ top: sigchk(); cond = oldcond; break; } - if (setjmp(j.j)) + if (sigsetjmp(j.j, 1)) break; jbreak.jb = &j; except(eBreak, jbreak, &e1); @@ -131,7 +131,7 @@ top: sigchk(); Jbwrap j; Estack e1, e2; Edata jbreak; - if (setjmp(j.j)) + if (sigsetjmp(j.j, 1)) break; jbreak.jb = &j; except(eBreak, jbreak, &e1); @@ -148,6 +148,7 @@ top: sigchk(); } case nSubshell: if (dofork(TRUE)) { + setsigdefaults(FALSE); walk(n->u[0].p, FALSE); rc_exit(getstatus()); } diff --git a/which.c b/which.c index 372cc92..9a6e1bb 100644 --- a/which.c +++ b/which.c @@ -9,18 +9,17 @@ */ #include "rc.h" + #include -#include #include -#include + +#include "getgroups.h" #define X_USR 0100 #define X_GRP 0010 #define X_OTH 0001 #define X_ALL (X_USR|X_GRP|X_OTH) -extern int stat(const char *, struct stat *); - static bool initialized = FALSE; static uid_t uid; static gid_t gid; @@ -32,7 +31,7 @@ static GETGROUPS_T *gidset; /* determine whether gid lies in gidset */ static int ingidset(gid_t g) { - gid_t i; + int i; for (i = 0; i < ngroups; ++i) if (g == gidset[i]) return 1; @@ -87,12 +86,17 @@ extern char *which(char *name, bool verbose) { uid = geteuid(); gid = getegid(); #if HAVE_GETGROUPS - ngroups = getgroups(0, (gid_t *)0); - gidset = malloc(ngroups * sizeof(gid_t)); - if (!gidset) - uerror("malloc"); - else - getgroups(ngroups, gidset); +#if HAVE_POSIX_GETGROUPS + ngroups = getgroups(0, (GETGROUPS_T *)0); + if (ngroups < 0) { + uerror("getgroups"); + rc_exit(1); + } +#else + ngroups = NGROUPS; +#endif + gidset = ealloc(ngroups * sizeof(GETGROUPS_T)); + getgroups(ngroups, gidset); #endif } if (isabsolute(name)) /* absolute pathname? */ diff --git a/y.tab.c b/y.tab.c deleted file mode 100644 index 4538689..0000000 --- a/y.tab.c +++ /dev/null @@ -1,1070 +0,0 @@ -#ifndef lint -static char const yysccsid[] = "@(#)yaccpar 1.9 (Berkeley) 02/21/93"; -#endif -#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) -/* cfront 1.2 defines "c_plusplus" instead of "__cplusplus" */ -#ifdef c_plusplus -#ifndef __cplusplus -#define __cplusplus -#endif -#endif -#ifdef __cplusplus -extern "C" { char *getenv(const char *); } -#else -extern char *getenv(); -extern int yylex(); -extern int yyparse(); -#endif -#define YYPREFIX "yy" -#line 8 "parse.y" -#include "rc.h" -#ifndef lint -#define lint /* hush up gcc -Wall, leave out the dumb sccsid's. */ -#endif -static Node *star, *nolist; -Node *parsetree; /* not using yylval because bison declares it as an auto */ -#line 28 "parse.y" -typedef union { - struct Node *node; - struct Redir redir; - struct Pipe pipe; - struct Dup dup; - struct Word word; - char *keyword; -} YYSTYPE; -#line 43 "y.tab.c" -#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 -#define YYERRCODE 256 -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 -char *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 -#ifdef YYSTACKSIZE -#undef YYMAXDEPTH -#define YYMAXDEPTH YYSTACKSIZE -#else -#ifdef YYMAXDEPTH -#define YYSTACKSIZE YYMAXDEPTH -#else -#define YYSTACKSIZE 500 -#define YYMAXDEPTH 500 -#endif -#endif -int yydebug; -int yynerrs; -int yyerrflag; -int yychar; -short *yyssp; -YYSTYPE *yyvsp; -YYSTYPE yyval; -YYSTYPE yylval; -short yyss[YYSTACKSIZE]; -YYSTYPE yyvs[YYSTACKSIZE]; -#define yystacksize YYSTACKSIZE -#line 169 "parse.y" - -void initparse() { - star = treecpy(mk(nVar,mk(nWord,"*",NULL)), ealloc); - nolist = treecpy(mk(nVar,mk(nWord,"ifs",NULL)), ealloc); -} - -#line 590 "y.tab.c" -#define YYABORT goto yyabort -#define YYREJECT goto yyabort -#define YYACCEPT goto yyaccept -#define YYERROR goto yyerrlab - -int -yyparse() -{ - register int yym, yyn, yystate; -#if YYDEBUG - register char *yys; - - if ((yys = getenv("YYDEBUG"))) - { - yyn = *yys; - if (yyn >= '0' && yyn <= '9') - yydebug = yyn - '0'; - } -#endif - - yynerrs = 0; - yyerrflag = 0; - yychar = (-1); - - 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 >= yyss + yystacksize - 1) - { - 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 >= yyss + yystacksize - 1) - { - 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 49 "parse.y" -{ parsetree = yyvsp[-1].node; YYACCEPT; } -break; -case 2: -#line 50 "parse.y" -{ yyerrok; parsetree = NULL; YYABORT; } -break; -case 3: -#line 53 "parse.y" -{ if (!heredoc(1)) YYABORT; } -break; -case 4: -#line 54 "parse.y" -{ if (!heredoc(0)) YYABORT; } -break; -case 6: -#line 58 "parse.y" -{ yyval.node = (yyvsp[-1].node != NULL ? mk(nNowait,yyvsp[-1].node) : yyvsp[-1].node); } -break; -case 8: -#line 62 "parse.y" -{ yyval.node = (yyvsp[-1].node != NULL ? mk(nBody,yyvsp[-1].node,yyvsp[0].node) : yyvsp[0].node); } -break; -case 10: -#line 66 "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 69 "parse.y" -{ yyval.node = yyvsp[-1].node; if (!heredoc(0)) YYABORT; } -break; -case 13: -#line 71 "parse.y" -{ yyval.node = yyvsp[-1].node; } -break; -case 14: -#line 73 "parse.y" -{ yyval.node = yyvsp[-1].node; } -break; -case 15: -#line 75 "parse.y" -{ yyval.node = mk(nAssign,yyvsp[-2].node,yyvsp[0].node); } -break; -case 16: -#line 77 "parse.y" -{ yyval.node = NULL; } -break; -case 17: -#line 78 "parse.y" -{ yyval.node = mk(nEpilog,yyvsp[-1].node,yyvsp[0].node); } -break; -case 18: -#line 81 "parse.y" -{ yyval.node = mk(nDup,yyvsp[0].dup.type,yyvsp[0].dup.left,yyvsp[0].dup.right); } -break; -case 19: -#line 82 "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 85 "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 89 "parse.y" -{ yyval.node = mk(nCase, yyvsp[-1].node); } -break; -case 22: -#line 90 "parse.y" -{ yyval.node = mk(nCase, yyvsp[-1].node); } -break; -case 23: -#line 92 "parse.y" -{ yyval.node = mk(nCbody, yyvsp[0].node, NULL); } -break; -case 24: -#line 93 "parse.y" -{ yyval.node = mk(nCbody, yyvsp[-1].node, yyvsp[0].node); } -break; -case 25: -#line 94 "parse.y" -{ yyval.node = mk(nCbody, yyvsp[-1].node, yyvsp[0].node); } -break; -case 27: -#line 97 "parse.y" -{ yyval.node = mk(nElse,yyvsp[-3].node,yyvsp[0].node); } -break; -case 28: -#line 99 "parse.y" -{ yyval.node = NULL; } -break; -case 30: -#line 101 "parse.y" -{ yyval.node = mk(nBrace,yyvsp[-1].node,yyvsp[0].node); } -break; -case 31: -#line 102 "parse.y" -{ yyval.node = mk(nIf,yyvsp[-2].node,yyvsp[0].node); } -break; -case 32: -#line 103 "parse.y" -{ yyval.node = mk(nForin,yyvsp[-5].node,yyvsp[-3].node,yyvsp[0].node); } -break; -case 33: -#line 104 "parse.y" -{ yyval.node = mk(nForin,yyvsp[-3].node,star,yyvsp[0].node); } -break; -case 34: -#line 105 "parse.y" -{ yyval.node = mk(nWhile,yyvsp[-2].node,yyvsp[0].node); } -break; -case 35: -#line 106 "parse.y" -{ yyval.node = mk(nSwitch,yyvsp[-5].node,yyvsp[-1].node); } -break; -case 36: -#line 107 "parse.y" -{ yyval.node = mk(nMatch,yyvsp[-1].node,yyvsp[0].node); } -break; -case 37: -#line 108 "parse.y" -{ yyval.node = mk(nAndalso,yyvsp[-3].node,yyvsp[0].node); } -break; -case 38: -#line 109 "parse.y" -{ yyval.node = mk(nOrelse,yyvsp[-3].node,yyvsp[0].node); } -break; -case 39: -#line 110 "parse.y" -{ yyval.node = mk(nPipe,yyvsp[-2].pipe.left,yyvsp[-2].pipe.right,yyvsp[-3].node,yyvsp[0].node); } -break; -case 40: -#line 111 "parse.y" -{ yyval.node = (yyvsp[0].node != NULL ? mk(nPre,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); } -break; -case 41: -#line 112 "parse.y" -{ yyval.node = (yyvsp[0].node != NULL ? mk(nPre,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); } -break; -case 42: -#line 113 "parse.y" -{ yyval.node = mk(nBang,yyvsp[0].node); } -break; -case 43: -#line 114 "parse.y" -{ yyval.node = mk(nSubshell,yyvsp[0].node); } -break; -case 44: -#line 115 "parse.y" -{ yyval.node = mk(nNewfn,yyvsp[-1].node,yyvsp[0].node); } -break; -case 45: -#line 116 "parse.y" -{ yyval.node = mk(nRmfn,yyvsp[0].node); } -break; -case 49: -#line 122 "parse.y" -{ yyval.node = (yyvsp[0].node != NULL ? mk(nArgs,yyvsp[-1].node,yyvsp[0].node) : yyvsp[-1].node); } -break; -case 50: -#line 123 "parse.y" -{ yyval.node = mk(nArgs,yyvsp[-1].node,yyvsp[0].node); } -break; -case 52: -#line 126 "parse.y" -{ yyval.node = mk(nConcat,yyvsp[-2].node,yyvsp[0].node); } -break; -case 54: -#line 129 "parse.y" -{ yyval.node = mk(nWord,yyvsp[0].keyword, NULL); } -break; -case 56: -#line 132 "parse.y" -{ yyval.node = mk(nConcat,yyvsp[-2].node,yyvsp[0].node); } -break; -case 57: -#line 134 "parse.y" -{ yyval.node = mk(nVar,yyvsp[0].node); } -break; -case 58: -#line 135 "parse.y" -{ yyval.node = mk(nVarsub,yyvsp[-3].node,yyvsp[-1].node); } -break; -case 59: -#line 136 "parse.y" -{ yyval.node = mk(nCount,yyvsp[0].node); } -break; -case 60: -#line 137 "parse.y" -{ yyval.node = mk(nFlat, yyvsp[0].node); } -break; -case 61: -#line 138 "parse.y" -{ yyval.node = mk(nBackq,nolist,yyvsp[0].node); } -break; -case 62: -#line 139 "parse.y" -{ yyval.node = mk(nBackq,nolist,yyvsp[0].node); } -break; -case 63: -#line 140 "parse.y" -{ yyval.node = mk(nBackq,yyvsp[-1].node,yyvsp[0].node); } -break; -case 64: -#line 141 "parse.y" -{ yyval.node = mk(nBackq,yyvsp[-1].node,yyvsp[0].node); } -break; -case 65: -#line 142 "parse.y" -{ yyval.node = yyvsp[-1].node; } -break; -case 66: -#line 143 "parse.y" -{ yyval.node = mk(nNmpipe,yyvsp[-1].redir.type,yyvsp[-1].redir.fd,yyvsp[0].node); } -break; -case 67: -#line 144 "parse.y" -{ yyval.node = (yyvsp[0].word.w[0] == '\'') ? mk(nQword, yyvsp[0].word.w+1, NULL) : mk(nWord,yyvsp[0].word.w, yyvsp[0].word.m); } -break; -case 68: -#line 146 "parse.y" -{ yyval.keyword = "for"; } -break; -case 69: -#line 147 "parse.y" -{ yyval.keyword = "in"; } -break; -case 70: -#line 148 "parse.y" -{ yyval.keyword = "while"; } -break; -case 71: -#line 149 "parse.y" -{ yyval.keyword = "if"; } -break; -case 72: -#line 150 "parse.y" -{ yyval.keyword = "switch"; } -break; -case 73: -#line 151 "parse.y" -{ yyval.keyword = "fn"; } -break; -case 74: -#line 152 "parse.y" -{ yyval.keyword = "else"; } -break; -case 75: -#line 153 "parse.y" -{ yyval.keyword = "case"; } -break; -case 76: -#line 154 "parse.y" -{ yyval.keyword = "~"; } -break; -case 77: -#line 155 "parse.y" -{ yyval.keyword = "!"; } -break; -case 78: -#line 156 "parse.y" -{ yyval.keyword = "@"; } -break; -case 79: -#line 158 "parse.y" -{ yyval.node = NULL; } -break; -case 80: -#line 159 "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 161 "parse.y" -{ yyval.node = NULL; } -break; -case 83: -#line 163 "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 1015 "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 >= yyss + yystacksize - 1) - { - goto yyoverflow; - } - *++yyssp = yystate; - *++yyvsp = yyval; - goto yyloop; -yyoverflow: - yyerror("yacc stack overflow"); -yyabort: - return (1); -yyaccept: - return (0); -} diff --git a/y.tab.h b/y.tab.h deleted file mode 100644 index 76f8b74..0000000 --- a/y.tab.h +++ /dev/null @@ -1,33 +0,0 @@ -#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; -- cgit v1.2.3