]> git.ipfire.org Git - thirdparty/bash.git/commitdiff
commit bash-20040816 snapshot
authorChet Ramey <chet.ramey@case.edu>
Sat, 3 Dec 2011 18:35:02 +0000 (13:35 -0500)
committerChet Ramey <chet.ramey@case.edu>
Sat, 3 Dec 2011 18:35:02 +0000 (13:35 -0500)
26 files changed:
CWRU/CWRU.chlog
CWRU/CWRU.chlog~
aclocal.m4
aclocal.m4~ [new file with mode: 0644]
autom4te.cache/output.0
autom4te.cache/requests
builtins/echo.def
builtins/echo.def~ [new file with mode: 0644]
builtins/fg_bg.def
builtins/fg_bg.def~ [new file with mode: 0644]
configure
doc/bash.1
doc/bash.1~ [new file with mode: 0644]
doc/bashref.texi
doc/bashref.texi~
doc/version.texi
doc/version.texi~
lib/malloc/malloc.c
lib/malloc/malloc.c~ [new file with mode: 0644]
lib/malloc/shmalloc.h
lib/malloc/shmalloc.h~ [new file with mode: 0644]
lib/readline/vi_mode.c
lib/readline/vi_mode.c~
lib/sh/strftime.c
lib/sh/strftime.c~ [new file with mode: 0644]
tests/RUN-ONE-TEST

index 3da1e8ba8a327c6d1308522a651c1bb6cd3cc6cf..454c667be73757c2c1f20d08e9713285cec76982 100644 (file)
@@ -9863,3 +9863,40 @@ subst.c
        - in verify_substring_values, fix off-by-one error checking bounds of
          `offset', esp. in array values (e.g., getting the highest element
          of an array)
+
+                                  8/16
+                                  ----
+aclocal.m4
+       - change BASH_CHECK_DEV_FD to make sure that file descriptors > 2 are
+         accessible via /dev/fd, unlike FreeBSD 5.x
+
+lib/sh/strftime.c
+       - make sure `zone' is initialized with gettimeofday before it is used
+       - work around HPUX lack of `altzone' and differing definitions of
+         `timezone'
+
+lib/malloc/malloc.c
+       - internal_memalign and memalign now take a `size_t' as their first
+         argument, which seems to be the prevailing standard
+
+lib/malloc/{malloc.c,shmalloc.h}
+       - change sh_memalign to take a `size_t' as its first argument
+
+builtins/echo.def
+       - if posixly_correct and xpg_echo are both set, don't try to interpret
+         any arguments at all, as POSIX/XOPEN requires (fix inspired by Paul
+         Eggert)
+
+doc/bashref.texi
+       - amend description of bash posix mode to include new echo behavior
+
+builtins/fg_bg.def
+       - allow bg to take multiple job arguments, as posix seems to specify,
+         placing them all in the background, returning the status of the last
+         one as the status of `bg'
+
+lib/readline/vi_mode
+       - fix _rl_vi_change_mbchar_case (multibyte-char version of `~'
+         command) to have the right behavior at EOL -- handle case where vi
+         mode backs up at the end of the line
+
index d2bc981ad4ca136807c7f8d65b9dd923ecfe8ee4..64f9b1636cdc378e6f9fb246a73f947e691f206c 100644 (file)
@@ -9856,3 +9856,45 @@ support/Makefile.in
 lib/readline/vi_mode.c
        - make same change for EOL in multibyte character case of
          rl_vi_change_char
+
+                                  8/12
+                                  ----
+subst.c
+       - in verify_substring_values, fix off-by-one error checking bounds of
+         `offset', esp. in array values (e.g., getting the highest element
+         of an array)
+
+                                  8/16
+                                  ----
+aclocal.m4
+       - change BASH_CHECK_DEV_FD to make sure that file descriptors > 2 are
+         accessible via /dev/fd, unlike FreeBSD 5.x
+
+lib/sh/strftime.c
+       - make sure `zone' is initialized with gettimeofday before it is used
+       - work around HPUX lack of `altzone' and differing definitions of
+         `timezone'
+
+lib/malloc/malloc.c
+       - internal_memalign and memalign now take a `size_t' as their first
+         argument, which seems to be the prevailing standard
+
+lib/malloc/{malloc.c,shmalloc.h}
+       - change sh_memalign to take a `size_t' as its first argument
+
+builtins/echo.def
+       - if posixly_correct and xpg_echo are both set, don't try to interpret
+         any arguments at all, as POSIX/XOPEN requires (fix inspired by Paul
+         Eggert)
+
+doc/bashref.texi
+       - amend description of bash posix mode to include new echo behavior
+
+builtins/fg_bg.def
+       - allow bg to take multiple job arguments, as posix seems to specify,
+         placing them all in the background, returning the status of the last
+         one as the status of `bg'
+
+lib/readline/vi_mode
+       - fix _rl_vi_change_mbchar_case (multibyte-char version of `~'
+         command) to have the right behavior at EOL
index 9d2ed54420cca39631f7f76f11cb5524378fecec..30d9b81312bd6dbb1950b0701833d244221dd216 100644 (file)
@@ -1541,7 +1541,14 @@ AC_DEFUN(BASH_CHECK_DEV_FD,
 [AC_MSG_CHECKING(whether /dev/fd is available)
 AC_CACHE_VAL(bash_cv_dev_fd,
 [if test -d /dev/fd  && test -r /dev/fd/0 < /dev/null; then
-   bash_cv_dev_fd=standard
+# check for systems like FreeBSD 5 that only provide /dev/fd/[012]
+   exec 3<&0
+   if test -r /dev/fd/3; then
+     bash_cv_dev_fd=standard
+   else
+     bash_cv_dev_fd=absent
+   fi
+   exec 3<&-
  elif test -d /proc/self/fd && test -r /proc/self/fd/0 < /dev/null; then
    bash_cv_dev_fd=whacky
  else
diff --git a/aclocal.m4~ b/aclocal.m4~
new file mode 100644 (file)
index 0000000..9d2ed54
--- /dev/null
@@ -0,0 +1,3913 @@
+dnl
+dnl Bash specific tests
+dnl
+dnl Some derived from PDKSH 5.1.3 autoconf tests
+dnl
+
+AC_DEFUN(BASH_C_LONG_LONG,
+[AC_CACHE_CHECK(for long long, ac_cv_c_long_long,
+[if test "$GCC" = yes; then
+  ac_cv_c_long_long=yes
+else
+AC_TRY_RUN([
+int
+main()
+{
+long long foo = 0;
+exit(sizeof(long long) < sizeof(long));
+}
+], ac_cv_c_long_long=yes, ac_cv_c_long_long=no)
+fi])
+if test $ac_cv_c_long_long = yes; then
+  AC_DEFINE(HAVE_LONG_LONG, 1, [Define if the `long long' type works.])
+fi
+])
+
+dnl
+dnl This is very similar to AC_C_LONG_DOUBLE, with the fix for IRIX
+dnl (< changed to <=) added.
+dnl
+AC_DEFUN(BASH_C_LONG_DOUBLE,
+[AC_CACHE_CHECK(for long double, ac_cv_c_long_double,
+[if test "$GCC" = yes; then
+  ac_cv_c_long_double=yes
+else
+AC_TRY_RUN([
+int
+main()
+{
+  /* The Stardent Vistra knows sizeof(long double), but does not
+     support it. */
+  long double foo = 0.0;
+  /* On Ultrix 4.3 cc, long double is 4 and double is 8.  */
+  /* On IRIX 5.3, the compiler converts long double to double with a warning,
+     but compiles this successfully. */
+  exit(sizeof(long double) <= sizeof(double));
+}
+], ac_cv_c_long_double=yes, ac_cv_c_long_double=no)
+fi])
+if test $ac_cv_c_long_double = yes; then
+  AC_DEFINE(HAVE_LONG_DOUBLE, 1, [Define if the `long double' type works.])
+fi
+])
+
+dnl
+dnl Check for <inttypes.h>.  This is separated out so that it can be
+dnl AC_REQUIREd.
+dnl
+dnl BASH_HEADER_INTTYPES
+AC_DEFUN(BASH_HEADER_INTTYPES,
+[
+ AC_CHECK_HEADERS(inttypes.h)
+])
+
+dnl
+dnl check for typedef'd symbols in header files, but allow the caller to
+dnl specify the include files to be checked in addition to the default
+dnl 
+dnl BASH_CHECK_TYPE(TYPE, HEADERS, DEFAULT[, VALUE-IF-FOUND])
+AC_DEFUN(BASH_CHECK_TYPE,
+[
+AC_REQUIRE([AC_HEADER_STDC])dnl
+AC_REQUIRE([BASH_HEADER_INTTYPES])
+AC_MSG_CHECKING(for $1)
+AC_CACHE_VAL(bash_cv_type_$1,
+[AC_EGREP_CPP($1, [#include <sys/types.h>
+#if STDC_HEADERS
+#include <stdlib.h>
+#include <stddef.h>
+#endif
+#if HAVE_INTTYPES_H
+#include <inttypes.h>
+#endif
+$2
+], bash_cv_type_$1=yes, bash_cv_type_$1=no)])
+AC_MSG_RESULT($bash_cv_type_$1)
+ifelse($#, 4, [if test $bash_cv_type_$1 = yes; then
+       AC_DEFINE($4)
+       fi])
+if test $bash_cv_type_$1 = no; then
+  AC_DEFINE_UNQUOTED($1, $3)
+fi
+])
+
+dnl
+dnl BASH_CHECK_DECL(FUNC)
+dnl
+dnl Check for a declaration of FUNC in stdlib.h and inttypes.h like
+dnl AC_CHECK_DECL
+dnl
+AC_DEFUN(BASH_CHECK_DECL,
+[
+AC_REQUIRE([AC_HEADER_STDC])
+AC_REQUIRE([BASH_HEADER_INTTYPES])
+AC_CACHE_CHECK([for declaration of $1], bash_cv_decl_$1,
+[AC_TRY_LINK(
+[
+#if STDC_HEADERS
+#  include <stdlib.h>
+#endif
+#if HAVE_INTTYPES_H
+#  include <inttypes.h>
+#endif
+],
+[return !$1;],
+bash_cv_decl_$1=yes, bash_cv_decl_$1=no)])
+bash_tr_func=HAVE_DECL_`echo $1 | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'`
+if test $bash_cv_decl_$1 = yes; then
+  AC_DEFINE_UNQUOTED($bash_tr_func, 1)
+else
+  AC_DEFINE_UNQUOTED($bash_tr_func, 0)
+fi
+])
+
+AC_DEFUN(BASH_DECL_PRINTF,
+[AC_MSG_CHECKING(for declaration of printf in <stdio.h>)
+AC_CACHE_VAL(bash_cv_printf_declared,
+[AC_TRY_RUN([
+#include <stdio.h>
+#ifdef __STDC__
+typedef int (*_bashfunc)(const char *, ...);
+#else
+typedef int (*_bashfunc)();
+#endif
+main()
+{
+_bashfunc pf;
+pf = (_bashfunc) printf;
+exit(pf == 0);
+}
+], bash_cv_printf_declared=yes, bash_cv_printf_declared=no,
+   [AC_MSG_WARN(cannot check printf declaration if cross compiling -- defaulting to yes)
+    bash_cv_printf_declared=yes]
+)])
+AC_MSG_RESULT($bash_cv_printf_declared)
+if test $bash_cv_printf_declared = yes; then
+AC_DEFINE(PRINTF_DECLARED)
+fi
+])
+
+AC_DEFUN(BASH_DECL_SBRK,
+[AC_MSG_CHECKING(for declaration of sbrk in <unistd.h>)
+AC_CACHE_VAL(bash_cv_sbrk_declared,
+[AC_EGREP_HEADER(sbrk, unistd.h,
+ bash_cv_sbrk_declared=yes, bash_cv_sbrk_declared=no)])
+AC_MSG_RESULT($bash_cv_sbrk_declared)
+if test $bash_cv_sbrk_declared = yes; then
+AC_DEFINE(SBRK_DECLARED)
+fi
+])
+
+dnl
+dnl Check for sys_siglist[] or _sys_siglist[]
+dnl
+AC_DEFUN(BASH_DECL_UNDER_SYS_SIGLIST,
+[AC_MSG_CHECKING([for _sys_siglist in signal.h or unistd.h])
+AC_CACHE_VAL(bash_cv_decl_under_sys_siglist,
+[AC_TRY_COMPILE([
+#include <sys/types.h>
+#include <signal.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif], [ char *msg = _sys_siglist[2]; ],
+  bash_cv_decl_under_sys_siglist=yes, bash_cv_decl_under_sys_siglist=no,
+  [AC_MSG_WARN(cannot check for _sys_siglist[] if cross compiling -- defaulting to no)])])dnl
+AC_MSG_RESULT($bash_cv_decl_under_sys_siglist)
+if test $bash_cv_decl_under_sys_siglist = yes; then
+AC_DEFINE(UNDER_SYS_SIGLIST_DECLARED)
+fi
+])
+
+AC_DEFUN(BASH_UNDER_SYS_SIGLIST,
+[AC_REQUIRE([BASH_DECL_UNDER_SYS_SIGLIST])
+AC_MSG_CHECKING([for _sys_siglist in system C library])
+AC_CACHE_VAL(bash_cv_under_sys_siglist,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#include <signal.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+#ifndef UNDER_SYS_SIGLIST_DECLARED
+extern char *_sys_siglist[];
+#endif
+main()
+{
+char *msg = (char *)_sys_siglist[2];
+exit(msg == 0);
+}],
+       bash_cv_under_sys_siglist=yes, bash_cv_under_sys_siglist=no,
+       [AC_MSG_WARN(cannot check for _sys_siglist[] if cross compiling -- defaulting to no)
+        bash_cv_under_sys_siglist=no])])
+AC_MSG_RESULT($bash_cv_under_sys_siglist)
+if test $bash_cv_under_sys_siglist = yes; then
+AC_DEFINE(HAVE_UNDER_SYS_SIGLIST)
+fi
+])
+
+AC_DEFUN(BASH_SYS_SIGLIST,
+[AC_REQUIRE([AC_DECL_SYS_SIGLIST])
+AC_MSG_CHECKING([for sys_siglist in system C library])
+AC_CACHE_VAL(bash_cv_sys_siglist,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#include <signal.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+#ifndef SYS_SIGLIST_DECLARED
+extern char *sys_siglist[];
+#endif
+main()
+{
+char *msg = sys_siglist[2];
+exit(msg == 0);
+}],
+       bash_cv_sys_siglist=yes, bash_cv_sys_siglist=no,
+       [AC_MSG_WARN(cannot check for sys_siglist if cross compiling -- defaulting to no)
+        bash_cv_sys_siglist=no])])
+AC_MSG_RESULT($bash_cv_sys_siglist)
+if test $bash_cv_sys_siglist = yes; then
+AC_DEFINE(HAVE_SYS_SIGLIST)
+fi
+])
+
+dnl Check for the various permutations of sys_siglist and make sure we
+dnl compile in siglist.o if they're not defined
+AC_DEFUN(BASH_CHECK_SYS_SIGLIST, [
+AC_REQUIRE([BASH_SYS_SIGLIST])
+AC_REQUIRE([BASH_DECL_UNDER_SYS_SIGLIST])
+AC_REQUIRE([BASH_FUNC_STRSIGNAL])
+if test "$bash_cv_sys_siglist" = no && test "$bash_cv_under_sys_siglist" = no && test "$bash_cv_have_strsignal" = no; then
+  SIGLIST_O=siglist.o
+else
+  SIGLIST_O=
+fi
+AC_SUBST([SIGLIST_O])
+])
+
+dnl Check for sys_errlist[] and sys_nerr, check for declaration
+AC_DEFUN(BASH_SYS_ERRLIST,
+[AC_MSG_CHECKING([for sys_errlist and sys_nerr])
+AC_CACHE_VAL(bash_cv_sys_errlist,
+[AC_TRY_LINK([#include <errno.h>],
+[extern char *sys_errlist[];
+ extern int sys_nerr;
+ char *msg = sys_errlist[sys_nerr - 1];],
+    bash_cv_sys_errlist=yes, bash_cv_sys_errlist=no)])dnl
+AC_MSG_RESULT($bash_cv_sys_errlist)
+if test $bash_cv_sys_errlist = yes; then
+AC_DEFINE(HAVE_SYS_ERRLIST)
+fi
+])
+
+dnl
+dnl Check if dup2() does not clear the close on exec flag
+dnl
+AC_DEFUN(BASH_FUNC_DUP2_CLOEXEC_CHECK,
+[AC_MSG_CHECKING(if dup2 fails to clear the close-on-exec flag)
+AC_CACHE_VAL(bash_cv_dup2_broken,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#include <fcntl.h>
+main()
+{
+  int fd1, fd2, fl;
+  fd1 = open("/dev/null", 2);
+  if (fcntl(fd1, 2, 1) < 0)
+    exit(1);
+  fd2 = dup2(fd1, 1);
+  if (fd2 < 0)
+    exit(2);
+  fl = fcntl(fd2, 1, 0);
+  /* fl will be 1 if dup2 did not reset the close-on-exec flag. */
+  exit(fl != 1);
+}
+], bash_cv_dup2_broken=yes, bash_cv_dup2_broken=no,
+    [AC_MSG_WARN(cannot check dup2 if cross compiling -- defaulting to no)
+     bash_cv_dup2_broken=no])
+])
+AC_MSG_RESULT($bash_cv_dup2_broken)
+if test $bash_cv_dup2_broken = yes; then
+AC_DEFINE(DUP2_BROKEN)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_STRSIGNAL,
+[AC_MSG_CHECKING([for the existence of strsignal])
+AC_CACHE_VAL(bash_cv_have_strsignal,
+[AC_TRY_LINK([#include <sys/types.h>
+#include <signal.h>],
+[char *s = (char *)strsignal(2);],
+ bash_cv_have_strsignal=yes, bash_cv_have_strsignal=no)])
+AC_MSG_RESULT($bash_cv_have_strsignal)
+if test $bash_cv_have_strsignal = yes; then
+AC_DEFINE(HAVE_STRSIGNAL)
+fi
+])
+
+dnl Check to see if opendir will open non-directories (not a nice thing)
+AC_DEFUN(BASH_FUNC_OPENDIR_CHECK,
+[AC_REQUIRE([AC_HEADER_DIRENT])dnl
+AC_MSG_CHECKING(if opendir() opens non-directories)
+AC_CACHE_VAL(bash_cv_opendir_not_robust,
+[AC_TRY_RUN([
+#include <stdio.h>
+#include <sys/types.h>
+#include <fcntl.h>
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif /* HAVE_UNISTD_H */
+#if defined(HAVE_DIRENT_H)
+# include <dirent.h>
+#else
+# define dirent direct
+# ifdef HAVE_SYS_NDIR_H
+#  include <sys/ndir.h>
+# endif /* SYSNDIR */
+# ifdef HAVE_SYS_DIR_H
+#  include <sys/dir.h>
+# endif /* SYSDIR */
+# ifdef HAVE_NDIR_H
+#  include <ndir.h>
+# endif
+#endif /* HAVE_DIRENT_H */
+main()
+{
+DIR *dir;
+int fd, err;
+err = mkdir("/tmp/bash-aclocal", 0700);
+if (err < 0) {
+  perror("mkdir");
+  exit(1);
+}
+unlink("/tmp/bash-aclocal/not_a_directory");
+fd = open("/tmp/bash-aclocal/not_a_directory", O_WRONLY|O_CREAT|O_EXCL, 0666);
+write(fd, "\n", 1);
+close(fd);
+dir = opendir("/tmp/bash-aclocal/not_a_directory");
+unlink("/tmp/bash-aclocal/not_a_directory");
+rmdir("/tmp/bash-aclocal");
+exit (dir == 0);
+}], bash_cv_opendir_not_robust=yes,bash_cv_opendir_not_robust=no,
+    [AC_MSG_WARN(cannot check opendir if cross compiling -- defaulting to no)
+     bash_cv_opendir_not_robust=no]
+)])
+AC_MSG_RESULT($bash_cv_opendir_not_robust)
+if test $bash_cv_opendir_not_robust = yes; then
+AC_DEFINE(OPENDIR_NOT_ROBUST)
+fi
+])
+
+dnl
+AC_DEFUN(BASH_TYPE_SIGHANDLER,
+[AC_MSG_CHECKING([whether signal handlers are of type void])
+AC_CACHE_VAL(bash_cv_void_sighandler,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <signal.h>
+#ifdef signal
+#undef signal
+#endif
+#ifdef __cplusplus
+extern "C"
+#endif
+void (*signal ()) ();],
+[int i;], bash_cv_void_sighandler=yes, bash_cv_void_sighandler=no)])dnl
+AC_MSG_RESULT($bash_cv_void_sighandler)
+if test $bash_cv_void_sighandler = yes; then
+AC_DEFINE(VOID_SIGHANDLER)
+fi
+])
+
+dnl
+dnl A signed 16-bit integer quantity
+dnl
+AC_DEFUN(BASH_TYPE_BITS16_T,
+[
+if test "$ac_cv_sizeof_short" = 2; then
+  AC_CHECK_TYPE(bits16_t, short)
+elif test "$ac_cv_sizeof_char" = 2; then
+  AC_CHECK_TYPE(bits16_t, char)
+else
+  AC_CHECK_TYPE(bits16_t, short)
+fi
+])
+
+dnl
+dnl An unsigned 16-bit integer quantity
+dnl
+AC_DEFUN(BASH_TYPE_U_BITS16_T,
+[
+if test "$ac_cv_sizeof_short" = 2; then
+  AC_CHECK_TYPE(u_bits16_t, unsigned short)
+elif test "$ac_cv_sizeof_char" = 2; then
+  AC_CHECK_TYPE(u_bits16_t, unsigned char)
+else
+  AC_CHECK_TYPE(u_bits16_t, unsigned short)
+fi
+])
+
+dnl
+dnl A signed 32-bit integer quantity
+dnl
+AC_DEFUN(BASH_TYPE_BITS32_T,
+[
+if test "$ac_cv_sizeof_int" = 4; then
+  AC_CHECK_TYPE(bits32_t, int)
+elif test "$ac_cv_sizeof_long" = 4; then
+  AC_CHECK_TYPE(bits32_t, long)
+else
+  AC_CHECK_TYPE(bits32_t, int)
+fi
+])
+
+dnl
+dnl An unsigned 32-bit integer quantity
+dnl
+AC_DEFUN(BASH_TYPE_U_BITS32_T,
+[
+if test "$ac_cv_sizeof_int" = 4; then
+  AC_CHECK_TYPE(u_bits32_t, unsigned int)
+elif test "$ac_cv_sizeof_long" = 4; then
+  AC_CHECK_TYPE(u_bits32_t, unsigned long)
+else
+  AC_CHECK_TYPE(u_bits32_t, unsigned int)
+fi
+])
+
+AC_DEFUN(BASH_TYPE_PTRDIFF_T,
+[
+if test "$ac_cv_sizeof_int" = "$ac_cv_sizeof_char_p"; then
+  AC_CHECK_TYPE(ptrdiff_t, int)
+elif test "$ac_cv_sizeof_long" = "$ac_cv_sizeof_char_p"; then
+  AC_CHECK_TYPE(ptrdiff_t, long)
+elif test "$ac_cv_type_long_long" = yes && test "$ac_cv_sizeof_long_long" = "$ac_cv_sizeof_char_p"; then
+  AC_CHECK_TYPE(ptrdiff_t, [long long])
+else
+  AC_CHECK_TYPE(ptrdiff_t, int)
+fi
+])
+
+dnl
+dnl A signed 64-bit quantity
+dnl
+AC_DEFUN(BASH_TYPE_BITS64_T,
+[
+if test "$ac_cv_sizeof_char_p" = 8; then
+  AC_CHECK_TYPE(bits64_t, char *)
+elif test "$ac_cv_sizeof_double" = 8; then
+  AC_CHECK_TYPE(bits64_t, double)
+elif test -n "$ac_cv_type_long_long" && test "$ac_cv_sizeof_long_long" = 8; then
+  AC_CHECK_TYPE(bits64_t, [long long])
+elif test "$ac_cv_sizeof_long" = 8; then
+  AC_CHECK_TYPE(bits64_t, long)
+else
+  AC_CHECK_TYPE(bits64_t, double)
+fi
+])
+
+AC_DEFUN(BASH_TYPE_LONG_LONG,
+[
+AC_CACHE_CHECK([for long long], bash_cv_type_long_long,
+[AC_TRY_LINK([
+long long ll = 1; int i = 63;],
+[
+long long llm = (long long) -1;
+return ll << i | ll >> i | llm / ll | llm % ll;
+], bash_cv_type_long_long='long long', bash_cv_type_long_long='long')])
+if test "$bash_cv_type_long_long" = 'long long'; then
+  AC_DEFINE(HAVE_LONG_LONG, 1)
+fi
+])
+
+AC_DEFUN(BASH_TYPE_UNSIGNED_LONG_LONG,
+[
+AC_CACHE_CHECK([for unsigned long long], bash_cv_type_unsigned_long_long,
+[AC_TRY_LINK([
+unsigned long long ull = 1; int i = 63;],
+[
+unsigned long long ullmax = (unsigned long long) -1;
+return ull << i | ull >> i | ullmax / ull | ullmax % ull;
+], bash_cv_type_unsigned_long_long='unsigned long long',
+   bash_cv_type_unsigned_long_long='unsigned long')])
+if test "$bash_cv_type_unsigned_long_long" = 'unsigned long long'; then
+  AC_DEFINE(HAVE_UNSIGNED_LONG_LONG, 1)
+fi
+])
+
+dnl
+dnl Type of struct rlimit fields: some systems (OSF/1, NetBSD, RISC/os 5.0)
+dnl have a rlim_t, others (4.4BSD based systems) use quad_t, others use
+dnl long and still others use int (HP-UX 9.01, SunOS 4.1.3).  To simplify
+dnl matters, this just checks for rlim_t, quad_t, or long.
+dnl
+AC_DEFUN(BASH_TYPE_RLIMIT,
+[AC_MSG_CHECKING(for size and type of struct rlimit fields)
+AC_CACHE_VAL(bash_cv_type_rlimit,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/resource.h>],
+[rlim_t xxx;], bash_cv_type_rlimit=rlim_t,[
+AC_TRY_RUN([
+#include <sys/types.h>
+#include <sys/time.h>
+#include <sys/resource.h>
+main()
+{
+#ifdef HAVE_QUAD_T
+  struct rlimit rl;
+  if (sizeof(rl.rlim_cur) == sizeof(quad_t))
+    exit(0);
+#endif
+  exit(1);
+}], bash_cv_type_rlimit=quad_t, bash_cv_type_rlimit=long,
+        [AC_MSG_WARN(cannot check quad_t if cross compiling -- defaulting to long)
+         bash_cv_type_rlimit=long])])
+])
+AC_MSG_RESULT($bash_cv_type_rlimit)
+if test $bash_cv_type_rlimit = quad_t; then
+AC_DEFINE(RLIMTYPE, quad_t)
+elif test $bash_cv_type_rlimit = rlim_t; then
+AC_DEFINE(RLIMTYPE, rlim_t)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_LSTAT,
+[dnl Cannot use AC_CHECK_FUNCS(lstat) because Linux defines lstat() as an
+dnl inline function in <sys/stat.h>.
+AC_CACHE_CHECK([for lstat], bash_cv_func_lstat,
+[AC_TRY_LINK([
+#include <sys/types.h>
+#include <sys/stat.h>
+],[ lstat(".",(struct stat *)0); ],
+bash_cv_func_lstat=yes, bash_cv_func_lstat=no)])
+if test $bash_cv_func_lstat = yes; then
+  AC_DEFINE(HAVE_LSTAT)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_INET_ATON,
+[
+AC_CACHE_CHECK([for inet_aton], bash_cv_func_inet_aton,
+[AC_TRY_LINK([
+#include <sys/types.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+struct in_addr ap;], [ inet_aton("127.0.0.1", &ap); ],
+bash_cv_func_inet_aton=yes, bash_cv_func_inet_aton=no)])
+if test $bash_cv_func_inet_aton = yes; then
+  AC_DEFINE(HAVE_INET_ATON)
+else
+  AC_LIBOBJ(inet_aton)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_GETENV,
+[AC_MSG_CHECKING(to see if getenv can be redefined)
+AC_CACHE_VAL(bash_cv_getenv_redef,
+[AC_TRY_RUN([
+#ifdef HAVE_UNISTD_H
+#  include <unistd.h>
+#endif
+#ifndef __STDC__
+#  ifndef const
+#    define const
+#  endif
+#endif
+char *
+getenv (name)
+#if defined (__linux__) || defined (__bsdi__) || defined (convex)
+     const char *name;
+#else
+     char const *name;
+#endif /* !__linux__ && !__bsdi__ && !convex */
+{
+return "42";
+}
+main()
+{
+char *s;
+/* The next allows this program to run, but does not allow bash to link
+   when it redefines getenv.  I'm not really interested in figuring out
+   why not. */
+#if defined (NeXT)
+exit(1);
+#endif
+s = getenv("ABCDE");
+exit(s == 0);  /* force optimizer to leave getenv in */
+}
+], bash_cv_getenv_redef=yes, bash_cv_getenv_redef=no,
+   [AC_MSG_WARN(cannot check getenv redefinition if cross compiling -- defaulting to yes)
+    bash_cv_getenv_redef=yes]
+)])
+AC_MSG_RESULT($bash_cv_getenv_redef)
+if test $bash_cv_getenv_redef = yes; then
+AC_DEFINE(CAN_REDEFINE_GETENV)
+fi
+])
+
+# We should check for putenv before calling this
+AC_DEFUN(BASH_FUNC_STD_PUTENV,
+[
+AC_REQUIRE([AC_HEADER_STDC])
+AC_REQUIRE([AC_C_PROTOTYPES])
+AC_CACHE_CHECK([for standard-conformant putenv declaration], bash_cv_std_putenv,
+[AC_TRY_LINK([
+#if STDC_HEADERS
+#include <stdlib.h>
+#include <stddef.h>
+#endif
+#ifndef __STDC__
+#  ifndef const
+#    define const
+#  endif
+#endif
+#ifdef PROTOTYPES
+extern int putenv (char *);
+#else
+extern int putenv ();
+#endif
+],
+[return (putenv == 0);],
+bash_cv_std_putenv=yes, bash_cv_std_putenv=no
+)])
+if test $bash_cv_std_putenv = yes; then
+AC_DEFINE(HAVE_STD_PUTENV)
+fi
+])
+
+# We should check for unsetenv before calling this
+AC_DEFUN(BASH_FUNC_STD_UNSETENV,
+[
+AC_REQUIRE([AC_HEADER_STDC])
+AC_REQUIRE([AC_C_PROTOTYPES])
+AC_CACHE_CHECK([for standard-conformant unsetenv declaration], bash_cv_std_unsetenv,
+[AC_TRY_LINK([
+#if STDC_HEADERS
+#include <stdlib.h>
+#include <stddef.h>
+#endif
+#ifndef __STDC__
+#  ifndef const
+#    define const
+#  endif
+#endif
+#ifdef PROTOTYPES
+extern int unsetenv (const char *);
+#else
+extern int unsetenv ();
+#endif
+],
+[return (unsetenv == 0);],
+bash_cv_std_unsetenv=yes, bash_cv_std_unsetenv=no
+)])
+if test $bash_cv_std_unsetenv = yes; then
+AC_DEFINE(HAVE_STD_UNSETENV)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_ULIMIT_MAXFDS,
+[AC_MSG_CHECKING(whether ulimit can substitute for getdtablesize)
+AC_CACHE_VAL(bash_cv_ulimit_maxfds,
+[AC_TRY_RUN([
+main()
+{
+long maxfds = ulimit(4, 0L);
+exit (maxfds == -1L);
+}
+], bash_cv_ulimit_maxfds=yes, bash_cv_ulimit_maxfds=no,
+   [AC_MSG_WARN(cannot check ulimit if cross compiling -- defaulting to no)
+    bash_cv_ulimit_maxfds=no]
+)])
+AC_MSG_RESULT($bash_cv_ulimit_maxfds)
+if test $bash_cv_ulimit_maxfds = yes; then
+AC_DEFINE(ULIMIT_MAXFDS)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_GETCWD,
+[AC_MSG_CHECKING([if getcwd() will dynamically allocate memory])
+AC_CACHE_VAL(bash_cv_getcwd_malloc,
+[AC_TRY_RUN([
+#include <stdio.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
+main()
+{
+       char    *xpwd;
+       xpwd = getcwd(0, 0);
+       exit (xpwd == 0);
+}
+], bash_cv_getcwd_malloc=yes, bash_cv_getcwd_malloc=no,
+   [AC_MSG_WARN(cannot check whether getcwd allocates memory when cross-compiling -- defaulting to no)
+    bash_cv_getcwd_malloc=no]
+)])
+AC_MSG_RESULT($bash_cv_getcwd_malloc)
+if test $bash_cv_getcwd_malloc = no; then
+AC_DEFINE(GETCWD_BROKEN)
+AC_LIBOBJ(getcwd)
+fi
+])
+
+dnl
+dnl This needs BASH_CHECK_SOCKLIB, but since that's not called on every
+dnl system, we can't use AC_PREREQ
+dnl
+AC_DEFUN(BASH_FUNC_GETHOSTBYNAME,
+[if test "X$bash_cv_have_gethostbyname" = "X"; then
+_bash_needmsg=yes
+else
+AC_MSG_CHECKING(for gethostbyname in socket library)
+_bash_needmsg=
+fi
+AC_CACHE_VAL(bash_cv_have_gethostbyname,
+[AC_TRY_LINK([#include <netdb.h>],
+[ struct hostent *hp;
+  hp = gethostbyname("localhost");
+], bash_cv_have_gethostbyname=yes, bash_cv_have_gethostbyname=no)]
+)
+if test "X$_bash_needmsg" = Xyes; then
+    AC_MSG_CHECKING(for gethostbyname in socket library)
+fi
+AC_MSG_RESULT($bash_cv_have_gethostbyname)
+if test "$bash_cv_have_gethostbyname" = yes; then
+AC_DEFINE(HAVE_GETHOSTBYNAME)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_FNMATCH_EXTMATCH,
+[AC_MSG_CHECKING(if fnmatch does extended pattern matching with FNM_EXTMATCH)
+AC_CACHE_VAL(bash_cv_fnm_extmatch,
+[AC_TRY_RUN([
+#include <fnmatch.h>
+
+main()
+{
+#ifdef FNM_EXTMATCH
+  exit (0);
+#else
+  exit (1);
+#endif
+}
+], bash_cv_fnm_extmatch=yes, bash_cv_fnm_extmatch=no,
+    [AC_MSG_WARN(cannot check FNM_EXTMATCH if cross compiling -- defaulting to no)
+     bash_cv_fnm_extmatch=no])
+])
+AC_MSG_RESULT($bash_cv_fnm_extmatch)
+if test $bash_cv_fnm_extmatch = yes; then
+AC_DEFINE(HAVE_LIBC_FNM_EXTMATCH)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_POSIX_SETJMP,
+[AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE])
+AC_MSG_CHECKING(for presence of POSIX-style sigsetjmp/siglongjmp)
+AC_CACHE_VAL(bash_cv_func_sigsetjmp,
+[AC_TRY_RUN([
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+#include <sys/types.h>
+#include <signal.h>
+#include <setjmp.h>
+
+main()
+{
+#if !defined (_POSIX_VERSION) || !defined (HAVE_POSIX_SIGNALS)
+exit (1);
+#else
+
+int code;
+sigset_t set, oset;
+sigjmp_buf xx;
+
+/* get the mask */
+sigemptyset(&set);
+sigemptyset(&oset);
+sigprocmask(SIG_BLOCK, (sigset_t *)NULL, &set);
+sigprocmask(SIG_BLOCK, (sigset_t *)NULL, &oset);
+
+/* save it */
+code = sigsetjmp(xx, 1);
+if (code)
+  exit(0);     /* could get sigmask and compare to oset here. */
+
+/* change it */
+sigaddset(&set, SIGINT);
+sigprocmask(SIG_BLOCK, &set, (sigset_t *)NULL);
+
+/* and siglongjmp */
+siglongjmp(xx, 10);
+exit(1);
+#endif
+}], bash_cv_func_sigsetjmp=present, bash_cv_func_sigsetjmp=missing,
+    [AC_MSG_WARN(cannot check for sigsetjmp/siglongjmp if cross-compiling -- defaulting to missing)
+     bash_cv_func_sigsetjmp=missing]
+)])
+AC_MSG_RESULT($bash_cv_func_sigsetjmp)
+if test $bash_cv_func_sigsetjmp = present; then
+AC_DEFINE(HAVE_POSIX_SIGSETJMP)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_STRCOLL,
+[
+AC_MSG_CHECKING(whether or not strcoll and strcmp differ)
+AC_CACHE_VAL(bash_cv_func_strcoll_broken,
+[AC_TRY_RUN([
+#include <stdio.h>
+#if defined (HAVE_LOCALE_H)
+#include <locale.h>
+#endif
+
+main(c, v)
+int     c;
+char    *v[];
+{
+        int     r1, r2;
+        char    *deflocale, *defcoll;
+
+#ifdef HAVE_SETLOCALE
+        deflocale = setlocale(LC_ALL, "");
+       defcoll = setlocale(LC_COLLATE, "");
+#endif
+
+#ifdef HAVE_STRCOLL
+       /* These two values are taken from tests/glob-test. */
+        r1 = strcoll("abd", "aXd");
+#else
+       r1 = 0;
+#endif
+        r2 = strcmp("abd", "aXd");
+
+       /* These two should both be greater than 0.  It is permissible for
+          a system to return different values, as long as the sign is the
+          same. */
+
+        /* Exit with 1 (failure) if these two values are both > 0, since
+          this tests whether strcoll(3) is broken with respect to strcmp(3)
+          in the default locale. */
+       exit (r1 > 0 && r2 > 0);
+}
+], bash_cv_func_strcoll_broken=yes, bash_cv_func_strcoll_broken=no,
+   [AC_MSG_WARN(cannot check strcoll if cross compiling -- defaulting to no)
+    bash_cv_func_strcoll_broken=no]
+)])
+AC_MSG_RESULT($bash_cv_func_strcoll_broken)
+if test $bash_cv_func_strcoll_broken = yes; then
+AC_DEFINE(STRCOLL_BROKEN)
+fi
+])
+
+AC_DEFUN(BASH_FUNC_PRINTF_A_FORMAT,
+[AC_MSG_CHECKING([for printf floating point output in hex notation])
+AC_CACHE_VAL(bash_cv_printf_a_format,
+[AC_TRY_RUN([
+#include <stdio.h>
+#include <string.h>
+
+int
+main()
+{
+       double y = 0.0;
+       char abuf[1024];
+
+       sprintf(abuf, "%A", y);
+       exit(strchr(abuf, 'P') == (char *)0);
+}
+], bash_cv_printf_a_format=yes, bash_cv_printf_a_format=no,
+   [AC_MSG_WARN(cannot check printf if cross compiling -- defaulting to no)
+    bash_cv_printf_a_format=no]
+)])
+AC_MSG_RESULT($bash_cv_printf_a_format)
+if test $bash_cv_printf_a_format = yes; then
+AC_DEFINE(HAVE_PRINTF_A_FORMAT)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_TERMIOS_LDISC,
+[
+AC_CHECK_MEMBER(struct termios.c_line, AC_DEFINE(TERMIOS_LDISC), ,[
+#include <sys/types.h>
+#include <termios.h>
+])
+])
+
+AC_DEFUN(BASH_STRUCT_TERMIO_LDISC,
+[
+AC_CHECK_MEMBER(struct termio.c_line, AC_DEFINE(TERMIO_LDISC), ,[
+#include <sys/types.h>
+#include <termio.h>
+])
+])
+
+dnl
+dnl Like AC_STRUCT_ST_BLOCKS, but doesn't muck with LIBOBJS
+dnl
+dnl sets bash_cv_struct_stat_st_blocks
+dnl
+dnl unused for now; we'll see how AC_CHECK_MEMBERS works
+dnl
+AC_DEFUN(BASH_STRUCT_ST_BLOCKS,
+[
+AC_MSG_CHECKING([for struct stat.st_blocks])
+AC_CACHE_VAL(bash_cv_struct_stat_st_blocks,
+[AC_TRY_COMPILE(
+[
+#include <sys/types.h>
+#include <sys/stat.h>
+],
+[
+main()
+{
+static struct stat a;
+if (a.st_blocks) return 0;
+return 0;
+}
+], bash_cv_struct_stat_st_blocks=yes, bash_cv_struct_stat_st_blocks=no)
+])
+AC_MSG_RESULT($bash_cv_struct_stat_st_blocks)
+if test "$bash_cv_struct_stat_st_blocks" = "yes"; then
+AC_DEFINE(HAVE_STRUCT_STAT_ST_BLOCKS)
+fi
+])
+
+AC_DEFUN(BASH_CHECK_LIB_TERMCAP,
+[
+if test "X$bash_cv_termcap_lib" = "X"; then
+_bash_needmsg=yes
+else
+AC_MSG_CHECKING(which library has the termcap functions)
+_bash_needmsg=
+fi
+AC_CACHE_VAL(bash_cv_termcap_lib,
+[AC_CHECK_FUNC(tgetent, bash_cv_termcap_lib=libc,
+  [AC_CHECK_LIB(termcap, tgetent, bash_cv_termcap_lib=libtermcap,
+    [AC_CHECK_LIB(tinfo, tgetent, bash_cv_termcap_lib=libtinfo,
+        [AC_CHECK_LIB(curses, tgetent, bash_cv_termcap_lib=libcurses,
+           [AC_CHECK_LIB(ncurses, tgetent, bash_cv_termcap_lib=libncurses,
+               bash_cv_termcap_lib=gnutermcap)])])])])])
+if test "X$_bash_needmsg" = "Xyes"; then
+AC_MSG_CHECKING(which library has the termcap functions)
+fi
+AC_MSG_RESULT(using $bash_cv_termcap_lib)
+if test $bash_cv_termcap_lib = gnutermcap && test -z "$prefer_curses"; then
+LDFLAGS="$LDFLAGS -L./lib/termcap"
+TERMCAP_LIB="./lib/termcap/libtermcap.a"
+TERMCAP_DEP="./lib/termcap/libtermcap.a"
+elif test $bash_cv_termcap_lib = libtermcap && test -z "$prefer_curses"; then
+TERMCAP_LIB=-ltermcap
+TERMCAP_DEP=
+elif test $bash_cv_termcap_lib = libtinfo; then
+TERMCAP_LIB=-ltinfo
+TERMCAP_DEP=
+elif test $bash_cv_termcap_lib = libncurses; then
+TERMCAP_LIB=-lncurses
+TERMCAP_DEP=
+elif test $bash_cv_termcap_lib = libc; then
+TERMCAP_LIB=
+TERMCAP_DEP=
+else
+TERMCAP_LIB=-lcurses
+TERMCAP_DEP=
+fi
+])
+
+dnl
+dnl Check for the presence of getpeername in libsocket.
+dnl If libsocket is present, check for libnsl and add it to LIBS if
+dnl it's there, since most systems with libsocket require linking
+dnl with libnsl as well.  This should only be called if getpeername
+dnl was not found in libc.
+dnl
+dnl NOTE: IF WE FIND GETPEERNAME, WE ASSUME THAT WE HAVE BIND/CONNECT
+dnl      AS WELL
+dnl
+AC_DEFUN(BASH_CHECK_LIB_SOCKET,
+[
+if test "X$bash_cv_have_socklib" = "X"; then
+_bash_needmsg=
+else
+AC_MSG_CHECKING(for socket library)
+_bash_needmsg=yes
+fi
+AC_CACHE_VAL(bash_cv_have_socklib,
+[AC_CHECK_LIB(socket, getpeername,
+        bash_cv_have_socklib=yes, bash_cv_have_socklib=no, -lnsl)])
+if test "X$_bash_needmsg" = Xyes; then
+  AC_MSG_RESULT($bash_cv_have_socklib)
+  _bash_needmsg=
+fi
+if test $bash_cv_have_socklib = yes; then
+  # check for libnsl, add it to LIBS if present
+  if test "X$bash_cv_have_libnsl" = "X"; then
+    _bash_needmsg=
+  else
+    AC_MSG_CHECKING(for libnsl)
+    _bash_needmsg=yes
+  fi
+  AC_CACHE_VAL(bash_cv_have_libnsl,
+          [AC_CHECK_LIB(nsl, t_open,
+                bash_cv_have_libnsl=yes, bash_cv_have_libnsl=no)])
+  if test "X$_bash_needmsg" = Xyes; then
+    AC_MSG_RESULT($bash_cv_have_libnsl)
+    _bash_needmsg=
+  fi
+  if test $bash_cv_have_libnsl = yes; then
+    LIBS="-lsocket -lnsl $LIBS"
+  else
+    LIBS="-lsocket $LIBS"
+  fi
+  AC_DEFINE(HAVE_LIBSOCKET)
+  AC_DEFINE(HAVE_GETPEERNAME)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_DIRENT_D_INO,
+[AC_REQUIRE([AC_HEADER_DIRENT])
+AC_MSG_CHECKING(for struct dirent.d_ino)
+AC_CACHE_VAL(bash_cv_dirent_has_dino,
+[AC_TRY_COMPILE([
+#include <stdio.h>
+#include <sys/types.h>
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif /* HAVE_UNISTD_H */
+#if defined(HAVE_DIRENT_H)
+# include <dirent.h>
+#else
+# define dirent direct
+# ifdef HAVE_SYS_NDIR_H
+#  include <sys/ndir.h>
+# endif /* SYSNDIR */
+# ifdef HAVE_SYS_DIR_H
+#  include <sys/dir.h>
+# endif /* SYSDIR */
+# ifdef HAVE_NDIR_H
+#  include <ndir.h>
+# endif
+#endif /* HAVE_DIRENT_H */
+],[
+struct dirent d; int z; z = d.d_ino;
+], bash_cv_dirent_has_dino=yes, bash_cv_dirent_has_dino=no)])
+AC_MSG_RESULT($bash_cv_dirent_has_dino)
+if test $bash_cv_dirent_has_dino = yes; then
+AC_DEFINE(HAVE_STRUCT_DIRENT_D_INO)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_DIRENT_D_FILENO,
+[AC_REQUIRE([AC_HEADER_DIRENT])
+AC_MSG_CHECKING(for struct dirent.d_fileno)
+AC_CACHE_VAL(bash_cv_dirent_has_d_fileno,
+[AC_TRY_COMPILE([
+#include <stdio.h>
+#include <sys/types.h>
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif /* HAVE_UNISTD_H */
+#if defined(HAVE_DIRENT_H)
+# include <dirent.h>
+#else
+# define dirent direct
+# ifdef HAVE_SYS_NDIR_H
+#  include <sys/ndir.h>
+# endif /* SYSNDIR */
+# ifdef HAVE_SYS_DIR_H
+#  include <sys/dir.h>
+# endif /* SYSDIR */
+# ifdef HAVE_NDIR_H
+#  include <ndir.h>
+# endif
+#endif /* HAVE_DIRENT_H */
+],[
+struct dirent d; int z; z = d.d_fileno;
+], bash_cv_dirent_has_d_fileno=yes, bash_cv_dirent_has_d_fileno=no)])
+AC_MSG_RESULT($bash_cv_dirent_has_d_fileno)
+if test $bash_cv_dirent_has_d_fileno = yes; then
+AC_DEFINE(HAVE_STRUCT_DIRENT_D_FILENO)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_DIRENT_D_NAMLEN,
+[AC_REQUIRE([AC_HEADER_DIRENT])
+AC_MSG_CHECKING(for struct dirent.d_namlen)
+AC_CACHE_VAL(bash_cv_dirent_has_d_namlen,
+[AC_TRY_COMPILE([
+#include <stdio.h>
+#include <sys/types.h>
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif /* HAVE_UNISTD_H */
+#if defined(HAVE_DIRENT_H)
+# include <dirent.h>
+#else
+# define dirent direct
+# ifdef HAVE_SYS_NDIR_H
+#  include <sys/ndir.h>
+# endif /* SYSNDIR */
+# ifdef HAVE_SYS_DIR_H
+#  include <sys/dir.h>
+# endif /* SYSDIR */
+# ifdef HAVE_NDIR_H
+#  include <ndir.h>
+# endif
+#endif /* HAVE_DIRENT_H */
+],[
+struct dirent d; int z; z = d.d_namlen;
+], bash_cv_dirent_has_d_namlen=yes, bash_cv_dirent_has_d_namlen=no)])
+AC_MSG_RESULT($bash_cv_dirent_has_d_namlen)
+if test $bash_cv_dirent_has_d_namlen = yes; then
+AC_DEFINE(HAVE_STRUCT_DIRENT_D_NAMLEN)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_TIMEVAL,
+[AC_MSG_CHECKING(for struct timeval in sys/time.h and time.h)
+AC_CACHE_VAL(bash_cv_struct_timeval,
+[
+AC_EGREP_HEADER(struct timeval, sys/time.h,
+               bash_cv_struct_timeval=yes,
+               AC_EGREP_HEADER(struct timeval, time.h,
+                       bash_cv_struct_timeval=yes,
+                       bash_cv_struct_timeval=no))
+])
+AC_MSG_RESULT($bash_cv_struct_timeval)
+if test $bash_cv_struct_timeval = yes; then
+  AC_DEFINE(HAVE_TIMEVAL)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_TIMEZONE,
+[AC_MSG_CHECKING(for struct timezone in sys/time.h and time.h)
+AC_CACHE_VAL(bash_cv_struct_timezone,
+[
+AC_EGREP_HEADER(struct timezone, sys/time.h,
+               bash_cv_struct_timezone=yes,
+               AC_EGREP_HEADER(struct timezone, time.h,
+                       bash_cv_struct_timezone=yes,
+                       bash_cv_struct_timezone=no))
+])
+AC_MSG_RESULT($bash_cv_struct_timezone)
+if test $bash_cv_struct_timezone = yes; then
+  AC_DEFINE(HAVE_STRUCT_TIMEZONE)
+fi
+])
+
+AC_DEFUN(BASH_STRUCT_WINSIZE,
+[AC_MSG_CHECKING(for struct winsize in sys/ioctl.h and termios.h)
+AC_CACHE_VAL(bash_cv_struct_winsize_header,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/ioctl.h>], [struct winsize x;],
+  bash_cv_struct_winsize_header=ioctl_h,
+  [AC_TRY_COMPILE([#include <sys/types.h>
+#include <termios.h>], [struct winsize x;],
+  bash_cv_struct_winsize_header=termios_h, bash_cv_struct_winsize_header=other)
+])])
+if test $bash_cv_struct_winsize_header = ioctl_h; then
+  AC_MSG_RESULT(sys/ioctl.h)
+  AC_DEFINE(STRUCT_WINSIZE_IN_SYS_IOCTL)
+elif test $bash_cv_struct_winsize_header = termios_h; then
+  AC_MSG_RESULT(termios.h)
+  AC_DEFINE(STRUCT_WINSIZE_IN_TERMIOS)
+else
+  AC_MSG_RESULT(not found)
+fi
+])
+
+dnl Check type of signal routines (posix, 4.2bsd, 4.1bsd or v7)
+AC_DEFUN(BASH_SYS_SIGNAL_VINTAGE,
+[AC_REQUIRE([AC_TYPE_SIGNAL])
+AC_MSG_CHECKING(for type of signal functions)
+AC_CACHE_VAL(bash_cv_signal_vintage,
+[
+  AC_TRY_LINK([#include <signal.h>],[
+    sigset_t ss;
+    struct sigaction sa;
+    sigemptyset(&ss); sigsuspend(&ss);
+    sigaction(SIGINT, &sa, (struct sigaction *) 0);
+    sigprocmask(SIG_BLOCK, &ss, (sigset_t *) 0);
+  ], bash_cv_signal_vintage=posix,
+  [
+    AC_TRY_LINK([#include <signal.h>], [
+       int mask = sigmask(SIGINT);
+       sigsetmask(mask); sigblock(mask); sigpause(mask);
+    ], bash_cv_signal_vintage=4.2bsd,
+    [
+      AC_TRY_LINK([
+       #include <signal.h>
+       RETSIGTYPE foo() { }], [
+               int mask = sigmask(SIGINT);
+               sigset(SIGINT, foo); sigrelse(SIGINT);
+               sighold(SIGINT); sigpause(SIGINT);
+        ], bash_cv_signal_vintage=svr3, bash_cv_signal_vintage=v7
+    )]
+  )]
+)
+])
+AC_MSG_RESULT($bash_cv_signal_vintage)
+if test "$bash_cv_signal_vintage" = posix; then
+AC_DEFINE(HAVE_POSIX_SIGNALS)
+elif test "$bash_cv_signal_vintage" = "4.2bsd"; then
+AC_DEFINE(HAVE_BSD_SIGNALS)
+elif test "$bash_cv_signal_vintage" = svr3; then
+AC_DEFINE(HAVE_USG_SIGHOLD)
+fi
+])
+
+dnl Check if the pgrp of setpgrp() can't be the pid of a zombie process.
+AC_DEFUN(BASH_SYS_PGRP_SYNC,
+[AC_REQUIRE([AC_FUNC_GETPGRP])
+AC_MSG_CHECKING(whether pgrps need synchronization)
+AC_CACHE_VAL(bash_cv_pgrp_pipe,
+[AC_TRY_RUN([
+#ifdef HAVE_UNISTD_H
+#  include <unistd.h>
+#endif
+main()
+{
+# ifdef GETPGRP_VOID
+#  define getpgID()    getpgrp()
+# else
+#  define getpgID()    getpgrp(0)
+#  define setpgid(x,y) setpgrp(x,y)
+# endif
+       int pid1, pid2, fds[2];
+       int status;
+       char ok;
+
+       switch (pid1 = fork()) {
+         case -1:
+           exit(1);
+         case 0:
+           setpgid(0, getpid());
+           exit(0);
+       }
+       setpgid(pid1, pid1);
+
+       sleep(2);       /* let first child die */
+
+       if (pipe(fds) < 0)
+         exit(2);
+
+       switch (pid2 = fork()) {
+         case -1:
+           exit(3);
+         case 0:
+           setpgid(0, pid1);
+           ok = getpgID() == pid1;
+           write(fds[1], &ok, 1);
+           exit(0);
+       }
+       setpgid(pid2, pid1);
+
+       close(fds[1]);
+       if (read(fds[0], &ok, 1) != 1)
+         exit(4);
+       wait(&status);
+       wait(&status);
+       exit(ok ? 0 : 5);
+}
+], bash_cv_pgrp_pipe=no,bash_cv_pgrp_pipe=yes,
+   [AC_MSG_WARN(cannot check pgrp synchronization if cross compiling -- defaulting to no)
+    bash_cv_pgrp_pipe=no])
+])
+AC_MSG_RESULT($bash_cv_pgrp_pipe)
+if test $bash_cv_pgrp_pipe = yes; then
+AC_DEFINE(PGRP_PIPE)
+fi
+])
+
+AC_DEFUN(BASH_SYS_REINSTALL_SIGHANDLERS,
+[AC_REQUIRE([AC_TYPE_SIGNAL])
+AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE])
+AC_MSG_CHECKING([if signal handlers must be reinstalled when invoked])
+AC_CACHE_VAL(bash_cv_must_reinstall_sighandlers,
+[AC_TRY_RUN([
+#include <signal.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
+typedef RETSIGTYPE sigfunc();
+
+int nsigint;
+
+#ifdef HAVE_POSIX_SIGNALS
+sigfunc *
+set_signal_handler(sig, handler)
+     int sig;
+     sigfunc *handler;
+{
+  struct sigaction act, oact;
+  act.sa_handler = handler;
+  act.sa_flags = 0;
+  sigemptyset (&act.sa_mask);
+  sigemptyset (&oact.sa_mask);
+  sigaction (sig, &act, &oact);
+  return (oact.sa_handler);
+}
+#else
+#define set_signal_handler(s, h) signal(s, h)
+#endif
+
+RETSIGTYPE
+sigint(s)
+int s;
+{
+  nsigint++;
+}
+
+main()
+{
+       nsigint = 0;
+       set_signal_handler(SIGINT, sigint);
+       kill((int)getpid(), SIGINT);
+       kill((int)getpid(), SIGINT);
+       exit(nsigint != 2);
+}
+], bash_cv_must_reinstall_sighandlers=no, bash_cv_must_reinstall_sighandlers=yes,
+   [AC_MSG_WARN(cannot check signal handling if cross compiling -- defaulting to no)
+    bash_cv_must_reinstall_sighandlers=no]
+)])
+AC_MSG_RESULT($bash_cv_must_reinstall_sighandlers)
+if test $bash_cv_must_reinstall_sighandlers = yes; then
+AC_DEFINE(MUST_REINSTALL_SIGHANDLERS)
+fi
+])
+
+dnl check that some necessary job control definitions are present
+AC_DEFUN(BASH_SYS_JOB_CONTROL_MISSING,
+[AC_REQUIRE([BASH_SYS_SIGNAL_VINTAGE])
+AC_MSG_CHECKING(for presence of necessary job control definitions)
+AC_CACHE_VAL(bash_cv_job_control_missing,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#ifdef HAVE_SYS_WAIT_H
+#include <sys/wait.h>
+#endif
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+#include <signal.h>
+
+/* Add more tests in here as appropriate. */
+main()
+{
+/* signal type */
+#if !defined (HAVE_POSIX_SIGNALS) && !defined (HAVE_BSD_SIGNALS)
+exit(1);
+#endif
+
+/* signals and tty control. */
+#if !defined (SIGTSTP) || !defined (SIGSTOP) || !defined (SIGCONT)
+exit (1);
+#endif
+
+/* process control */
+#if !defined (WNOHANG) || !defined (WUNTRACED) 
+exit(1);
+#endif
+
+/* Posix systems have tcgetpgrp and waitpid. */
+#if defined (_POSIX_VERSION) && !defined (HAVE_TCGETPGRP)
+exit(1);
+#endif
+
+#if defined (_POSIX_VERSION) && !defined (HAVE_WAITPID)
+exit(1);
+#endif
+
+/* Other systems have TIOCSPGRP/TIOCGPRGP and wait3. */
+#if !defined (_POSIX_VERSION) && !defined (HAVE_WAIT3)
+exit(1);
+#endif
+
+exit(0);
+}], bash_cv_job_control_missing=present, bash_cv_job_control_missing=missing,
+    [AC_MSG_WARN(cannot check job control if cross-compiling -- defaulting to missing)
+     bash_cv_job_control_missing=missing]
+)])
+AC_MSG_RESULT($bash_cv_job_control_missing)
+if test $bash_cv_job_control_missing = missing; then
+AC_DEFINE(JOB_CONTROL_MISSING)
+fi
+])
+
+dnl check whether named pipes are present
+dnl this requires a previous check for mkfifo, but that is awkward to specify
+AC_DEFUN(BASH_SYS_NAMED_PIPES,
+[AC_MSG_CHECKING(for presence of named pipes)
+AC_CACHE_VAL(bash_cv_sys_named_pipes,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#include <sys/stat.h>
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
+/* Add more tests in here as appropriate. */
+main()
+{
+int fd, err;
+
+#if defined (HAVE_MKFIFO)
+exit (0);
+#endif
+
+#if !defined (S_IFIFO) && (defined (_POSIX_VERSION) && !defined (S_ISFIFO))
+exit (1);
+#endif
+
+#if defined (NeXT)
+exit (1);
+#endif
+err = mkdir("/tmp/bash-aclocal", 0700);
+if (err < 0) {
+  perror ("mkdir");
+  exit(1);
+}
+fd = mknod ("/tmp/bash-aclocal/sh-np-autoconf", 0666 | S_IFIFO, 0);
+if (fd == -1) {
+  rmdir ("/tmp/bash-aclocal");
+  exit (1);
+}
+close(fd);
+unlink ("/tmp/bash-aclocal/sh-np-autoconf");
+rmdir ("/tmp/bash-aclocal");
+exit(0);
+}], bash_cv_sys_named_pipes=present, bash_cv_sys_named_pipes=missing,
+    [AC_MSG_WARN(cannot check for named pipes if cross-compiling -- defaulting to missing)
+     bash_cv_sys_named_pipes=missing]
+)])
+AC_MSG_RESULT($bash_cv_sys_named_pipes)
+if test $bash_cv_sys_named_pipes = missing; then
+AC_DEFINE(NAMED_PIPES_MISSING)
+fi
+])
+
+AC_DEFUN(BASH_SYS_DEFAULT_MAIL_DIR,
+[AC_MSG_CHECKING(for default mail directory)
+AC_CACHE_VAL(bash_cv_mail_dir,
+[if test -d /var/mail; then
+   bash_cv_mail_dir=/var/mail
+ elif test -d /var/spool/mail; then
+   bash_cv_mail_dir=/var/spool/mail
+ elif test -d /usr/mail; then
+   bash_cv_mail_dir=/usr/mail
+ elif test -d /usr/spool/mail; then
+   bash_cv_mail_dir=/usr/spool/mail
+ else
+   bash_cv_mail_dir=unknown
+ fi
+])
+AC_MSG_RESULT($bash_cv_mail_dir)
+AC_DEFINE_UNQUOTED(DEFAULT_MAIL_DIRECTORY, "$bash_cv_mail_dir")
+])
+
+AC_DEFUN(BASH_HAVE_TIOCGWINSZ,
+[AC_MSG_CHECKING(for TIOCGWINSZ in sys/ioctl.h)
+AC_CACHE_VAL(bash_cv_tiocgwinsz_in_ioctl,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/ioctl.h>], [int x = TIOCGWINSZ;],
+  bash_cv_tiocgwinsz_in_ioctl=yes,bash_cv_tiocgwinsz_in_ioctl=no)])
+AC_MSG_RESULT($bash_cv_tiocgwinsz_in_ioctl)
+if test $bash_cv_tiocgwinsz_in_ioctl = yes; then   
+AC_DEFINE(GWINSZ_IN_SYS_IOCTL)
+fi
+])
+
+AC_DEFUN(BASH_HAVE_TIOCSTAT,
+[AC_MSG_CHECKING(for TIOCSTAT in sys/ioctl.h)
+AC_CACHE_VAL(bash_cv_tiocstat_in_ioctl,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/ioctl.h>], [int x = TIOCSTAT;],
+  bash_cv_tiocstat_in_ioctl=yes,bash_cv_tiocstat_in_ioctl=no)])
+AC_MSG_RESULT($bash_cv_tiocstat_in_ioctl)
+if test $bash_cv_tiocstat_in_ioctl = yes; then   
+AC_DEFINE(TIOCSTAT_IN_SYS_IOCTL)
+fi
+])
+
+AC_DEFUN(BASH_HAVE_FIONREAD,
+[AC_MSG_CHECKING(for FIONREAD in sys/ioctl.h)
+AC_CACHE_VAL(bash_cv_fionread_in_ioctl,
+[AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/ioctl.h>], [int x = FIONREAD;],
+  bash_cv_fionread_in_ioctl=yes,bash_cv_fionread_in_ioctl=no)])
+AC_MSG_RESULT($bash_cv_fionread_in_ioctl)
+if test $bash_cv_fionread_in_ioctl = yes; then   
+AC_DEFINE(FIONREAD_IN_SYS_IOCTL)
+fi
+])
+
+dnl
+dnl See if speed_t is declared in <sys/types.h>.  Some versions of linux
+dnl require a definition of speed_t each time <termcap.h> is included,
+dnl but you can only get speed_t if you include <termios.h> (on some
+dnl versions) or <sys/types.h> (on others).
+dnl
+AC_DEFUN(BASH_CHECK_SPEED_T,
+[AC_MSG_CHECKING(for speed_t in sys/types.h)
+AC_CACHE_VAL(bash_cv_speed_t_in_sys_types,
+[AC_TRY_COMPILE([#include <sys/types.h>], [speed_t x;],
+  bash_cv_speed_t_in_sys_types=yes,bash_cv_speed_t_in_sys_types=no)])
+AC_MSG_RESULT($bash_cv_speed_t_in_sys_types)
+if test $bash_cv_speed_t_in_sys_types = yes; then   
+AC_DEFINE(SPEED_T_IN_SYS_TYPES)
+fi
+])
+
+AC_DEFUN(BASH_CHECK_GETPW_FUNCS,
+[AC_MSG_CHECKING(whether getpw functions are declared in pwd.h)
+AC_CACHE_VAL(bash_cv_getpw_declared,
+[AC_EGREP_CPP(getpwuid,
+[
+#include <sys/types.h>
+#ifdef HAVE_UNISTD_H
+#  include <unistd.h>
+#endif
+#include <pwd.h>
+],
+bash_cv_getpw_declared=yes,bash_cv_getpw_declared=no)])
+AC_MSG_RESULT($bash_cv_getpw_declared)
+if test $bash_cv_getpw_declared = yes; then
+AC_DEFINE(HAVE_GETPW_DECLS)
+fi
+])
+
+AC_DEFUN(BASH_CHECK_DEV_FD,
+[AC_MSG_CHECKING(whether /dev/fd is available)
+AC_CACHE_VAL(bash_cv_dev_fd,
+[if test -d /dev/fd  && test -r /dev/fd/0 < /dev/null; then
+   bash_cv_dev_fd=standard
+ elif test -d /proc/self/fd && test -r /proc/self/fd/0 < /dev/null; then
+   bash_cv_dev_fd=whacky
+ else
+   bash_cv_dev_fd=absent
+ fi
+])
+AC_MSG_RESULT($bash_cv_dev_fd)
+if test $bash_cv_dev_fd = "standard"; then
+  AC_DEFINE(HAVE_DEV_FD)
+  AC_DEFINE(DEV_FD_PREFIX, "/dev/fd/")
+elif test $bash_cv_dev_fd = "whacky"; then
+  AC_DEFINE(HAVE_DEV_FD)
+  AC_DEFINE(DEV_FD_PREFIX, "/proc/self/fd/")
+fi
+])
+
+AC_DEFUN(BASH_CHECK_DEV_STDIN,
+[AC_MSG_CHECKING(whether /dev/stdin stdout stderr are available)
+AC_CACHE_VAL(bash_cv_dev_stdin,
+[if test -d /dev/fd && test -r /dev/stdin < /dev/null; then
+   bash_cv_dev_stdin=present
+ elif test -d /proc/self/fd && test -r /dev/stdin < /dev/null; then
+   bash_cv_dev_stdin=present
+ else
+   bash_cv_dev_stdin=absent
+ fi
+])
+AC_MSG_RESULT($bash_cv_dev_stdin)
+if test $bash_cv_dev_stdin = "present"; then
+  AC_DEFINE(HAVE_DEV_STDIN)
+fi
+])
+
+dnl
+dnl Check if HPUX needs _KERNEL defined for RLIMIT_* definitions
+dnl
+AC_DEFUN(BASH_CHECK_KERNEL_RLIMIT,
+[AC_MSG_CHECKING([whether $host_os needs _KERNEL for RLIMIT defines])
+AC_CACHE_VAL(bash_cv_kernel_rlimit,
+[AC_TRY_COMPILE([
+#include <sys/types.h>
+#include <sys/resource.h>
+],
+[
+  int f;
+  f = RLIMIT_DATA;
+], bash_cv_kernel_rlimit=no,
+[AC_TRY_COMPILE([
+#include <sys/types.h>
+#define _KERNEL
+#include <sys/resource.h>
+#undef _KERNEL
+],
+[
+       int f;
+        f = RLIMIT_DATA;
+], bash_cv_kernel_rlimit=yes, bash_cv_kernel_rlimit=no)]
+)])
+AC_MSG_RESULT($bash_cv_kernel_rlimit)
+if test $bash_cv_kernel_rlimit = yes; then
+AC_DEFINE(RLIMIT_NEEDS_KERNEL)
+fi
+])
+
+dnl
+dnl Check for 64-bit off_t -- used for malloc alignment
+dnl
+dnl C does not allow duplicate case labels, so the compile will fail if
+dnl sizeof(off_t) is > 4.
+dnl
+AC_DEFUN(BASH_CHECK_OFF_T_64,
+[AC_CACHE_CHECK(for 64-bit off_t, bash_cv_off_t_64,
+AC_TRY_COMPILE([
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+#include <sys/types.h>
+],[
+switch (0) case 0: case (sizeof (off_t) <= 4):;
+], bash_cv_off_t_64=no, bash_cv_off_t_64=yes))
+if test $bash_cv_off_t_64 = yes; then
+        AC_DEFINE(HAVE_OFF_T_64)
+fi])
+
+AC_DEFUN(BASH_CHECK_RTSIGS,
+[AC_MSG_CHECKING(for unusable real-time signals due to large values)
+AC_CACHE_VAL(bash_cv_unusable_rtsigs,
+[AC_TRY_RUN([
+#include <sys/types.h>
+#include <signal.h>
+
+#ifndef NSIG
+#  define NSIG 64
+#endif
+
+main ()
+{
+  int n_sigs = 2 * NSIG;
+#ifdef SIGRTMIN
+  int rtmin = SIGRTMIN;
+#else
+  int rtmin = 0;
+#endif
+
+  exit(rtmin < n_sigs);
+}], bash_cv_unusable_rtsigs=yes, bash_cv_unusable_rtsigs=no,
+    [AC_MSG_WARN(cannot check real-time signals if cross compiling -- defaulting to yes)
+     bash_cv_unusable_rtsigs=yes]
+)])
+AC_MSG_RESULT($bash_cv_unusable_rtsigs)
+if test $bash_cv_unusable_rtsigs = yes; then
+AC_DEFINE(UNUSABLE_RT_SIGNALS)
+fi
+])
+
+dnl
+dnl check for availability of multibyte characters and functions
+dnl
+AC_DEFUN(BASH_CHECK_MULTIBYTE,
+[
+AC_CHECK_HEADERS(wctype.h)
+AC_CHECK_HEADERS(wchar.h)
+AC_CHECK_HEADERS(langinfo.h)
+
+AC_CHECK_FUNC(mbsrtowcs, AC_DEFINE(HAVE_MBSRTOWCS))
+AC_CHECK_FUNC(mbrtowc, AC_DEFINE(HAVE_MBRTOWC))
+AC_CHECK_FUNC(mbrlen, AC_DEFINE(HAVE_MBRLEN))
+AC_CHECK_FUNC(wctomb, AC_DEFINE(HAVE_WCTOMB))
+AC_CHECK_FUNC(wcwidth, AC_DEFINE(HAVE_WCWIDTH))
+AC_CHECK_FUNC(wcsdup, AC_DEFINE(HAVE_WCSDUP))
+
+AC_CACHE_CHECK([for mbstate_t], bash_cv_have_mbstate_t,
+[AC_TRY_COMPILE([
+#include <wchar.h>], [
+  mbstate_t ps;
+  mbstate_t *psp;
+  psp = (mbstate_t *)0;
+], bash_cv_have_mbstate_t=yes,  bash_cv_have_mbstate_t=no)])
+if test $bash_cv_have_mbstate_t = yes; then
+       AC_DEFINE(HAVE_MBSTATE_T)
+fi
+
+AC_CACHE_CHECK([for nl_langinfo and CODESET], bash_cv_langinfo_codeset,
+[AC_TRY_LINK(
+[#include <langinfo.h>],
+[char* cs = nl_langinfo(CODESET);],
+bash_cv_langinfo_codeset=yes, bash_cv_langinfo_codeset=no)])
+if test $bash_cv_langinfo_codeset = yes; then
+  AC_DEFINE(HAVE_LANGINFO_CODESET)
+fi
+
+])
+
+dnl need: prefix exec_prefix libdir includedir CC TERMCAP_LIB
+dnl require:
+dnl    AC_PROG_CC
+dnl    BASH_CHECK_LIB_TERMCAP
+
+AC_DEFUN(RL_LIB_READLINE_VERSION,
+[
+AC_REQUIRE([BASH_CHECK_LIB_TERMCAP])
+
+AC_MSG_CHECKING([version of installed readline library])
+
+# What a pain in the ass this is.
+
+# save cpp and ld options
+_save_CFLAGS="$CFLAGS"
+_save_LDFLAGS="$LDFLAGS"
+_save_LIBS="$LIBS"
+
+# Don't set ac_cv_rl_prefix if the caller has already assigned a value.  This
+# allows the caller to do something like $_rl_prefix=$withval if the user
+# specifies --with-installed-readline=PREFIX as an argument to configure
+
+if test -z "$ac_cv_rl_prefix"; then
+test "x$prefix" = xNONE && ac_cv_rl_prefix=$ac_default_prefix || ac_cv_rl_prefix=${prefix}
+fi
+
+eval ac_cv_rl_includedir=${ac_cv_rl_prefix}/include
+eval ac_cv_rl_libdir=${ac_cv_rl_prefix}/lib
+
+LIBS="$LIBS -lreadline ${TERMCAP_LIB}"
+CFLAGS="$CFLAGS -I${ac_cv_rl_includedir}"
+LDFLAGS="$LDFLAGS -L${ac_cv_rl_libdir}"
+
+AC_CACHE_VAL(ac_cv_rl_version,
+[AC_TRY_RUN([
+#include <stdio.h>
+#include <readline/readline.h>
+
+main()
+{
+       FILE *fp;
+       fp = fopen("conftest.rlv", "w");
+       if (fp == 0) exit(1);
+       fprintf(fp, "%s\n", rl_library_version ? rl_library_version : "0.0");
+       fclose(fp);
+       exit(0);
+}
+],
+ac_cv_rl_version=`cat conftest.rlv`,
+ac_cv_rl_version='0.0',
+ac_cv_rl_version='4.2')])
+
+CFLAGS="$_save_CFLAGS"
+LDFLAGS="$_save_LDFLAGS"
+LIBS="$_save_LIBS"
+
+RL_MAJOR=0
+RL_MINOR=0
+
+# (
+case "$ac_cv_rl_version" in
+2*|3*|4*|5*|6*|7*|8*|9*)
+       RL_MAJOR=`echo $ac_cv_rl_version | sed 's:\..*$::'`
+       RL_MINOR=`echo $ac_cv_rl_version | sed -e 's:^.*\.::' -e 's:[[a-zA-Z]]*$::'`
+       ;;
+esac
+
+# (((
+case $RL_MAJOR in
+[[0-9][0-9]])  _RL_MAJOR=$RL_MAJOR ;;
+[[0-9]])       _RL_MAJOR=0$RL_MAJOR ;;
+*)             _RL_MAJOR=00 ;;
+esac
+
+# (((
+case $RL_MINOR in
+[[0-9][0-9]])  _RL_MINOR=$RL_MINOR ;;
+[[0-9]])       _RL_MINOR=0$RL_MINOR ;;
+*)             _RL_MINOR=00 ;;
+esac
+
+RL_VERSION="0x${_RL_MAJOR}${_RL_MINOR}"
+
+# Readline versions greater than 4.2 have these defines in readline.h
+
+if test $ac_cv_rl_version = '0.0' ; then
+       AC_MSG_WARN([Could not test version of installed readline library.])
+elif test $RL_MAJOR -gt 4 || { test $RL_MAJOR = 4 && test $RL_MINOR -gt 2 ; } ; then
+       # set these for use by the caller
+       RL_PREFIX=$ac_cv_rl_prefix
+       RL_LIBDIR=$ac_cv_rl_libdir
+       RL_INCLUDEDIR=$ac_cv_rl_includedir
+       AC_MSG_RESULT($ac_cv_rl_version)
+else
+
+AC_DEFINE_UNQUOTED(RL_READLINE_VERSION, $RL_VERSION, [encoded version of the installed readline library])
+AC_DEFINE_UNQUOTED(RL_VERSION_MAJOR, $RL_MAJOR, [major version of installed readline library])
+AC_DEFINE_UNQUOTED(RL_VERSION_MINOR, $RL_MINOR, [minor version of installed readline library])
+
+AC_SUBST(RL_VERSION)
+AC_SUBST(RL_MAJOR)
+AC_SUBST(RL_MINOR)
+
+# set these for use by the caller
+RL_PREFIX=$ac_cv_rl_prefix
+RL_LIBDIR=$ac_cv_rl_libdir
+RL_INCLUDEDIR=$ac_cv_rl_includedir
+
+AC_MSG_RESULT($ac_cv_rl_version)
+
+fi
+])
+
+AC_DEFUN(BASH_FUNC_CTYPE_NONASCII,
+[
+AC_MSG_CHECKING(whether the ctype macros accept non-ascii characters)
+AC_CACHE_VAL(bash_cv_func_ctype_nonascii,
+[AC_TRY_RUN([
+#ifdef HAVE_LOCALE_H
+#include <locale.h>
+#endif
+#include <stdio.h>
+#include <ctype.h>
+
+main(c, v)
+int    c;
+char   *v[];
+{
+       char    *deflocale;
+       unsigned char x;
+       int     r1, r2;
+
+#ifdef HAVE_SETLOCALE
+       /* We take a shot here.  If that locale is not known, try the
+          system default.  We try this one because '\342' (226) is
+          known to be a printable character in that locale. */
+       deflocale = setlocale(LC_ALL, "en_US.ISO8859-1");
+       if (deflocale == 0)
+               deflocale = setlocale(LC_ALL, "");
+#endif
+
+       x = '\342';
+       r1 = isprint(x);
+       x -= 128;
+       r2 = isprint(x);
+       exit (r1 == 0 || r2 == 0);
+}
+], bash_cv_func_ctype_nonascii=yes, bash_cv_func_ctype_nonascii=no,
+   [AC_MSG_WARN(cannot check ctype macros if cross compiling -- defaulting to no)
+    bash_cv_func_ctype_nonascii=no]
+)])
+AC_MSG_RESULT($bash_cv_func_ctype_nonascii)
+if test $bash_cv_func_ctype_nonascii = yes; then
+AC_DEFINE(CTYPE_NON_ASCII)
+fi
+])
+
+dnl
+dnl tests added for bashdb
+dnl
+
+
+AC_DEFUN([AM_PATH_LISPDIR],
+ [AC_ARG_WITH(lispdir, AC_HELP_STRING([--with-lispdir], [override the default lisp directory]),
+  [ lispdir="$withval" 
+    AC_MSG_CHECKING([where .elc files should go])
+    AC_MSG_RESULT([$lispdir])],
+  [
+  # If set to t, that means we are running in a shell under Emacs.
+  # If you have an Emacs named "t", then use the full path.
+  test x"$EMACS" = xt && EMACS=
+  AC_CHECK_PROGS(EMACS, emacs xemacs, no)
+  if test $EMACS != "no"; then
+    if test x${lispdir+set} != xset; then
+      AC_CACHE_CHECK([where .elc files should go], [am_cv_lispdir], [dnl
+       am_cv_lispdir=`$EMACS -batch -q -eval '(while load-path (princ (concat (car load-path) "\n")) (setq load-path (cdr load-path)))' | sed -n -e 's,/$,,' -e '/.*\/lib\/\(x\?emacs\/site-lisp\)$/{s,,${libdir}/\1,;p;q;}' -e '/.*\/share\/\(x\?emacs\/site-lisp\)$/{s,,${datadir}/\1,;p;q;}'`
+       if test -z "$am_cv_lispdir"; then
+         am_cv_lispdir='${datadir}/emacs/site-lisp'
+       fi
+      ])
+      lispdir="$am_cv_lispdir"
+    fi
+  fi
+ ])
+ AC_SUBST(lispdir)
+])
+
+dnl
+dnl tests added for gettext
+dnl
+# codeset.m4 serial AM1 (gettext-0.10.40)
+dnl Copyright (C) 2000-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+AC_DEFUN([AM_LANGINFO_CODESET],
+[
+  AC_CACHE_CHECK([for nl_langinfo and CODESET], am_cv_langinfo_codeset,
+    [AC_TRY_LINK([#include <langinfo.h>],
+      [char* cs = nl_langinfo(CODESET);],
+      am_cv_langinfo_codeset=yes,
+      am_cv_langinfo_codeset=no)
+    ])
+  if test $am_cv_langinfo_codeset = yes; then
+    AC_DEFINE(HAVE_LANGINFO_CODESET, 1,
+      [Define if you have <langinfo.h> and nl_langinfo(CODESET).])
+  fi
+])
+# gettext.m4 serial 20 (gettext-0.12)
+dnl Copyright (C) 1995-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+dnl
+dnl This file can can be used in projects which are not available under
+dnl the GNU General Public License or the GNU Library General Public
+dnl License but which still want to provide support for the GNU gettext
+dnl functionality.
+dnl Please note that the actual code of the GNU gettext library is covered
+dnl by the GNU Library General Public License, and the rest of the GNU
+dnl gettext package package is covered by the GNU General Public License.
+dnl They are *not* in the public domain.
+
+dnl Authors:
+dnl   Ulrich Drepper <drepper@cygnus.com>, 1995-2000.
+dnl   Bruno Haible <haible@clisp.cons.org>, 2000-2003.
+
+dnl Macro to add for using GNU gettext.
+
+dnl Usage: AM_GNU_GETTEXT([INTLSYMBOL], [NEEDSYMBOL], [INTLDIR]).
+dnl INTLSYMBOL can be one of 'external', 'no-libtool', 'use-libtool'. The
+dnl    default (if it is not specified or empty) is 'no-libtool'.
+dnl    INTLSYMBOL should be 'external' for packages with no intl directory,
+dnl    and 'no-libtool' or 'use-libtool' for packages with an intl directory.
+dnl    If INTLSYMBOL is 'use-libtool', then a libtool library
+dnl    $(top_builddir)/intl/libintl.la will be created (shared and/or static,
+dnl    depending on --{enable,disable}-{shared,static} and on the presence of
+dnl    AM-DISABLE-SHARED). If INTLSYMBOL is 'no-libtool', a static library
+dnl    $(top_builddir)/intl/libintl.a will be created.
+dnl If NEEDSYMBOL is specified and is 'need-ngettext', then GNU gettext
+dnl    implementations (in libc or libintl) without the ngettext() function
+dnl    will be ignored.  If NEEDSYMBOL is specified and is
+dnl    'need-formatstring-macros', then GNU gettext implementations that don't
+dnl    support the ISO C 99 <inttypes.h> formatstring macros will be ignored.
+dnl INTLDIR is used to find the intl libraries.  If empty,
+dnl    the value `$(top_builddir)/intl/' is used.
+dnl
+dnl The result of the configuration is one of three cases:
+dnl 1) GNU gettext, as included in the intl subdirectory, will be compiled
+dnl    and used.
+dnl    Catalog format: GNU --> install in $(datadir)
+dnl    Catalog extension: .mo after installation, .gmo in source tree
+dnl 2) GNU gettext has been found in the system's C library.
+dnl    Catalog format: GNU --> install in $(datadir)
+dnl    Catalog extension: .mo after installation, .gmo in source tree
+dnl 3) No internationalization, always use English msgid.
+dnl    Catalog format: none
+dnl    Catalog extension: none
+dnl If INTLSYMBOL is 'external', only cases 2 and 3 can occur.
+dnl The use of .gmo is historical (it was needed to avoid overwriting the
+dnl GNU format catalogs when building on a platform with an X/Open gettext),
+dnl but we keep it in order not to force irrelevant filename changes on the
+dnl maintainers.
+dnl
+AC_DEFUN([AM_GNU_GETTEXT],
+[
+  dnl Argument checking.
+  ifelse([$1], [], , [ifelse([$1], [external], , [ifelse([$1], [no-libtool], , [ifelse([$1], [use-libtool], ,
+    [errprint([ERROR: invalid first argument to AM_GNU_GETTEXT
+])])])])])
+  ifelse([$2], [], , [ifelse([$2], [need-ngettext], , [ifelse([$2], [need-formatstring-macros], ,
+    [errprint([ERROR: invalid second argument to AM_GNU_GETTEXT
+])])])])
+  define(gt_included_intl, ifelse([$1], [external], [no], [yes]))
+  define(gt_libtool_suffix_prefix, ifelse([$1], [use-libtool], [l], []))
+
+  AC_REQUIRE([AM_PO_SUBDIRS])dnl
+  ifelse(gt_included_intl, yes, [
+    AC_REQUIRE([AM_INTL_SUBDIR])dnl
+  ])
+
+  dnl Prerequisites of AC_LIB_LINKFLAGS_BODY.
+  AC_REQUIRE([AC_LIB_PREPARE_PREFIX])
+  AC_REQUIRE([AC_LIB_RPATH])
+
+  dnl Sometimes libintl requires libiconv, so first search for libiconv.
+  dnl Ideally we would do this search only after the
+  dnl      if test "$USE_NLS" = "yes"; then
+  dnl        if test "$gt_cv_func_gnugettext_libc" != "yes"; then
+  dnl tests. But if configure.in invokes AM_ICONV after AM_GNU_GETTEXT
+  dnl the configure script would need to contain the same shell code
+  dnl again, outside any 'if'. There are two solutions:
+  dnl - Invoke AM_ICONV_LINKFLAGS_BODY here, outside any 'if'.
+  dnl - Control the expansions in more detail using AC_PROVIDE_IFELSE.
+  dnl Since AC_PROVIDE_IFELSE is only in autoconf >= 2.52 and not
+  dnl documented, we avoid it.
+  ifelse(gt_included_intl, yes, , [
+    AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY])
+  ])
+
+  dnl Set USE_NLS.
+  AM_NLS
+
+  ifelse(gt_included_intl, yes, [
+    BUILD_INCLUDED_LIBINTL=no
+    USE_INCLUDED_LIBINTL=no
+  ])
+  LIBINTL=
+  LTLIBINTL=
+  POSUB=
+
+  dnl If we use NLS figure out what method
+  if test "$USE_NLS" = "yes"; then
+    gt_use_preinstalled_gnugettext=no
+    ifelse(gt_included_intl, yes, [
+      AC_MSG_CHECKING([whether included gettext is requested])
+      AC_ARG_WITH(included-gettext,
+        [  --with-included-gettext use the GNU gettext library included here],
+        nls_cv_force_use_gnu_gettext=$withval,
+        nls_cv_force_use_gnu_gettext=no)
+      AC_MSG_RESULT($nls_cv_force_use_gnu_gettext)
+
+      nls_cv_use_gnu_gettext="$nls_cv_force_use_gnu_gettext"
+      if test "$nls_cv_force_use_gnu_gettext" != "yes"; then
+    ])
+        dnl User does not insist on using GNU NLS library.  Figure out what
+        dnl to use.  If GNU gettext is available we use this.  Else we have
+        dnl to fall back to GNU NLS library.
+
+        dnl Add a version number to the cache macros.
+        define([gt_api_version], ifelse([$2], [need-formatstring-macros], 3, ifelse([$2], [need-ngettext], 2, 1)))
+        define([gt_cv_func_gnugettext_libc], [gt_cv_func_gnugettext]gt_api_version[_libc])
+        define([gt_cv_func_gnugettext_libintl], [gt_cv_func_gnugettext]gt_api_version[_libintl])
+
+        AC_CACHE_CHECK([for GNU gettext in libc], gt_cv_func_gnugettext_libc,
+         [AC_TRY_LINK([#include <libintl.h>
+]ifelse([$2], [need-formatstring-macros],
+[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION
+#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1)
+#endif
+changequote(,)dnl
+typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1];
+changequote([,])dnl
+], [])[extern int _nl_msg_cat_cntr;
+extern int *_nl_domain_bindings;],
+            [bindtextdomain ("", "");
+return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_domain_bindings],
+            gt_cv_func_gnugettext_libc=yes,
+            gt_cv_func_gnugettext_libc=no)])
+
+        if test "$gt_cv_func_gnugettext_libc" != "yes"; then
+          dnl Sometimes libintl requires libiconv, so first search for libiconv.
+          ifelse(gt_included_intl, yes, , [
+            AM_ICONV_LINK
+          ])
+          dnl Search for libintl and define LIBINTL, LTLIBINTL and INCINTL
+          dnl accordingly. Don't use AC_LIB_LINKFLAGS_BODY([intl],[iconv])
+          dnl because that would add "-liconv" to LIBINTL and LTLIBINTL
+          dnl even if libiconv doesn't exist.
+          AC_LIB_LINKFLAGS_BODY([intl])
+          AC_CACHE_CHECK([for GNU gettext in libintl],
+            gt_cv_func_gnugettext_libintl,
+           [gt_save_CPPFLAGS="$CPPFLAGS"
+            CPPFLAGS="$CPPFLAGS $INCINTL"
+            gt_save_LIBS="$LIBS"
+            LIBS="$LIBS $LIBINTL"
+            dnl Now see whether libintl exists and does not depend on libiconv.
+            AC_TRY_LINK([#include <libintl.h>
+]ifelse([$2], [need-formatstring-macros],
+[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION
+#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1)
+#endif
+changequote(,)dnl
+typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1];
+changequote([,])dnl
+], [])[extern int _nl_msg_cat_cntr;
+extern
+#ifdef __cplusplus
+"C"
+#endif
+const char *_nl_expand_alias ();],
+              [bindtextdomain ("", "");
+return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_expand_alias (0)],
+              gt_cv_func_gnugettext_libintl=yes,
+              gt_cv_func_gnugettext_libintl=no)
+            dnl Now see whether libintl exists and depends on libiconv.
+            if test "$gt_cv_func_gnugettext_libintl" != yes && test -n "$LIBICONV"; then
+              LIBS="$LIBS $LIBICONV"
+              AC_TRY_LINK([#include <libintl.h>
+]ifelse([$2], [need-formatstring-macros],
+[#ifndef __GNU_GETTEXT_SUPPORTED_REVISION
+#define __GNU_GETTEXT_SUPPORTED_REVISION(major) ((major) == 0 ? 0 : -1)
+#endif
+changequote(,)dnl
+typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1];
+changequote([,])dnl
+], [])[extern int _nl_msg_cat_cntr;
+extern
+#ifdef __cplusplus
+"C"
+#endif
+const char *_nl_expand_alias ();],
+                [bindtextdomain ("", "");
+return (int) gettext ("")]ifelse([$2], [need-ngettext], [ + (int) ngettext ("", "", 0)], [])[ + _nl_msg_cat_cntr + *_nl_expand_alias (0)],
+               [LIBINTL="$LIBINTL $LIBICONV"
+                LTLIBINTL="$LTLIBINTL $LTLIBICONV"
+                gt_cv_func_gnugettext_libintl=yes
+               ])
+            fi
+            CPPFLAGS="$gt_save_CPPFLAGS"
+            LIBS="$gt_save_LIBS"])
+        fi
+
+        dnl If an already present or preinstalled GNU gettext() is found,
+        dnl use it.  But if this macro is used in GNU gettext, and GNU
+        dnl gettext is already preinstalled in libintl, we update this
+        dnl libintl.  (Cf. the install rule in intl/Makefile.in.)
+        if test "$gt_cv_func_gnugettext_libc" = "yes" \
+           || { test "$gt_cv_func_gnugettext_libintl" = "yes" \
+                && test "$PACKAGE" != gettext-runtime \
+                && test "$PACKAGE" != gettext-tools; }; then
+          gt_use_preinstalled_gnugettext=yes
+        else
+          dnl Reset the values set by searching for libintl.
+          LIBINTL=
+          LTLIBINTL=
+          INCINTL=
+        fi
+
+    ifelse(gt_included_intl, yes, [
+        if test "$gt_use_preinstalled_gnugettext" != "yes"; then
+          dnl GNU gettext is not found in the C library.
+          dnl Fall back on included GNU gettext library.
+          nls_cv_use_gnu_gettext=yes
+        fi
+      fi
+
+      if test "$nls_cv_use_gnu_gettext" = "yes"; then
+        dnl Mark actions used to generate GNU NLS library.
+        BUILD_INCLUDED_LIBINTL=yes
+        USE_INCLUDED_LIBINTL=yes
+        LIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LIBICONV"
+        LTLIBINTL="ifelse([$3],[],\${top_builddir}/intl,[$3])/libintl.[]gt_libtool_suffix_prefix[]a $LTLIBICONV"
+        LIBS=`echo " $LIBS " | sed -e 's/ -lintl / /' -e 's/^ //' -e 's/ $//'`
+      fi
+
+      if test "$gt_use_preinstalled_gnugettext" = "yes" \
+         || test "$nls_cv_use_gnu_gettext" = "yes"; then
+        dnl Mark actions to use GNU gettext tools.
+        CATOBJEXT=.gmo
+      fi
+    ])
+
+    if test "$gt_use_preinstalled_gnugettext" = "yes" \
+       || test "$nls_cv_use_gnu_gettext" = "yes"; then
+      AC_DEFINE(ENABLE_NLS, 1,
+        [Define to 1 if translation of program messages to the user's native language
+   is requested.])
+    else
+      USE_NLS=no
+    fi
+  fi
+
+  AC_MSG_CHECKING([whether to use NLS])
+  AC_MSG_RESULT([$USE_NLS])
+  if test "$USE_NLS" = "yes"; then
+    AC_MSG_CHECKING([where the gettext function comes from])
+    if test "$gt_use_preinstalled_gnugettext" = "yes"; then
+      if test "$gt_cv_func_gnugettext_libintl" = "yes"; then
+        gt_source="external libintl"
+      else
+        gt_source="libc"
+      fi
+    else
+      gt_source="included intl directory"
+    fi
+    AC_MSG_RESULT([$gt_source])
+  fi
+
+  if test "$USE_NLS" = "yes"; then
+
+    if test "$gt_use_preinstalled_gnugettext" = "yes"; then
+      if test "$gt_cv_func_gnugettext_libintl" = "yes"; then
+        AC_MSG_CHECKING([how to link with libintl])
+        AC_MSG_RESULT([$LIBINTL])
+        AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCINTL])
+      fi
+
+      dnl For backward compatibility. Some packages may be using this.
+      AC_DEFINE(HAVE_GETTEXT, 1,
+       [Define if the GNU gettext() function is already present or preinstalled.])
+      AC_DEFINE(HAVE_DCGETTEXT, 1,
+       [Define if the GNU dcgettext() function is already present or preinstalled.])
+    fi
+
+    dnl We need to process the po/ directory.
+    POSUB=po
+  fi
+
+  ifelse(gt_included_intl, yes, [
+    dnl If this is used in GNU gettext we have to set BUILD_INCLUDED_LIBINTL
+    dnl to 'yes' because some of the testsuite requires it.
+    if test "$PACKAGE" = gettext-runtime || test "$PACKAGE" = gettext-tools; then
+      BUILD_INCLUDED_LIBINTL=yes
+    fi
+
+    dnl Make all variables we use known to autoconf.
+    AC_SUBST(BUILD_INCLUDED_LIBINTL)
+    AC_SUBST(USE_INCLUDED_LIBINTL)
+    AC_SUBST(CATOBJEXT)
+
+    dnl For backward compatibility. Some configure.ins may be using this.
+    nls_cv_header_intl=
+    nls_cv_header_libgt=
+
+    dnl For backward compatibility. Some Makefiles may be using this.
+    DATADIRNAME=share
+    AC_SUBST(DATADIRNAME)
+
+    dnl For backward compatibility. Some Makefiles may be using this.
+    INSTOBJEXT=.mo
+    AC_SUBST(INSTOBJEXT)
+
+    dnl For backward compatibility. Some Makefiles may be using this.
+    GENCAT=gencat
+    AC_SUBST(GENCAT)
+
+    dnl For backward compatibility. Some Makefiles may be using this.
+    if test "$USE_INCLUDED_LIBINTL" = yes; then
+      INTLOBJS="\$(GETTOBJS)"
+    fi
+    AC_SUBST(INTLOBJS)
+
+    dnl Enable libtool support if the surrounding package wishes it.
+    INTL_LIBTOOL_SUFFIX_PREFIX=gt_libtool_suffix_prefix
+    AC_SUBST(INTL_LIBTOOL_SUFFIX_PREFIX)
+  ])
+
+  dnl For backward compatibility. Some Makefiles may be using this.
+  INTLLIBS="$LIBINTL"
+  AC_SUBST(INTLLIBS)
+
+  dnl Make all documented variables known to autoconf.
+  AC_SUBST(LIBINTL)
+  AC_SUBST(LTLIBINTL)
+  AC_SUBST(POSUB)
+])
+
+
+dnl Checks for all prerequisites of the intl subdirectory,
+dnl except for INTL_LIBTOOL_SUFFIX_PREFIX (and possibly LIBTOOL), INTLOBJS,
+dnl            USE_INCLUDED_LIBINTL, BUILD_INCLUDED_LIBINTL.
+AC_DEFUN([AM_INTL_SUBDIR],
+[
+  AC_REQUIRE([AC_PROG_INSTALL])dnl
+  AC_REQUIRE([AM_MKINSTALLDIRS])dnl
+  AC_REQUIRE([AC_PROG_CC])dnl
+  AC_REQUIRE([AC_CANONICAL_HOST])dnl
+  AC_REQUIRE([AC_PROG_RANLIB])dnl
+  AC_REQUIRE([AC_ISC_POSIX])dnl
+  AC_REQUIRE([AC_HEADER_STDC])dnl
+  AC_REQUIRE([AC_C_CONST])dnl
+  AC_REQUIRE([AC_C_INLINE])dnl
+  AC_REQUIRE([AC_TYPE_OFF_T])dnl
+  AC_REQUIRE([AC_TYPE_SIZE_T])dnl
+  AC_REQUIRE([AC_FUNC_ALLOCA])dnl
+  AC_REQUIRE([AC_FUNC_MMAP])dnl
+  AC_REQUIRE([jm_GLIBC21])dnl
+  AC_REQUIRE([gt_INTDIV0])dnl
+  AC_REQUIRE([jm_AC_TYPE_UINTMAX_T])dnl
+  AC_REQUIRE([gt_HEADER_INTTYPES_H])dnl
+  AC_REQUIRE([gt_INTTYPES_PRI])dnl
+
+  AC_CHECK_HEADERS([argz.h limits.h locale.h nl_types.h malloc.h stddef.h \
+stdlib.h string.h unistd.h sys/param.h])
+  AC_CHECK_FUNCS([feof_unlocked fgets_unlocked getc_unlocked getcwd getegid \
+geteuid getgid getuid mempcpy munmap putenv setenv setlocale stpcpy \
+strcasecmp strdup strtoul tsearch __argz_count __argz_stringify __argz_next \
+__fsetlocking])
+
+  AM_ICONV
+  AM_LANGINFO_CODESET
+  if test $ac_cv_header_locale_h = yes; then
+    AM_LC_MESSAGES
+  fi
+
+  dnl intl/plural.c is generated from intl/plural.y. It requires bison,
+  dnl because plural.y uses bison specific features. It requires at least
+  dnl bison-1.26 because earlier versions generate a plural.c that doesn't
+  dnl compile.
+  dnl bison is only needed for the maintainer (who touches plural.y). But in
+  dnl order to avoid separate Makefiles or --enable-maintainer-mode, we put
+  dnl the rule in general Makefile. Now, some people carelessly touch the
+  dnl files or have a broken "make" program, hence the plural.c rule will
+  dnl sometimes fire. To avoid an error, defines BISON to ":" if it is not
+  dnl present or too old.
+  AC_CHECK_PROGS([INTLBISON], [bison])
+  if test -z "$INTLBISON"; then
+    ac_verc_fail=yes
+  else
+    dnl Found it, now check the version.
+    AC_MSG_CHECKING([version of bison])
+changequote(<<,>>)dnl
+    ac_prog_version=`$INTLBISON --version 2>&1 | sed -n 's/^.*GNU Bison.* \([0-9]*\.[0-9.]*\).*$/\1/p'`
+    case $ac_prog_version in
+      '') ac_prog_version="v. ?.??, bad"; ac_verc_fail=yes;;
+      1.2[6-9]* | 1.[3-9][0-9]* | [2-9].*)
+changequote([,])dnl
+         ac_prog_version="$ac_prog_version, ok"; ac_verc_fail=no;;
+      *) ac_prog_version="$ac_prog_version, bad"; ac_verc_fail=yes;;
+    esac
+    AC_MSG_RESULT([$ac_prog_version])
+  fi
+  if test $ac_verc_fail = yes; then
+    INTLBISON=:
+  fi
+])
+
+
+dnl Usage: AM_GNU_GETTEXT_VERSION([gettext-version])
+AC_DEFUN([AM_GNU_GETTEXT_VERSION], [])
+# glibc21.m4 serial 2 (fileutils-4.1.3, gettext-0.10.40)
+dnl Copyright (C) 2000-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+# Test for the GNU C Library, version 2.1 or newer.
+# From Bruno Haible.
+
+AC_DEFUN([jm_GLIBC21],
+  [
+    AC_CACHE_CHECK(whether we are using the GNU C Library 2.1 or newer,
+      ac_cv_gnu_library_2_1,
+      [AC_EGREP_CPP([Lucky GNU user],
+       [
+#include <features.h>
+#ifdef __GNU_LIBRARY__
+ #if (__GLIBC__ == 2 && __GLIBC_MINOR__ >= 1) || (__GLIBC__ > 2)
+  Lucky GNU user
+ #endif
+#endif
+       ],
+       ac_cv_gnu_library_2_1=yes,
+       ac_cv_gnu_library_2_1=no)
+      ]
+    )
+    AC_SUBST(GLIBC21)
+    GLIBC21="$ac_cv_gnu_library_2_1"
+  ]
+)
+# iconv.m4 serial AM4 (gettext-0.11.3)
+dnl Copyright (C) 2000-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+AC_DEFUN([AM_ICONV_LINKFLAGS_BODY],
+[
+  dnl Prerequisites of AC_LIB_LINKFLAGS_BODY.
+  AC_REQUIRE([AC_LIB_PREPARE_PREFIX])
+  AC_REQUIRE([AC_LIB_RPATH])
+
+  dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV
+  dnl accordingly.
+  AC_LIB_LINKFLAGS_BODY([iconv])
+])
+
+AC_DEFUN([AM_ICONV_LINK],
+[
+  dnl Some systems have iconv in libc, some have it in libiconv (OSF/1 and
+  dnl those with the standalone portable GNU libiconv installed).
+
+  dnl Search for libiconv and define LIBICONV, LTLIBICONV and INCICONV
+  dnl accordingly.
+  AC_REQUIRE([AM_ICONV_LINKFLAGS_BODY])
+
+  dnl Add $INCICONV to CPPFLAGS before performing the following checks,
+  dnl because if the user has installed libiconv and not disabled its use
+  dnl via --without-libiconv-prefix, he wants to use it. The first
+  dnl AC_TRY_LINK will then fail, the second AC_TRY_LINK will succeed.
+  am_save_CPPFLAGS="$CPPFLAGS"
+  AC_LIB_APPENDTOVAR([CPPFLAGS], [$INCICONV])
+
+  AC_CACHE_CHECK(for iconv, am_cv_func_iconv, [
+    am_cv_func_iconv="no, consider installing GNU libiconv"
+    am_cv_lib_iconv=no
+    AC_TRY_LINK([#include <stdlib.h>
+#include <iconv.h>],
+      [iconv_t cd = iconv_open("","");
+       iconv(cd,NULL,NULL,NULL,NULL);
+       iconv_close(cd);],
+      am_cv_func_iconv=yes)
+    if test "$am_cv_func_iconv" != yes; then
+      am_save_LIBS="$LIBS"
+      LIBS="$LIBS $LIBICONV"
+      AC_TRY_LINK([#include <stdlib.h>
+#include <iconv.h>],
+        [iconv_t cd = iconv_open("","");
+         iconv(cd,NULL,NULL,NULL,NULL);
+         iconv_close(cd);],
+        am_cv_lib_iconv=yes
+        am_cv_func_iconv=yes)
+      LIBS="$am_save_LIBS"
+    fi
+  ])
+  if test "$am_cv_func_iconv" = yes; then
+    AC_DEFINE(HAVE_ICONV, 1, [Define if you have the iconv() function.])
+  fi
+  if test "$am_cv_lib_iconv" = yes; then
+    AC_MSG_CHECKING([how to link with libiconv])
+    AC_MSG_RESULT([$LIBICONV])
+  else
+    dnl If $LIBICONV didn't lead to a usable library, we don't need $INCICONV
+    dnl either.
+    CPPFLAGS="$am_save_CPPFLAGS"
+    LIBICONV=
+    LTLIBICONV=
+  fi
+  AC_SUBST(LIBICONV)
+  AC_SUBST(LTLIBICONV)
+])
+
+AC_DEFUN([AM_ICONV],
+[
+  AM_ICONV_LINK
+  if test "$am_cv_func_iconv" = yes; then
+    AC_MSG_CHECKING([for iconv declaration])
+    AC_CACHE_VAL(am_cv_proto_iconv, [
+      AC_TRY_COMPILE([
+#include <stdlib.h>
+#include <iconv.h>
+extern
+#ifdef __cplusplus
+"C"
+#endif
+#if defined(__STDC__) || defined(__cplusplus)
+size_t iconv (iconv_t cd, char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft);
+#else
+size_t iconv();
+#endif
+], [], am_cv_proto_iconv_arg1="", am_cv_proto_iconv_arg1="const")
+      am_cv_proto_iconv="extern size_t iconv (iconv_t cd, $am_cv_proto_iconv_arg1 char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft);"])
+    am_cv_proto_iconv=`echo "[$]am_cv_proto_iconv" | tr -s ' ' | sed -e 's/( /(/'`
+    AC_MSG_RESULT([$]{ac_t:-
+         }[$]am_cv_proto_iconv)
+    AC_DEFINE_UNQUOTED(ICONV_CONST, $am_cv_proto_iconv_arg1,
+      [Define as const if the declaration of iconv() needs const.])
+  fi
+])
+# intdiv0.m4 serial 1 (gettext-0.11.3)
+dnl Copyright (C) 2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+AC_DEFUN([gt_INTDIV0],
+[
+  AC_REQUIRE([AC_PROG_CC])dnl
+  AC_REQUIRE([AC_CANONICAL_HOST])dnl
+
+  AC_CACHE_CHECK([whether integer division by zero raises SIGFPE],
+    gt_cv_int_divbyzero_sigfpe,
+    [
+      AC_TRY_RUN([
+#include <stdlib.h>
+#include <signal.h>
+
+static void
+#ifdef __cplusplus
+sigfpe_handler (int sig)
+#else
+sigfpe_handler (sig) int sig;
+#endif
+{
+  /* Exit with code 0 if SIGFPE, with code 1 if any other signal.  */
+  exit (sig != SIGFPE);
+}
+
+int x = 1;
+int y = 0;
+int z;
+int nan;
+
+int main ()
+{
+  signal (SIGFPE, sigfpe_handler);
+/* IRIX and AIX (when "xlc -qcheck" is used) yield signal SIGTRAP.  */
+#if (defined (__sgi) || defined (_AIX)) && defined (SIGTRAP)
+  signal (SIGTRAP, sigfpe_handler);
+#endif
+/* Linux/SPARC yields signal SIGILL.  */
+#if defined (__sparc__) && defined (__linux__)
+  signal (SIGILL, sigfpe_handler);
+#endif
+
+  z = x / y;
+  nan = y / y;
+  exit (1);
+}
+], gt_cv_int_divbyzero_sigfpe=yes, gt_cv_int_divbyzero_sigfpe=no,
+        [
+          # Guess based on the CPU.
+          case "$host_cpu" in
+            alpha* | i[34567]86 | m68k | s390*)
+              gt_cv_int_divbyzero_sigfpe="guessing yes";;
+            *)
+              gt_cv_int_divbyzero_sigfpe="guessing no";;
+          esac
+        ])
+    ])
+  case "$gt_cv_int_divbyzero_sigfpe" in
+    *yes) value=1;;
+    *) value=0;;
+  esac
+  AC_DEFINE_UNQUOTED(INTDIV0_RAISES_SIGFPE, $value,
+    [Define if integer division by zero raises signal SIGFPE.])
+])
+# inttypes.m4 serial 1 (gettext-0.11.4)
+dnl Copyright (C) 1997-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Paul Eggert.
+
+# Define HAVE_INTTYPES_H if <inttypes.h> exists and doesn't clash with
+# <sys/types.h>.
+
+AC_DEFUN([gt_HEADER_INTTYPES_H],
+[
+  AC_CACHE_CHECK([for inttypes.h], gt_cv_header_inttypes_h,
+  [
+    AC_TRY_COMPILE(
+      [#include <sys/types.h>
+#include <inttypes.h>],
+      [], gt_cv_header_inttypes_h=yes, gt_cv_header_inttypes_h=no)
+  ])
+  if test $gt_cv_header_inttypes_h = yes; then
+    AC_DEFINE_UNQUOTED(HAVE_INTTYPES_H, 1,
+      [Define if <inttypes.h> exists and doesn't clash with <sys/types.h>.])
+  fi
+])
+# inttypes_h.m4 serial 5 (gettext-0.12)
+dnl Copyright (C) 1997-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Paul Eggert.
+
+# Define HAVE_INTTYPES_H_WITH_UINTMAX if <inttypes.h> exists,
+# doesn't clash with <sys/types.h>, and declares uintmax_t.
+
+AC_DEFUN([jm_AC_HEADER_INTTYPES_H],
+[
+  AC_CACHE_CHECK([for inttypes.h], jm_ac_cv_header_inttypes_h,
+  [AC_TRY_COMPILE(
+    [#include <sys/types.h>
+#include <inttypes.h>],
+    [uintmax_t i = (uintmax_t) -1;],
+    jm_ac_cv_header_inttypes_h=yes,
+    jm_ac_cv_header_inttypes_h=no)])
+  if test $jm_ac_cv_header_inttypes_h = yes; then
+    AC_DEFINE_UNQUOTED(HAVE_INTTYPES_H_WITH_UINTMAX, 1,
+      [Define if <inttypes.h> exists, doesn't clash with <sys/types.h>,
+       and declares uintmax_t. ])
+  fi
+])
+# inttypes-pri.m4 serial 1 (gettext-0.11.4)
+dnl Copyright (C) 1997-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+# Define PRI_MACROS_BROKEN if <inttypes.h> exists and defines the PRI*
+# macros to non-string values.  This is the case on AIX 4.3.3.
+
+AC_DEFUN([gt_INTTYPES_PRI],
+[
+  AC_REQUIRE([gt_HEADER_INTTYPES_H])
+  if test $gt_cv_header_inttypes_h = yes; then
+    AC_CACHE_CHECK([whether the inttypes.h PRIxNN macros are broken],
+      gt_cv_inttypes_pri_broken,
+      [
+        AC_TRY_COMPILE([#include <inttypes.h>
+#ifdef PRId32
+char *p = PRId32;
+#endif
+], [], gt_cv_inttypes_pri_broken=no, gt_cv_inttypes_pri_broken=yes)
+      ])
+  fi
+  if test "$gt_cv_inttypes_pri_broken" = yes; then
+    AC_DEFINE_UNQUOTED(PRI_MACROS_BROKEN, 1,
+      [Define if <inttypes.h> exists and defines unusable PRI* macros.])
+  fi
+])
+# isc-posix.m4 serial 2 (gettext-0.11.2)
+dnl Copyright (C) 1995-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+# This file is not needed with autoconf-2.53 and newer.  Remove it in 2005.
+
+# This test replaces the one in autoconf.
+# Currently this macro should have the same name as the autoconf macro
+# because gettext's gettext.m4 (distributed in the automake package)
+# still uses it.  Otherwise, the use in gettext.m4 makes autoheader
+# give these diagnostics:
+#   configure.in:556: AC_TRY_COMPILE was called before AC_ISC_POSIX
+#   configure.in:556: AC_TRY_RUN was called before AC_ISC_POSIX
+
+undefine([AC_ISC_POSIX])
+
+AC_DEFUN([AC_ISC_POSIX],
+  [
+    dnl This test replaces the obsolescent AC_ISC_POSIX kludge.
+    AC_CHECK_LIB(cposix, strerror, [LIBS="$LIBS -lcposix"])
+  ]
+)
+# lcmessage.m4 serial 3 (gettext-0.11.3)
+dnl Copyright (C) 1995-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+dnl
+dnl This file can can be used in projects which are not available under
+dnl the GNU General Public License or the GNU Library General Public
+dnl License but which still want to provide support for the GNU gettext
+dnl functionality.
+dnl Please note that the actual code of the GNU gettext library is covered
+dnl by the GNU Library General Public License, and the rest of the GNU
+dnl gettext package package is covered by the GNU General Public License.
+dnl They are *not* in the public domain.
+
+dnl Authors:
+dnl   Ulrich Drepper <drepper@cygnus.com>, 1995.
+
+# Check whether LC_MESSAGES is available in <locale.h>.
+
+AC_DEFUN([AM_LC_MESSAGES],
+[
+  AC_CACHE_CHECK([for LC_MESSAGES], am_cv_val_LC_MESSAGES,
+    [AC_TRY_LINK([#include <locale.h>], [return LC_MESSAGES],
+       am_cv_val_LC_MESSAGES=yes, am_cv_val_LC_MESSAGES=no)])
+  if test $am_cv_val_LC_MESSAGES = yes; then
+    AC_DEFINE(HAVE_LC_MESSAGES, 1,
+      [Define if your <locale.h> file defines LC_MESSAGES.])
+  fi
+])
+# lib-ld.m4 serial 2 (gettext-0.12)
+dnl Copyright (C) 1996-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl Subroutines of libtool.m4,
+dnl with replacements s/AC_/AC_LIB/ and s/lt_cv/acl_cv/ to avoid collision
+dnl with libtool.m4.
+
+dnl From libtool-1.4. Sets the variable with_gnu_ld to yes or no.
+AC_DEFUN([AC_LIB_PROG_LD_GNU],
+[AC_CACHE_CHECK([if the linker ($LD) is GNU ld], acl_cv_prog_gnu_ld,
+[# I'd rather use --version here, but apparently some GNU ld's only accept -v.
+if $LD -v 2>&1 </dev/null | egrep '(GNU|with BFD)' 1>&5; then
+  acl_cv_prog_gnu_ld=yes
+else
+  acl_cv_prog_gnu_ld=no
+fi])
+with_gnu_ld=$acl_cv_prog_gnu_ld
+])
+
+dnl From libtool-1.4. Sets the variable LD.
+AC_DEFUN([AC_LIB_PROG_LD],
+[AC_ARG_WITH(gnu-ld,
+[  --with-gnu-ld           assume the C compiler uses GNU ld [default=no]],
+test "$withval" = no || with_gnu_ld=yes, with_gnu_ld=no)
+AC_REQUIRE([AC_PROG_CC])dnl
+AC_REQUIRE([AC_CANONICAL_HOST])dnl
+# Prepare PATH_SEPARATOR.
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+  echo "#! /bin/sh" >conf$$.sh
+  echo  "exit 0"   >>conf$$.sh
+  chmod +x conf$$.sh
+  if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then
+    PATH_SEPARATOR=';'
+  else
+    PATH_SEPARATOR=:
+  fi
+  rm -f conf$$.sh
+fi
+ac_prog=ld
+if test "$GCC" = yes; then
+  # Check if gcc -print-prog-name=ld gives a path.
+  AC_MSG_CHECKING([for ld used by GCC])
+  case $host in
+  *-*-mingw*)
+    # gcc leaves a trailing carriage return which upsets mingw
+    ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;;
+  *)
+    ac_prog=`($CC -print-prog-name=ld) 2>&5` ;;
+  esac
+  case $ac_prog in
+    # Accept absolute paths.
+    [[\\/]* | [A-Za-z]:[\\/]*)]
+      [re_direlt='/[^/][^/]*/\.\./']
+      # Canonicalize the path of ld
+      ac_prog=`echo $ac_prog| sed 's%\\\\%/%g'`
+      while echo $ac_prog | grep "$re_direlt" > /dev/null 2>&1; do
+       ac_prog=`echo $ac_prog| sed "s%$re_direlt%/%"`
+      done
+      test -z "$LD" && LD="$ac_prog"
+      ;;
+  "")
+    # If it fails, then pretend we aren't using GCC.
+    ac_prog=ld
+    ;;
+  *)
+    # If it is relative, then search for the first ld in PATH.
+    with_gnu_ld=unknown
+    ;;
+  esac
+elif test "$with_gnu_ld" = yes; then
+  AC_MSG_CHECKING([for GNU ld])
+else
+  AC_MSG_CHECKING([for non-GNU ld])
+fi
+AC_CACHE_VAL(acl_cv_path_LD,
+[if test -z "$LD"; then
+  IFS="${IFS=  }"; ac_save_ifs="$IFS"; IFS="${IFS}${PATH_SEPARATOR-:}"
+  for ac_dir in $PATH; do
+    test -z "$ac_dir" && ac_dir=.
+    if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then
+      acl_cv_path_LD="$ac_dir/$ac_prog"
+      # Check to see if the program is GNU ld.  I'd rather use --version,
+      # but apparently some GNU ld's only accept -v.
+      # Break only if it was the GNU/non-GNU ld that we prefer.
+      if "$acl_cv_path_LD" -v 2>&1 < /dev/null | egrep '(GNU|with BFD)' > /dev/null; then
+       test "$with_gnu_ld" != no && break
+      else
+       test "$with_gnu_ld" != yes && break
+      fi
+    fi
+  done
+  IFS="$ac_save_ifs"
+else
+  acl_cv_path_LD="$LD" # Let the user override the test with a path.
+fi])
+LD="$acl_cv_path_LD"
+if test -n "$LD"; then
+  AC_MSG_RESULT($LD)
+else
+  AC_MSG_RESULT(no)
+fi
+test -z "$LD" && AC_MSG_ERROR([no acceptable ld found in \$PATH])
+AC_LIB_PROG_LD_GNU
+])
+# lib-link.m4 serial 4 (gettext-0.12)
+dnl Copyright (C) 2001-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+dnl AC_LIB_LINKFLAGS(name [, dependencies]) searches for libname and
+dnl the libraries corresponding to explicit and implicit dependencies.
+dnl Sets and AC_SUBSTs the LIB${NAME} and LTLIB${NAME} variables and
+dnl augments the CPPFLAGS variable.
+AC_DEFUN([AC_LIB_LINKFLAGS],
+[
+  AC_REQUIRE([AC_LIB_PREPARE_PREFIX])
+  AC_REQUIRE([AC_LIB_RPATH])
+  define([Name],[translit([$1],[./-], [___])])
+  define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-],
+                               [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])])
+  AC_CACHE_CHECK([how to link with lib[]$1], [ac_cv_lib[]Name[]_libs], [
+    AC_LIB_LINKFLAGS_BODY([$1], [$2])
+    ac_cv_lib[]Name[]_libs="$LIB[]NAME"
+    ac_cv_lib[]Name[]_ltlibs="$LTLIB[]NAME"
+    ac_cv_lib[]Name[]_cppflags="$INC[]NAME"
+  ])
+  LIB[]NAME="$ac_cv_lib[]Name[]_libs"
+  LTLIB[]NAME="$ac_cv_lib[]Name[]_ltlibs"
+  INC[]NAME="$ac_cv_lib[]Name[]_cppflags"
+  AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME)
+  AC_SUBST([LIB]NAME)
+  AC_SUBST([LTLIB]NAME)
+  dnl Also set HAVE_LIB[]NAME so that AC_LIB_HAVE_LINKFLAGS can reuse the
+  dnl results of this search when this library appears as a dependency.
+  HAVE_LIB[]NAME=yes
+  undefine([Name])
+  undefine([NAME])
+])
+
+dnl AC_LIB_HAVE_LINKFLAGS(name, dependencies, includes, testcode)
+dnl searches for libname and the libraries corresponding to explicit and
+dnl implicit dependencies, together with the specified include files and
+dnl the ability to compile and link the specified testcode. If found, it
+dnl sets and AC_SUBSTs HAVE_LIB${NAME}=yes and the LIB${NAME} and
+dnl LTLIB${NAME} variables and augments the CPPFLAGS variable, and
+dnl #defines HAVE_LIB${NAME} to 1. Otherwise, it sets and AC_SUBSTs
+dnl HAVE_LIB${NAME}=no and LIB${NAME} and LTLIB${NAME} to empty.
+AC_DEFUN([AC_LIB_HAVE_LINKFLAGS],
+[
+  AC_REQUIRE([AC_LIB_PREPARE_PREFIX])
+  AC_REQUIRE([AC_LIB_RPATH])
+  define([Name],[translit([$1],[./-], [___])])
+  define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-],
+                               [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])])
+
+  dnl Search for lib[]Name and define LIB[]NAME, LTLIB[]NAME and INC[]NAME
+  dnl accordingly.
+  AC_LIB_LINKFLAGS_BODY([$1], [$2])
+
+  dnl Add $INC[]NAME to CPPFLAGS before performing the following checks,
+  dnl because if the user has installed lib[]Name and not disabled its use
+  dnl via --without-lib[]Name-prefix, he wants to use it.
+  ac_save_CPPFLAGS="$CPPFLAGS"
+  AC_LIB_APPENDTOVAR([CPPFLAGS], [$INC]NAME)
+
+  AC_CACHE_CHECK([for lib[]$1], [ac_cv_lib[]Name], [
+    ac_save_LIBS="$LIBS"
+    LIBS="$LIBS $LIB[]NAME"
+    AC_TRY_LINK([$3], [$4], [ac_cv_lib[]Name=yes], [ac_cv_lib[]Name=no])
+    LIBS="$ac_save_LIBS"
+  ])
+  if test "$ac_cv_lib[]Name" = yes; then
+    HAVE_LIB[]NAME=yes
+    AC_DEFINE([HAVE_LIB]NAME, 1, [Define if you have the $1 library.])
+    AC_MSG_CHECKING([how to link with lib[]$1])
+    AC_MSG_RESULT([$LIB[]NAME])
+  else
+    HAVE_LIB[]NAME=no
+    dnl If $LIB[]NAME didn't lead to a usable library, we don't need
+    dnl $INC[]NAME either.
+    CPPFLAGS="$ac_save_CPPFLAGS"
+    LIB[]NAME=
+    LTLIB[]NAME=
+  fi
+  AC_SUBST([HAVE_LIB]NAME)
+  AC_SUBST([LIB]NAME)
+  AC_SUBST([LTLIB]NAME)
+  undefine([Name])
+  undefine([NAME])
+])
+
+dnl Determine the platform dependent parameters needed to use rpath:
+dnl libext, shlibext, hardcode_libdir_flag_spec, hardcode_libdir_separator,
+dnl hardcode_direct, hardcode_minus_L.
+AC_DEFUN([AC_LIB_RPATH],
+[
+  AC_REQUIRE([AC_PROG_CC])                dnl we use $CC, $GCC, $LDFLAGS
+  AC_REQUIRE([AC_LIB_PROG_LD])            dnl we use $LD, $with_gnu_ld
+  AC_REQUIRE([AC_CANONICAL_HOST])         dnl we use $host
+  AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT]) dnl we use $ac_aux_dir
+  AC_CACHE_CHECK([for shared library run path origin], acl_cv_rpath, [
+    CC="$CC" GCC="$GCC" LDFLAGS="$LDFLAGS" LD="$LD" with_gnu_ld="$with_gnu_ld" \
+    ${CONFIG_SHELL-/bin/sh} "$ac_aux_dir/config.rpath" "$host" > conftest.sh
+    . ./conftest.sh
+    rm -f ./conftest.sh
+    acl_cv_rpath=done
+  ])
+  wl="$acl_cv_wl"
+  libext="$acl_cv_libext"
+  shlibext="$acl_cv_shlibext"
+  hardcode_libdir_flag_spec="$acl_cv_hardcode_libdir_flag_spec"
+  hardcode_libdir_separator="$acl_cv_hardcode_libdir_separator"
+  hardcode_direct="$acl_cv_hardcode_direct"
+  hardcode_minus_L="$acl_cv_hardcode_minus_L"
+  dnl Determine whether the user wants rpath handling at all.
+  AC_ARG_ENABLE(rpath,
+    [  --disable-rpath         do not hardcode runtime library paths],
+    :, enable_rpath=yes)
+])
+
+dnl AC_LIB_LINKFLAGS_BODY(name [, dependencies]) searches for libname and
+dnl the libraries corresponding to explicit and implicit dependencies.
+dnl Sets the LIB${NAME}, LTLIB${NAME} and INC${NAME} variables.
+AC_DEFUN([AC_LIB_LINKFLAGS_BODY],
+[
+  define([NAME],[translit([$1],[abcdefghijklmnopqrstuvwxyz./-],
+                               [ABCDEFGHIJKLMNOPQRSTUVWXYZ___])])
+  dnl By default, look in $includedir and $libdir.
+  use_additional=yes
+  AC_LIB_WITH_FINAL_PREFIX([
+    eval additional_includedir=\"$includedir\"
+    eval additional_libdir=\"$libdir\"
+  ])
+  AC_LIB_ARG_WITH([lib$1-prefix],
+[  --with-lib$1-prefix[=DIR]  search for lib$1 in DIR/include and DIR/lib
+  --without-lib$1-prefix     don't search for lib$1 in includedir and libdir],
+[
+    if test "X$withval" = "Xno"; then
+      use_additional=no
+    else
+      if test "X$withval" = "X"; then
+        AC_LIB_WITH_FINAL_PREFIX([
+          eval additional_includedir=\"$includedir\"
+          eval additional_libdir=\"$libdir\"
+        ])
+      else
+        additional_includedir="$withval/include"
+        additional_libdir="$withval/lib"
+      fi
+    fi
+])
+  dnl Search the library and its dependencies in $additional_libdir and
+  dnl $LDFLAGS. Using breadth-first-seach.
+  LIB[]NAME=
+  LTLIB[]NAME=
+  INC[]NAME=
+  rpathdirs=
+  ltrpathdirs=
+  names_already_handled=
+  names_next_round='$1 $2'
+  while test -n "$names_next_round"; do
+    names_this_round="$names_next_round"
+    names_next_round=
+    for name in $names_this_round; do
+      already_handled=
+      for n in $names_already_handled; do
+        if test "$n" = "$name"; then
+          already_handled=yes
+          break
+        fi
+      done
+      if test -z "$already_handled"; then
+        names_already_handled="$names_already_handled $name"
+        dnl See if it was already located by an earlier AC_LIB_LINKFLAGS
+        dnl or AC_LIB_HAVE_LINKFLAGS call.
+        uppername=`echo "$name" | sed -e 'y|abcdefghijklmnopqrstuvwxyz./-|ABCDEFGHIJKLMNOPQRSTUVWXYZ___|'`
+        eval value=\"\$HAVE_LIB$uppername\"
+        if test -n "$value"; then
+          if test "$value" = yes; then
+            eval value=\"\$LIB$uppername\"
+            test -z "$value" || LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$value"
+            eval value=\"\$LTLIB$uppername\"
+            test -z "$value" || LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$value"
+          else
+            dnl An earlier call to AC_LIB_HAVE_LINKFLAGS has determined
+            dnl that this library doesn't exist. So just drop it.
+            :
+          fi
+        else
+          dnl Search the library lib$name in $additional_libdir and $LDFLAGS
+          dnl and the already constructed $LIBNAME/$LTLIBNAME.
+          found_dir=
+          found_la=
+          found_so=
+          found_a=
+          if test $use_additional = yes; then
+            if test -n "$shlibext" && test -f "$additional_libdir/lib$name.$shlibext"; then
+              found_dir="$additional_libdir"
+              found_so="$additional_libdir/lib$name.$shlibext"
+              if test -f "$additional_libdir/lib$name.la"; then
+                found_la="$additional_libdir/lib$name.la"
+              fi
+            else
+              if test -f "$additional_libdir/lib$name.$libext"; then
+                found_dir="$additional_libdir"
+                found_a="$additional_libdir/lib$name.$libext"
+                if test -f "$additional_libdir/lib$name.la"; then
+                  found_la="$additional_libdir/lib$name.la"
+                fi
+              fi
+            fi
+          fi
+          if test "X$found_dir" = "X"; then
+            for x in $LDFLAGS $LTLIB[]NAME; do
+              AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+              case "$x" in
+                -L*)
+                  dir=`echo "X$x" | sed -e 's/^X-L//'`
+                  if test -n "$shlibext" && test -f "$dir/lib$name.$shlibext"; then
+                    found_dir="$dir"
+                    found_so="$dir/lib$name.$shlibext"
+                    if test -f "$dir/lib$name.la"; then
+                      found_la="$dir/lib$name.la"
+                    fi
+                  else
+                    if test -f "$dir/lib$name.$libext"; then
+                      found_dir="$dir"
+                      found_a="$dir/lib$name.$libext"
+                      if test -f "$dir/lib$name.la"; then
+                        found_la="$dir/lib$name.la"
+                      fi
+                    fi
+                  fi
+                  ;;
+              esac
+              if test "X$found_dir" != "X"; then
+                break
+              fi
+            done
+          fi
+          if test "X$found_dir" != "X"; then
+            dnl Found the library.
+            LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$found_dir -l$name"
+            if test "X$found_so" != "X"; then
+              dnl Linking with a shared library. We attempt to hardcode its
+              dnl directory into the executable's runpath, unless it's the
+              dnl standard /usr/lib.
+              if test "$enable_rpath" = no || test "X$found_dir" = "X/usr/lib"; then
+                dnl No hardcoding is needed.
+                LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so"
+              else
+                dnl Use an explicit option to hardcode DIR into the resulting
+                dnl binary.
+                dnl Potentially add DIR to ltrpathdirs.
+                dnl The ltrpathdirs will be appended to $LTLIBNAME at the end.
+                haveit=
+                for x in $ltrpathdirs; do
+                  if test "X$x" = "X$found_dir"; then
+                    haveit=yes
+                    break
+                  fi
+                done
+                if test -z "$haveit"; then
+                  ltrpathdirs="$ltrpathdirs $found_dir"
+                fi
+                dnl The hardcoding into $LIBNAME is system dependent.
+                if test "$hardcode_direct" = yes; then
+                  dnl Using DIR/libNAME.so during linking hardcodes DIR into the
+                  dnl resulting binary.
+                  LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so"
+                else
+                  if test -n "$hardcode_libdir_flag_spec" && test "$hardcode_minus_L" = no; then
+                    dnl Use an explicit option to hardcode DIR into the resulting
+                    dnl binary.
+                    LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so"
+                    dnl Potentially add DIR to rpathdirs.
+                    dnl The rpathdirs will be appended to $LIBNAME at the end.
+                    haveit=
+                    for x in $rpathdirs; do
+                      if test "X$x" = "X$found_dir"; then
+                        haveit=yes
+                        break
+                      fi
+                    done
+                    if test -z "$haveit"; then
+                      rpathdirs="$rpathdirs $found_dir"
+                    fi
+                  else
+                    dnl Rely on "-L$found_dir".
+                    dnl But don't add it if it's already contained in the LDFLAGS
+                    dnl or the already constructed $LIBNAME
+                    haveit=
+                    for x in $LDFLAGS $LIB[]NAME; do
+                      AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+                      if test "X$x" = "X-L$found_dir"; then
+                        haveit=yes
+                        break
+                      fi
+                    done
+                    if test -z "$haveit"; then
+                      LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir"
+                    fi
+                    if test "$hardcode_minus_L" != no; then
+                      dnl FIXME: Not sure whether we should use
+                      dnl "-L$found_dir -l$name" or "-L$found_dir $found_so"
+                      dnl here.
+                      LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_so"
+                    else
+                      dnl We cannot use $hardcode_runpath_var and LD_RUN_PATH
+                      dnl here, because this doesn't fit in flags passed to the
+                      dnl compiler. So give up. No hardcoding. This affects only
+                      dnl very old systems.
+                      dnl FIXME: Not sure whether we should use
+                      dnl "-L$found_dir -l$name" or "-L$found_dir $found_so"
+                      dnl here.
+                      LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name"
+                    fi
+                  fi
+                fi
+              fi
+            else
+              if test "X$found_a" != "X"; then
+                dnl Linking with a static library.
+                LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$found_a"
+              else
+                dnl We shouldn't come here, but anyway it's good to have a
+                dnl fallback.
+                LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$found_dir -l$name"
+              fi
+            fi
+            dnl Assume the include files are nearby.
+            additional_includedir=
+            case "$found_dir" in
+              */lib | */lib/)
+                basedir=`echo "X$found_dir" | sed -e 's,^X,,' -e 's,/lib/*$,,'`
+                additional_includedir="$basedir/include"
+                ;;
+            esac
+            if test "X$additional_includedir" != "X"; then
+              dnl Potentially add $additional_includedir to $INCNAME.
+              dnl But don't add it
+              dnl   1. if it's the standard /usr/include,
+              dnl   2. if it's /usr/local/include and we are using GCC on Linux,
+              dnl   3. if it's already present in $CPPFLAGS or the already
+              dnl      constructed $INCNAME,
+              dnl   4. if it doesn't exist as a directory.
+              if test "X$additional_includedir" != "X/usr/include"; then
+                haveit=
+                if test "X$additional_includedir" = "X/usr/local/include"; then
+                  if test -n "$GCC"; then
+                    case $host_os in
+                      linux*) haveit=yes;;
+                    esac
+                  fi
+                fi
+                if test -z "$haveit"; then
+                  for x in $CPPFLAGS $INC[]NAME; do
+                    AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+                    if test "X$x" = "X-I$additional_includedir"; then
+                      haveit=yes
+                      break
+                    fi
+                  done
+                  if test -z "$haveit"; then
+                    if test -d "$additional_includedir"; then
+                      dnl Really add $additional_includedir to $INCNAME.
+                      INC[]NAME="${INC[]NAME}${INC[]NAME:+ }-I$additional_includedir"
+                    fi
+                  fi
+                fi
+              fi
+            fi
+            dnl Look for dependencies.
+            if test -n "$found_la"; then
+              dnl Read the .la file. It defines the variables
+              dnl dlname, library_names, old_library, dependency_libs, current,
+              dnl age, revision, installed, dlopen, dlpreopen, libdir.
+              save_libdir="$libdir"
+              case "$found_la" in
+                */* | *\\*) . "$found_la" ;;
+                *) . "./$found_la" ;;
+              esac
+              libdir="$save_libdir"
+              dnl We use only dependency_libs.
+              for dep in $dependency_libs; do
+                case "$dep" in
+                  -L*)
+                    additional_libdir=`echo "X$dep" | sed -e 's/^X-L//'`
+                    dnl Potentially add $additional_libdir to $LIBNAME and $LTLIBNAME.
+                    dnl But don't add it
+                    dnl   1. if it's the standard /usr/lib,
+                    dnl   2. if it's /usr/local/lib and we are using GCC on Linux,
+                    dnl   3. if it's already present in $LDFLAGS or the already
+                    dnl      constructed $LIBNAME,
+                    dnl   4. if it doesn't exist as a directory.
+                    if test "X$additional_libdir" != "X/usr/lib"; then
+                      haveit=
+                      if test "X$additional_libdir" = "X/usr/local/lib"; then
+                        if test -n "$GCC"; then
+                          case $host_os in
+                            linux*) haveit=yes;;
+                          esac
+                        fi
+                      fi
+                      if test -z "$haveit"; then
+                        haveit=
+                        for x in $LDFLAGS $LIB[]NAME; do
+                          AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+                          if test "X$x" = "X-L$additional_libdir"; then
+                            haveit=yes
+                            break
+                          fi
+                        done
+                        if test -z "$haveit"; then
+                          if test -d "$additional_libdir"; then
+                            dnl Really add $additional_libdir to $LIBNAME.
+                            LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-L$additional_libdir"
+                          fi
+                        fi
+                        haveit=
+                        for x in $LDFLAGS $LTLIB[]NAME; do
+                          AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+                          if test "X$x" = "X-L$additional_libdir"; then
+                            haveit=yes
+                            break
+                          fi
+                        done
+                        if test -z "$haveit"; then
+                          if test -d "$additional_libdir"; then
+                            dnl Really add $additional_libdir to $LTLIBNAME.
+                            LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-L$additional_libdir"
+                          fi
+                        fi
+                      fi
+                    fi
+                    ;;
+                  -R*)
+                    dir=`echo "X$dep" | sed -e 's/^X-R//'`
+                    if test "$enable_rpath" != no; then
+                      dnl Potentially add DIR to rpathdirs.
+                      dnl The rpathdirs will be appended to $LIBNAME at the end.
+                      haveit=
+                      for x in $rpathdirs; do
+                        if test "X$x" = "X$dir"; then
+                          haveit=yes
+                          break
+                        fi
+                      done
+                      if test -z "$haveit"; then
+                        rpathdirs="$rpathdirs $dir"
+                      fi
+                      dnl Potentially add DIR to ltrpathdirs.
+                      dnl The ltrpathdirs will be appended to $LTLIBNAME at the end.
+                      haveit=
+                      for x in $ltrpathdirs; do
+                        if test "X$x" = "X$dir"; then
+                          haveit=yes
+                          break
+                        fi
+                      done
+                      if test -z "$haveit"; then
+                        ltrpathdirs="$ltrpathdirs $dir"
+                      fi
+                    fi
+                    ;;
+                  -l*)
+                    dnl Handle this in the next round.
+                    names_next_round="$names_next_round "`echo "X$dep" | sed -e 's/^X-l//'`
+                    ;;
+                  *.la)
+                    dnl Handle this in the next round. Throw away the .la's
+                    dnl directory; it is already contained in a preceding -L
+                    dnl option.
+                    names_next_round="$names_next_round "`echo "X$dep" | sed -e 's,^X.*/,,' -e 's,^lib,,' -e 's,\.la$,,'`
+                    ;;
+                  *)
+                    dnl Most likely an immediate library name.
+                    LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$dep"
+                    LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }$dep"
+                    ;;
+                esac
+              done
+            fi
+          else
+            dnl Didn't find the library; assume it is in the system directories
+            dnl known to the linker and runtime loader. (All the system
+            dnl directories known to the linker should also be known to the
+            dnl runtime loader, otherwise the system is severely misconfigured.)
+            LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }-l$name"
+            LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-l$name"
+          fi
+        fi
+      fi
+    done
+  done
+  if test "X$rpathdirs" != "X"; then
+    if test -n "$hardcode_libdir_separator"; then
+      dnl Weird platform: only the last -rpath option counts, the user must
+      dnl pass all path elements in one option. We can arrange that for a
+      dnl single library, but not when more than one $LIBNAMEs are used.
+      alldirs=
+      for found_dir in $rpathdirs; do
+        alldirs="${alldirs}${alldirs:+$hardcode_libdir_separator}$found_dir"
+      done
+      dnl Note: hardcode_libdir_flag_spec uses $libdir and $wl.
+      acl_save_libdir="$libdir"
+      libdir="$alldirs"
+      eval flag=\"$hardcode_libdir_flag_spec\"
+      libdir="$acl_save_libdir"
+      LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag"
+    else
+      dnl The -rpath options are cumulative.
+      for found_dir in $rpathdirs; do
+        acl_save_libdir="$libdir"
+        libdir="$found_dir"
+        eval flag=\"$hardcode_libdir_flag_spec\"
+        libdir="$acl_save_libdir"
+        LIB[]NAME="${LIB[]NAME}${LIB[]NAME:+ }$flag"
+      done
+    fi
+  fi
+  if test "X$ltrpathdirs" != "X"; then
+    dnl When using libtool, the option that works for both libraries and
+    dnl executables is -R. The -R options are cumulative.
+    for found_dir in $ltrpathdirs; do
+      LTLIB[]NAME="${LTLIB[]NAME}${LTLIB[]NAME:+ }-R$found_dir"
+    done
+  fi
+])
+
+dnl AC_LIB_APPENDTOVAR(VAR, CONTENTS) appends the elements of CONTENTS to VAR,
+dnl unless already present in VAR.
+dnl Works only for CPPFLAGS, not for LIB* variables because that sometimes
+dnl contains two or three consecutive elements that belong together.
+AC_DEFUN([AC_LIB_APPENDTOVAR],
+[
+  for element in [$2]; do
+    haveit=
+    for x in $[$1]; do
+      AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+      if test "X$x" = "X$element"; then
+        haveit=yes
+        break
+      fi
+    done
+    if test -z "$haveit"; then
+      [$1]="${[$1]}${[$1]:+ }$element"
+    fi
+  done
+])
+# lib-prefix.m4 serial 2 (gettext-0.12)
+dnl Copyright (C) 2001-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Bruno Haible.
+
+dnl AC_LIB_ARG_WITH is synonymous to AC_ARG_WITH in autoconf-2.13, and
+dnl similar to AC_ARG_WITH in autoconf 2.52...2.57 except that is doesn't
+dnl require excessive bracketing.
+ifdef([AC_HELP_STRING],
+[AC_DEFUN([AC_LIB_ARG_WITH], [AC_ARG_WITH([$1],[[$2]],[$3],[$4])])],
+[AC_DEFUN([AC_LIB_ARG_WITH], [AC_ARG_WITH([$1],[$2],[$3],[$4])])])
+
+dnl AC_LIB_PREFIX adds to the CPPFLAGS and LDFLAGS the flags that are needed
+dnl to access previously installed libraries. The basic assumption is that
+dnl a user will want packages to use other packages he previously installed
+dnl with the same --prefix option.
+dnl This macro is not needed if only AC_LIB_LINKFLAGS is used to locate
+dnl libraries, but is otherwise very convenient.
+AC_DEFUN([AC_LIB_PREFIX],
+[
+  AC_BEFORE([$0], [AC_LIB_LINKFLAGS])
+  AC_REQUIRE([AC_PROG_CC])
+  AC_REQUIRE([AC_CANONICAL_HOST])
+  AC_REQUIRE([AC_LIB_PREPARE_PREFIX])
+  dnl By default, look in $includedir and $libdir.
+  use_additional=yes
+  AC_LIB_WITH_FINAL_PREFIX([
+    eval additional_includedir=\"$includedir\"
+    eval additional_libdir=\"$libdir\"
+  ])
+  AC_LIB_ARG_WITH([lib-prefix],
+[  --with-lib-prefix[=DIR] search for libraries in DIR/include and DIR/lib
+  --without-lib-prefix    don't search for libraries in includedir and libdir],
+[
+    if test "X$withval" = "Xno"; then
+      use_additional=no
+    else
+      if test "X$withval" = "X"; then
+        AC_LIB_WITH_FINAL_PREFIX([
+          eval additional_includedir=\"$includedir\"
+          eval additional_libdir=\"$libdir\"
+        ])
+      else
+        additional_includedir="$withval/include"
+        additional_libdir="$withval/lib"
+      fi
+    fi
+])
+  if test $use_additional = yes; then
+    dnl Potentially add $additional_includedir to $CPPFLAGS.
+    dnl But don't add it
+    dnl   1. if it's the standard /usr/include,
+    dnl   2. if it's already present in $CPPFLAGS,
+    dnl   3. if it's /usr/local/include and we are using GCC on Linux,
+    dnl   4. if it doesn't exist as a directory.
+    if test "X$additional_includedir" != "X/usr/include"; then
+      haveit=
+      for x in $CPPFLAGS; do
+        AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+        if test "X$x" = "X-I$additional_includedir"; then
+          haveit=yes
+          break
+        fi
+      done
+      if test -z "$haveit"; then
+        if test "X$additional_includedir" = "X/usr/local/include"; then
+          if test -n "$GCC"; then
+            case $host_os in
+              linux*) haveit=yes;;
+            esac
+          fi
+        fi
+        if test -z "$haveit"; then
+          if test -d "$additional_includedir"; then
+            dnl Really add $additional_includedir to $CPPFLAGS.
+            CPPFLAGS="${CPPFLAGS}${CPPFLAGS:+ }-I$additional_includedir"
+          fi
+        fi
+      fi
+    fi
+    dnl Potentially add $additional_libdir to $LDFLAGS.
+    dnl But don't add it
+    dnl   1. if it's the standard /usr/lib,
+    dnl   2. if it's already present in $LDFLAGS,
+    dnl   3. if it's /usr/local/lib and we are using GCC on Linux,
+    dnl   4. if it doesn't exist as a directory.
+    if test "X$additional_libdir" != "X/usr/lib"; then
+      haveit=
+      for x in $LDFLAGS; do
+        AC_LIB_WITH_FINAL_PREFIX([eval x=\"$x\"])
+        if test "X$x" = "X-L$additional_libdir"; then
+          haveit=yes
+          break
+        fi
+      done
+      if test -z "$haveit"; then
+        if test "X$additional_libdir" = "X/usr/local/lib"; then
+          if test -n "$GCC"; then
+            case $host_os in
+              linux*) haveit=yes;;
+            esac
+          fi
+        fi
+        if test -z "$haveit"; then
+          if test -d "$additional_libdir"; then
+            dnl Really add $additional_libdir to $LDFLAGS.
+            LDFLAGS="${LDFLAGS}${LDFLAGS:+ }-L$additional_libdir"
+          fi
+        fi
+      fi
+    fi
+  fi
+])
+
+dnl AC_LIB_PREPARE_PREFIX creates variables acl_final_prefix,
+dnl acl_final_exec_prefix, containing the values to which $prefix and
+dnl $exec_prefix will expand at the end of the configure script.
+AC_DEFUN([AC_LIB_PREPARE_PREFIX],
+[
+  dnl Unfortunately, prefix and exec_prefix get only finally determined
+  dnl at the end of configure.
+  if test "X$prefix" = "XNONE"; then
+    acl_final_prefix="$ac_default_prefix"
+  else
+    acl_final_prefix="$prefix"
+  fi
+  if test "X$exec_prefix" = "XNONE"; then
+    acl_final_exec_prefix='${prefix}'
+  else
+    acl_final_exec_prefix="$exec_prefix"
+  fi
+  acl_save_prefix="$prefix"
+  prefix="$acl_final_prefix"
+  eval acl_final_exec_prefix=\"$acl_final_exec_prefix\"
+  prefix="$acl_save_prefix"
+])
+
+dnl AC_LIB_WITH_FINAL_PREFIX([statement]) evaluates statement, with the
+dnl variables prefix and exec_prefix bound to the values they will have
+dnl at the end of the configure script.
+AC_DEFUN([AC_LIB_WITH_FINAL_PREFIX],
+[
+  acl_save_prefix="$prefix"
+  prefix="$acl_final_prefix"
+  acl_save_exec_prefix="$exec_prefix"
+  exec_prefix="$acl_final_exec_prefix"
+  $1
+  exec_prefix="$acl_save_exec_prefix"
+  prefix="$acl_save_prefix"
+])
+# nls.m4 serial 1 (gettext-0.12)
+dnl Copyright (C) 1995-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+dnl
+dnl This file can can be used in projects which are not available under
+dnl the GNU General Public License or the GNU Library General Public
+dnl License but which still want to provide support for the GNU gettext
+dnl functionality.
+dnl Please note that the actual code of the GNU gettext library is covered
+dnl by the GNU Library General Public License, and the rest of the GNU
+dnl gettext package package is covered by the GNU General Public License.
+dnl They are *not* in the public domain.
+
+dnl Authors:
+dnl   Ulrich Drepper <drepper@cygnus.com>, 1995-2000.
+dnl   Bruno Haible <haible@clisp.cons.org>, 2000-2003.
+
+AC_DEFUN([AM_NLS],
+[
+  AC_MSG_CHECKING([whether NLS is requested])
+  dnl Default is enabled NLS
+  AC_ARG_ENABLE(nls,
+    [  --disable-nls           do not use Native Language Support],
+    USE_NLS=$enableval, USE_NLS=yes)
+  AC_MSG_RESULT($USE_NLS)
+  AC_SUBST(USE_NLS)
+])
+
+AC_DEFUN([AM_MKINSTALLDIRS],
+[
+  dnl If the AC_CONFIG_AUX_DIR macro for autoconf is used we possibly
+  dnl find the mkinstalldirs script in another subdir but $(top_srcdir).
+  dnl Try to locate it.
+  MKINSTALLDIRS=
+  if test -n "$ac_aux_dir"; then
+    case "$ac_aux_dir" in
+      /*) MKINSTALLDIRS="$ac_aux_dir/mkinstalldirs" ;;
+      *) MKINSTALLDIRS="\$(top_builddir)/$ac_aux_dir/mkinstalldirs" ;;
+    esac
+  fi
+  if test -z "$MKINSTALLDIRS"; then
+    MKINSTALLDIRS="\$(top_srcdir)/mkinstalldirs"
+  fi
+  AC_SUBST(MKINSTALLDIRS)
+])
+# po.m4 serial 1 (gettext-0.12)
+dnl Copyright (C) 1995-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+dnl
+dnl This file can can be used in projects which are not available under
+dnl the GNU General Public License or the GNU Library General Public
+dnl License but which still want to provide support for the GNU gettext
+dnl functionality.
+dnl Please note that the actual code of the GNU gettext library is covered
+dnl by the GNU Library General Public License, and the rest of the GNU
+dnl gettext package package is covered by the GNU General Public License.
+dnl They are *not* in the public domain.
+
+dnl Authors:
+dnl   Ulrich Drepper <drepper@cygnus.com>, 1995-2000.
+dnl   Bruno Haible <haible@clisp.cons.org>, 2000-2003.
+
+dnl Checks for all prerequisites of the po subdirectory.
+AC_DEFUN([AM_PO_SUBDIRS],
+[
+  AC_REQUIRE([AC_PROG_MAKE_SET])dnl
+  AC_REQUIRE([AC_PROG_INSTALL])dnl
+  AC_REQUIRE([AM_MKINSTALLDIRS])dnl
+  AC_REQUIRE([AM_NLS])dnl
+
+  dnl Perform the following tests also if --disable-nls has been given,
+  dnl because they are needed for "make dist" to work.
+
+  dnl Search for GNU msgfmt in the PATH.
+  dnl The first test excludes Solaris msgfmt and early GNU msgfmt versions.
+  dnl The second test excludes FreeBSD msgfmt.
+  AM_PATH_PROG_WITH_TEST(MSGFMT, msgfmt,
+    [$ac_dir/$ac_word --statistics /dev/null >/dev/null 2>&1 &&
+     (if $ac_dir/$ac_word --statistics /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)],
+    :)
+  AC_PATH_PROG(GMSGFMT, gmsgfmt, $MSGFMT)
+
+  dnl Search for GNU xgettext 0.12 or newer in the PATH.
+  dnl The first test excludes Solaris xgettext and early GNU xgettext versions.
+  dnl The second test excludes FreeBSD xgettext.
+  AM_PATH_PROG_WITH_TEST(XGETTEXT, xgettext,
+    [$ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null >/dev/null 2>&1 &&
+     (if $ac_dir/$ac_word --omit-header --copyright-holder= --msgid-bugs-address= /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi)],
+    :)
+  dnl Remove leftover from FreeBSD xgettext call.
+  rm -f messages.po
+
+  dnl Search for GNU msgmerge 0.11 or newer in the PATH.
+  AM_PATH_PROG_WITH_TEST(MSGMERGE, msgmerge,
+    [$ac_dir/$ac_word --update -q /dev/null /dev/null >/dev/null 2>&1], :)
+
+  dnl This could go away some day; the PATH_PROG_WITH_TEST already does it.
+  dnl Test whether we really found GNU msgfmt.
+  if test "$GMSGFMT" != ":"; then
+    dnl If it is no GNU msgfmt we define it as : so that the
+    dnl Makefiles still can work.
+    if $GMSGFMT --statistics /dev/null >/dev/null 2>&1 &&
+       (if $GMSGFMT --statistics /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi); then
+      : ;
+    else
+      GMSGFMT=`echo "$GMSGFMT" | sed -e 's,^.*/,,'`
+      AC_MSG_RESULT(
+        [found $GMSGFMT program is not GNU msgfmt; ignore it])
+      GMSGFMT=":"
+    fi
+  fi
+
+  dnl This could go away some day; the PATH_PROG_WITH_TEST already does it.
+  dnl Test whether we really found GNU xgettext.
+  if test "$XGETTEXT" != ":"; then
+    dnl If it is no GNU xgettext we define it as : so that the
+    dnl Makefiles still can work.
+    if $XGETTEXT --omit-header --copyright-holder= --msgid-bugs-address= /dev/null >/dev/null 2>&1 &&
+       (if $XGETTEXT --omit-header --copyright-holder= --msgid-bugs-address= /dev/null 2>&1 >/dev/null | grep usage >/dev/null; then exit 1; else exit 0; fi); then
+      : ;
+    else
+      AC_MSG_RESULT(
+        [found xgettext program is not GNU xgettext; ignore it])
+      XGETTEXT=":"
+    fi
+    dnl Remove leftover from FreeBSD xgettext call.
+    rm -f messages.po
+  fi
+
+  AC_OUTPUT_COMMANDS([
+    for ac_file in $CONFIG_FILES; do
+      # Support "outfile[:infile[:infile...]]"
+      case "$ac_file" in
+        *:*) ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;;
+      esac
+      # PO directories have a Makefile.in generated from Makefile.in.in.
+      case "$ac_file" in */Makefile.in)
+        # Adjust a relative srcdir.
+        ac_dir=`echo "$ac_file"|sed 's%/[^/][^/]*$%%'`
+        ac_dir_suffix="/`echo "$ac_dir"|sed 's%^\./%%'`"
+        ac_dots=`echo "$ac_dir_suffix"|sed 's%/[^/]*%../%g'`
+        # In autoconf-2.13 it is called $ac_given_srcdir.
+        # In autoconf-2.50 it is called $srcdir.
+        test -n "$ac_given_srcdir" || ac_given_srcdir="$srcdir"
+        case "$ac_given_srcdir" in
+          .)  top_srcdir=`echo $ac_dots|sed 's%/$%%'` ;;
+          /*) top_srcdir="$ac_given_srcdir" ;;
+          *)  top_srcdir="$ac_dots$ac_given_srcdir" ;;
+        esac
+        if test -f "$ac_given_srcdir/$ac_dir/POTFILES.in"; then
+          rm -f "$ac_dir/POTFILES"
+          test -n "$as_me" && echo "$as_me: creating $ac_dir/POTFILES" || echo "creating $ac_dir/POTFILES"
+          cat "$ac_given_srcdir/$ac_dir/POTFILES.in" | sed -e "/^#/d" -e "/^[  ]*\$/d" -e "s,.*,     $top_srcdir/& \\\\," | sed -e "\$s/\(.*\) \\\\/\1/" > "$ac_dir/POTFILES"
+          POMAKEFILEDEPS="POTFILES.in"
+          # ALL_LINGUAS, POFILES, GMOFILES, UPDATEPOFILES, DUMMYPOFILES depend
+          # on $ac_dir but don't depend on user-specified configuration
+          # parameters.
+          if test -f "$ac_given_srcdir/$ac_dir/LINGUAS"; then
+            # The LINGUAS file contains the set of available languages.
+            if test -n "$OBSOLETE_ALL_LINGUAS"; then
+              test -n "$as_me" && echo "$as_me: setting ALL_LINGUAS in configure.in is obsolete" || echo "setting ALL_LINGUAS in configure.in is obsolete"
+            fi
+            ALL_LINGUAS_=`sed -e "/^#/d" "$ac_given_srcdir/$ac_dir/LINGUAS"`
+            # Hide the ALL_LINGUAS assigment from automake.
+            eval 'ALL_LINGUAS''=$ALL_LINGUAS_'
+            POMAKEFILEDEPS="$POMAKEFILEDEPS LINGUAS"
+          else
+            # The set of available languages was given in configure.in.
+            eval 'ALL_LINGUAS''=$OBSOLETE_ALL_LINGUAS'
+          fi
+          case "$ac_given_srcdir" in
+            .) srcdirpre= ;;
+            *) srcdirpre='$(srcdir)/' ;;
+          esac
+          POFILES=
+          GMOFILES=
+          UPDATEPOFILES=
+          DUMMYPOFILES=
+          for lang in $ALL_LINGUAS; do
+            POFILES="$POFILES $srcdirpre$lang.po"
+            GMOFILES="$GMOFILES $srcdirpre$lang.gmo"
+            UPDATEPOFILES="$UPDATEPOFILES $lang.po-update"
+            DUMMYPOFILES="$DUMMYPOFILES $lang.nop"
+          done
+          # CATALOGS depends on both $ac_dir and the user's LINGUAS
+          # environment variable.
+          INST_LINGUAS=
+          if test -n "$ALL_LINGUAS"; then
+            for presentlang in $ALL_LINGUAS; do
+              useit=no
+              if test "%UNSET%" != "$LINGUAS"; then
+                desiredlanguages="$LINGUAS"
+              else
+                desiredlanguages="$ALL_LINGUAS"
+              fi
+              for desiredlang in $desiredlanguages; do
+                # Use the presentlang catalog if desiredlang is
+                #   a. equal to presentlang, or
+                #   b. a variant of presentlang (because in this case,
+                #      presentlang can be used as a fallback for messages
+                #      which are not translated in the desiredlang catalog).
+                case "$desiredlang" in
+                  "$presentlang"*) useit=yes;;
+                esac
+              done
+              if test $useit = yes; then
+                INST_LINGUAS="$INST_LINGUAS $presentlang"
+              fi
+            done
+          fi
+          CATALOGS=
+          if test -n "$INST_LINGUAS"; then
+            for lang in $INST_LINGUAS; do
+              CATALOGS="$CATALOGS $lang.gmo"
+            done
+          fi
+          test -n "$as_me" && echo "$as_me: creating $ac_dir/Makefile" || echo "creating $ac_dir/Makefile"
+          sed -e "/^POTFILES =/r $ac_dir/POTFILES" -e "/^# Makevars/r $ac_given_srcdir/$ac_dir/Makevars" -e "s|@POFILES@|$POFILES|g" -e "s|@GMOFILES@|$GMOFILES|g" -e "s|@UPDATEPOFILES@|$UPDATEPOFILES|g" -e "s|@DUMMYPOFILES@|$DUMMYPOFILES|g" -e "s|@CATALOGS@|$CATALOGS|g" -e "s|@POMAKEFILEDEPS@|$POMAKEFILEDEPS|g" "$ac_dir/Makefile.in" > "$ac_dir/Makefile"
+          for f in "$ac_given_srcdir/$ac_dir"/Rules-*; do
+            if test -f "$f"; then
+              case "$f" in
+                *.orig | *.bak | *~) ;;
+                *) cat "$f" >> "$ac_dir/Makefile" ;;
+              esac
+            fi
+          done
+        fi
+        ;;
+      esac
+    done],
+   [# Capture the value of obsolete ALL_LINGUAS because we need it to compute
+    # POFILES, GMOFILES, UPDATEPOFILES, DUMMYPOFILES, CATALOGS. But hide it
+    # from automake.
+    eval 'OBSOLETE_ALL_LINGUAS''="$ALL_LINGUAS"'
+    # Capture the value of LINGUAS because we need it to compute CATALOGS.
+    LINGUAS="${LINGUAS-%UNSET%}"
+   ])
+])
+# progtest.m4 serial 3 (gettext-0.12)
+dnl Copyright (C) 1996-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+dnl
+dnl This file can can be used in projects which are not available under
+dnl the GNU General Public License or the GNU Library General Public
+dnl License but which still want to provide support for the GNU gettext
+dnl functionality.
+dnl Please note that the actual code of the GNU gettext library is covered
+dnl by the GNU Library General Public License, and the rest of the GNU
+dnl gettext package package is covered by the GNU General Public License.
+dnl They are *not* in the public domain.
+
+dnl Authors:
+dnl   Ulrich Drepper <drepper@cygnus.com>, 1996.
+
+# Search path for a program which passes the given test.
+
+dnl AM_PATH_PROG_WITH_TEST(VARIABLE, PROG-TO-CHECK-FOR,
+dnl   TEST-PERFORMED-ON-FOUND_PROGRAM [, VALUE-IF-NOT-FOUND [, PATH]])
+AC_DEFUN([AM_PATH_PROG_WITH_TEST],
+[
+# Prepare PATH_SEPARATOR.
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+  echo "#! /bin/sh" >conf$$.sh
+  echo  "exit 0"   >>conf$$.sh
+  chmod +x conf$$.sh
+  if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then
+    PATH_SEPARATOR=';'
+  else
+    PATH_SEPARATOR=:
+  fi
+  rm -f conf$$.sh
+fi
+
+# Find out how to test for executable files. Don't use a zero-byte file,
+# as systems may use methods other than mode bits to determine executability.
+cat >conf$$.file <<_ASEOF
+#! /bin/sh
+exit 0
+_ASEOF
+chmod +x conf$$.file
+if test -x conf$$.file >/dev/null 2>&1; then
+  ac_executable_p="test -x"
+else
+  ac_executable_p="test -f"
+fi
+rm -f conf$$.file
+
+# Extract the first word of "$2", so it can be a program name with args.
+set dummy $2; ac_word=[$]2
+AC_MSG_CHECKING([for $ac_word])
+AC_CACHE_VAL(ac_cv_path_$1,
+[case "[$]$1" in
+  [[\\/]]* | ?:[[\\/]]*)
+    ac_cv_path_$1="[$]$1" # Let the user override the test with a path.
+    ;;
+  *)
+    ac_save_IFS="$IFS"; IFS=$PATH_SEPARATOR
+    for ac_dir in ifelse([$5], , $PATH, [$5]); do
+      IFS="$ac_save_IFS"
+      test -z "$ac_dir" && ac_dir=.
+      for ac_exec_ext in '' $ac_executable_extensions; do
+        if $ac_executable_p "$ac_dir/$ac_word$ac_exec_ext"; then
+          if [$3]; then
+            ac_cv_path_$1="$ac_dir/$ac_word$ac_exec_ext"
+            break 2
+          fi
+        fi
+      done
+    done
+    IFS="$ac_save_IFS"
+dnl If no 4th arg is given, leave the cache variable unset,
+dnl so AC_PATH_PROGS will keep looking.
+ifelse([$4], , , [  test -z "[$]ac_cv_path_$1" && ac_cv_path_$1="$4"
+])dnl
+    ;;
+esac])dnl
+$1="$ac_cv_path_$1"
+if test ifelse([$4], , [-n "[$]$1"], ["[$]$1" != "$4"]); then
+  AC_MSG_RESULT([$]$1)
+else
+  AC_MSG_RESULT(no)
+fi
+AC_SUBST($1)dnl
+])
+# stdint_h.m4 serial 3 (gettext-0.12)
+dnl Copyright (C) 1997-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Paul Eggert.
+
+# Define HAVE_STDINT_H_WITH_UINTMAX if <stdint.h> exists,
+# doesn't clash with <sys/types.h>, and declares uintmax_t.
+
+AC_DEFUN([jm_AC_HEADER_STDINT_H],
+[
+  AC_CACHE_CHECK([for stdint.h], jm_ac_cv_header_stdint_h,
+  [AC_TRY_COMPILE(
+    [#include <sys/types.h>
+#include <stdint.h>],
+    [uintmax_t i = (uintmax_t) -1;],
+    jm_ac_cv_header_stdint_h=yes,
+    jm_ac_cv_header_stdint_h=no)])
+  if test $jm_ac_cv_header_stdint_h = yes; then
+    AC_DEFINE_UNQUOTED(HAVE_STDINT_H_WITH_UINTMAX, 1,
+      [Define if <stdint.h> exists, doesn't clash with <sys/types.h>,
+       and declares uintmax_t. ])
+  fi
+])
+# uintmax_t.m4 serial 7 (gettext-0.12)
+dnl Copyright (C) 1997-2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Paul Eggert.
+
+AC_PREREQ(2.13)
+
+# Define uintmax_t to 'unsigned long' or 'unsigned long long'
+# if it is not already defined in <stdint.h> or <inttypes.h>.
+
+AC_DEFUN([jm_AC_TYPE_UINTMAX_T],
+[
+  AC_REQUIRE([jm_AC_HEADER_INTTYPES_H])
+  AC_REQUIRE([jm_AC_HEADER_STDINT_H])
+  if test $jm_ac_cv_header_inttypes_h = no && test $jm_ac_cv_header_stdint_h = no; then
+    AC_REQUIRE([jm_AC_TYPE_UNSIGNED_LONG_LONG])
+    test $ac_cv_type_unsigned_long_long = yes \
+      && ac_type='unsigned long long' \
+      || ac_type='unsigned long'
+    AC_DEFINE_UNQUOTED(uintmax_t, $ac_type,
+      [Define to unsigned long or unsigned long long
+       if <stdint.h> and <inttypes.h> don't define.])
+  else
+    AC_DEFINE(HAVE_UINTMAX_T, 1,
+      [Define if you have the 'uintmax_t' type in <stdint.h> or <inttypes.h>.])
+  fi
+])
+# ulonglong.m4 serial 2 (fileutils-4.0.32, gettext-0.10.40)
+dnl Copyright (C) 1999-2002 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+dnl From Paul Eggert.
+
+AC_DEFUN([jm_AC_TYPE_UNSIGNED_LONG_LONG],
+[
+  AC_CACHE_CHECK([for unsigned long long], ac_cv_type_unsigned_long_long,
+  [AC_TRY_LINK([unsigned long long ull = 1; int i = 63;],
+    [unsigned long long ullmax = (unsigned long long) -1;
+     return ull << i | ull >> i | ullmax / ull | ullmax % ull;],
+    ac_cv_type_unsigned_long_long=yes,
+    ac_cv_type_unsigned_long_long=no)])
+  if test $ac_cv_type_unsigned_long_long = yes; then
+    AC_DEFINE(HAVE_UNSIGNED_LONG_LONG, 1,
+      [Define if you have the unsigned long long type.])
+  fi
+])
index feeb0c0aaba2fca891a1fb573bd185f63e3e5037..0e5bd742ccc88a857b63b47d363977bb99cdb0fb 100644 (file)
@@ -23803,7 +23803,14 @@ if test "${bash_cv_dev_fd+set}" = set; then
   echo $ECHO_N "(cached) $ECHO_C" >&6
 else
   if test -d /dev/fd  && test -r /dev/fd/0 < /dev/null; then
-   bash_cv_dev_fd=standard
+# check for systems like FreeBSD 5 that only provide /dev/fd/[012]
+   exec 3<&0
+   if test -r /dev/fd/3; then
+     bash_cv_dev_fd=standard
+   else
+     bash_cv_dev_fd=absent
+   fi
+   exec 3<&-
  elif test -d /proc/self/fd && test -r /proc/self/fd/0 < /dev/null; then
    bash_cv_dev_fd=whacky
  else
index a60ef56fa5fa1a6de96a5d04838f302092449377..066abfdcbbb29270875b0ade28d6d18ea43c40db 100644 (file)
                         'configure.in'
                       ],
                       {
-                        'AC_DEFINE_TRACE_LITERAL' => 1,
+                        'm4_include' => 1,
+                        'AC_CONFIG_AUX_DIR' => 1,
+                        'AC_FUNC_STRERROR_R' => 1,
+                        'AC_FUNC_FORK' => 1,
+                        'AC_C_VOLATILE' => 1,
+                        'AC_FUNC_STRCOLL' => 1,
+                        'AC_FUNC_MKTIME' => 1,
+                        'AC_HEADER_TIME' => 1,
                         'AC_STRUCT_TIMEZONE' => 1,
-                        'AC_FUNC_MMAP' => 1,
-                        'AC_PROG_YACC' => 1,
-                        'AC_FUNC_STRFTIME' => 1,
-                        'AC_PROG_RANLIB' => 1,
+                        'AC_FUNC_REALLOC' => 1,
+                        'AC_TYPE_MODE_T' => 1,
+                        'AM_GNU_GETTEXT' => 1,
                         'AM_AUTOMAKE_VERSION' => 1,
-                        'AC_STRUCT_TM' => 1,
-                        'm4_include' => 1,
+                        'AC_FUNC_UTIME_NULL' => 1,
+                        'AC_FUNC_STRFTIME' => 1,
+                        'AC_CHECK_LIB' => 1,
+                        'AC_PROG_INSTALL' => 1,
+                        'AC_HEADER_MAJOR' => 1,
+                        'AC_REPLACE_FNMATCH' => 1,
+                        'include' => 1,
+                        'AC_INIT' => 1,
+                        'AC_FUNC_ERROR_AT_LINE' => 1,
+                        'AC_PROG_CPP' => 1,
+                        'AC_PROG_LIBTOOL' => 1,
+                        'AC_PATH_X' => 1,
+                        'AC_DECL_SYS_SIGLIST' => 1,
+                        'AC_CANONICAL_HOST' => 1,
+                        'AC_STRUCT_ST_BLOCKS' => 1,
+                        'AC_FUNC_CLOSEDIR_VOID' => 1,
+                        'AC_TYPE_SIZE_T' => 1,
+                        'AC_FUNC_FSEEKO' => 1,
+                        'm4_pattern_forbid' => 1,
                         'AC_FUNC_SETPGRP' => 1,
-                        'AC_FUNC_GETPGRP' => 1,
-                        'AC_PROG_CXX' => 1,
-                        'AC_HEADER_DIRENT' => 1,
-                        'AC_CONFIG_HEADERS' => 1,
-                        'AC_PROG_CC' => 1,
-                        'AC_HEADER_SYS_WAIT' => 1,
+                        'm4_pattern_allow' => 1,
+                        'AC_FUNC_STAT' => 1,
                         'AM_PROG_CC_C_O' => 1,
                         'AC_HEADER_STDC' => 1,
-                        'AM_GNU_GETTEXT' => 1,
-                        'AC_FUNC_FSEEKO' => 1,
-                        'AC_TYPE_SIZE_T' => 1,
-                        'AC_FUNC_CHOWN' => 1,
+                        'AC_FUNC_STRTOD' => 1,
+                        'AC_CHECK_MEMBERS' => 1,
+                        'AC_PROG_CXX' => 1,
+                        'AC_FUNC_MMAP' => 1,
+                        'AC_TYPE_SIGNAL' => 1,
+                        'AC_CONFIG_HEADERS' => 1,
+                        'AC_C_CONST' => 1,
                         'AC_CHECK_TYPES' => 1,
-                        'm4_pattern_allow' => 1,
-                        'AH_OUTPUT' => 1,
-                        'AC_TYPE_UID_T' => 1,
-                        'AC_HEADER_STAT' => 1,
-                        'AC_FUNC_UTIME_NULL' => 1,
+                        'AC_FUNC_CHOWN' => 1,
                         'AC_FUNC_GETMNTENT' => 1,
-                        'AC_FUNC_STRTOD' => 1,
-                        'AC_CONFIG_FILES' => 1,
-                        'AC_FUNC_SETVBUF_REVERSED' => 1,
-                        'AC_FUNC_MEMCMP' => 1,
-                        'AC_FUNC_STAT' => 1,
+                        'AM_MAINTAINER_MODE' => 1,
+                        'AM_CONDITIONAL' => 1,
+                        'AC_FUNC_MBRTOWC' => 1,
+                        'AC_HEADER_SYS_WAIT' => 1,
+                        'AC_C_INLINE' => 1,
                         'AC_PROG_MAKE_SET' => 1,
-                        'AC_FUNC_STRCOLL' => 1,
+                        'AC_DEFINE_TRACE_LITERAL' => 1,
+                        'AC_FUNC_GETPGRP' => 1,
+                        'AH_OUTPUT' => 1,
+                        'AC_PROG_AWK' => 1,
                         'AC_FUNC_VPRINTF' => 1,
-                        'AC_FUNC_ERROR_AT_LINE' => 1,
+                        'AC_FUNC_MEMCMP' => 1,
+                        'AC_FUNC_SELECT_ARGTYPES' => 1,
+                        'AC_HEADER_STAT' => 1,
+                        'AC_PROG_LN_S' => 1,
+                        'AC_PROG_CC' => 1,
+                        'AC_STRUCT_TM' => 1,
+                        'AC_CANONICAL_SYSTEM' => 1,
                         'AC_SUBST' => 1,
-                        'AC_FUNC_OBSTACK' => 1,
-                        'AC_FUNC_MKTIME' => 1,
-                        'AC_PROG_INSTALL' => 1,
-                        'AC_PROG_AWK' => 1,
-                        'AC_PROG_LEX' => 1,
-                        'AC_FUNC_GETGROUPS' => 1,
-                        'AC_FUNC_CLOSEDIR_VOID' => 1,
-                        'AC_FUNC_STRNLEN' => 1,
-                        'AC_CANONICAL_HOST' => 1,
                         'AM_INIT_AUTOMAKE' => 1,
-                        'AC_LIBSOURCE' => 1,
+                        'AC_TYPE_PID_T' => 1,
+                        'AC_CONFIG_SUBDIRS' => 1,
+                        'AC_PROG_GCC_TRADITIONAL' => 1,
+                        'AC_FUNC_LSTAT_FOLLOWS_SLASHED_SYMLINK' => 1,
                         'AC_CHECK_HEADERS' => 1,
-                        'include' => 1,
-                        'AC_PATH_X' => 1,
-                        'AC_HEADER_TIME' => 1,
-                        'AC_CONFIG_AUX_DIR' => 1,
-                        'AC_PROG_LIBTOOL' => 1,
-                        'AC_FUNC_MBRTOWC' => 1,
-                        'AC_PROG_CPP' => 1,
-                        'AC_FUNC_ALLOCA' => 1,
+                        'AC_FUNC_OBSTACK' => 1,
+                        'AC_CHECK_FUNCS' => 1,
+                        'AC_HEADER_DIRENT' => 1,
                         'AC_FUNC_LSTAT' => 1,
-                        'AC_TYPE_SIGNAL' => 1,
-                        'AC_INIT' => 1,
-                        'AC_C_CONST' => 1,
-                        'AC_C_INLINE' => 1,
-                        'AC_HEADER_MAJOR' => 1,
-                        'AC_PROG_LN_S' => 1,
-                        'AC_REPLACE_FNMATCH' => 1,
-                        'AC_FUNC_SELECT_ARGTYPES' => 1,
-                        'm4_pattern_forbid' => 1,
-                        'AC_CHECK_LIB' => 1,
-                        'AC_FUNC_REALLOC' => 1,
+                        'AC_PROG_LEX' => 1,
+                        'AC_PROG_YACC' => 1,
                         'AC_TYPE_OFF_T' => 1,
-                        'AC_CANONICAL_SYSTEM' => 1,
-                        'AC_CHECK_FUNCS' => 1,
-                        'AC_CONFIG_SUBDIRS' => 1,
-                        'AM_CONDITIONAL' => 1,
-                        'AC_TYPE_MODE_T' => 1,
-                        'AC_STRUCT_ST_BLOCKS' => 1,
-                        'AC_DECL_SYS_SIGLIST' => 1,
-                        'AC_TYPE_PID_T' => 1,
-                        'AC_FUNC_LSTAT_FOLLOWS_SLASHED_SYMLINK' => 1,
+                        'AC_PROG_RANLIB' => 1,
+                        'AC_CONFIG_FILES' => 1,
                         'AC_FUNC_GETLOADAVG' => 1,
-                        'AC_FUNC_MALLOC' => 1,
-                        'AC_PROG_GCC_TRADITIONAL' => 1,
+                        'AC_FUNC_ALLOCA' => 1,
+                        'AC_FUNC_STRNLEN' => 1,
+                        'AC_TYPE_UID_T' => 1,
+                        'AC_LIBSOURCE' => 1,
                         'AC_FUNC_WAIT3' => 1,
-                        'AC_CHECK_MEMBERS' => 1,
-                        'AC_C_VOLATILE' => 1,
-                        'AC_FUNC_STRERROR_R' => 1,
-                        'AM_MAINTAINER_MODE' => 1,
-                        'AC_FUNC_FORK' => 1
+                        'AC_FUNC_MALLOC' => 1,
+                        'AC_FUNC_GETGROUPS' => 1,
+                        'AC_FUNC_SETVBUF_REVERSED' => 1
                       }
                     ], 'Request' )
            );
index a91c8e4cb6e799ec91783079d9f9e99c47eb0c0d..9d141e5c5f28f52a27371e64fb6ce1beee12ee82 100644 (file)
@@ -78,6 +78,8 @@ int xpg_echo = 1;
 int xpg_echo = 0;
 #endif /* DEFAULT_ECHO_TO_XPG */
 
+extern int posixly_correct;
+
 /* Print the words in LIST to standard output.  If the first word is
    `-n', then don't print a trailing newline.  We also support the
    echo syntax from Version 9 Unix systems. */
@@ -91,6 +93,9 @@ echo_builtin (list)
   do_v9 = xpg_echo;
   display_return = 1;
 
+  if (posixly_correct && xpg_echo)
+    goto just_echo;
+
   for (; list && (temp = list->word->word) && *temp == '-'; list = list->next)
     {
       /* If it appears that we are handling options, then make sure that
diff --git a/builtins/echo.def~ b/builtins/echo.def~
new file mode 100644 (file)
index 0000000..d9296c8
--- /dev/null
@@ -0,0 +1,180 @@
+This file is echo.def, from which is created echo.c.
+It implements the builtin "echo" in Bash.
+
+Copyright (C) 1987-2002 Free Software Foundation, Inc.
+
+This file is part of GNU Bash, the Bourne Again SHell.
+
+Bash is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free
+Software Foundation; either version 2, or (at your option) any later
+version.
+
+Bash is distributed in the hope that it will be useful, but WITHOUT ANY
+WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License along
+with Bash; see the file COPYING.  If not, write to the Free Software
+Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA.
+
+$PRODUCES echo.c
+#include <config.h>
+
+#if defined (HAVE_UNISTD_H)
+#  include <unistd.h>
+#endif
+
+#include "../bashansi.h"
+
+#include <stdio.h>
+#include "../shell.h"
+
+$BUILTIN echo
+$FUNCTION echo_builtin
+$DEPENDS_ON V9_ECHO
+$SHORT_DOC echo [-neE] [arg ...]
+Output the ARGs.  If -n is specified, the trailing newline is
+suppressed.  If the -e option is given, interpretation of the
+following backslash-escaped characters is turned on:
+       \a      alert (bell)
+       \b      backspace
+       \c      suppress trailing newline
+       \E      escape character
+       \f      form feed
+       \n      new line
+       \r      carriage return
+       \t      horizontal tab
+       \v      vertical tab
+       \\      backslash
+       \num    the character whose ASCII code is NUM (octal).
+
+You can explicitly turn off the interpretation of the above characters
+with the -E option.
+$END
+
+$BUILTIN echo
+$FUNCTION echo_builtin
+$DEPENDS_ON !V9_ECHO
+$SHORT_DOC echo [-n] [arg ...]
+Output the ARGs.  If -n is specified, the trailing newline is suppressed.
+$END
+
+#if defined (V9_ECHO)
+#  define VALID_ECHO_OPTIONS "neE"
+#else /* !V9_ECHO */
+#  define VALID_ECHO_OPTIONS "n"
+#endif /* !V9_ECHO */
+
+/* System V machines already have a /bin/sh with a v9 behaviour.  We
+   give Bash the identical behaviour for these machines so that the
+   existing system shells won't barf.  Regrettably, the SUS v2 has
+   standardized the Sys V echo behavior.  This variable is external
+   so that we can have a `shopt' variable to control it at runtime. */
+#if defined (DEFAULT_ECHO_TO_XPG)
+int xpg_echo = 1;
+#else
+int xpg_echo = 0;
+#endif /* DEFAULT_ECHO_TO_XPG */
+
+/* Print the words in LIST to standard output.  If the first word is
+   `-n', then don't print a trailing newline.  We also support the
+   echo syntax from Version 9 Unix systems. */
+int
+echo_builtin (list)
+     WORD_LIST *list;
+{
+  int display_return, do_v9, i, len;
+  char *temp, *s;
+
+  do_v9 = xpg_echo;
+  display_return = 1;
+
+  if (posixly_correct && xpg_echo)
+    goto just_echo;
+
+  for (; list && (temp = list->word->word) && *temp == '-'; list = list->next)
+    {
+      /* If it appears that we are handling options, then make sure that
+        all of the options specified are actually valid.  Otherwise, the
+        string should just be echoed. */
+      temp++;
+
+      for (i = 0; temp[i]; i++)
+       {
+         if (strchr (VALID_ECHO_OPTIONS, temp[i]) == 0)
+           break;
+       }
+
+      /* echo - and echo -<nonopt> both mean to just echo the arguments. */
+      if (*temp == 0 || temp[i])
+       break;
+
+      /* All of the options in TEMP are valid options to ECHO.
+        Handle them. */
+      while (i = *temp++)
+       {
+         switch (i)
+           {
+           case 'n':
+             display_return = 0;
+             break;
+#if defined (V9_ECHO)
+           case 'e':
+             do_v9 = 1;
+             break;
+           case 'E':
+             do_v9 = 0;
+             break;
+#endif /* V9_ECHO */
+           default:
+             goto just_echo;   /* XXX */
+           }
+       }
+    }
+
+just_echo:
+
+  clearerr (stdout);   /* clear error before writing and testing success */
+
+  while (list)
+    {
+      i = len = 0;
+      temp = do_v9 ? ansicstr (list->word->word, STRLEN (list->word->word), 1, &i, &len)
+                  : list->word->word;
+      if (temp)
+       {
+         if (do_v9)
+           {
+             for (s = temp; len > 0; len--)
+               putchar (*s++);
+           }
+         else      
+           printf ("%s", temp);
+#if defined (SunOS5)
+         fflush (stdout);      /* Fix for bug in SunOS 5.5 printf(3) */
+#endif
+       }
+      if (do_v9 && temp)
+       free (temp);
+      list = list->next;
+      if (i)
+       {
+         display_return = 0;
+         break;
+       }
+      if (list)
+       putchar(' ');
+    }
+
+  if (display_return)
+    putchar ('\n');
+  fflush (stdout);
+  if (ferror (stdout))
+    {
+      clearerr (stdout);
+      return (EXECUTION_FAILURE);
+    }
+  return (EXECUTION_SUCCESS);
+}
index ea13bef3de58ce702094d2af8c8bffd5cfd5a936..4fc796e14203057bd75bc6a256cec68c583028d3 100644 (file)
@@ -94,6 +94,8 @@ int
 bg_builtin (list)
      WORD_LIST *list;
 {
+  int r;
+
   if (job_control == 0)
     {
       sh_nojobs ((char *)NULL);
@@ -104,7 +106,17 @@ bg_builtin (list)
     return (EX_USAGE);
   list = loptend;
 
-  return (fg_bg (list, 0));
+  /* This relies on the fact that fg_bg() takes a WORD_LIST *, but only acts
+     on the first member (if any) of that list. */
+  do
+    {
+      r = fg_bg (list, 0);
+      if (list)
+       list = list->next;
+    }
+  while (list);
+
+  return r;
 }
 
 /* How to put a job into the foreground/background. */
diff --git a/builtins/fg_bg.def~ b/builtins/fg_bg.def~
new file mode 100644 (file)
index 0000000..ea13bef
--- /dev/null
@@ -0,0 +1,161 @@
+This file is fg_bg.def, from which is created fg_bg.c.
+It implements the builtins "bg" and "fg" in Bash.
+
+Copyright (C) 1987-2003 Free Software Foundation, Inc.
+
+This file is part of GNU Bash, the Bourne Again SHell.
+
+Bash is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free
+Software Foundation; either version 2, or (at your option) any later
+version.
+
+Bash is distributed in the hope that it will be useful, but WITHOUT ANY
+WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License along
+with Bash; see the file COPYING.  If not, write to the Free Software
+Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA.
+
+$PRODUCES fg_bg.c
+
+$BUILTIN fg
+$FUNCTION fg_builtin
+$DEPENDS_ON JOB_CONTROL
+$SHORT_DOC fg [job_spec]
+Place JOB_SPEC in the foreground, and make it the current job.  If
+JOB_SPEC is not present, the shell's notion of the current job is
+used.
+$END
+
+#include <config.h>
+
+#include "../bashtypes.h"
+#include <signal.h>
+
+#if defined (HAVE_UNISTD_H)
+#  include <unistd.h>
+#endif
+
+#include "../bashintl.h"
+
+#include "../shell.h"
+#include "../jobs.h"
+#include "common.h"
+#include "bashgetopt.h"
+
+#if defined (JOB_CONTROL)
+extern char *this_command_name;
+
+static int fg_bg __P((WORD_LIST *, int));
+
+/* How to bring a job into the foreground. */
+int
+fg_builtin (list)
+     WORD_LIST *list;
+{
+  int fg_bit;
+  register WORD_LIST *t;
+
+  if (job_control == 0)
+    {
+      sh_nojobs ((char *)NULL);
+      return (EXECUTION_FAILURE);
+    }
+
+  if (no_options (list))
+    return (EX_USAGE);
+  list = loptend;
+
+  /* If the last arg on the line is '&', then start this job in the
+     background.  Else, fg the job. */
+  for (t = list; t && t->next; t = t->next)
+    ;
+  fg_bit = (t && t->word->word[0] == '&' && t->word->word[1] == '\0') == 0;
+
+  return (fg_bg (list, fg_bit));
+}
+#endif /* JOB_CONTROL */
+
+$BUILTIN bg
+$FUNCTION bg_builtin
+$DEPENDS_ON JOB_CONTROL
+$SHORT_DOC bg [job_spec]
+Place JOB_SPEC in the background, as if it had been started with
+`&'.  If JOB_SPEC is not present, the shell's notion of the current
+job is used.
+$END
+
+#if defined (JOB_CONTROL)
+/* How to put a job into the background. */
+int
+bg_builtin (list)
+     WORD_LIST *list;
+{
+  if (job_control == 0)
+    {
+      sh_nojobs ((char *)NULL);
+      return (EXECUTION_FAILURE);
+    }
+
+  if (no_options (list))
+    return (EX_USAGE);
+  list = loptend;
+
+  return (fg_bg (list, 0));
+}
+
+/* How to put a job into the foreground/background. */
+static int
+fg_bg (list, foreground)
+     WORD_LIST *list;
+     int foreground;
+{
+  sigset_t set, oset;
+  int job, status, old_async_pid;
+
+  BLOCK_CHILD (set, oset);
+  job = get_job_spec (list);
+
+  if (job < 0 || job >= job_slots || jobs[job] == 0)
+    {
+      if (job != DUP_JOB)
+       sh_badjob (list ? list->word->word : "current");
+
+      goto failure;
+    }
+
+  /* Or if jobs[job]->pgrp == shell_pgrp. */
+  if (IS_JOBCONTROL (job) == 0)
+    {
+      builtin_error (_("job %d started without job control"), job + 1);
+      goto failure;
+    }
+
+  if (foreground == 0)
+    {
+      old_async_pid = last_asynchronous_pid;
+      last_asynchronous_pid = jobs[job]->pgrp; /* As per Posix.2 5.4.2 */
+    }
+
+  status = start_job (job, foreground);
+
+  if (status >= 0)
+    {
+    /* win: */
+      UNBLOCK_CHILD (oset);
+      return (status);
+    }
+  else
+    {
+      if (foreground == 0)
+       last_asynchronous_pid = old_async_pid;
+
+    failure:
+      UNBLOCK_CHILD (oset);
+      return (EXECUTION_FAILURE);
+    }
+}
+#endif /* JOB_CONTROL */
index 2fdac20af9c5e57d31b7a487df2ee5fed10df28b..0954a0625fe7e8775dc10fd3b6ffb702cec1ab5b 100755 (executable)
--- a/configure
+++ b/configure
@@ -23803,7 +23803,14 @@ if test "${bash_cv_dev_fd+set}" = set; then
   echo $ECHO_N "(cached) $ECHO_C" >&6
 else
   if test -d /dev/fd  && test -r /dev/fd/0 < /dev/null; then
-   bash_cv_dev_fd=standard
+# check for systems like FreeBSD 5 that only provide /dev/fd/[012]
+   exec 3<&0
+   if test -r /dev/fd/3; then
+     bash_cv_dev_fd=standard
+   else
+     bash_cv_dev_fd=absent
+   fi
+   exec 3<&-
  elif test -d /proc/self/fd && test -r /proc/self/fd/0 < /dev/null; then
    bash_cv_dev_fd=whacky
  else
index 21d0aba7841000989bf628840c8f4fef8cda7e40..532d52d0be9d0ee404e0cfa1816f65024c36fb09 100644 (file)
@@ -6,7 +6,7 @@
 .\"    Case Western Reserve University
 .\"    chet@po.CWRU.Edu
 .\"
-.\"    Last Change: Sat Jun 26 14:26:44 EDT 2004
+.\"    Last Change: Mon Aug 16 23:07:25 EDT 2004
 .\"
 .\" bash_builtins, strip all but Built-Ins section
 .if \n(zZ=1 .ig zZ
@@ -5872,8 +5872,8 @@ is supplied, the name and value of the alias is printed.
 \fBAlias\fP returns true unless a \fIname\fP is given for which
 no alias has been defined.
 .TP
-\fBbg\fP [\fIjobspec\fP]
-Resume the suspended job \fIjobspec\fP in the background, as if it
+\fBbg\fP [\fIjobspec\fP ...]
+Resume each suspended job \fIjobspec\fP in the background, as if it
 had been started with
 .BR & .
 If \fIjobspec\fP is not present, the shell's notion of the
@@ -5881,8 +5881,8 @@ If \fIjobspec\fP is not present, the shell's notion of the
 .B bg
 .I jobspec
 returns 0 unless run when job control is disabled or, when run with
-job control enabled, if \fIjobspec\fP was not found or started without
-job control.
+job control enabled, if the last \fIjobspec\fP was not found or was
+started without job control.
 .TP
 \fBbind\fP [\fB\-m\fP \fIkeymap\fP] [\fB\-lpsvPSV\fP]
 .PD 0
diff --git a/doc/bash.1~ b/doc/bash.1~
new file mode 100644 (file)
index 0000000..21d0aba
--- /dev/null
@@ -0,0 +1,8739 @@
+.\"
+.\" MAN PAGE COMMENTS to
+.\"
+.\"    Chet Ramey
+.\"    Information Network Services
+.\"    Case Western Reserve University
+.\"    chet@po.CWRU.Edu
+.\"
+.\"    Last Change: Sat Jun 26 14:26:44 EDT 2004
+.\"
+.\" bash_builtins, strip all but Built-Ins section
+.if \n(zZ=1 .ig zZ
+.if \n(zY=1 .ig zY
+.TH BASH 1 "2004 June 26" "GNU Bash-3.0"
+.\"
+.\" There's some problem with having a `@'
+.\" in a tagged paragraph with the BSD man macros.
+.\" It has to do with `@' appearing in the }1 macro.
+.\" This is a problem on 4.3 BSD and Ultrix, but Sun
+.\" appears to have fixed it.
+.\" If you're seeing the characters
+.\" `@u-3p' appearing before the lines reading
+.\" `possible-hostname-completions
+.\" and `complete-hostname' down in READLINE,
+.\" then uncomment this redefinition.
+.\"
+.de }1
+.ds ]X \&\\*(]B\\
+.nr )E 0
+.if !"\\$1"" .nr )I \\$1n
+.}f
+.ll \\n(LLu
+.in \\n()Ru+\\n(INu+\\n()Iu
+.ti \\n(INu
+.ie !\\n()Iu+\\n()Ru-\w\a\\*(]X\au-3p \{\\*(]X
+.br\}
+.el \\*(]X\h\a|\\n()Iu+\\n()Ru\a\c
+.}f
+..
+.\"
+.\" File Name macro.  This used to be `.PN', for Path Name,
+.\" but Sun doesn't seem to like that very much.
+.\"
+.de FN
+\fI\|\\$1\|\fP
+..
+.SH NAME
+bash \- GNU Bourne-Again SHell
+.SH SYNOPSIS
+.B bash
+[options]
+[file]
+.SH COPYRIGHT
+.if n Bash is Copyright (C) 1989-2004 by the Free Software Foundation, Inc.
+.if t Bash is Copyright \(co 1989-2004 by the Free Software Foundation, Inc.
+.SH DESCRIPTION
+.B Bash
+is an \fBsh\fR-compatible command language interpreter that
+executes commands read from the standard input or from a file.
+.B Bash
+also incorporates useful features from the \fIKorn\fP and \fIC\fP
+shells (\fBksh\fP and \fBcsh\fP).
+.PP
+.B Bash
+is intended to be a conformant implementation of the IEEE
+POSIX Shell and Tools specification (IEEE Working Group 1003\.2).
+.SH OPTIONS
+In addition to the single-character shell options documented in the
+description of the \fBset\fR builtin command, \fBbash\fR
+interprets the following options when it is invoked:
+.PP
+.PD 0
+.TP 10
+.BI \-c "\| string\^"
+If the
+.B \-c
+option is present, then commands are read from
+.IR string .
+If there are arguments after the
+.IR string ,
+they are assigned to the positional parameters, starting with
+.BR $0 .
+.TP
+.B \-i
+If the
+.B \-i
+option is present, the shell is
+.IR interactive .
+.TP
+.B \-l
+Make
+.B bash
+act as if it had been invoked as a login shell (see
+.SM
+.B INVOCATION
+below).
+.TP
+.B \-r
+If the
+.B \-r
+option is present, the shell becomes
+.I restricted
+(see
+.SM
+.B "RESTRICTED SHELL"
+below).
+.TP
+.B \-s
+If the
+.B \-s
+option is present, or if no arguments remain after option
+processing, then commands are read from the standard input.
+This option allows the positional parameters to be set
+when invoking an interactive shell.
+.TP
+.B \-D
+A list of all double-quoted strings preceded by \fB$\fP
+is printed on the standard ouput.
+These are the strings that
+are subject to language translation when the current locale
+is not \fBC\fP or \fBPOSIX\fP.
+This implies the \fB\-n\fP option; no commands will be executed.
+.TP
+.B [\-+]O [\fIshopt_option\fP]
+\fIshopt_option\fP is one of the shell options accepted by the
+\fBshopt\fP builtin (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+If \fIshopt_option\fP is present, \fB\-O\fP sets the value of that option;
+\fB+O\fP unsets it.
+If \fIshopt_option\fP is not supplied, the names and values of the shell
+options accepted by \fBshopt\fP are printed on the standard output.
+If the invocation option is \fB+O\fP, the output is displayed in a format
+that may be reused as input.
+.TP
+.B \-\-
+A
+.B \-\-
+signals the end of options and disables further option processing.
+Any arguments after the
+.B \-\-
+are treated as filenames and arguments.  An argument of
+.B \-
+is equivalent to \fB\-\-\fP.
+.PD
+.PP
+.B Bash
+also interprets a number of multi-character options.
+These options must appear on the command line before the
+single-character options to be recognized.
+.PP
+.PD 0
+.TP
+.B \-\-debugger
+Arrange for the debugger profile to be executed before the shell
+starts.  Turns on extended debugging mode (see the description of the
+.B extdebug
+option to the
+.B shopt
+builtin below) and shell function tracing (see the description of the
+\fB\-o functrace\fP option to the
+.B set
+builtin below).
+.TP
+.B \-\-dump\-po\-strings
+Equivalent to \fB\-D\fP, but the output is in the GNU \fIgettext\fP
+\fBpo\fP (portable object) file format.
+.TP
+.B \-\-dump\-strings
+Equivalent to \fB\-D\fP.
+.TP
+.B \-\-help
+Display a usage message on standard output and exit successfully.
+.TP
+\fB\-\-init\-file\fP \fIfile\fP
+.PD 0
+.TP
+\fB\-\-rcfile\fP \fIfile\fP
+.PD
+Execute commands from
+.I file
+instead of the standard personal initialization file
+.I ~/.bashrc
+if the shell is interactive (see
+.SM
+.B INVOCATION
+below).
+.TP
+.B \-\-login
+Equivalent to \fB\-l\fP.
+.TP
+.B \-\-noediting
+Do not use the GNU
+.B readline
+library to read command lines when the shell is interactive.
+.TP
+.B \-\-noprofile
+Do not read either the system-wide startup file
+.FN /etc/profile
+or any of the personal initialization files
+.IR ~/.bash_profile ,
+.IR ~/.bash_login ,
+or
+.IR ~/.profile .
+By default,
+.B bash
+reads these files when it is invoked as a login shell (see
+.SM
+.B INVOCATION
+below).
+.TP
+.B \-\-norc
+Do not read and execute the personal initialization file
+.I ~/.bashrc
+if the shell is interactive.
+This option is on by default if the shell is invoked as
+.BR sh .
+.TP
+.B \-\-posix
+Change the behavior of \fBbash\fP where the default operation differs
+from the POSIX 1003.2 standard to match the standard (\fIposix mode\fP).
+.TP
+.B \-\-restricted
+The shell becomes restricted (see
+.SM
+.B "RESTRICTED SHELL"
+below).
+.TP
+.B \-\-verbose
+Equivalent to  \fB\-v\fP.
+.TP
+.B \-\-version
+Show version information for this instance of
+.B bash
+on the standard output and exit successfully.
+.PD
+.SH ARGUMENTS
+If arguments remain after option processing, and neither the
+.B \-c
+nor the
+.B \-s
+option has been supplied, the first argument is assumed to
+be the name of a file containing shell commands.
+If
+.B bash
+is invoked in this fashion, 
+.B $0
+is set to the name of the file, and the positional parameters
+are set to the remaining arguments.
+.B Bash
+reads and executes commands from this file, then exits.
+\fBBash\fP's exit status is the exit status of the last command
+executed in the script.
+If no commands are executed, the exit status is 0.
+An attempt is first made to open the file in the current directory, and,
+if no file is found, then the shell searches the directories in
+.SM
+.B PATH
+for the script.
+.SH INVOCATION
+A \fIlogin shell\fP is one whose first character of argument zero is a
+.BR \- ,
+or one started with the 
+.B \-\-login
+option.
+.PP
+An \fIinteractive\fP shell is one started without non-option arguments
+and without the
+.B \-c
+option
+whose standard input and error are
+both connected to terminals (as determined by
+.IR isatty (3)),
+or one started with the
+.B \-i
+option.
+.SM
+.B PS1
+is set and
+.B $\-
+includes
+.B i
+if
+.B bash
+is interactive,
+allowing a shell script or a startup file to test this state.
+.PP
+The following paragraphs describe how
+.B bash
+executes its startup files.
+If any of the files exist but cannot be read,
+.B bash
+reports an error.
+Tildes are expanded in file names as described below under
+.B "Tilde Expansion"
+in the
+.SM
+.B EXPANSION
+section.
+.PP
+When
+.B bash
+is invoked as an interactive login shell, or as a non-interactive shell
+with the \fB\-\-login\fP option, it first reads and
+executes commands from the file \fI/etc/profile\fP, if that
+file exists.
+After reading that file, it looks for \fI~/.bash_profile\fP,
+\fI~/.bash_login\fP, and \fI~/.profile\fP, in that order, and reads
+and executes commands from the first one that exists and is readable.
+The
+.B \-\-noprofile
+option may be used when the shell is started to inhibit this behavior.
+.PP
+When a login shell exits,
+.B bash
+reads and executes commands from the file \fI~/.bash_logout\fP, if it
+exists.
+.PP
+When an interactive shell that is not a login shell is started,
+.B bash
+reads and executes commands from \fI~/.bashrc\fP, if that file exists.
+This may be inhibited by using the
+.B \-\-norc
+option.
+The \fB\-\-rcfile\fP \fIfile\fP option will force
+.B bash
+to read and execute commands from \fIfile\fP instead of \fI~/.bashrc\fP.
+.PP
+When
+.B bash
+is started non-interactively, to run a shell script, for example, it
+looks for the variable
+.SM
+.B BASH_ENV
+in the environment, expands its value if it appears there, and uses the
+expanded value as the name of a file to read and execute.
+.B Bash
+behaves as if the following command were executed:
+.sp .5
+.RS
+.if t \f(CWif [ \-n "$BASH_ENV" ]; then . "$BASH_ENV"; fi\fP
+.if n if [ \-n "$BASH_ENV" ]; then . "$BASH_ENV"; fi
+.RE
+.sp .5
+but the value of the
+.SM
+.B PATH
+variable is not used to search for the file name.
+.PP
+If
+.B bash
+is invoked with the name
+.BR sh ,
+it tries to mimic the startup behavior of historical versions of
+.B sh
+as closely as possible,
+while conforming to the POSIX standard as well.
+When invoked as an interactive login shell, or a non-interactive
+shell with the \fB\-\-login\fP option, it first attempts to
+read and execute commands from
+.I /etc/profile
+and
+.IR ~/.profile ,
+in that order.
+The
+.B \-\-noprofile
+option may be used to inhibit this behavior.
+When invoked as an interactive shell with the name
+.BR sh ,
+.B bash
+looks for the variable
+.SM
+.BR ENV ,
+expands its value if it is defined, and uses the
+expanded value as the name of a file to read and execute.
+Since a shell invoked as
+.B sh
+does not attempt to read and execute commands from any other startup
+files, the
+.B \-\-rcfile
+option has no effect.
+A non-interactive shell invoked with the name
+.B sh
+does not attempt to read any other startup files. 
+When invoked as
+.BR sh ,
+.B bash
+enters
+.I posix
+mode after the startup files are read.
+.PP
+When
+.B bash
+is started in
+.I posix
+mode, as with the
+.B \-\-posix
+command line option, it follows the POSIX standard for startup files.
+In this mode, interactive shells expand the
+.SM
+.B ENV
+variable and commands are read and executed from the file
+whose name is the expanded value.
+No other startup files are read.
+.PP
+.B Bash
+attempts to determine when it is being run by the remote shell
+daemon, usually \fIrshd\fP.
+If
+.B bash
+determines it is being run by \fIrshd\fP, it reads and executes
+commands from \fI~/.bashrc\fP, if that file exists and is readable.
+It will not do this if invoked as \fBsh\fP.
+The
+.B \-\-norc
+option may be used to inhibit this behavior, and the
+.B \-\-rcfile
+option may be used to force another file to be read, but
+\fIrshd\fP does not generally invoke the shell with those options
+or allow them to be specified.
+.PP
+If the shell is started with the effective user (group) id not equal to the
+real user (group) id, and the \fB\-p\fP option is not supplied, no startup
+files are read, shell functions are not inherited from the environment, the
+.SM
+.B SHELLOPTS
+variable, if it appears in the environment, is ignored,
+and the effective user id is set to the real user id.
+If the \fB\-p\fP option is supplied at invocation, the startup behavior is
+the same, but the effective user id is not reset.
+.SH DEFINITIONS
+.PP
+The following definitions are used throughout the rest of this
+document.
+.PD 0
+.TP
+.B blank 
+A space or tab.
+.TP
+.B word
+A sequence of characters considered as a single unit by the shell.
+Also known as a
+.BR token .
+.TP
+.B name
+A 
+.I word
+consisting only of alphanumeric characters and underscores, and
+beginning with an alphabetic character or an underscore.  Also
+referred to as an
+.BR identifier .
+.TP
+.B metacharacter
+A character that, when unquoted, separates words.  One of the following:
+.br
+.RS
+.PP
+.if t \fB|  &  ;  (  )  <  >  space  tab\fP
+.if n \fB|  & ; ( ) < > space tab\fP
+.RE
+.PP
+.TP
+.B control operator
+A \fItoken\fP that performs a control function.  It is one of the following
+symbols:
+.RS
+.PP
+.if t \fB\(bv\(bv  &  &&  ;  ;;  (  )  |  <newline>\fP
+.if n \fB|| & && ; ;; ( ) | <newline>\fP
+.RE
+.PD
+.SH "RESERVED WORDS"
+\fIReserved words\fP are words that have a special meaning to the shell.
+The following words are recognized as reserved when unquoted and either
+the first word of a simple command (see
+.SM
+.B SHELL GRAMMAR
+below) or the third word of a 
+.B case 
+or
+.B for
+command:
+.if t .RS
+.PP
+.B
+.if n ! case  do done elif else esac fi for function if in select then until while { } time [[ ]]
+.if t !    case    do    done    elif    else    esac    fi    for    function    if    in    select    then    until    while    {    }    time    [[    ]]
+.if t .RE
+.SH "SHELL GRAMMAR"
+.SS Simple Commands
+.PP
+A \fIsimple command\fP is a sequence of optional variable assignments
+followed by \fBblank\fP-separated words and redirections, and
+terminated by a \fIcontrol operator\fP.  The first word
+specifies the command to be executed, and is passed as argument zero.
+The remaining words are passed as arguments to the invoked command.
+.PP
+The return value of a \fIsimple command\fP is its exit status, or
+128+\fIn\^\fP if the command is terminated by signal
+.IR n .
+.SS Pipelines
+.PP
+A \fIpipeline\fP is a sequence of one or more commands separated by
+the character
+.BR | .
+The format for a pipeline is:
+.RS
+.PP
+[\fBtime\fP [\fB\-p\fP]] [ ! ] \fIcommand\fP [ \fB|\fP \fIcommand2\fP ... ]
+.RE
+.PP
+The standard output of
+.I command
+is connected via a pipe to the standard input of
+.IR command2 .
+This connection is performed before any redirections specified by the
+command (see
+.SM
+.B REDIRECTION
+below).
+.PP
+The return status of a pipeline is the exit status of the last
+command, unless the \fBpipefail\fP option is enabled.
+If \fBpipefail\fP is enabled, the pipeline's return status is the
+value of the last (rightmost) command to exit with a non-zero status,
+or zero if all commands exit successfully.
+If the reserved word
+.B !
+precedes a pipeline, the exit status of that pipeline is the logical
+negation of the exit status as described above.
+The shell waits for all commands in the pipeline to
+terminate before returning a value.
+.PP
+If the
+.B time
+reserved word precedes a pipeline, the elapsed as well as user and
+system time consumed by its execution are reported when the pipeline
+terminates.
+The \fB\-p\fP option changes the output format to that specified by POSIX.
+The
+.SM
+.B TIMEFORMAT
+variable may be set to a format string that specifies how the timing
+information should be displayed; see the description of
+.SM
+.B TIMEFORMAT
+under
+.B "Shell Variables"
+below.
+.PP
+Each command in a pipeline is executed as a separate process (i.e., in a
+subshell).
+.SS Lists
+.PP
+A \fIlist\fP is a sequence of one or more pipelines separated by one
+of the operators
+.BR ; ,
+.BR & ,
+.BR && ,
+or
+.BR \(bv\(bv ,
+and optionally terminated by one of
+.BR ; ,
+.BR & ,
+or
+.BR <newline> .
+.PP
+Of these list operators,
+.B &&
+and
+.B \(bv\(bv
+have equal precedence, followed by
+.B ;
+and
+.BR &,
+which have equal precedence.
+.PP
+A sequence of one or more newlines may appear in a \fIlist\fP instead
+of a semicolon to delimit commands.
+.PP
+If a command is terminated by the control operator
+.BR & ,
+the shell executes the command in the \fIbackground\fP
+in a subshell.  The shell does not wait for the command to
+finish, and the return status is 0.  Commands separated by a
+.B ;
+are executed sequentially; the shell waits for each
+command to terminate in turn.  The return status is the
+exit status of the last command executed.
+.PP
+The control operators
+.B &&
+and
+.B \(bv\(bv
+denote AND lists and OR lists, respectively.
+An AND list has the form
+.RS
+.PP
+\fIcommand1\fP \fB&&\fP \fIcommand2\fP
+.RE
+.PP
+.I command2
+is executed if, and only if,
+.I command1
+returns an exit status of zero.
+.PP
+An OR list has the form
+.RS
+.PP
+\fIcommand1\fP \fB\(bv\(bv\fP \fIcommand2\fP
+.PP
+.RE
+.PP
+.I command2
+is executed if and only if
+.I command1
+returns a non-zero exit status.  The return status of
+AND and OR lists is the exit status of the last command
+executed in the list.
+.SS Compound Commands
+.PP
+A \fIcompound command\fP is one of the following:
+.TP
+(\fIlist\fP)
+\fIlist\fP is executed in a subshell environment (see
+.SM
+\fBCOMMAND EXECUTION ENVIRONMENT\fP
+below).
+Variable assignments and builtin
+commands that affect the shell's environment do not remain in effect
+after the command completes.  The return status is the exit status of
+\fIlist\fP.
+.TP
+{ \fIlist\fP; }
+\fIlist\fP is simply executed in the current shell environment.
+\fIlist\fP must be terminated with a newline or semicolon.
+This is known as a \fIgroup command\fP.
+The return status is the exit status of
+\fIlist\fP.
+Note that unlike the metacharacters \fB(\fP and \fB)\fP, \fB{\fP and
+\fB}\fP are \fIreserved words\fP and must occur where a reserved
+word is permitted to be recognized.  Since they do not cause a word
+break, they must be separated from \fIlist\fP by whitespace.
+.TP
+((\fIexpression\fP))
+The \fIexpression\fP is evaluated according to the rules described
+below under
+.SM
+.BR "ARITHMETIC EVALUATION" .
+If the value of the expression is non-zero, the return status is 0;
+otherwise the return status is 1.  This is exactly equivalent to
+\fBlet "\fIexpression\fP"\fR.
+.TP
+\fB[[\fP \fIexpression\fP \fB]]\fP
+Return a status of 0 or 1 depending on the evaluation of
+the conditional expression \fIexpression\fP.
+Expressions are composed of the primaries described below under
+.SM
+.BR "CONDITIONAL EXPRESSIONS" .
+Word splitting and pathname expansion are not performed on the words
+between the \fB[[\fP and \fB]]\fP; tilde expansion, parameter and
+variable expansion, arithmetic expansion, command substitution, process
+substitution, and quote removal are performed.
+Conditional operators such as \fB\-f\fP must be unquoted to be recognized
+as primaries.
+.if t .sp 0.5
+.if n .sp 1
+When the \fB==\fP and \fB!=\fP operators are used, the string to the
+right of the operator is considered a pattern and matched according
+to the rules described below under \fBPattern Matching\fP.
+The return value is 0 if the string matches or does not match
+the pattern, respectively, and 1 otherwise.
+Any part of the pattern may be quoted to force it to be matched as a
+string.
+.if t .sp 0.5
+.if n .sp 1
+An additional binary operator, \fB=~\fP, is available, with the same
+precedence as \fB==\fP and \fB!=\fP.
+When it is used, the string to the right of the operator is considered
+an extended regular expression and matched accordingly (as in \fIregex\fP(3)).  
+The return value is 0 if the string matches
+the pattern, and 1 otherwise.
+If the regular expression is syntactically incorrect, the conditional
+expression's return value is 2.
+If the shell option
+.B nocaseglob
+is enabled, the match is performed without regard to the case
+of alphabetic characters.
+Substrings matched by parenthesized subexpressions within the regular
+expression are saved in the array variable \fBBASH_REMATCH\fP.
+The element of \fBBASH_REMATCH\fP with index 0 is the portion of the string
+matching the entire regular expression.
+The element of \fBBASH_REMATCH\fP with index \fIn\fP is the portion of the
+string matching the \fIn\fPth parenthesized subexpression.
+.if t .sp 0.5
+.if n .sp 1
+Expressions may be combined using the following operators, listed
+in decreasing order of precedence:
+.if t .sp 0.5
+.if n .sp 1
+.RS
+.PD 0
+.TP
+.B ( \fIexpression\fP )
+Returns the value of \fIexpression\fP.
+This may be used to override the normal precedence of operators.
+.TP
+.B ! \fIexpression\fP
+True if
+.I expression
+is false.
+.TP
+\fIexpression1\fP \fB&&\fP \fIexpression2\fP
+True if both
+.I expression1
+and
+.I expression2
+are true.
+.TP
+.if t \fIexpression1\fP \fB\(bv\(bv\fP \fIexpression2\fP
+.if n \fIexpression1\fP \fB||\fP \fIexpression2\fP
+True if either
+.I expression1
+or
+.I expression2
+is true.
+.PD
+.LP
+The \fB&&\fP and
+.if t \fB\(bv\(bv\fP
+.if n \fB||\fP
+operators do not evaluate \fIexpression2\fP if the value of
+\fIexpression1\fP is sufficient to determine the return value of
+the entire conditional expression.
+.RE
+.TP
+\fBfor\fP \fIname\fP [ \fBin\fP \fIword\fP ] ; \fBdo\fP \fIlist\fP ; \fBdone\fP
+The list of words following \fBin\fP is expanded, generating a list
+of items.
+The variable \fIname\fP is set to each element of this list
+in turn, and \fIlist\fP is executed each time.
+If the \fBin\fP \fIword\fP is omitted, the \fBfor\fP command executes
+\fIlist\fP once for each positional parameter that is set (see
+.SM
+.B PARAMETERS
+below).
+The return status is the exit status of the last command that executes.
+If the expansion of the items following \fBin\fP results in an empty
+list, no commands are executed, and the return status is 0.
+.TP
+\fBfor\fP (( \fIexpr1\fP ; \fIexpr2\fP ; \fIexpr3\fP )) ; \fBdo\fP \fIlist\fP ; \fBdone\fP
+First, the arithmetic expression \fIexpr1\fP is evaluated according
+to the rules described below under
+.SM
+.BR "ARITHMETIC EVALUATION" .
+The arithmetic expression \fIexpr2\fP is then evaluated repeatedly
+until it evaluates to zero.
+Each time \fIexpr2\fP evaluates to a non-zero value, \fIlist\fP is
+executed and the arithmetic expression \fIexpr3\fP is evaluated.
+If any expression is omitted, it behaves as if it evaluates to 1.
+The return value is the exit status of the last command in \fIlist\fP
+that is executed, or false if any of the expressions is invalid.
+.TP
+\fBselect\fP \fIname\fP [ \fBin\fP \fIword\fP ] ; \fBdo\fP \fIlist\fP ; \fBdone\fP
+The list of words following \fBin\fP is expanded, generating a list
+of items.  The set of expanded words is printed on the standard
+error, each preceded by a number.  If the \fBin\fP
+\fIword\fP is omitted, the positional parameters are printed (see
+.SM
+.B PARAMETERS
+below).  The
+.B PS3
+prompt is then displayed and a line read from the standard input.
+If the line consists of a number corresponding to one of
+the displayed words, then the value of
+.I name
+is set to that word.  If the line is empty, the words and prompt
+are displayed again.  If EOF is read, the command completes.  Any
+other value read causes
+.I name
+to be set to null.  The line read is saved in the variable
+.BR REPLY .
+The
+.I list
+is executed after each selection until a
+.B break
+command is executed.
+The exit status of
+.B select
+is the exit status of the last command executed in
+.IR list ,
+or zero if no commands were executed.
+.TP
+\fBcase\fP \fIword\fP \fBin\fP [ [(] \fIpattern\fP [ \fB|\fP \fIpattern\fP ] \
+... ) \fIlist\fP ;; ] ... \fBesac\fP
+A \fBcase\fP command first expands \fIword\fP, and tries to match
+it against each \fIpattern\fP in turn, using the same matching rules
+as for pathname expansion (see
+.B Pathname Expansion
+below).  When a match is found, the
+corresponding \fIlist\fP is executed.  After the first match, no
+subsequent matches are attempted.  The exit status is zero if no
+pattern matches.  Otherwise, it is the exit status of the
+last command executed in \fIlist\fP.
+.TP
+\fBif\fP \fIlist\fP; \fBthen\fP \fIlist;\fP \
+[ \fBelif\fP \fIlist\fP; \fBthen\fP \fIlist\fP; ] ... \
+[ \fBelse\fP \fIlist\fP; ] \fBfi\fP
+The
+.B if 
+.I list
+is executed.  If its exit status is zero, the
+\fBthen\fP \fIlist\fP is executed.  Otherwise, each \fBelif\fP
+\fIlist\fP is executed in turn, and if its exit status is zero,
+the corresponding \fBthen\fP \fIlist\fP is executed and the
+command completes.  Otherwise, the \fBelse\fP \fIlist\fP is
+executed, if present.  The exit status is the exit status of the
+last command executed, or zero if no condition tested true.
+.TP
+\fBwhile\fP \fIlist\fP; \fBdo\fP \fIlist\fP; \fBdone\fP
+.PD 0
+.TP
+\fBuntil\fP \fIlist\fP; \fBdo\fP \fIlist\fP; \fBdone\fP
+.PD
+The \fBwhile\fP command continuously executes the \fBdo\fP
+\fIlist\fP as long as the last command in \fIlist\fP returns
+an exit status of zero.  The \fBuntil\fP command is identical
+to the \fBwhile\fP command, except that the test is negated;
+the
+.B do
+.I list
+is executed as long as the last command in
+.I list
+returns a non-zero exit status.
+The exit status of the \fBwhile\fP and \fBuntil\fP commands
+is the exit status
+of the last \fBdo\fP \fIlist\fP command executed, or zero if
+none was executed.
+.SS Shell Function Definitions
+.PP
+A shell function is an object that is called like a simple command and
+executes a compound command with a new set of positional parameters.
+Shell functions are declared as follows:
+.TP
+[ \fBfunction\fP ] \fIname\fP () \fIcompound\-command\fP [\fIredirection\fP]
+This defines a function named \fIname\fP.
+The reserved word \fBfunction\fP is optional.
+If the \fBfunction\fP reserved word is supplied, the parentheses are optional.
+The \fIbody\fP of the function is the compound command
+.I compound\-command 
+(see \fBCompound Commands\fP above).
+That command is usually a \fIlist\fP of commands between { and }, but
+may be any command listed under \fBCompound Commands\fP above.
+\fIcompound\-command\fP is executed whenever \fIname\fP is specified as the
+name of a simple command.
+Any redirections (see
+.SM
+.B REDIRECTION
+below) specified when a function is defined are performed
+when the function is executed.
+The exit status of a function definition is zero unless a syntax error
+occurs or a readonly function with the same name already exists.
+When executed, the exit status of a function is the exit status of the
+last command executed in the body.  (See
+.SM
+.B FUNCTIONS
+below.)
+.SH COMMENTS
+In a non-interactive shell, or an interactive shell in which the
+.B interactive_comments
+option to the
+.B shopt
+builtin is enabled (see
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below), a word beginning with
+.B #
+causes that word and all remaining characters on that line to
+be ignored.  An interactive shell without the
+.B interactive_comments
+option enabled does not allow comments.  The
+.B interactive_comments
+option is on by default in interactive shells.
+.SH QUOTING
+\fIQuoting\fP is used to remove the special meaning of certain
+characters or words to the shell.  Quoting can be used to 
+disable special treatment for special characters, to prevent
+reserved words from being recognized as such, and to prevent
+parameter expansion.
+.PP
+Each of the \fImetacharacters\fP listed above under
+.SM
+.B DEFINITIONS
+has special meaning to the shell and must be quoted if it is to
+represent itself.
+.PP
+When the command history expansion facilities are being used, the
+\fIhistory expansion\fP character, usually \fB!\fP, must be quoted
+to prevent history expansion.
+.PP
+There are three quoting mechanisms: the
+.IR "escape character" ,
+single quotes, and double quotes.
+.PP
+A non-quoted backslash (\fB\e\fP) is the
+.IR "escape character" .
+It preserves the literal value of the next character that follows,
+with the exception of <newline>.  If a \fB\e\fP<newline> pair
+appears, and the backslash is not itself quoted, the \fB\e\fP<newline>
+is treated as a line continuation (that is, it is removed from the
+input stream and effectively ignored).
+.PP
+Enclosing characters in single quotes preserves the literal value
+of each character within the quotes.  A single quote may not occur
+between single quotes, even when preceded by a backslash.
+.PP
+Enclosing characters in double quotes preserves the literal value
+of all characters within the quotes, with the exception of
+.BR $ ,
+.BR ` ,
+and
+.BR \e .
+The characters
+.B $
+and
+.B `
+retain their special meaning within double quotes.  The backslash
+retains its special meaning only when followed by one of the following
+characters:
+.BR $ ,
+.BR ` ,
+\^\fB"\fP\^,
+.BR \e ,
+or
+.BR <newline> .
+A double quote may be quoted within double quotes by preceding it with
+a backslash.
+When command history is being used, the double quote may not be used to
+quote the history expansion character.
+.PP
+The special parameters
+.B *
+and
+.B @
+have special meaning when in double
+quotes (see
+.SM
+.B PARAMETERS
+below).
+.PP
+Words of the form \fB$\fP'\fIstring\fP' are treated specially.  The
+word expands to \fIstring\fP, with backslash-escaped characters replaced
+as specifed by the ANSI C standard.  Backslash escape sequences, if
+present, are decoded as follows:
+.RS
+.PD 0
+.TP
+.B \ea
+alert (bell)
+.TP
+.B \eb
+backspace
+.TP
+.B \ee
+an escape character
+.TP   
+.B \ef
+form feed
+.TP  
+.B \en
+new line
+.TP     
+.B \er
+carriage return
+.TP
+.B \et
+horizontal tab
+.TP   
+.B \ev
+vertical tab
+.TP
+.B \e\e
+backslash
+.TP
+.B \e'
+single quote
+.TP   
+.B \e\fInnn\fP
+the eight-bit character whose value is the octal value \fInnn\fP
+(one to three digits)
+.TP
+.B \ex\fIHH\fP
+the eight-bit character whose value is the hexadecimal value \fIHH\fP
+(one or two hex digits)
+.TP
+.B \ec\fIx\fP
+a control-\fIx\fP character
+.PD
+.RE
+.LP
+The expanded result is single-quoted, as if the dollar sign had
+not been present.
+.PP
+A double-quoted string preceded by a dollar sign (\fB$\fP) will cause
+the string to be translated according to the current locale.
+If the current locale is \fBC\fP or \fBPOSIX\fP, the dollar sign
+is ignored.
+If the string is translated and replaced, the replacement is
+double-quoted.
+.SH PARAMETERS
+A
+.I parameter
+is an entity that stores values.
+It can be a
+.IR name ,
+a number, or one of the special characters listed below under
+.BR "Special Parameters" .
+A
+.I variable
+is a parameter denoted by a
+.IR name .
+A variable has a \fIvalue\fP and zero or more \fIattributes\fP.
+Attributes are assigned using the
+.B declare
+builtin command (see
+.B declare
+below in
+.SM
+.BR "SHELL BUILTIN COMMANDS" ).
+.PP
+A parameter is set if it has been assigned a value.  The null string is
+a valid value.  Once a variable is set, it may be unset only by using
+the
+.B unset
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.PP
+A
+.I variable
+may be assigned to by a statement of the form
+.RS
+.PP
+\fIname\fP=[\fIvalue\fP]
+.RE
+.PP
+If
+.I value
+is not given, the variable is assigned the null string.  All
+.I values
+undergo tilde expansion, parameter and variable expansion,
+command substitution, arithmetic expansion, and quote
+removal (see
+.SM
+.B EXPANSION
+below).  If the variable has its
+.B integer
+attribute set, then
+.I value
+is evaluated as an arithmetic expression even if the $((...)) expansion is
+not used (see
+.B "Arithmetic Expansion"
+below).
+Word splitting is not performed, with the exception
+of \fB"$@"\fP as explained below under
+.BR "Special Parameters" .
+Pathname expansion is not performed.
+Assignment statements may also appear as arguments to the
+.BR alias ,
+.BR declare ,
+.BR typeset ,
+.BR export ,
+.BR readonly ,
+and
+.B local
+builtin commands.
+.SS Positional Parameters
+.PP
+A
+.I positional parameter
+is a parameter denoted by one or more
+digits, other than the single digit 0.  Positional parameters are
+assigned from the shell's arguments when it is invoked,
+and may be reassigned using the
+.B set
+builtin command.  Positional parameters may not be assigned to
+with assignment statements.  The positional parameters are
+temporarily replaced when a shell function is executed (see
+.SM
+.B FUNCTIONS
+below).
+.PP
+When a positional parameter consisting of more than a single
+digit is expanded, it must be enclosed in braces (see
+.SM
+.B EXPANSION
+below).
+.SS Special Parameters
+.PP
+The shell treats several parameters specially.  These parameters may
+only be referenced; assignment to them is not allowed.
+.PD 0
+.TP
+.B *
+Expands to the positional parameters, starting from one.  When the
+expansion occurs within double quotes, it expands to a single word
+with the value of each parameter separated by the first character
+of the 
+.SM
+.B IFS
+special variable.  That is, "\fB$*\fP" is equivalent
+to "\fB$1\fP\fIc\fP\fB$2\fP\fIc\fP\fB...\fP", where
+.I c
+is the first character of the value of the
+.SM
+.B IFS
+variable.  If
+.SM
+.B IFS
+is unset, the parameters are separated by spaces.
+If
+.SM
+.B IFS
+is null, the parameters are joined without intervening separators.
+.TP
+.B @
+Expands to the positional parameters, starting from one.  When the
+expansion occurs within double quotes, each parameter expands to a
+separate word.  That is, "\fB$@\fP" is equivalent to
+"\fB$1\fP" "\fB$2\fP" ...
+When there are no positional parameters, "\fB$@\fP" and 
+.B $@
+expand to nothing (i.e., they are removed).
+.TP
+.B #
+Expands to the number of positional parameters in decimal.
+.TP
+.B ?
+Expands to the status of the most recently executed foreground
+pipeline.
+.TP
+.B \-
+Expands to the current option flags as specified upon invocation, 
+by the
+.B set
+builtin command, or those set by the shell itself
+(such as the
+.B \-i
+option).
+.TP
+.B $
+Expands to the process ID of the shell.  In a () subshell, it
+expands to the process ID of the current shell, not the
+subshell.
+.TP
+.B !
+Expands to the process ID of the most recently executed background
+(asynchronous) command.
+.TP
+.B 0
+Expands to the name of the shell or shell script.  This is set at
+shell initialization.  If
+.B bash
+is invoked with a file of commands,
+.B $0
+is set to the name of that file.  If
+.B bash
+is started with the
+.B \-c
+option, then
+.B $0
+is set to the first argument after the string to be
+executed, if one is present.  Otherwise, it is set
+to the file name used to invoke
+.BR bash ,
+as given by argument zero.
+.TP
+.B _
+At shell startup, set to the absolute file name of the shell or shell
+script being executed as passed in the argument list.
+Subsequently, expands to the last argument to the previous command,
+after expansion.
+Also set to the full file name of each command executed and placed in
+the environment exported to that command.
+When checking mail, this parameter holds the name of the mail file
+currently being checked.
+.PD
+.SS Shell Variables
+.PP
+The following variables are set by the shell:
+.PP
+.PD 0
+.TP
+.B BASH
+Expands to the full file name used to invoke this instance of
+.BR bash .
+.TP
+.B BASH_ARGC
+An array variable whose values are the number of parameters in each
+frame of the current bash execution call stack.  The number of
+parameters to the current subroutine (shell function or script executed
+with \fB.\fP or \fBsource\fP) is at the top of the stack.  When a
+subroutine is executed, the number of parameters passed is pushed onto
+\fBBASH_ARGC\fP.
+.TP
+.B BASH_ARGV
+An array variable containing all of the parameters in the current bash
+execution call stack.  The final parameter of the last subroutine call
+is at the top of the stack; the first parameter of the initial call is
+at the bottom.  When a subroutine is executed, the parameters supplied
+are pushed onto \fBBASH_ARGV\fP.
+.TP
+.B BASH_COMMAND
+The command currently being executed or about to be executed, unless the
+shell is executing a command as the result of a trap,
+in which case it is the command executing at the time of the trap.
+.TP
+.B BASH_EXECUTION_STRING
+The command argument to the \fB\-c\fP invocation option.
+.TP
+.B BASH_LINENO
+An array variable whose members are the line numbers in source files
+corresponding to each member of @var{FUNCNAME}.
+\fB${BASH_LINENO[\fP\fI$i\fP\fB]}\fP is the line number in the source
+file where \fB${FUNCNAME[\fP\fI$i + 1\fP\fB]}\fP was called.
+The corresponding source file name is \fB${BASH_SOURCE[\fP\fI$i + 1\fP\fB]}\fB.
+Use \fBLINENO\fP to obtain the current line number.
+.TP
+.B BASH_REMATCH
+An array variable whose members are assigned by the \fB=~\fP binary
+operator to the \fB[[\fP conditional command.
+The element with index 0 is the portion of the string
+matching the entire regular expression.
+The element with index \fIn\fP is the portion of the
+string matching the \fIn\fPth parenthesized subexpression.
+This variable is read-only.
+.TP
+.B BASH_SOURCE
+An array variable whose members are the source filenames corresponding
+to the elements in the \fBFUNCNAME\fP array variable.
+.TP
+.B BASH_SUBSHELL
+Incremented by one each time a subshell or subshell environment is spawned.
+The initial value is 0.
+.TP
+.B BASH_VERSINFO
+A readonly array variable whose members hold version information for
+this instance of
+.BR bash .
+The values assigned to the array members are as follows:
+.sp .5
+.RS
+.PD 0
+.TP 24
+.B BASH_VERSINFO[\fR0\fP]
+The major version number (the \fIrelease\fP).
+.TP
+.B BASH_VERSINFO[\fR1\fP]
+The minor version number (the \fIversion\fP).
+.TP
+.B BASH_VERSINFO[\fR2\fP]
+The patch level.
+.TP
+.B BASH_VERSINFO[\fR3\fP]
+The build version.
+.TP
+.B BASH_VERSINFO[\fR4\fP]
+The release status (e.g., \fIbeta1\fP).
+.TP
+.B BASH_VERSINFO[\fR5\fP]
+The value of \fBMACHTYPE\fP.
+.PD
+.RE
+.TP
+.B BASH_VERSION
+Expands to a string describing the version of this instance of
+.BR bash .
+.TP
+.B COMP_CWORD
+An index into \fB${COMP_WORDS}\fP of the word containing the current
+cursor position.
+This variable is available only in shell functions invoked by the
+programmable completion facilities (see \fBProgrammable Completion\fP
+below).
+.TP
+.B COMP_LINE
+The current command line.
+This variable is available only in shell functions and external
+commands invoked by the
+programmable completion facilities (see \fBProgrammable Completion\fP
+below).
+.TP
+.B COMP_POINT
+The index of the current cursor position relative to the beginning of
+the current command.
+If the current cursor position is at the end of the current command,
+the value of this variable is equal to \fB${#COMP_LINE}\fP.
+This variable is available only in shell functions and external
+commands invoked by the
+programmable completion facilities (see \fBProgrammable Completion\fP
+below).
+.TP
+.B COMP_WORDBREAKS
+The set of characters that the Readline library treats as word
+separators when performing word completion.
+If
+.SM
+.B COMP_WORDBREAKS
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B COMP_WORDS
+An array variable (see \fBArrays\fP below) consisting of the individual
+words in the current command line.
+This variable is available only in shell functions invoked by the
+programmable completion facilities (see \fBProgrammable Completion\fP
+below).
+.TP
+.B DIRSTACK
+An array variable (see
+.B Arrays
+below) containing the current contents of the directory stack.
+Directories appear in the stack in the order they are displayed by the
+.B dirs
+builtin.
+Assigning to members of this array variable may be used to modify
+directories already in the stack, but the
+.B pushd
+and
+.B popd
+builtins must be used to add and remove directories.
+Assignment to this variable will not change the current directory.
+If
+.SM
+.B DIRSTACK
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B EUID
+Expands to the effective user ID of the current user, initialized at
+shell startup.  This variable is readonly.
+.TP
+.B FUNCNAME
+An array variable containing the names of all shell functions
+currently in the execution call stack.
+The element with index 0 is the name of any currently-executing
+shell function.
+The bottom-most element is "main".
+This variable exists only when a shell function is executing.
+Assignments to
+.SM
+.B FUNCNAME
+have no effect and return an error status.
+If
+.SM
+.B FUNCNAME
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B GROUPS
+An array variable containing the list of groups of which the current
+user is a member.
+Assignments to    
+.SM
+.B GROUPS
+have no effect and return an error status.
+If
+.SM
+.B GROUPS
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B HISTCMD
+The history number, or index in the history list, of the current
+command.
+If
+.SM
+.B HISTCMD
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B HOSTNAME
+Automatically set to the name of the current host.
+.TP
+.B HOSTTYPE
+Automatically set to a string that uniquely
+describes the type of machine on which
+.B bash
+is executing.
+The default is system-dependent.
+.TP
+.B LINENO
+Each time this parameter is referenced, the shell substitutes
+a decimal number representing the current sequential line number
+(starting with 1) within a script or function.  When not in a
+script or function, the value substituted is not guaranteed to
+be meaningful.
+If
+.SM
+.B LINENO
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B MACHTYPE
+Automatically set to a string that fully describes the system
+type on which
+.B bash
+is executing, in the standard GNU \fIcpu-company-system\fP format.
+The default is system-dependent.
+.TP
+.B OLDPWD
+The previous working directory as set by the
+.B cd
+command.
+.TP
+.B OPTARG
+The value of the last option argument processed by the
+.B getopts
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.TP
+.B OPTIND
+The index of the next argument to be processed by the
+.B getopts
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.TP
+.B OSTYPE
+Automatically set to a string that
+describes the operating system on which
+.B bash
+is executing.
+The default is system-dependent.
+.TP
+.B PIPESTATUS
+An array variable (see
+.B Arrays
+below) containing a list of exit status values from the processes
+in the most-recently-executed foreground pipeline (which may
+contain only a single command).
+.TP
+.B PPID
+The process ID of the shell's parent.  This variable is readonly.
+.TP
+.B PWD
+The current working directory as set by the
+.B cd
+command.
+.TP
+.B RANDOM
+Each time this parameter is referenced, a random integer between
+0 and 32767 is
+generated.  The sequence of random numbers may be initialized by assigning
+a value to
+.SM
+.BR RANDOM .
+If
+.SM
+.B RANDOM
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B REPLY
+Set to the line of input read by the
+.B read
+builtin command when no arguments are supplied.
+.TP
+.B SECONDS
+Each time this parameter is
+referenced, the number of seconds since shell invocation is returned.  If a
+value is assigned to 
+.SM
+.BR SECONDS ,
+the value returned upon subsequent
+references is
+the number of seconds since the assignment plus the value assigned.
+If
+.SM
+.B SECONDS
+is unset, it loses its special properties, even if it is
+subsequently reset.
+.TP
+.B SHELLOPTS
+A colon-separated list of enabled shell options.  Each word in
+the list is a valid argument for the
+.B \-o
+option to the
+.B set
+builtin command (see
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below).  The options appearing in
+.SM
+.B SHELLOPTS
+are those reported as
+.I on
+by \fBset \-o\fP.
+If this variable is in the environment when
+.B bash
+starts up, each shell option in the list will be enabled before
+reading any startup files.
+This variable is read-only.
+.TP
+.B SHLVL
+Incremented by one each time an instance of
+.B bash
+is started.
+.TP
+.B UID
+Expands to the user ID of the current user, initialized at shell startup.
+This variable is readonly.
+.PD
+.PP
+The following variables are used by the shell.  In some cases,
+.B bash
+assigns a default value to a variable; these cases are noted
+below.
+.PP
+.PD 0
+.TP
+.B BASH_ENV
+If this parameter is set when \fBbash\fP is executing a shell script,
+its value is interpreted as a filename containing commands to
+initialize the shell, as in
+.IR ~/.bashrc .
+The value of
+.SM
+.B BASH_ENV
+is subjected to parameter expansion, command substitution, and arithmetic
+expansion before being interpreted as a file name.
+.SM
+.B PATH
+is not used to search for the resultant file name.
+.TP
+.B CDPATH
+The search path for the
+.B cd
+command.
+This is a colon-separated list of directories in which the shell looks
+for destination directories specified by the
+.B cd
+command.
+A sample value is
+.if t \f(CW".:~:/usr"\fP.
+.if n ".:~:/usr".
+.TP
+.B COLUMNS
+Used by the \fBselect\fP builtin command to determine the terminal width
+when printing selection lists.  Automatically set upon receipt of a SIGWINCH.
+.TP
+.B COMPREPLY
+An array variable from which \fBbash\fP reads the possible completions
+generated by a shell function invoked by the programmable completion
+facility (see \fBProgrammable Completion\fP below).
+.TP
+.B EMACS
+If \fBbash\fP finds this variable in the environment when the shell starts
+with value
+.if t \f(CWt\fP,
+.if n "t",
+it assumes that the shell is running in an emacs shell buffer and disables
+line editing.
+.TP
+.B FCEDIT
+The default editor for the
+.B fc
+builtin command.
+.TP
+.B FIGNORE
+A colon-separated list of suffixes to ignore when performing
+filename completion (see
+.SM
+.B READLINE
+below).
+A filename whose suffix matches one of the entries in 
+.SM
+.B FIGNORE
+is excluded from the list of matched filenames.
+A sample value is
+.if t \f(CW".o:~"\fP.
+.if n ".o:~".
+.TP
+.B GLOBIGNORE
+A colon-separated list of patterns defining the set of filenames to
+be ignored by pathname expansion.
+If a filename matched by a pathname expansion pattern also matches one
+of the patterns in
+.SM
+.BR GLOBIGNORE ,
+it is removed from the list of matches.
+.TP
+.B HISTCONTROL
+A colon-separated list of values controlling how commands are saved on
+the history list.
+If the list of values includes
+.IR ignorespace ,
+lines which begin with a
+.B space
+character are not saved in the history list.
+A value of 
+.I ignoredups
+causes lines matching the previous history entry to not be saved.
+A value of
+.I ignoreboth
+is shorthand for \fIignorespace\fP and \fIignoredups\fP.
+A value of
+.IR erasedups
+causes all previous lines matching the current line to be removed from
+the history list before that line is saved.
+Any value not in the above list is ignored.
+If \fBHISTCONTROL\fP is unset, or does not include a valid value,
+all lines read by the shell parser are saved on the history list,
+subject to the value of
+.BR HISTIGNORE .
+The second and subsequent lines of a multi-line compound command are
+not tested, and are added to the history regardless of the value of
+.BR HISTCONTROL .
+.TP
+.B HISTFILE
+The name of the file in which command history is saved (see
+.SM
+.B HISTORY
+below).  The default value is \fI~/.bash_history\fP.  If unset, the
+command history is not saved when an interactive shell exits.
+.TP
+.B HISTFILESIZE
+The maximum number of lines contained in the history file.  When this
+variable is assigned a value, the history file is truncated, if
+necessary, to contain no more than that number of lines.  The default
+value is 500.  The history file is also truncated to this size after
+writing it when an interactive shell exits.
+.TP
+.B HISTIGNORE
+A colon-separated list of patterns used to decide which command lines
+should be saved on the history list.  Each pattern is anchored at the
+beginning of the line and must match the complete line (no implicit
+`\fB*\fP' is appended).  Each pattern is tested against the line
+after the checks specified by
+.B HISTCONTROL
+are applied.
+In addition to the normal shell pattern matching characters, `\fB&\fP'
+matches the previous history line.  `\fB&\fP' may be escaped using a
+backslash; the backslash is removed before attempting a match.
+The second and subsequent lines of a multi-line compound command are
+not tested, and are added to the history regardless of the value of
+.BR HISTIGNORE .
+.TP
+.B HISTSIZE
+The number of commands to remember in the command history (see
+.SM
+.B HISTORY
+below).  The default value is 500.
+.TP
+.B HISTTIMEFORMAT
+If this variable is set and not null, its value is used as a format string
+for \fIstrftime\fP(3) to print the time stamp associated with each history
+entry displayed by the \fBhistory\fP builtin.
+If this variable is set, time stamps are written to the history file so
+they may be preserved across shell sessions.
+.TP
+.B HOME
+The home directory of the current user; the default argument for the
+\fBcd\fP builtin command.
+The value of this variable is also used when performing tilde expansion.
+.TP
+.B HOSTFILE
+Contains the name of a file in the same format as
+.FN /etc/hosts
+that should be read when the shell needs to complete a
+hostname.
+The list of possible hostname completions may be changed while the
+shell is running;
+the next time hostname completion is attempted after the
+value is changed,
+.B bash
+adds the contents of the new file to the existing list.
+If
+.SM
+.B HOSTFILE
+is set, but has no value, \fBbash\fP attempts to read
+.FN /etc/hosts
+to obtain the list of possible hostname completions.
+When
+.SM
+.B HOSTFILE
+is unset, the hostname list is cleared.
+.TP
+.B IFS
+The
+.I Internal Field Separator
+that is used
+for word splitting after expansion and to
+split lines into words with the
+.B read
+builtin command.  The default value is
+``<space><tab><newline>''.
+.TP
+.B IGNOREEOF
+Controls the
+action of an interactive shell on receipt of an
+.SM
+.B EOF
+character as the sole input.  If set, the value is the number of
+consecutive
+.SM
+.B EOF
+characters which must be
+typed as the first characters on an input line before
+.B bash
+exits.  If the variable exists but does not have a numeric value, or
+has no value, the default value is 10.  If it does not exist,
+.SM
+.B EOF
+signifies the end of input to the shell.
+.TP
+.B INPUTRC
+The filename for the
+.B readline
+startup file, overriding the default of
+.FN ~/.inputrc
+(see
+.SM
+.B READLINE
+below).
+.TP
+.B LANG
+Used to determine the locale category for any category not specifically
+selected with a variable starting with \fBLC_\fP.
+.TP
+.B LC_ALL
+This variable overrides the value of \fBLANG\fP and any other
+\fBLC_\fP variable specifying a locale category.
+.TP
+.B LC_COLLATE
+This variable determines the collation order used when sorting the
+results of pathname expansion, and determines the behavior of range
+expressions, equivalence classes, and collating sequences within
+pathname expansion and pattern matching.
+.TP
+.B LC_CTYPE
+This variable determines the interpretation of characters and the
+behavior of character classes within pathname expansion and pattern
+matching.
+.TP
+.B LC_MESSAGES
+This variable determines the locale used to translate double-quoted
+strings preceded by a \fB$\fP.
+.TP
+.B LC_NUMERIC
+This variable determines the locale category used for number formatting.
+.TP
+.B LINES
+Used by the \fBselect\fP builtin command to determine the column length
+for printing selection lists.  Automatically set upon receipt of a SIGWINCH.
+.TP
+.B MAIL
+If this parameter is set to a file name and the
+.SM
+.B MAILPATH
+variable is not set,
+.B bash
+informs the user of the arrival of mail in the specified file.
+.TP
+.B MAILCHECK
+Specifies how
+often (in seconds)
+.B bash
+checks for mail.  The default is 60 seconds.  When it is time to check
+for mail, the shell does so before displaying the primary prompt.
+If this variable is unset, or set to a value that is not a number
+greater than or equal to zero, the shell disables mail checking.
+.TP
+.B MAILPATH
+A colon-separated list of file names to be checked for mail. 
+The message to be printed when mail arrives in a particular file
+may be specified by separating the file name from the message with a `?'.
+When used in the text of the message, \fB$_\fP expands to the name of
+the current mailfile. 
+Example:
+.RS
+.PP
+\fBMAILPATH\fP='/var/mail/bfox?"You have mail":~/shell\-mail?"$_ has mail!"'
+.PP
+.B Bash
+supplies a default value for this variable, but the location of the user
+mail files that it uses is system dependent (e.g., /var/mail/\fB$USER\fP).
+.RE
+.TP
+.B OPTERR
+If set to the value 1,
+.B bash
+displays error messages generated by the
+.B getopts
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.SM
+.B OPTERR
+is initialized to 1 each time the shell is invoked or a shell
+script is executed.
+.TP
+.B PATH
+The search path for commands.  It
+is a colon-separated list of directories in which
+the shell looks for commands (see
+.SM
+.B COMMAND EXECUTION
+below).
+A zero-length (null) directory name in the value of \fBPATH\fP indicates the
+current directory.
+A null directory name may appear as two adjacent colons, or as an initial
+or trailing colon.
+The default path is system-dependent,
+and is set by the administrator who installs
+.BR bash .
+A common value is
+.if t \f(CW/usr/gnu/bin:/usr/local/bin:/usr/ucb:/bin:/usr/bin\fP.
+.if n ``/usr/gnu/bin:/usr/local/bin:/usr/ucb:/bin:/usr/bin''.
+.TP
+.B POSIXLY_CORRECT
+If this variable is in the environment when \fBbash\fP starts, the shell
+enters \fIposix mode\fP before reading the startup files, as if the
+.B \-\-posix
+invocation option had been supplied.  If it is set while the shell is
+running, \fBbash\fP enables \fIposix mode\fP, as if the command
+.if t \f(CWset -o posix\fP
+.if n \fIset -o posix\fP
+had been executed.
+.TP
+.B PROMPT_COMMAND
+If set, the value is executed as a command prior to issuing each primary
+prompt.
+.TP
+.B PS1
+The value of this parameter is expanded (see
+.SM
+.B PROMPTING
+below) and used as the primary prompt string.  The default value is
+``\fB\es\-\ev\e$ \fP''.
+.TP
+.B PS2
+The value of this parameter is expanded as with
+.B PS1
+and used as the secondary prompt string.  The default is
+``\fB> \fP''.
+.TP
+.B PS3
+The value of this parameter is used as the prompt for the
+.B select
+command (see
+.SM
+.B SHELL GRAMMAR
+above).
+.TP
+.B PS4
+The value of this parameter is expanded as with
+.B PS1
+and the value is printed before each command
+.B bash
+displays during an execution trace.  The first character of
+.SM
+.B PS4
+is replicated multiple times, as necessary, to indicate multiple
+levels of indirection.  The default is ``\fB+ \fP''.
+.TP
+.B SHELL
+The full pathname to the shell is kept in this environment variable.
+If it is not set when the shell starts,
+.B bash
+assigns to it the full pathname of the current user's login shell.
+.TP
+.B TIMEFORMAT
+The value of this parameter is used as a format string specifying
+how the timing information for pipelines prefixed with the
+.B time
+reserved word should be displayed.
+The \fB%\fP character introduces an escape sequence that is
+expanded to a time value or other information.
+The escape sequences and their meanings are as follows; the
+braces denote optional portions.
+.sp .5
+.RS
+.PD 0
+.TP 10
+.B %%
+A literal \fB%\fP.
+.TP
+.B %[\fIp\fP][l]R
+The elapsed time in seconds.
+.TP
+.B %[\fIp\fP][l]U
+The number of CPU seconds spent in user mode.
+.TP
+.B %[\fIp\fP][l]S
+The number of CPU seconds spent in system mode.
+.TP
+.B %P
+The CPU percentage, computed as (%U + %S) / %R.
+.PD
+.RE
+.IP
+The optional \fIp\fP is a digit specifying the \fIprecision\fP,
+the number of fractional digits after a decimal point.
+A value of 0 causes no decimal point or fraction to be output.
+At most three places after the decimal point may be specified;
+values of \fIp\fP greater than 3 are changed to 3.
+If \fIp\fP is not specified, the value 3 is used.
+.IP
+The optional \fBl\fP specifies a longer format, including
+minutes, of the form \fIMM\fPm\fISS\fP.\fIFF\fPs.
+The value of \fIp\fP determines whether or not the fraction is
+included.
+.IP
+If this variable is not set, \fBbash\fP acts as if it had the
+value \fB$'\enreal\et%3lR\enuser\et%3lU\ensys\t%3lS'\fP.
+If the value is null, no timing information is displayed.
+A trailing newline is added when the format string is displayed.
+.TP
+.B TMOUT
+If set to a value greater than zero, \fBTMOUT\fP is treated as the
+default timeout for the \fBread\fP builtin.
+The \fBselect\fP command terminates if input does not arrive
+after \fBTMOUT\fP seconds when input is coming from a terminal.
+In an interactive shell, the value is interpreted as the
+number of seconds to wait for input after issuing the primary prompt.
+.B Bash
+terminates after waiting for that number of seconds if input does
+not arrive.
+.TP
+.B auto_resume
+This variable controls how the shell interacts with the user and
+job control.  If this variable is set, single word simple
+commands without redirections are treated as candidates for resumption
+of an existing stopped job.  There is no ambiguity allowed; if there is
+more than one job beginning with the string typed, the job most recently
+accessed is selected.  The
+.I name
+of a stopped job, in this context, is the command line used to
+start it.
+If set to the value
+.IR exact ,
+the string supplied must match the name of a stopped job exactly;
+if set to
+.IR substring ,
+the string supplied needs to match a substring of the name of a
+stopped job.  The
+.I substring
+value provides functionality analogous to the
+.B %?
+job identifier (see
+.SM
+.B JOB CONTROL
+below).  If set to any other value, the supplied string must
+be a prefix of a stopped job's name; this provides functionality
+analogous to the
+.B %
+job identifier.
+.TP
+.B histchars
+The two or three characters which control history expansion
+and tokenization (see
+.SM
+.B HISTORY EXPANSION
+below).  The first character is the \fIhistory expansion\fP character,
+the character which signals the start of a history
+expansion, normally `\fB!\fP'.
+The second character is the \fIquick substitution\fP
+character, which is used as shorthand for re-running the previous
+command entered, substituting one string for another in the command.
+The default is `\fB^\fP'.
+The optional third character is the character
+which indicates that the remainder of the line is a comment when found
+as the first character of a word, normally `\fB#\fP'.  The history
+comment character causes history substitution to be skipped for the
+remaining words on the line.  It does not necessarily cause the shell
+parser to treat the rest of the line as a comment.
+.PD
+.SS Arrays
+.B Bash
+provides one-dimensional array variables.  Any variable may be used as
+an array; the
+.B declare
+builtin will explicitly declare an array.  There is no maximum
+limit on the size of an array, nor any requirement that members
+be indexed or assigned contiguously.  Arrays are indexed using
+integers and are zero-based.
+.PP
+An array is created automatically if any variable is assigned to using
+the syntax \fIname\fP[\fIsubscript\fP]=\fIvalue\fP.  The
+.I subscript
+is treated as an arithmetic expression that must evaluate to a number
+greater than or equal to zero.  To explicitly declare an array, use
+.B declare \-a \fIname\fP
+(see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.B declare \-a \fIname\fP[\fIsubscript\fP]
+is also accepted; the \fIsubscript\fP is ignored.  Attributes may be
+specified for an array variable using the
+.B declare
+and
+.B readonly
+builtins.  Each attribute applies to all members of an array.
+.PP
+Arrays are assigned to using compound assignments of the form
+\fIname\fP=\fB(\fPvalue\fI1\fP ... value\fIn\fP\fB)\fP, where each
+\fIvalue\fP is of the form [\fIsubscript\fP]=\fIstring\fP.  Only
+\fIstring\fP is required.  If
+the optional brackets and subscript are supplied, that index is assigned to;
+otherwise the index of the element assigned is the last index assigned
+to by the statement plus one.  Indexing starts at zero.
+This syntax is also accepted by the
+.B declare
+builtin.  Individual array elements may be assigned to using the
+\fIname\fP[\fIsubscript\fP]=\fIvalue\fP syntax introduced above.
+.PP
+Any element of an array may be referenced using
+${\fIname\fP[\fIsubscript\fP]}.  The braces are required to avoid
+conflicts with pathname expansion.  If
+\fIsubscript\fP is \fB@\fP or \fB*\fP, the word expands to
+all members of \fIname\fP.  These subscripts differ only when the
+word appears within double quotes.  If the word is double-quoted,
+${\fIname\fP[*]} expands to a single
+word with the value of each array member separated by the first
+character of the
+.SM
+.B IFS
+special variable, and ${\fIname\fP[@]} expands each element of
+\fIname\fP to a separate word.  When there are no array members,
+${\fIname\fP[@]} expands to nothing.  This is analogous to the expansion
+of the special parameters \fB*\fP and \fB@\fP (see
+.B Special Parameters
+above).  ${#\fIname\fP[\fIsubscript\fP]} expands to the length of
+${\fIname\fP[\fIsubscript\fP]}.  If \fIsubscript\fP is \fB*\fP or
+\fB@\fP, the expansion is the number of elements in the array.
+Referencing an array variable without a subscript is equivalent to
+referencing element zero.
+.PP
+The
+.B unset
+builtin is used to destroy arrays.  \fBunset\fP \fIname\fP[\fIsubscript\fP]
+destroys the array element at index \fIsubscript\fP.
+\fBunset\fP \fIname\fP, where \fIname\fP is an array, or
+\fBunset\fP \fIname\fP[\fIsubscript\fP], where
+\fIsubscript\fP is \fB*\fP or \fB@\fP, removes the entire array.
+.PP
+The
+.BR declare ,
+.BR local ,
+and
+.B readonly
+builtins each accept a
+.B \-a
+option to specify an array.  The
+.B read
+builtin accepts a
+.B \-a
+option to assign a list of words read from the standard input
+to an array.  The
+.B set
+and
+.B declare
+builtins display array values in a way that allows them to be
+reused as assignments.
+.SH EXPANSION
+Expansion is performed on the command line after it has been split into
+words.  There are seven kinds of expansion performed:
+.IR "brace expansion" ,
+.IR "tilde expansion" ,
+.IR "parameter and variable expansion" ,
+.IR "command substitution" ,
+.IR "arithmetic expansion" ,
+.IR "word splitting" ,
+and
+.IR "pathname expansion" .
+.PP
+The order of expansions is: brace expansion, tilde expansion,
+parameter, variable and arithmetic expansion and
+command substitution
+(done in a left-to-right fashion), word splitting, and pathname
+expansion.
+.PP
+On systems that can support it, there is an additional expansion
+available: \fIprocess substitution\fP.
+.PP
+Only brace expansion, word splitting, and pathname expansion
+can change the number of words of the expansion; other expansions
+expand a single word to a single word.
+The only exceptions to this are the expansions of
+"\fB$@\fP" and "\fB${\fP\fIname\fP\fB[@]}\fP"
+as explained above (see
+.SM
+.BR PARAMETERS ).
+.SS Brace Expansion
+.PP
+.I "Brace expansion"
+is a mechanism by which arbitrary strings
+may be generated.  This mechanism is similar to
+\fIpathname expansion\fP, but the filenames generated
+need not exist.  Patterns to be brace expanded take
+the form of an optional
+.IR preamble ,
+followed by either a series of comma-separated strings or
+a sequence expression between a pair of braces, followed by
+an optional
+.IR postscript .
+The preamble is prefixed to each string contained
+within the braces, and the postscript is then appended
+to each resulting string, expanding left to right.
+.PP
+Brace expansions may be nested.  The results of each expanded
+string are not sorted; left to right order is preserved.
+For example, a\fB{\fPd,c,b\fB}\fPe expands into `ade ace abe'.
+.PP
+A sequence expression takes the form \fB{\fP\fIx\fP\fB..\fP\fIy\fP\fB}\fP,
+where \fIx\fP and \fIy\fP are either integers or single characters.
+When integers are supplied, the expression expands to each number between
+\fIx\fP and \fIy\fP, inclusive.
+When characters are supplied, the expression expands to each character
+lexicographically between \fIx\fP and \fIy\fP, inclusive.  Note that
+both \fIx\fP and \fIy\fP must be of the same type.
+.PP
+Brace expansion is performed before any other expansions,
+and any characters special to other expansions are preserved
+in the result.  It is strictly textual.
+.B Bash
+does not apply any syntactic interpretation to the context of the
+expansion or the text between the braces.
+.PP
+A correctly-formed brace expansion must contain unquoted opening
+and closing braces, and at least one unquoted comma or a valid
+sequence expression.
+Any incorrectly formed brace expansion is left unchanged.
+A \fB{\fP or \fB,\fP may be quoted with a backslash to prevent its
+being considered part of a brace expression.
+To avoid conflicts with parameter expansion, the string \fB${\fP
+is not considered eligible for brace expansion.
+.PP
+This construct is typically used as shorthand when the common
+prefix of the strings to be generated is longer than in the
+above example:
+.RS
+.PP
+mkdir /usr/local/src/bash/{old,new,dist,bugs}
+.RE
+or
+.RS
+chown root /usr/{ucb/{ex,edit},lib/{ex?.?*,how_ex}}
+.RE
+.PP
+Brace expansion introduces a slight incompatibility with
+historical versions of
+.BR sh .
+.B sh
+does not treat opening or closing braces specially when they
+appear as part of a word, and preserves them in the output.
+.B Bash
+removes braces from words as a consequence of brace
+expansion.  For example, a word entered to
+.B sh
+as \fIfile{1,2}\fP
+appears identically in the output.  The same word is
+output as
+.I file1 file2
+after expansion by
+.BR bash .
+If strict compatibility with
+.B sh
+is desired, start
+.B bash
+with the
+.B +B 
+option or disable brace expansion with the
+.B +B
+option to the
+.B set
+command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.SS Tilde Expansion
+.PP
+If a word begins with an unquoted tilde character (`\fB~\fP'), all of
+the characters preceding the first unquoted slash (or all characters,
+if there is no unquoted slash) are considered a \fItilde-prefix\fP.
+If none of the characters in the tilde-prefix are quoted, the
+characters in the tilde-prefix following the tilde are treated as a
+possible \fIlogin name\fP.
+If this login name is the null string, the tilde is replaced with the
+value of the shell parameter
+.SM
+.BR HOME .
+If
+.SM
+.B HOME
+is unset, the home directory of the user executing the shell is
+substituted instead.
+Otherwise, the tilde-prefix is replaced with the home directory
+associated with the specified login name.
+.PP
+If the tilde-prefix is a `~+', the value of the shell variable
+.SM
+.B PWD
+replaces the tilde-prefix.
+If the tilde-prefix is a `~\-', the value of the shell variable
+.SM
+.BR OLDPWD ,
+if it is set, is substituted.
+If the characters following the tilde in the tilde-prefix consist
+of a number \fIN\fP, optionally prefixed
+by a `+' or a `\-', the tilde-prefix is replaced with the corresponding
+element from the directory stack, as it would be displayed by the
+.B dirs
+builtin invoked with the tilde-prefix as an argument.
+If the characters following the tilde in the tilde-prefix consist of a
+number without a leading `+' or `\-', `+' is assumed.
+.PP
+If the login name is invalid, or the tilde expansion fails, the word
+is unchanged.
+.PP
+Each variable assignment is checked for unquoted tilde-prefixes immediately
+following a
+.B :
+or
+.BR = .
+In these cases, tilde expansion is also performed.
+Consequently, one may use file names with tildes in assignments to
+.SM
+.BR PATH ,
+.SM
+.BR MAILPATH ,
+and
+.SM
+.BR CDPATH ,
+and the shell assigns the expanded value.
+.SS Parameter Expansion
+.PP
+The `\fB$\fP' character introduces parameter expansion,
+command substitution, or arithmetic expansion.  The parameter name
+or symbol to be expanded may be enclosed in braces, which
+are optional but serve to protect the variable to be expanded from
+characters immediately following it which could be
+interpreted as part of the name.
+.PP
+When braces are used, the matching ending brace is the first `\fB}\fP'
+not escaped by a backslash or within a quoted string, and not within an
+embedded arithmetic expansion, command substitution, or paramter
+expansion.
+.PP
+.PD 0
+.TP
+${\fIparameter\fP}
+The value of \fIparameter\fP is substituted.  The braces are required
+when
+.I parameter
+is a positional parameter with more than one digit,
+or when
+.I parameter
+is followed by a character which is not to be
+interpreted as part of its name.
+.PD
+.PP
+If the first character of \fIparameter\fP is an exclamation point,
+a level of variable indirection is introduced.
+\fBBash\fP uses the value of the variable formed from the rest of
+\fIparameter\fP as the name of the variable; this variable is then
+expanded and that value is used in the rest of the substitution, rather
+than the value of \fIparameter\fP itself.
+This is known as \fIindirect expansion\fP.
+The exceptions to this are the expansions of ${!\fIprefix\fP*} and
+${\fB!\fP\fIname\fP[\fI@\fP]} described below.
+The exclamation point must immediately follow the left brace in order to
+introduce indirection.
+.PP
+In each of the cases below, \fIword\fP is subject to tilde expansion,
+parameter expansion, command substitution, and arithmetic expansion.
+When not performing substring expansion, \fBbash\fP tests for a parameter
+that is unset or null; omitting the colon results in a test only for a
+parameter that is unset.
+.PP
+.PD 0
+.TP
+${\fIparameter\fP\fB:\-\fP\fIword\fP}
+\fBUse Default Values\fP.  If
+.I parameter
+is unset or null, the expansion of
+.I word
+is substituted.  Otherwise, the value of
+.I parameter
+is substituted.
+.TP
+${\fIparameter\fP\fB:=\fP\fIword\fP}
+\fBAssign Default Values\fP.
+If
+.I parameter
+is unset or null, the expansion of
+.I word
+is assigned to
+.IR parameter .
+The value of
+.I parameter
+is then substituted.  Positional parameters and special parameters may
+not be assigned to in this way.
+.TP
+${\fIparameter\fP\fB:?\fP\fIword\fP}
+\fBDisplay Error if Null or Unset\fP.
+If
+.I parameter
+is null or unset, the expansion of \fIword\fP (or a message to that effect
+if
+.I word
+is not present) is written to the standard error and the shell, if it
+is not interactive, exits.  Otherwise, the value of \fIparameter\fP is
+substituted.
+.TP
+${\fIparameter\fP\fB:+\fP\fIword\fP}
+\fBUse Alternate Value\fP.
+If
+.I parameter
+is null or unset, nothing is substituted, otherwise the expansion of
+.I word
+is substituted.
+.TP
+${\fIparameter\fP\fB:\fP\fIoffset\fP}
+.PD 0
+.TP
+${\fIparameter\fP\fB:\fP\fIoffset\fP\fB:\fP\fIlength\fP}
+.PD
+\fBSubstring Expansion.\fP
+Expands to up to \fIlength\fP characters of \fIparameter\fP
+starting at the character specified by \fIoffset\fP.
+If \fIlength\fP is omitted, expands to the substring of
+\fIparameter\fP starting at the character specified by \fIoffset\fP.
+\fIlength\fP and \fIoffset\fP are arithmetic expressions (see
+.SM
+.B
+ARITHMETIC EVALUATION
+below).
+\fIlength\fP must evaluate to a number greater than or equal to zero.
+If \fIoffset\fP evaluates to a number less than zero, the value
+is used as an offset from the end of the value of \fIparameter\fP.
+If \fIparameter\fP is \fB@\fP, the result is \fIlength\fP positional
+parameters beginning at \fIoffset\fP.
+If \fIparameter\fP is an array name indexed by @ or *,
+the result is the \fIlength\fP
+members of the array beginning with ${\fIparameter\fP[\fIoffset\fP]}.
+Substring indexing is zero-based unless the positional parameters 
+are used, in which case the indexing starts at 1.
+.TP
+${\fB!\fP\fIprefix\fP\fB*\fP}
+.PD 0
+.TP
+${\fB!\fP\fIprefix\fP\fB@\fP}
+.PD
+Expands to the names of variables whose names begin with \fIprefix\fP,
+separated by the first character of the
+.SM
+.B IFS
+special variable.
+.TP
+${\fB!\fP\fIname\fP[\fI@\fP]}
+.PD 0
+.TP
+${\fB!\fP\fIname\fP[\fI*\fP]}
+.PD
+If \fIname\fP is an array variable, expands to the list of array indices
+(keys) assigned in \fIname\fP.
+If \fIname\fP is not an array, expands to 0 if \fIname\fP is set and null
+otherwise.
+When \fI@\fP is used and the expansion appears within double quotes, each
+key expands to a separate word.
+.TP
+${\fB#\fP\fIparameter\fP}
+The length in characters of the value of \fIparameter\fP is substituted.
+If
+.I parameter
+is
+.B *
+or 
+.BR @ ,
+the value substituted is the number of positional parameters.
+If
+.I parameter
+is an array name subscripted by
+.B *
+or
+.BR @ ,
+the value substituted is the number of elements in the array.
+.TP
+${\fIparameter\fP\fB#\fP\fIword\fP}
+.PD 0
+.TP
+${\fIparameter\fP\fB##\fP\fIword\fP}
+.PD
+The 
+.I word
+is expanded to produce a pattern just as in pathname
+expansion.  If the pattern matches the beginning of
+the value of
+.IR parameter ,
+then the result of the expansion is the expanded value of
+.I parameter
+with the shortest matching pattern (the ``\fB#\fP'' case) or the
+longest matching pattern (the ``\fB##\fP'' case) deleted.
+If
+.I parameter
+is
+.B @
+or
+.BR * ,
+the pattern removal operation is applied to each positional
+parameter in turn, and the expansion is the resultant list.
+If
+.I parameter
+is an array variable subscripted with
+.B @
+or
+.BR * ,
+the pattern removal operation is applied to each member of the
+array in turn, and the expansion is the resultant list.
+.TP
+${\fIparameter\fP\fB%\fP\fIword\fP}
+.PD 0
+.TP
+${\fIparameter\fP\fB%%\fP\fIword\fP}
+.PD
+The \fIword\fP is expanded to produce a pattern just as in
+pathname expansion.
+If the pattern matches a trailing portion of the expanded value of
+.IR parameter ,
+then the result of the expansion is the expanded value of
+.I parameter
+with the shortest matching pattern (the ``\fB%\fP'' case) or the
+longest matching pattern (the ``\fB%%\fP'' case) deleted.
+If
+.I parameter
+is
+.B @
+or
+.BR * ,
+the pattern removal operation is applied to each positional
+parameter in turn, and the expansion is the resultant list.
+If
+.I parameter
+is an array variable subscripted with
+.B @
+or
+.BR * ,
+the pattern removal operation is applied to each member of the
+array in turn, and the expansion is the resultant list.
+.TP
+${\fIparameter\fP\fB/\fP\fIpattern\fP\fB/\fP\fIstring\fP}
+.PD 0
+.TP
+${\fIparameter\fP\fB//\fP\fIpattern\fP\fB/\fP\fIstring\fP}
+.PD
+The \fIpattern\fP is expanded to produce a pattern just as in
+pathname expansion.
+\fIParameter\fP is expanded and the longest match of \fIpattern\fP
+against its value is replaced with \fIstring\fP.
+In the first form, only the first match is replaced.
+The second form causes all matches of \fIpattern\fP to be
+replaced with \fIstring\fP.
+If \fIpattern\fP begins with \fB#\fP, it must match at the beginning
+of the expanded value of \fIparameter\fP.
+If \fIpattern\fP begins with \fB%\fP, it must match at the end
+of the expanded value of \fIparameter\fP.
+If \fIstring\fP is null, matches of \fIpattern\fP are deleted
+and the \fB/\fP following \fIpattern\fP may be omitted.
+If
+.I parameter
+is
+.B @
+or
+.BR * ,
+the substitution operation is applied to each positional
+parameter in turn, and the expansion is the resultant list.
+If
+.I parameter
+is an array variable subscripted with
+.B @
+or
+.BR * ,
+the substitution operation is applied to each member of the
+array in turn, and the expansion is the resultant list.
+.SS Command Substitution
+.PP
+\fICommand substitution\fP allows the output of a command to replace
+the command name.  There are two forms:
+.PP
+.RS
+.PP
+\fB$(\fP\fIcommand\fP\|\fB)\fP
+.RE
+or
+.RS
+\fB`\fP\fIcommand\fP\fB`\fP
+.RE
+.PP
+.B Bash
+performs the expansion by executing \fIcommand\fP and
+replacing the command substitution with the standard output of the
+command, with any trailing newlines deleted.
+Embedded newlines are not deleted, but they may be removed during
+word splitting.
+The command substitution \fB$(cat \fIfile\fP)\fR can be replaced by
+the equivalent but faster \fB$(< \fIfile\fP)\fR.
+.PP
+When the old-style backquote form of substitution is used,
+backslash retains its literal meaning except when followed by
+.BR $ ,
+.BR ` ,
+or
+.BR \e .
+The first backquote not preceded by a backslash terminates the
+command substitution.
+When using the $(\^\fIcommand\fP\|) form, all characters between the
+parentheses make up the command; none are treated specially.
+.PP
+Command substitutions may be nested.  To nest when using the backquoted form,
+escape the inner backquotes with backslashes.
+.PP
+If the substitution appears within double quotes, word splitting and
+pathname expansion are not performed on the results.
+.SS Arithmetic Expansion
+.PP
+Arithmetic expansion allows the evaluation of an arithmetic expression
+and the substitution of the result.  The format for arithmetic expansion is:
+.RS
+.PP
+\fB$((\fP\fIexpression\fP\fB))\fP
+.RE
+.PP
+The
+.I expression
+is treated as if it were within double quotes, but a double quote
+inside the parentheses is not treated specially.
+All tokens in the expression undergo parameter expansion, string
+expansion, command substitution, and quote removal.
+Arithmetic expansions may be nested.
+.PP
+The evaluation is performed according to the rules listed below under
+.SM
+.BR "ARITHMETIC EVALUATION" .
+If
+.I expression
+is invalid,
+.B bash
+prints a message indicating failure and no substitution occurs.
+.SS Process Substitution
+.PP
+\fIProcess substitution\fP is supported on systems that support named
+pipes (\fIFIFOs\fP) or the \fB/dev/fd\fP method of naming open files.
+It takes the form of
+\fB<(\fP\fIlist\^\fP\fB)\fP
+or
+\fB>(\fP\fIlist\^\fP\fB)\fP.
+The process \fIlist\fP is run with its input or output connected to a
+\fIFIFO\fP or some file in \fB/dev/fd\fP.  The name of this file is
+passed as an argument to the current command as the result of the
+expansion.  If the \fB>(\fP\fIlist\^\fP\fB)\fP form is used, writing to
+the file will provide input for \fIlist\fP.  If the
+\fB<(\fP\fIlist\^\fP\fB)\fP form is used, the file passed as an
+argument should be read to obtain the output of \fIlist\fP.
+.PP
+When available, process substitution is performed
+simultaneously with parameter and variable expansion, 
+command substitution,
+and arithmetic expansion.
+.SS Word Splitting
+.PP
+The shell scans the results of
+parameter expansion,
+command substitution,
+and
+arithmetic expansion
+that did not occur within double quotes for
+.IR "word splitting" .
+.PP
+The shell treats each character of
+.SM
+.B IFS
+as a delimiter, and splits the results of the other
+expansions into words on these characters.  If
+.SM
+.B IFS
+is unset, or its
+value is exactly
+.BR <space><tab><newline> ,
+the default, then
+any sequence of
+.SM
+.B IFS
+characters serves to delimit words.  If
+.SM
+.B IFS
+has a value other than the default, then sequences of
+the whitespace characters
+.B space
+and
+.B tab
+are ignored at the beginning and end of the
+word, as long as the whitespace character is in the
+value of
+.SM
+.BR IFS
+(an
+.SM
+.B IFS
+whitespace character).
+Any character in
+.SM
+.B IFS
+that is not
+.SM
+.B IFS
+whitespace, along with any adjacent
+.SM
+.B IFS
+whitespace characters, delimits a field.
+A sequence of
+.SM
+.B IFS
+whitespace characters is also treated as a delimiter.
+If the value of
+.SM
+.B IFS
+is null, no word splitting occurs.
+.PP
+Explicit null arguments (\^\f3"\^"\fP or \^\f3'\^'\fP\^) are retained.
+Unquoted implicit null arguments, resulting from the expansion of
+parameters that have no values, are removed.
+If a parameter with no value is expanded within double quotes, a
+null argument results and is retained.
+.PP
+Note that if no expansion occurs, no splitting
+is performed.
+.SS Pathname Expansion
+.PP
+After word splitting,
+unless the
+.B \-f
+option has been set,
+.B bash
+scans each word for the characters
+.BR * ,
+.BR ? ,
+and
+.BR [ .
+If one of these characters appears, then the word is
+regarded as a
+.IR pattern ,
+and replaced with an alphabetically sorted list of
+file names matching the pattern.
+If no matching file names are found,
+and the shell option
+.B nullglob
+is disabled, the word is left unchanged.
+If the 
+.B nullglob
+option is set, and no matches are found,
+the word is removed.
+If the
+.B failglob
+shell option is set, and no matches are found, an error message
+is printed and the command is not executed.
+If the shell option
+.B nocaseglob
+is enabled, the match is performed without regard to the case
+of alphabetic characters.
+When a pattern is used for pathname expansion,
+the character
+.B ``.''
+at the start of a name or immediately following a slash
+must be matched explicitly, unless the shell option
+.B dotglob
+is set.
+When matching a pathname, the slash character must always be
+matched explicitly.
+In other cases, the
+.B ``.''
+character is not treated specially.
+See the description of
+.B shopt
+below under
+.SM
+.B SHELL BUILTIN COMMANDS
+for a description of the
+.BR nocaseglob ,
+.BR nullglob ,
+.BR failglob ,
+and
+.B dotglob
+shell options.
+.PP
+The
+.SM
+.B GLOBIGNORE
+shell variable may be used to restrict the set of file names matching a
+.IR pattern .
+If
+.SM
+.B GLOBIGNORE
+is set, each matching file name that also matches one of the patterns in
+.SM
+.B GLOBIGNORE
+is removed from the list of matches.
+The file names
+.B ``.''
+and
+.B ``..''
+are always ignored when
+.SM
+.B GLOBIGNORE
+is set and not null.  However, setting
+.SM
+.B GLOBIGNORE
+to a non-null value has the effect of enabling the
+.B dotglob
+shell option, so all other file names beginning with a
+.B ``.''
+will match.
+To get the old behavior of ignoring file names beginning with a
+.BR ``.'' ,
+make
+.B ``.*''
+one of the patterns in
+.SM
+.BR GLOBIGNORE .
+The
+.B dotglob
+option is disabled when
+.SM
+.B GLOBIGNORE
+is unset.
+.PP
+\fBPattern Matching\fP
+.PP
+Any character that appears in a pattern, other than the special pattern
+characters described below, matches itself.  The NUL character may not
+occur in a pattern.  A backslash escapes the following character; the
+escaping backslash is discarded when matching.
+The special pattern characters must be quoted if
+they are to be matched literally.
+.PP
+The special pattern characters have the following meanings:
+.PP
+.PD 0
+.TP
+.B *
+Matches any string, including the null string.
+.TP
+.B ?
+Matches any single character.
+.TP
+.B [...]
+Matches any one of the enclosed characters.  A pair of characters
+separated by a hyphen denotes a
+\fIrange expression\fP;
+any character that sorts between those two characters, inclusive,
+using the current locale's collating sequence and character set,
+is matched.  If the first character following the
+.B [
+is a
+.B !
+or a
+.B ^
+then any character not enclosed is matched.
+The sorting order of characters in range expressions is determined by
+the current locale and the value of the \fBLC_COLLATE\fP shell variable,
+if set.
+A 
+.B \-
+may be matched by including it as the first or last character
+in the set.
+A
+.B ]
+may be matched by including it as the first character
+in the set.
+.br
+.if t .sp 0.5
+.if n .sp 1
+Within
+.B [
+and
+.BR ] ,
+\fIcharacter classes\fP can be specified using the syntax
+\fB[:\fP\fIclass\fP\fB:]\fP, where \fIclass\fP is one of the
+following classes defined in the POSIX.2 standard:
+.PP
+.RS
+.B
+.if n alnum alpha ascii blank cntrl digit graph lower print punct space upper word xdigit
+.if t alnum   alpha   ascii   blank   cntrl   digit   graph   lower   print   punct   space   upper   word   xdigit
+.br
+A character class matches any character belonging to that class.
+The \fBword\fP character class matches letters, digits, and the character _.
+.br
+.if t .sp 0.5
+.if n .sp 1
+Within
+.B [
+and 
+.BR ] ,
+an \fIequivalence class\fP can be specified using the syntax
+\fB[=\fP\fIc\fP\fB=]\fP, which matches all characters with the
+same collation weight (as defined by the current locale) as
+the character \fIc\fP.
+.br
+.if t .sp 0.5
+.if n .sp 1
+Within
+.B [
+and 
+.BR ] ,
+the syntax \fB[.\fP\fIsymbol\fP\fB.]\fP matches the collating symbol
+\fIsymbol\fP.
+.RE
+.PD
+.PP
+If the \fBextglob\fP shell option is enabled using the \fBshopt\fP
+builtin, several extended pattern matching operators are recognized.
+In the following description, a \fIpattern-list\fP is a list of one
+or more patterns separated by a \fB|\fP.
+Composite patterns may be formed using one or more of the following
+sub-patterns:
+.sp 1
+.PD 0
+.RS
+.TP
+\fB?(\fP\^\fIpattern-list\^\fP\fB)\fP
+Matches zero or one occurrence of the given patterns
+.TP
+\fB*(\fP\^\fIpattern-list\^\fP\fB)\fP
+Matches zero or more occurrences of the given patterns
+.TP
+\fB+(\fP\^\fIpattern-list\^\fP\fB)\fP
+Matches one or more occurrences of the given patterns
+.TP
+\fB@(\fP\^\fIpattern-list\^\fP\fB)\fP
+Matches exactly one of the given patterns
+.TP
+\fB!(\fP\^\fIpattern-list\^\fP\fB)\fP
+Matches anything except one of the given patterns
+.RE
+.PD
+.SS Quote Removal
+.PP
+After the preceding expansions, all unquoted occurrences of the
+characters
+.BR \e ,
+.BR ' ,
+and \^\f3"\fP\^ that did not result from one of the above
+expansions are removed.
+.SH REDIRECTION
+Before a command is executed, its input and output
+may be
+.I redirected
+using a special notation interpreted by the shell.
+Redirection may also be used to open and close files for the
+current shell execution environment.  The following redirection
+operators may precede or appear anywhere within a
+.I simple command
+or may follow a
+.IR command .
+Redirections are processed in the order they appear, from
+left to right.
+.PP
+In the following descriptions, if the file descriptor number is
+omitted, and the first character of the redirection operator is
+.BR < ,
+the redirection refers to the standard input (file descriptor
+0).  If the first character of the redirection operator is
+.BR > ,
+the redirection refers to the standard output (file descriptor
+1).
+.PP
+The word following the redirection operator in the following
+descriptions, unless otherwise noted, is subjected to brace expansion,
+tilde expansion, parameter expansion, command substitution, arithmetic
+expansion, quote removal, pathname expansion, and word splitting.
+If it expands to more than one word,
+.B bash
+reports an error.
+.PP
+Note that the order of redirections is significant.  For example, 
+the command
+.RS
+.PP
+ls \fB>\fP dirlist 2\fB>&\fP1
+.RE
+.PP
+directs both standard output and standard error to the file 
+.IR dirlist ,
+while the command
+.RS
+.PP
+ls 2\fB>&\fP1 \fB>\fP dirlist
+.RE
+.PP
+directs only the standard output to file
+.IR dirlist ,
+because the standard error was duplicated as standard output
+before the standard output was redirected to
+.IR dirlist .
+.PP
+\fBBash\fP handles several filenames specially when they are used in
+redirections, as described in the following table:
+.RS
+.PP
+.PD 0
+.TP
+.B /dev/fd/\fIfd\fP
+If \fIfd\fP is a valid integer, file descriptor \fIfd\fP is duplicated.
+.TP
+.B /dev/stdin
+File descriptor 0 is duplicated.
+.TP
+.B /dev/stdout
+File descriptor 1 is duplicated.
+.TP
+.B /dev/stderr
+File descriptor 2 is duplicated.
+.TP
+.B /dev/tcp/\fIhost\fP/\fIport\fP
+If \fIhost\fP is a valid hostname or Internet address, and \fIport\fP
+is an integer port number or service name, \fBbash\fP attempts to open
+a TCP connection to the corresponding socket.
+.TP
+.B /dev/udp/\fIhost\fP/\fIport\fP
+If \fIhost\fP is a valid hostname or Internet address, and \fIport\fP
+is an integer port number or service name, \fBbash\fP attempts to open
+a UDP connection to the corresponding socket.
+.PD
+.RE
+.PP
+A failure to open or create a file causes the redirection to fail.
+.SS Redirecting Input
+.PP
+Redirection of input causes the file whose name results from
+the expansion of
+.I word
+to be opened for reading on file descriptor
+.IR n ,
+or the standard input (file descriptor 0) if
+.I n
+is not specified.
+.PP
+The general format for redirecting input is:
+.RS
+.PP
+[\fIn\fP]\fB<\fP\fIword\fP
+.RE
+.SS Redirecting Output
+.PP
+Redirection of output causes the file whose name results from
+the expansion of
+.I word
+to be opened for writing on file descriptor
+.IR n ,
+or the standard output (file descriptor 1) if
+.I n
+is not specified.  If the file does not exist it is created;
+if it does exist it is truncated to zero size.
+.PP
+The general format for redirecting output is:
+.RS
+.PP
+[\fIn\fP]\fB>\fP\fIword\fP
+.RE
+.PP
+If the redirection operator is
+.BR > ,
+and the
+.B noclobber
+option to the
+.B set
+builtin has been enabled, the redirection will fail if the file
+whose name results from the expansion of \fIword\fP exists and is
+a regular file.
+If the redirection operator is
+.BR >| ,
+or the redirection operator is
+.B >
+and the
+.B noclobber
+option to the
+.B set
+builtin command is not enabled, the redirection is attempted even
+if the file named by \fIword\fP exists.
+.SS Appending Redirected Output
+.PP
+Redirection of output in this fashion
+causes the file whose name results from
+the expansion of
+.I word
+to be opened for appending on file descriptor
+.IR n ,
+or the standard output (file descriptor 1) if
+.I n
+is not specified.  If the file does not exist it is created.
+.PP
+The general format for appending output is:
+.RS
+.PP
+[\fIn\fP]\fB>>\fP\fIword\fP
+.RE
+.PP
+.SS Redirecting Standard Output and Standard Error
+.PP
+.B Bash
+allows both the
+standard output (file descriptor 1) and
+the standard error output (file descriptor 2)
+to be redirected to the file whose name is the
+expansion of
+.I word
+with this construct.
+.PP
+There are two formats for redirecting standard output and
+standard error:
+.RS
+.PP
+\fB&>\fP\fIword\fP
+.RE
+and
+.RS
+\fB>&\fP\fIword\fP
+.RE
+.PP
+Of the two forms, the first is preferred.
+This is semantically equivalent to
+.RS
+.PP
+\fB>\fP\fIword\fP 2\fB>&\fP1
+.RE
+.SS Here Documents
+.PP
+This type of redirection instructs the shell to read input from the
+current source until a line containing only
+.I word
+(with no trailing blanks)
+is seen.  All of
+the lines read up to that point are then used as the standard
+input for a command.
+.PP
+The format of here-documents is:
+.RS
+.PP
+.nf
+\fB<<\fP[\fB\-\fP]\fIword\fP
+        \fIhere-document\fP
+\fIdelimiter\fP
+.fi
+.RE
+.PP
+No parameter expansion, command substitution, arithmetic expansion,
+or pathname expansion is performed on
+.IR word .
+If any characters in
+.I word
+are quoted, the
+.I delimiter
+is the result of quote removal on
+.IR word ,
+and the lines in the here-document are not expanded.
+If \fIword\fP is unquoted,
+all lines of the here-document are subjected to parameter expansion,
+command substitution, and arithmetic expansion.  In the latter
+case, the character sequence
+.B \e<newline>
+is ignored, and
+.B \e
+must be used to quote the characters
+.BR \e ,
+.BR $ ,
+and
+.BR ` .
+.PP
+If the redirection operator is
+.BR <<\- ,
+then all leading tab characters are stripped from input lines and the
+line containing
+.IR delimiter .
+This allows
+here-documents within shell scripts to be indented in a
+natural fashion.
+.SS "Here Strings"
+A variant of here documents, the format is:
+.RS
+.PP
+.nf
+\fB<<<\fP\fIword\fP
+.fi
+.RE
+.PP
+The \fIword\fP is expanded and supplied to the command on its standard
+input.
+.SS "Duplicating File Descriptors"
+.PP
+The redirection operator
+.RS
+.PP
+[\fIn\fP]\fB<&\fP\fIword\fP
+.RE
+.PP
+is used to duplicate input file descriptors.
+If
+.I word
+expands to one or more digits, the file descriptor denoted by
+.I n
+is made to be a copy of that file descriptor.
+If the digits in
+.I word
+do not specify a file descriptor open for input, a redirection error occurs.
+If
+.I word
+evaluates to
+.BR \- ,
+file descriptor
+.I n
+is closed.  If
+.I n
+is not specified, the standard input (file descriptor 0) is used.
+.PP
+The operator
+.RS
+.PP
+[\fIn\fP]\fB>&\fP\fIword\fP
+.RE
+.PP
+is used similarly to duplicate output file descriptors.  If
+.I n
+is not specified, the standard output (file descriptor 1) is used.
+If the digits in
+.I word
+do not specify a file descriptor open for output, a redirection error occurs.
+As a special case, if \fIn\fP is omitted, and \fIword\fP does not
+expand to one or more digits, the standard output and standard
+error are redirected as described previously.
+.SS "Moving File Descriptors"
+.PP
+The redirection operator
+.RS
+.PP
+[\fIn\fP]\fB<&\fP\fIdigit\fP\fB\-\fP
+.RE
+.PP
+moves the file descriptor \fIdigit\fP to file descriptor
+.IR n ,
+or the standard input (file descriptor 0) if \fIn\fP is not specified.
+\fIdigit\fP is closed after being duplicated to \fIn\fP.
+.PP
+Similarly, the redirection operator
+.RS
+.PP
+[\fIn\fP]\fB>&\fP\fIdigit\fP\fB\-\fP
+.RE
+.PP
+moves the file descriptor \fIdigit\fP to file descriptor
+.IR n ,
+or the standard output (file descriptor 1) if \fIn\fP is not specified.
+.SS "Opening File Descriptors for Reading and Writing"
+.PP
+The redirection operator
+.RS
+.PP
+[\fIn\fP]\fB<>\fP\fIword\fP
+.RE
+.PP
+causes the file whose name is the expansion of
+.I word
+to be opened for both reading and writing on file descriptor
+.IR n ,
+or on file descriptor 0 if
+.I n
+is not specified.  If the file does not exist, it is created.
+.SH ALIASES
+\fIAliases\fP allow a string to be substituted for a word when it is used
+as the first word of a simple command.
+The shell maintains a list of aliases that may be set and unset with the
+.B alias
+and
+.B unalias
+builtin commands (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+The first word of each simple command, if unquoted,
+is checked to see if it has an
+alias.  If so, that word is replaced by the text of the alias.
+The characters \fB/\fP, \fB$\fP, \fB`\fP, and \fB=\fP and
+any of the shell \fImetacharacters\fP or quoting characters
+listed above may not appear in an alias name.
+The replacement text may contain any valid shell input,
+including shell metacharacters.
+The first word of the replacement text is tested
+for aliases, but a word that is identical to an alias being expanded
+is not expanded a second time.
+This means that one may alias
+.B ls
+to
+.BR "ls \-F" ,
+for instance, and
+.B bash
+does not try to recursively expand the replacement text.
+If the last character of the alias value is a
+.IR blank ,
+then the next command
+word following the alias is also checked for alias expansion.
+.PP
+Aliases are created and listed with the
+.B alias
+command, and removed with the
+.B unalias
+command.
+.PP
+There is no mechanism for using arguments in the replacement text.
+If arguments are needed, a shell function should be used (see
+.SM
+.B FUNCTIONS
+below).
+.PP
+Aliases are not expanded when the shell is not interactive, unless
+the
+.B expand_aliases
+shell option is set using
+.B shopt
+(see the description of
+.B shopt
+under
+.SM
+\fBSHELL BUILTIN COMMANDS\fP
+below).
+.PP
+The rules concerning the definition and use of aliases are
+somewhat confusing.
+.B Bash
+always reads at least one complete line
+of input before executing any
+of the commands on that line.  Aliases are expanded when a
+command is read, not when it is executed.  Therefore, an
+alias definition appearing on the same line as another
+command does not take effect until the next line of input is read.
+The commands following the alias definition
+on that line are not affected by the new alias.
+This behavior is also an issue when functions are executed.
+Aliases are expanded when a function definition is read,
+not when the function is executed, because a function definition
+is itself a compound command.  As a consequence, aliases
+defined in a function are not available until after that
+function is executed.  To be safe, always put
+alias definitions on a separate line, and do not use
+.B alias
+in compound commands.
+.PP
+For almost every purpose, aliases are superseded by
+shell functions.
+.SH FUNCTIONS
+A shell function, defined as described above under
+.SM
+.BR "SHELL GRAMMAR" ,
+stores a series of commands for later execution.
+When the name of a shell function is used as a simple command name,
+the list of commands associated with that function name is executed.
+Functions are executed in the context of the
+current shell; no new process is created to interpret
+them (contrast this with the execution of a shell script).
+When a function is executed, the arguments to the
+function become the positional parameters
+during its execution.
+The special parameter
+.B #
+is updated to reflect the change.  Special parameter 0
+is unchanged.
+The first element of the
+.SM
+.B FUNCNAME
+variable is set to the name of the function while the function
+is executing.
+All other aspects of the shell execution
+environment are identical between a function and its caller
+with the exception that the
+.SM
+.B DEBUG
+trap (see the description of the
+.B trap
+builtin under
+.SM
+.B SHELL BUILTIN COMMANDS
+below) is not inherited unless the function has been given the
+\fBtrace\fP attribute (see the description of the
+.SM
+.B declare
+builtin below) or the
+\fB\-o functrace\fP shell option has been enabled with
+the \fBset\fP builtin
+(in which case all functions inherit the \fBDEBUG\fP trap).
+.PP
+Variables local to the function may be declared with the
+.B local
+builtin command.  Ordinarily, variables and their values
+are shared between the function and its caller.
+.PP
+If the builtin command
+.B return
+is executed in a function, the function completes and
+execution resumes with the next command after the function
+call.
+Any command associated with the \fBRETURN\fP trap is executed
+before execution resumes.
+When a function completes, the values of the
+positional parameters and the special parameter
+.B #
+are restored to the values they had prior to the function's
+execution.
+.PP
+Function names and definitions may be listed with the
+.B \-f
+option to the
+.B declare
+or
+.B typeset
+builtin commands.  The
+.B \-F
+option to
+.B declare
+or
+.B typeset
+will list the function names only
+(and optionally the source file and line number, if the \fBextdebug\fP
+shell option is enabled).
+Functions may be exported so that subshells
+automatically have them defined with the
+.B \-f
+option to the 
+.B export
+builtin.
+Note that shell functions and variables with the same name may result
+in multiple identically-named entries in the environment passed to the
+shell's children.
+Care should be taken in cases where this may cause a problem.
+.PP
+Functions may be recursive.  No limit is imposed on the number
+of recursive calls.
+.SH "ARITHMETIC EVALUATION"
+The shell allows arithmetic expressions to be evaluated, under
+certain circumstances (see the \fBlet\fP and \fBdeclare\fP builtin
+commands and \fBArithmetic Expansion\fP).
+Evaluation is done in fixed-width integers with no check for overflow,
+though division by 0 is trapped and flagged as an error.
+The operators and their precedence, associativity, and values
+are the same as in the C language.
+The following list of operators is grouped into levels of
+equal-precedence operators.
+The levels are listed in order of decreasing precedence.
+.PP
+.PD 0
+.TP
+.B \fIid\fP++ \fIid\fP\-\-
+variable post-increment and post-decrement
+.TP
+.B ++\fIid\fP \-\-\fIid\fP
+variable pre-increment and pre-decrement
+.TP
+.B \- +
+unary minus and plus
+.TP
+.B ! ~
+logical and bitwise negation
+.TP
+.B **
+exponentiation
+.TP
+.B * / %
+multiplication, division, remainder
+.TP
+.B + \-
+addition, subtraction
+.TP
+.B << >>
+left and right bitwise shifts
+.TP
+.B <= >= < >
+comparison
+.TP
+.B == !=
+equality and inequality
+.TP
+.B &
+bitwise AND
+.TP
+.B ^
+bitwise exclusive OR
+.TP
+.B |
+bitwise OR
+.TP
+.B &&
+logical AND
+.TP
+.B ||
+logical OR
+.TP
+.B \fIexpr\fP?\fIexpr\fP:\fIexpr\fP
+conditional operator
+.TP
+.B = *= /= %= += \-= <<= >>= &= ^= |=
+assignment
+.TP
+.B \fIexpr1\fP , \fIexpr2\fP
+comma
+.PD
+.PP
+Shell variables are allowed as operands; parameter expansion is
+performed before the expression is evaluated.
+Within an expression, shell variables may also be referenced by name
+without using the parameter expansion syntax.
+A shell variable that is null or unset evaluates to 0 when referenced
+by name without using the parameter expansion syntax.
+The value of a variable is evaluated as an arithmetic expression
+when it is referenced, or when a variable which has been given the
+\fIinteger\fP attribute using \fBdeclare -i\fP is assigned a value.
+A null value evaluates to 0.
+A shell variable need not have its integer attribute
+turned on to be used in an expression.
+.PP
+Constants with a leading 0 are interpreted as octal numbers.
+A leading 0x or 0X denotes hexadecimal.
+Otherwise, numbers take the form [\fIbase#\fP]n, where \fIbase\fP
+is a decimal number between 2 and 64 representing the arithmetic
+base, and \fIn\fP is a number in that base.
+If \fIbase#\fP is omitted, then base 10 is used.
+The digits greater than 9 are represented by the lowercase letters,
+the uppercase letters, @, and _, in that order.
+If \fIbase\fP is less than or equal to 36, lowercase and uppercase
+letters may be used interchangably to represent numbers between 10
+and 35.
+.PP
+Operators are evaluated in order of precedence.  Sub-expressions in
+parentheses are evaluated first and may override the precedence
+rules above.
+.SH "CONDITIONAL EXPRESSIONS"
+Conditional expressions are used by the \fB[[\fP compound command and
+the \fBtest\fP and \fB[\fP builtin commands to test file attributes
+and perform string and arithmetic comparisons.
+Expressions are formed from the following unary or binary primaries.
+If any \fIfile\fP argument to one of the primaries is of the form
+\fI/dev/fd/n\fP, then file descriptor \fIn\fP is checked.
+If the \fIfile\fP argument to one of the primaries is one of
+\fI/dev/stdin\fP, \fI/dev/stdout\fP, or \fI/dev/stderr\fP, file
+descriptor 0, 1, or 2, respectively, is checked.
+.sp 1
+.PD 0
+.TP
+.B \-a \fIfile\fP
+True if \fIfile\fP exists.
+.TP
+.B \-b \fIfile\fP
+True if \fIfile\fP exists and is a block special file.
+.TP
+.B \-c \fIfile\fP
+True if \fIfile\fP exists and is a character special file.
+.TP
+.B \-d \fIfile\fP
+True if \fIfile\fP exists and is a directory.
+.TP
+.B \-e \fIfile\fP
+True if \fIfile\fP exists.
+.TP
+.B \-f \fIfile\fP
+True if \fIfile\fP exists and is a regular file.
+.TP
+.B \-g \fIfile\fP
+True if \fIfile\fP exists and is set-group-id.
+.TP
+.B \-h \fIfile\fP
+True if \fIfile\fP exists and is a symbolic link.
+.TP
+.B \-k \fIfile\fP
+True if \fIfile\fP exists and its ``sticky'' bit is set.
+.TP
+.B \-p \fIfile\fP
+True if \fIfile\fP exists and is a named pipe (FIFO).
+.TP
+.B \-r \fIfile\fP
+True if \fIfile\fP exists and is readable.
+.TP
+.B \-s \fIfile\fP
+True if \fIfile\fP exists and has a size greater than zero.
+.TP
+.B \-t \fIfd\fP
+True if file descriptor
+.I fd
+is open and refers to a terminal.
+.TP
+.B \-u \fIfile\fP
+True if \fIfile\fP exists and its set-user-id bit is set.
+.TP
+.B \-w \fIfile\fP
+True if \fIfile\fP exists and is writable.
+.TP
+.B \-x \fIfile\fP
+True if \fIfile\fP exists and is executable.
+.TP
+.B \-O \fIfile\fP
+True if \fIfile\fP exists and is owned by the effective user id.
+.TP
+.B \-G \fIfile\fP
+True if \fIfile\fP exists and is owned by the effective group id.
+.TP
+.B \-L \fIfile\fP
+True if \fIfile\fP exists and is a symbolic link.
+.TP
+.B \-S \fIfile\fP
+True if \fIfile\fP exists and is a socket.
+.TP
+.B \-N \fIfile\fP
+True if \fIfile\fP exists and has been modified since it was last read.
+.TP
+\fIfile1\fP \-\fBnt\fP \fIfile2\fP
+True if \fIfile1\fP is newer (according to modification date) than \fIfile2\fP,
+or if \fIfile1\fP exists and \fPfile2\fP does not.
+.TP
+\fIfile1\fP \-\fBot\fP \fIfile2\fP
+True if \fIfile1\fP is older than \fIfile2\fP, or if \fIfile2\fP exists
+and \fIfile1\fP does not.
+.TP
+\fIfile1\fP \fB\-ef\fP \fIfile2\fP
+True if \fIfile1\fP and \fIfile2\fP refer to the same device and
+inode numbers.
+.TP
+.B \-o \fIoptname\fP
+True if shell option
+.I optname
+is enabled.
+See the list of options under the description of the
+.B \-o
+option to the
+.B set
+builtin below.
+.TP
+.B \-z \fIstring\fP
+True if the length of \fIstring\fP is zero.
+.TP
+\fIstring\fP
+.PD 0
+.TP
+.B \-n \fIstring\fP
+.PD
+True if the length of
+.I string
+is non-zero.
+.TP
+\fIstring1\fP \fB==\fP \fIstring2\fP
+True if the strings are equal.  \fB=\fP may be used in place of
+\fB==\fP for strict POSIX compliance.
+.TP
+\fIstring1\fP \fB!=\fP \fIstring2\fP
+True if the strings are not equal.
+.TP
+\fIstring1\fP \fB<\fP \fIstring2\fP
+True if \fIstring1\fP sorts before \fIstring2\fP lexicographically
+in the current locale.
+.TP
+\fIstring1\fP \fB>\fP \fIstring2\fP
+True if \fIstring1\fP sorts after \fIstring2\fP lexicographically
+in the current locale.
+.TP
+.I \fIarg1\fP \fBOP\fP \fIarg2\fP
+.SM
+.B OP
+is one of
+.BR \-eq ,
+.BR \-ne ,
+.BR \-lt ,
+.BR \-le ,
+.BR \-gt ,
+or
+.BR \-ge .
+These arithmetic binary operators return true if \fIarg1\fP
+is equal to, not equal to, less than, less than or equal to,
+greater than, or greater than or equal to \fIarg2\fP, respectively.
+.I Arg1
+and
+.I arg2
+may be positive or negative integers.
+.PD
+.SH "SIMPLE COMMAND EXPANSION"
+When a simple command is executed, the shell performs the following
+expansions, assignments, and redirections, from left to right.
+.IP 1.
+The words that the parser has marked as variable assignments (those
+preceding the command name) and redirections are saved for later
+processing.
+.IP 2.
+The words that are not variable assignments or redirections are
+expanded.  If any words remain after expansion, the first word
+is taken to be the name of the command and the remaining words are
+the arguments.
+.IP 3.
+Redirections are performed as described above under
+.SM
+.BR REDIRECTION .
+.IP 4.
+The text after the \fB=\fP in each variable assignment undergoes tilde
+expansion, parameter expansion, command substitution, arithmetic expansion,
+and quote removal before being assigned to the variable.
+.PP
+If no command name results, the variable assignments affect the current
+shell environment.  Otherwise, the variables are added to the environment
+of the executed command and do not affect the current shell environment.
+If any of the assignments attempts to assign a value to a readonly variable,
+an error occurs, and the command exits with a non-zero status.
+.PP
+If no command name results, redirections are performed, but do not
+affect the current shell environment.  A redirection error causes the
+command to exit with a non-zero status.
+.PP
+If there is a command name left after expansion, execution proceeds as
+described below.  Otherwise, the command exits.  If one of the expansions
+contained a command substitution, the exit status of the command is
+the exit status of the last command substitution performed.  If there
+were no command substitutions, the command exits with a status of zero.
+.SH "COMMAND EXECUTION"
+After a command has been split into words, if it results in a
+simple command and an optional list of arguments, the following
+actions are taken.
+.PP
+If the command name contains no slashes, the shell attempts to
+locate it.  If there exists a shell function by that name, that
+function is invoked as described above in
+.SM
+.BR FUNCTIONS .
+If the name does not match a function, the shell searches for
+it in the list of shell builtins.  If a match is found, that
+builtin is invoked.
+.PP
+If the name is neither a shell function nor a builtin,
+and contains no slashes,
+.B bash
+searches each element of the
+.SM
+.B PATH
+for a directory containing an executable file by that name.
+.B Bash
+uses a hash table to remember the full pathnames of executable
+files (see
+.B hash
+under
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below).
+A full search of the directories in
+.SM
+.B PATH
+is performed only if the command is not found in the hash table.
+If the search is unsuccessful, the shell prints an error
+message and returns an exit status of 127.
+.PP
+If the search is successful, or if the command name contains
+one or more slashes, the shell executes the named program in a
+separate execution environment.
+Argument 0 is set to the name given, and the remaining arguments
+to the command are set to the arguments given, if any.
+.PP
+If this execution fails because the file is not in executable
+format, and the file is not a directory, it is assumed to be
+a \fIshell script\fP, a file
+containing shell commands.  A subshell is spawned to execute
+it.  This subshell reinitializes itself, so
+that the effect is as if a new shell had been invoked
+to handle the script, with the exception that the locations of
+commands remembered by the parent (see
+.B hash
+below under
+.SM
+\fBSHELL BUILTIN COMMANDS\fP)
+are retained by the child.
+.PP
+If the program is a file beginning with
+.BR #! ,
+the remainder of the first line specifies an interpreter
+for the program.  The shell executes the
+specified interpreter on operating systems that do not
+handle this executable format themselves.  The arguments to the 
+interpreter consist of a single optional argument following the
+interpreter name on the first line of the program, followed
+by the name of the program, followed by the command
+arguments, if any.
+.SH COMMAND EXECUTION ENVIRONMENT
+The shell has an \fIexecution environment\fP, which consists of the
+following:
+.sp 1
+.IP \(bu
+open files inherited by the shell at invocation, as modified by
+redirections supplied to the \fBexec\fP builtin
+.IP \(bu
+the current working directory as set by \fBcd\fP, \fBpushd\fP, or
+\fBpopd\fP, or inherited by the shell at invocation
+.IP \(bu
+the file creation mode mask as set by \fBumask\fP or inherited from
+the shell's parent
+.IP \(bu
+current traps set by \fBtrap\fP
+.IP \(bu
+shell parameters that are set by variable assignment or with \fBset\fP
+or inherited from the shell's parent in the environment
+.IP \(bu
+shell functions defined during execution or inherited from the shell's
+parent in the environment
+.IP \(bu
+options enabled at invocation (either by default or with command-line
+arguments) or by \fBset\fP
+.IP \(bu
+options enabled by \fBshopt\fP
+.IP \(bu
+shell aliases defined with \fBalias\fP
+.IP \(bu
+various process IDs, including those of background jobs, the value
+of \fB$$\fP, and the value of \fB$PPID\fP
+.PP
+When a simple command other than a builtin or shell function
+is to be executed, it
+is invoked in a separate execution environment that consists of
+the following.  Unless otherwise noted, the values are inherited
+from the shell.
+.sp 1
+.IP \(bu
+the shell's open files, plus any modifications and additions specified
+by redirections to the command
+.IP \(bu
+the current working directory
+.IP \(bu
+the file creation mode mask
+.IP \(bu
+shell variables and functions marked for export, along with variables
+exported for the command, passed in the environment
+.IP \(bu
+traps caught by the shell are reset to the values inherited from the
+shell's parent, and traps ignored by the shell are ignored
+.PP
+A command invoked in this separate environment cannot affect the
+shell's execution environment. 
+.PP
+Command substitution, commands grouped with parentheses,
+and asynchronous commands are invoked in a
+subshell environment that is a duplicate of the shell environment,
+except that traps caught by the shell are reset to the values
+that the shell inherited from its parent at invocation.  Builtin
+commands that are invoked as part of a pipeline are also executed in a
+subshell environment.  Changes made to the subshell environment
+cannot affect the shell's execution environment.
+.PP
+If a command is followed by a \fB&\fP and job control is not active, the
+default standard input for the command is the empty file \fI/dev/null\fP.
+Otherwise, the invoked command inherits the file descriptors of the calling
+shell as modified by redirections.
+.SH ENVIRONMENT
+When a program is invoked it is given an array of strings
+called the
+.IR environment .
+This is a list of 
+\fIname\fP\-\fIvalue\fP pairs, of the form
+.IR "name\fR=\fPvalue" .
+.PP
+The shell provides several ways to manipulate the environment.
+On invocation, the shell scans its own environment and
+creates a parameter for each name found, automatically marking
+it for
+.I export
+to child processes.  Executed commands inherit the environment.
+The
+.B export
+and
+.B declare \-x
+commands allow parameters and functions to be added to and
+deleted from the environment.  If the value of a parameter
+in the environment is modified, the new value becomes part
+of the environment, replacing the old.  The environment
+inherited by any executed command consists of the shell's
+initial environment, whose values may be modified in the shell,
+less any pairs removed by the
+.B unset
+command, plus any additions via the
+.B export
+and
+.B declare \-x
+commands.
+.PP
+The environment for any
+.I simple command
+or function may be augmented temporarily by prefixing it with
+parameter assignments, as described above in
+.SM
+.BR PARAMETERS .
+These assignment statements affect only the environment seen
+by that command.
+.PP
+If the 
+.B \-k
+option is set (see the
+.B set
+builtin command below), then
+.I all
+parameter assignments are placed in the environment for a command,
+not just those that precede the command name.
+.PP
+When
+.B bash
+invokes an external command, the variable
+.B _
+is set to the full file name of the command and passed to that
+command in its environment.
+.SH "EXIT STATUS"
+For the shell's purposes, a command which exits with a 
+zero exit status has succeeded.  An exit status of zero
+indicates success.  A non-zero exit status indicates failure.
+When a command terminates on a fatal signal \fIN\fP, \fBbash\fP uses
+the value of 128+\fIN\fP as the exit status.
+.PP
+If a command is not found, the child process created to
+execute it returns a status of 127.  If a command is found
+but is not executable, the return status is 126.
+.PP
+If a command fails because of an error during expansion or redirection,
+the exit status is greater than zero.
+.PP
+Shell builtin commands return a status of 0 (\fItrue\fP) if
+successful, and non-zero (\fIfalse\fP) if an error occurs
+while they execute. 
+All builtins return an exit status of 2 to indicate incorrect usage.
+.PP
+\fBBash\fP itself returns the exit status of the last command
+executed, unless a syntax error occurs, in which case it exits
+with a non-zero value.  See also the \fBexit\fP builtin
+command below.
+.SH SIGNALS
+When \fBbash\fP is interactive, in the absence of any traps, it ignores
+.SM
+.B SIGTERM
+(so that \fBkill 0\fP does not kill an interactive shell),
+and
+.SM
+.B SIGINT
+is caught and handled (so that the \fBwait\fP builtin is interruptible).
+In all cases, \fBbash\fP ignores
+.SM
+.BR SIGQUIT .
+If job control is in effect,
+.B bash
+ignores
+.SM
+.BR SIGTTIN ,
+.SM
+.BR SIGTTOU ,
+and
+.SM
+.BR SIGTSTP .
+.PP
+Non-builtin commands run by \fBbash\fP have signal handlers
+set to the values inherited by the shell from its parent.
+When job control is not in effect, asynchronous commands
+ignore
+.SM
+.B SIGINT
+and
+.SM
+.B SIGQUIT
+in addition to these inherited handlers.
+Commands run as a result of command substitution ignore the
+keyboard-generated job control signals
+.SM
+.BR SIGTTIN ,
+.SM
+.BR SIGTTOU ,
+and
+.SM
+.BR SIGTSTP .
+.PP
+The shell exits by default upon receipt of a
+.SM
+.BR SIGHUP .
+Before exiting, an interactive shell resends the
+.SM
+.B SIGHUP
+to all jobs, running or stopped.
+Stopped jobs are sent
+.SM
+.B SIGCONT
+to ensure that they receive the
+.SM
+.BR SIGHUP .
+To prevent the shell from
+sending the signal to a particular job, it should be removed from the
+jobs table with the 
+.B disown
+builtin (see
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below) or marked 
+to not receive
+.SM
+.B SIGHUP
+using
+.BR "disown \-h" .
+.PP
+If the
+.B huponexit
+shell option has been set with
+.BR shopt ,
+.B bash
+sends a 
+.SM
+.B SIGHUP
+to all jobs when an interactive login shell exits.
+.PP
+If \Bbash\fP is waiting for a command to complete and receives a signal
+for which a trap has been set, the trap will not be executed until
+the command completes. 
+When \fBbash\fP is waiting for an asynchronous command via the \fBwait\fP
+builtin, the reception of a signal for which a trap has been set will
+cause the \fBwait\fP builtin to return immediately with an exit status
+greater than 128, immediately after which the trap is executed.
+.SH "JOB CONTROL"
+.I Job control
+refers to the ability to selectively stop (\fIsuspend\fP)
+the execution of processes and continue (\fIresume\fP)
+their execution at a later point.  A user typically employs
+this facility via an interactive interface supplied jointly
+by the system's terminal driver and
+.BR bash .
+.PP
+The shell associates a
+.I job
+with each pipeline.  It keeps a table of currently executing
+jobs, which may be listed with the
+.B jobs
+command.  When
+.B bash
+starts a job asynchronously (in the
+.IR background ),
+it prints a line that looks like:
+.RS
+.PP
+[1] 25647
+.RE
+.PP
+indicating that this job is job number 1 and that the process ID
+of the last process in the pipeline associated with this job is 25647.
+All of the processes in a single pipeline are members of the same job.
+.B Bash
+uses the
+.I job
+abstraction as the basis for job control.
+.PP
+To facilitate the implementation of the user interface to job
+control, the operating system maintains the notion of a \fIcurrent terminal
+process group ID\fP.  Members of this process group (processes whose
+process group ID is equal to the current terminal process group ID)
+receive keyboard-generated signals such as
+.SM
+.BR SIGINT .
+These processes are said to be in the
+.IR foreground .
+.I Background
+processes are those whose process group ID differs from the terminal's;
+such processes are immune to keyboard-generated signals.
+Only foreground processes are allowed to read from or write to the
+terminal.  Background processes which attempt to read from (write to) the
+terminal are sent a 
+.SM
+.B SIGTTIN (SIGTTOU)
+signal by the terminal driver, 
+which, unless caught, suspends the process.
+.PP
+If the operating system on which
+.B bash
+is running supports
+job control,
+.B bash
+contains facilities to use it.
+Typing the
+.I suspend
+character (typically
+.BR ^Z ,
+Control-Z) while a process is running
+causes that process to be stopped and returns control to 
+.BR bash .
+Typing the
+.I "delayed suspend"
+character (typically
+.BR ^Y ,
+Control-Y) causes the process to be stopped when it
+attempts to read input from the terminal, and control to
+be returned to
+.BR bash .
+The user may then manipulate the state of this job, using the
+.B bg
+command to continue it in the background, the
+.B fg
+command to continue it in the foreground, or
+the
+.B kill
+command to kill it.  A \fB^Z\fP takes effect immediately,
+and has the additional side effect of causing pending output
+and typeahead to be discarded.
+.PP
+There are a number of ways to refer to a job in the shell.
+The character
+.B %
+introduces a job name.  Job number
+.I n
+may be referred to as
+.BR %n .
+A job may also be referred to using a prefix of the name used to
+start it, or using a substring that appears in its command line.
+For example,
+.B %ce
+refers to a stopped
+.B ce
+job.  If a prefix matches more than one job,
+.B bash
+reports an error.  Using
+.BR %?ce ,
+on the other hand, refers to any job containing the string
+.B ce
+in its command line.  If the substring matches more than one job,
+.B bash
+reports an error.  The symbols
+.B %%
+and
+.B %+
+refer to the shell's notion of the
+.IR "current job" ,
+which is the last job stopped while it was in
+the foreground or started in the background.
+The 
+.I "previous job"
+may be referenced using
+.BR %\- .
+In output pertaining to jobs (e.g., the output of the
+.B jobs
+command), the current job is always flagged with a
+.BR + ,
+and the previous job with a
+.BR \- .
+.PP
+Simply naming a job can be used to bring it into the
+foreground:
+.B %1
+is a synonym for
+\fB``fg %1''\fP,
+bringing job 1 from the background into the foreground.
+Similarly,
+.B ``%1 &''
+resumes job 1 in the background, equivalent to
+\fB``bg %1''\fP.
+.PP
+The shell learns immediately whenever a job changes state.
+Normally,
+.B bash
+waits until it is about to print a prompt before reporting
+changes in a job's status so as to not interrupt
+any other output.  If the 
+.B \-b
+option to the
+.B set
+builtin command
+is enabled,
+.B bash
+reports such changes immediately.
+Any trap on
+.SM
+.B SIGCHLD
+is executed for each child that exits.
+.PP
+If an attempt to exit
+.B bash
+is made while jobs are stopped, the shell prints a warning message.  The
+.B jobs
+command may then be used to inspect their status.
+If a second attempt to exit is made without an intervening command,
+the shell does not print another warning, and the stopped
+jobs are terminated.
+.SH PROMPTING
+When executing interactively, 
+.B bash
+displays the primary prompt
+.SM
+.B PS1
+when it is ready to read a command, and the secondary prompt
+.SM
+.B PS2
+when it needs more input to complete a command.
+.B Bash
+allows these prompt strings to be customized by inserting a number of
+backslash-escaped special characters that are decoded as follows:
+.RS
+.PD 0
+.TP
+.B \ea
+an ASCII bell character (07)
+.TP
+.B \ed
+the date in "Weekday Month Date" format (e.g., "Tue May 26")
+.TP
+.B \eD{\fIformat\fP}
+the \fIformat\fP is passed to \fIstrftime\fP(3) and the result is inserted
+into the prompt string; an empty \fIformat\fP results in a locale-specific
+time representation.  The braces are required
+.TP
+.B \ee
+an ASCII escape character (033)
+.TP
+.B \eh
+the hostname up to the first `.'
+.TP
+.B \eH
+the hostname
+.TP
+.B \ej
+the number of jobs currently managed by the shell
+.TP
+.B \el
+the basename of the shell's terminal device name
+.TP
+.B \en
+newline
+.TP
+.B \er
+carriage return
+.TP
+.B \es
+the name of the shell, the basename of
+.B $0
+(the portion following the final slash)
+.TP
+.B \et
+the current time in 24-hour HH:MM:SS format
+.TP
+.B \eT
+the current time in 12-hour HH:MM:SS format
+.TP
+.B \e@
+the current time in 12-hour am/pm format
+.TP
+.B \eA
+the current time in 24-hour HH:MM format
+.TP
+.B \eu
+the username of the current user
+.TP
+.B \ev
+the version of \fBbash\fP (e.g., 2.00)
+.TP
+.B \eV
+the release of \fBbash\fP, version + patch level (e.g., 2.00.0)
+.TP
+.B \ew
+the current working directory, with \fB$HOME\fP abbreviated with a tilde
+.TP
+.B \eW
+the basename of the current working directory, with \fB$HOME\fP
+abbreviated with a tilde
+.TP
+.B \e!
+the history number of this command
+.TP
+.B \e#
+the command number of this command
+.TP
+.B \e$
+if the effective UID is 0, a
+.BR # ,
+otherwise a
+.B $
+.TP
+.B \e\fInnn\fP
+the character corresponding to the octal number \fInnn\fP
+.TP
+.B \e\e
+a backslash
+.TP
+.B \e[
+begin a sequence of non-printing characters, which could be used to
+embed a terminal control sequence into the prompt
+.TP
+.B \e]
+end a sequence of non-printing characters
+.PD
+.RE
+.PP
+The command number and the history number are usually different:
+the history number of a command is its position in the history
+list, which may include commands restored from the history file
+(see
+.SM
+.B HISTORY
+below), while the command number is the position in the sequence
+of commands executed during the current shell session.
+After the string is decoded, it is expanded via
+parameter expansion, command substitution, arithmetic
+expansion, and quote removal, subject to the value of the
+.B promptvars
+shell option (see the description of the
+.B shopt
+command under
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below).
+.SH READLINE
+This is the library that handles reading input when using an interactive
+shell, unless the
+.B \-\-noediting
+option is given at shell invocation.
+By default, the line editing commands are similar to those of emacs.
+A vi-style line editing interface is also available.
+To turn off line editing after the shell is running, use the
+.B +o emacs
+or
+.B +o vi
+options to the
+.B set
+builtin (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.SS "Readline Notation"
+.PP
+In this section, the emacs-style notation is used to denote
+keystrokes.  Control keys are denoted by C\-\fIkey\fR, e.g., C\-n
+means Control\-N.  Similarly, 
+.I meta
+keys are denoted by M\-\fIkey\fR, so M\-x means Meta\-X.  (On keyboards
+without a 
+.I meta
+key, M\-\fIx\fP means ESC \fIx\fP, i.e., press the Escape key
+then the
+.I x
+key.  This makes ESC the \fImeta prefix\fP.
+The combination M\-C\-\fIx\fP means ESC\-Control\-\fIx\fP,
+or press the Escape key
+then hold the Control key while pressing the
+.I x
+key.)
+.PP
+Readline commands may be given numeric
+.IR arguments ,
+which normally act as a repeat count.
+Sometimes, however, it is the sign of the argument that is significant.
+Passing a negative argument to a command that acts in the forward
+direction (e.g., \fBkill\-line\fP) causes that command to act in a
+backward direction. 
+Commands whose behavior with arguments deviates from this are noted
+below.
+.PP
+When a command is described as \fIkilling\fP text, the text
+deleted is saved for possible future retrieval
+(\fIyanking\fP).  The killed text is saved in a
+\fIkill ring\fP.  Consecutive kills cause the text to be
+accumulated into one unit, which can be yanked all at once. 
+Commands which do not kill text separate the chunks of text
+on the kill ring.
+.SS "Readline Initialization"
+.PP
+Readline is customized by putting commands in an initialization
+file (the \fIinputrc\fP file).
+The name of this file is taken from the value of the
+.SM
+.B INPUTRC
+variable.  If that variable is unset, the default is
+.IR ~/.inputrc .
+When a program which uses the readline library starts up, the
+initialization file is read, and the key bindings and variables
+are set.
+There are only a few basic constructs allowed in the
+readline initialization file.
+Blank lines are ignored.
+Lines beginning with a \fB#\fP are comments.
+Lines beginning with a \fB$\fP indicate conditional constructs.
+Other lines denote key bindings and variable settings.
+.PP
+The default key-bindings may be changed with an
+.I inputrc 
+file.
+Other programs that use this library may add their own commands
+and bindings.
+.PP
+For example, placing
+.RS
+.PP
+M\-Control\-u: universal\-argument
+.RE
+or
+.RS
+C\-Meta\-u: universal\-argument
+.RE
+into the 
+.I inputrc
+would make M\-C\-u execute the readline command
+.IR universal\-argument .
+.PP
+The following symbolic character names are recognized:
+.IR RUBOUT ,
+.IR DEL ,
+.IR ESC ,
+.IR LFD ,
+.IR NEWLINE ,
+.IR RET ,
+.IR RETURN ,
+.IR SPC ,
+.IR SPACE ,
+and
+.IR TAB .
+.PP
+In addition to command names, readline allows keys to be bound
+to a string that is inserted when the key is pressed (a \fImacro\fP).
+.SS "Readline Key Bindings"
+.PP
+The syntax for controlling key bindings in the
+.I inputrc
+file is simple.  All that is required is the name of the
+command or the text of a macro and a key sequence to which
+it should be bound. The name may be specified in one of two ways:
+as a symbolic key name, possibly with \fIMeta\-\fP or \fIControl\-\fP
+prefixes, or as a key sequence.
+.PP
+When using the form \fBkeyname\fP:\^\fIfunction\-name\fP or \fImacro\fP,
+.I keyname
+is the name of a key spelled out in English.  For example:
+.sp
+.RS
+Control-u: universal\-argument
+.br
+Meta-Rubout: backward-kill-word
+.br
+Control-o: "> output"
+.RE
+.LP
+In the above example,
+.I C\-u
+is bound to the function
+.BR universal\-argument ,
+.I M\-DEL
+is bound to the function
+.BR backward\-kill\-word ,
+and
+.I C\-o
+is bound to run the macro
+expressed on the right hand side (that is, to insert the text
+.if t \f(CW> output\fP
+.if n ``> output''
+into the line).
+.PP
+In the second form, \fB"keyseq"\fP:\^\fIfunction\-name\fP or \fImacro\fP,
+.B keyseq
+differs from
+.B keyname
+above in that strings denoting
+an entire key sequence may be specified by placing the sequence
+within double quotes.  Some GNU Emacs style key escapes can be
+used, as in the following example, but the symbolic character names
+are not recognized.
+.sp
+.RS
+"\eC\-u": universal\-argument
+.br
+"\eC\-x\eC\-r": re\-read\-init\-file
+.br
+"\ee[11~": "Function Key 1"
+.RE
+.PP
+In this example,
+.I C\-u
+is again bound to the function
+.BR universal\-argument .
+.I "C\-x C\-r"
+is bound to the function
+.BR re\-read\-init\-file ,
+and 
+.I "ESC [ 1 1 ~"
+is bound to insert the text
+.if t \f(CWFunction Key 1\fP.
+.if n ``Function Key 1''.
+.PP
+The full set of GNU Emacs style escape sequences is
+.RS
+.PD 0
+.TP
+.B \eC\-
+control prefix
+.TP
+.B \eM\-
+meta prefix
+.TP
+.B \ee
+an escape character
+.TP
+.B \e\e
+backslash
+.TP
+.B \e"
+literal "
+.TP
+.B \e'
+literal '
+.RE
+.PD
+.PP
+In addition to the GNU Emacs style escape sequences, a second
+set of backslash escapes is available:
+.RS
+.PD 0
+.TP
+.B \ea
+alert (bell)
+.TP
+.B \eb
+backspace
+.TP
+.B \ed
+delete
+.TP
+.B \ef
+form feed
+.TP
+.B \en
+newline
+.TP
+.B \er
+carriage return
+.TP
+.B \et
+horizontal tab
+.TP
+.B \ev
+vertical tab
+.TP
+.B \e\fInnn\fP
+the eight-bit character whose value is the octal value \fInnn\fP
+(one to three digits)
+.TP
+.B \ex\fIHH\fP
+the eight-bit character whose value is the hexadecimal value \fIHH\fP
+(one or two hex digits)
+.RE
+.PD
+.PP
+When entering the text of a macro, single or double quotes must
+be used to indicate a macro definition.
+Unquoted text is assumed to be a function name.
+In the macro body, the backslash escapes described above are expanded.
+Backslash will quote any other character in the macro text,
+including " and '.
+.PP
+.B Bash
+allows the current readline key bindings to be displayed or modified
+with the
+.B bind
+builtin command.  The editing mode may be switched during interactive
+use by using the
+.B \-o
+option to the
+.B set
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).
+.SS "Readline Variables"
+.PP
+Readline has variables that can be used to further customize its
+behavior.  A variable may be set in the
+.I inputrc
+file with a statement of the form
+.RS
+.PP
+\fBset\fP \fIvariable\-name\fP \fIvalue\fP
+.RE
+.PP
+Except where noted, readline variables can take the values
+.B On
+or
+.BR Off .
+The variables and their default values are:
+.PP
+.PD 0
+.TP
+.B bell\-style (audible)
+Controls what happens when readline wants to ring the terminal bell.
+If set to \fBnone\fP, readline never rings the bell.  If set to
+\fBvisible\fP, readline uses a visible bell if one is available.
+If set to \fBaudible\fP, readline attempts to ring the terminal's bell.
+.TP
+.B comment\-begin (``#'')
+The string that is inserted when the readline
+.B insert\-comment
+command is executed.
+This command is bound to
+.B M\-#
+in emacs mode and to
+.B #
+in vi command mode.
+.TP
+.B completion\-ignore\-case (Off)
+If set to \fBOn\fP, readline performs filename matching and completion
+in a case\-insensitive fashion.
+.TP
+.B completion\-query\-items (100)
+This determines when the user is queried about viewing
+the number of possible completions
+generated by the \fBpossible\-completions\fP command.
+It may be set to any integer value greater than or equal to
+zero.  If the number of possible completions is greater than
+or equal to the value of this variable, the user is asked whether
+or not he wishes to view them; otherwise they are simply listed
+on the terminal.
+.TP
+.B convert\-meta (On)
+If set to \fBOn\fP, readline will convert characters with the
+eighth bit set to an ASCII key sequence
+by stripping the eighth bit and prefixing an
+escape character (in effect, using escape as the \fImeta prefix\fP).
+.TP
+.B disable\-completion (Off)
+If set to \fBOn\fP, readline will inhibit word completion.  Completion
+characters will be inserted into the line as if they had been
+mapped to \fBself-insert\fP.
+.TP
+.B editing\-mode (emacs)
+Controls whether readline begins with a set of key bindings similar
+to \fIemacs\fP or \fIvi\fP.
+.B editing\-mode
+can be set to either
+.B emacs
+or
+.BR vi .
+.TP
+.B enable\-keypad (Off)
+When set to \fBOn\fP, readline will try to enable the application
+keypad when it is called.  Some systems need this to enable the
+arrow keys.
+.TP
+.B expand\-tilde (Off)
+If set to \fBon\fP, tilde expansion is performed when readline
+attempts word completion.
+.TP
+.B history-preserve-point
+If set to \fBon\fP, the history code attempts to place point at the
+same location on each history line retrived with \fBprevious-history\fP
+or \fBnext-history\fP.
+.TP
+.B horizontal\-scroll\-mode (Off)
+When set to \fBOn\fP, makes readline use a single line for display,
+scrolling the input horizontally on a single screen line when it
+becomes longer than the screen width rather than wrapping to a new line.
+.TP
+.B input\-meta (Off)
+If set to \fBOn\fP, readline will enable eight-bit input (that is,
+it will not strip the high bit from the characters it reads),
+regardless of what the terminal claims it can support.  The name
+.B meta\-flag
+is a synonym for this variable.
+.TP
+.B isearch\-terminators (``C\-[C\-J'')
+The string of characters that should terminate an incremental
+search without subsequently executing the character as a command.
+If this variable has not been given a value, the characters
+\fIESC\fP and \fIC\-J\fP will terminate an incremental search.
+.TP
+.B keymap (emacs)
+Set the current readline keymap.  The set of valid keymap names is
+\fIemacs, emacs\-standard, emacs\-meta, emacs\-ctlx, vi,
+vi\-command\fP, and
+.IR vi\-insert .
+\fIvi\fP is equivalent to \fIvi\-command\fP; \fIemacs\fP is
+equivalent to \fIemacs\-standard\fP.  The default value is
+.IR emacs ;
+the value of
+.B editing\-mode
+also affects the default keymap.
+.TP
+.B mark\-directories (On)
+If set to \fBOn\fP, completed directory names have a slash
+appended.
+.TP
+.B mark\-modified\-lines (Off)
+If set to \fBOn\fP, history lines that have been modified are displayed
+with a preceding asterisk (\fB*\fP).
+.TP
+.B mark\-symlinked\-directories (Off)
+If set to \fBOn\fP, completed names which are symbolic links to directories
+have a slash appended (subject to the value of
+\fBmark\-directories\fP).
+.TP
+.B match\-hidden\-files (On)
+This variable, when set to \fBOn\fP, causes readline to match files whose
+names begin with a `.' (hidden files) when performing filename 
+completion, unless the leading `.' is
+supplied by the user in the filename to be completed.
+.TP
+.B output\-meta (Off)
+If set to \fBOn\fP, readline will display characters with the
+eighth bit set directly rather than as a meta-prefixed escape
+sequence.
+.TP
+.B page\-completions (On)
+If set to \fBOn\fP, readline uses an internal \fImore\fP-like pager
+to display a screenful of possible completions at a time.
+.TP
+.B print\-completions\-horizontally (Off)
+If set to \fBOn\fP, readline will display completions with matches
+sorted horizontally in alphabetical order, rather than down the screen.
+.TP
+.B show\-all\-if\-ambiguous (Off)
+This alters the default behavior of the completion functions.  If
+set to
+.BR on ,
+words which have more than one possible completion cause the
+matches to be listed immediately instead of ringing the bell.
+.TP
+.B show\-all\-if\-unmodified (Off)
+This alters the default behavior of the completion functions in
+a fashion similar to \fBshow\-all\-if\-ambiguous\fP.
+If set to
+.BR on ,
+words which have more than one possible completion without any
+possible partial completion (the possible completions don't share
+a common prefix) cause the matches to be listed immediately instead
+of ringing the bell.
+.TP
+.B visible\-stats (Off)
+If set to \fBOn\fP, a character denoting a file's type as reported
+by \fIstat\fP(2) is appended to the filename when listing possible
+completions.
+.PD
+.SS "Readline Conditional Constructs"
+.PP
+Readline implements a facility similar in spirit to the conditional
+compilation features of the C preprocessor which allows key
+bindings and variable settings to be performed as the result
+of tests.  There are four parser directives used.
+.IP \fB$if\fP
+The 
+.B $if
+construct allows bindings to be made based on the
+editing mode, the terminal being used, or the application using
+readline.  The text of the test extends to the end of the line;
+no characters are required to isolate it.
+.RS
+.IP \fBmode\fP
+The \fBmode=\fP form of the \fB$if\fP directive is used to test
+whether readline is in emacs or vi mode.
+This may be used in conjunction
+with the \fBset keymap\fP command, for instance, to set bindings in
+the \fIemacs\-standard\fP and \fIemacs\-ctlx\fP keymaps only if
+readline is starting out in emacs mode.
+.IP \fBterm\fP
+The \fBterm=\fP form may be used to include terminal-specific
+key bindings, perhaps to bind the key sequences output by the
+terminal's function keys.  The word on the right side of the
+.B =
+is tested against the both full name of the terminal and the portion
+of the terminal name before the first \fB\-\fP.  This allows
+.I sun
+to match both
+.I sun
+and
+.IR sun\-cmd ,
+for instance.
+.IP \fBapplication\fP
+The \fBapplication\fP construct is used to include
+application-specific settings.  Each program using the readline
+library sets the \fIapplication name\fP, and an initialization
+file can test for a particular value.
+This could be used to bind key sequences to functions useful for
+a specific program.  For instance, the following command adds a
+key sequence that quotes the current or previous word in Bash:
+.sp 1
+.RS
+.nf
+\fB$if\fP Bash
+# Quote the current or previous word
+"\eC\-xq": "\eeb\e"\eef\e""
+\fB$endif\fP
+.fi
+.RE
+.RE
+.IP \fB$endif\fP
+This command, as seen in the previous example, terminates an
+\fB$if\fP command.
+.IP \fB$else\fP
+Commands in this branch of the \fB$if\fP directive are executed if
+the test fails.
+.IP \fB$include\fP
+This directive takes a single filename as an argument and reads commands
+and bindings from that file.  For example, the following directive
+would read \fI/etc/inputrc\fP:
+.sp 1
+.RS
+.nf
+\fB$include\fP \^ \fI/etc/inputrc\fP
+.fi
+.RE
+.SS Searching
+.PP
+Readline provides commands for searching through the command history
+(see
+.SM
+.B HISTORY
+below) for lines containing a specified string.
+There are two search modes:
+.I incremental
+and
+.IR non-incremental .
+.PP
+Incremental searches begin before the user has finished typing the
+search string.
+As each character of the search string is typed, readline displays
+the next entry from the history matching the string typed so far.
+An incremental search requires only as many characters as needed to
+find the desired history entry.
+The characters present in the value of the \fBisearch-terminators\fP
+variable are used to terminate an incremental search.
+If that variable has not been assigned a value the Escape and
+Control-J characters will terminate an incremental search.
+Control-G will abort an incremental search and restore the original
+line.
+When the search is terminated, the history entry containing the
+search string becomes the current line.
+.PP
+To find other matching entries in the history list, type Control-S or
+Control-R as appropriate.
+This will search backward or forward in the history for the next
+entry matching the search string typed so far.
+Any other key sequence bound to a readline command will terminate
+the search and execute that command.
+For instance, a \fInewline\fP will terminate the search and accept
+the line, thereby executing the command from the history list.
+.PP
+Readline remembers the last incremental search string.  If two
+Control-Rs are typed without any intervening characters defining a
+new search string, any remembered search string is used.
+.PP
+Non-incremental searches read the entire search string before starting
+to search for matching history lines.  The search string may be
+typed by the user or be part of the contents of the current line.
+.SS "Readline Command Names"
+.PP
+The following is a list of the names of the commands and the default
+key sequences to which they are bound.
+Command names without an accompanying key sequence are unbound by default.
+In the following descriptions, \fIpoint\fP refers to the current cursor
+position, and \fImark\fP refers to a cursor position saved by the
+\fBset\-mark\fP command.
+The text between the point and mark is referred to as the \fIregion\fP.
+.SS Commands for Moving
+.PP
+.PD 0
+.TP
+.B beginning\-of\-line (C\-a)
+Move to the start of the current line.
+.TP
+.B end\-of\-line (C\-e)
+Move to the end of the line.
+.TP
+.B forward\-char (C\-f)
+Move forward a character.
+.TP
+.B backward\-char (C\-b)
+Move back a character.
+.TP
+.B forward\-word (M\-f)
+Move forward to the end of the next word.  Words are composed of
+alphanumeric characters (letters and digits).
+.TP
+.B backward\-word (M\-b)
+Move back to the start of the current or previous word.  Words are
+composed of alphanumeric characters (letters and digits).
+.TP
+.B clear\-screen (C\-l)
+Clear the screen leaving the current line at the top of the screen.
+With an argument, refresh the current line without clearing the
+screen.
+.TP
+.B redraw\-current\-line
+Refresh the current line.
+.PD
+.SS Commands for Manipulating the History
+.PP
+.PD 0
+.TP
+.B accept\-line (Newline, Return)
+Accept the line regardless of where the cursor is.  If this line is
+non-empty, add it to the history list according to the state of the
+.SM
+.B HISTCONTROL
+variable.  If the line is a modified history
+line, then restore the history line to its original state.
+.TP
+.B previous\-history (C\-p)
+Fetch the previous command from the history list, moving back in
+the list.
+.TP
+.B next\-history (C\-n)
+Fetch the next command from the history list, moving forward in the
+list.
+.TP
+.B beginning\-of\-history (M\-<)
+Move to the first line in the history.
+.TP
+.B end\-of\-history (M\->)
+Move to the end of the input history, i.e., the line currently being
+entered.
+.TP
+.B reverse\-search\-history (C\-r)
+Search backward starting at the current line and moving `up' through
+the history as necessary.  This is an incremental search.
+.TP
+.B forward\-search\-history (C\-s)
+Search forward starting at the current line and moving `down' through
+the history as necessary.  This is an incremental search.
+.TP
+.B non\-incremental\-reverse\-search\-history (M\-p)
+Search backward through the history starting at the current line
+using a non-incremental search for a string supplied by the user.
+.TP
+.B non\-incremental\-forward\-search\-history (M\-n)
+Search forward through the history using a non-incremental search for
+a string supplied by the user.
+.TP
+.B history\-search\-forward
+Search forward through the history for the string of characters
+between the start of the current line and the point.
+This is a non-incremental search.
+.TP
+.B history\-search\-backward
+Search backward through the history for the string of characters
+between the start of the current line and the point.
+This is a non-incremental search.
+.TP
+.B yank\-nth\-arg (M\-C\-y)
+Insert the first argument to the previous command (usually
+the second word on the previous line) at point.
+With an argument
+.IR n ,
+insert the \fIn\fPth word from the previous command (the words
+in the previous command begin with word 0).  A negative argument
+inserts the \fIn\fPth word from the end of the previous command.
+.TP
+.B
+yank\-last\-arg (M\-.\^, M\-_\^)
+Insert the last argument to the previous command (the last word of
+the previous history entry).  With an argument,
+behave exactly like \fByank\-nth\-arg\fP.
+Successive calls to \fByank\-last\-arg\fP move back through the history
+list, inserting the last argument of each line in turn.
+.TP
+.B shell\-expand\-line (M\-C\-e)
+Expand the line as the shell does.  This
+performs alias and history expansion as well as all of the shell
+word expansions.  See
+.SM
+.B HISTORY EXPANSION
+below for a description of history expansion.
+.TP
+.B history\-expand\-line (M\-^)
+Perform history expansion on the current line.
+See
+.SM
+.B HISTORY EXPANSION
+below for a description of history expansion.
+.TP
+.B magic\-space
+Perform history expansion on the current line and insert a space.
+See
+.SM
+.B HISTORY EXPANSION
+below for a description of history expansion.
+.TP
+.B alias\-expand\-line
+Perform alias expansion on the current line.
+See
+.SM
+.B ALIASES
+above for a description of alias expansion.
+.TP
+.B history\-and\-alias\-expand\-line
+Perform history and alias expansion on the current line.
+.TP
+.B insert\-last\-argument (M\-.\^, M\-_\^)
+A synonym for \fByank\-last\-arg\fP.
+.TP
+.B operate\-and\-get\-next (C\-o)
+Accept the current line for execution and fetch the next line
+relative to the current line from the history for editing.  Any
+argument is ignored.
+.TP
+.B edit\-and\-execute\-command (C\-xC\-e)
+Invoke an editor on the current command line, and execute the result as shell
+commands.
+\fBBash\fP attempts to invoke
+.SM
+.BR $FCEDIT ,
+.SM
+.BR $EDITOR ,
+and \fIemacs\fP as the editor, in that order.
+.PD
+.SS Commands for Changing Text
+.PP
+.PD 0
+.TP
+.B delete\-char (C\-d)
+Delete the character at point.  If point is at the
+beginning of the line, there are no characters in the line, and
+the last character typed was not bound to \fBdelete\-char\fP,
+then return
+.SM
+.BR EOF .
+.TP
+.B backward\-delete\-char (Rubout)
+Delete the character behind the cursor.  When given a numeric argument,
+save the deleted text on the kill ring.
+.TP
+.B forward\-backward\-delete\-char
+Delete the character under the cursor, unless the cursor is at the
+end of the line, in which case the character behind the cursor is
+deleted.
+.TP
+.B quoted\-insert (C\-q, C\-v)
+Add the next character typed to the line verbatim.  This is
+how to insert characters like \fBC\-q\fP, for example.
+.TP
+.B tab\-insert (C\-v TAB)
+Insert a tab character.
+.TP
+.B self\-insert (a,\ b,\ A,\ 1,\ !,\ ...)
+Insert the character typed.
+.TP
+.B transpose\-chars (C\-t)
+Drag the character before point forward over the character at point,
+moving point forward as well.
+If point is at the end of the line, then this transposes
+the two characters before point.
+Negative arguments have no effect.
+.TP
+.B transpose\-words (M\-t)
+Drag the word before point past the word after point,
+moving point over that word as well.
+If point is at the end of the line, this transposes
+the last two words on the line.   
+.TP
+.B upcase\-word (M\-u)
+Uppercase the current (or following) word.  With a negative argument,
+uppercase the previous word, but do not move point.
+.TP
+.B downcase\-word (M\-l)
+Lowercase the current (or following) word.  With a negative argument,
+lowercase the previous word, but do not move point.
+.TP
+.B capitalize\-word (M\-c)
+Capitalize the current (or following) word.  With a negative argument,
+capitalize the previous word, but do not move point.
+.TP
+.B overwrite\-mode
+Toggle overwrite mode.  With an explicit positive numeric argument,
+switches to overwrite mode.  With an explicit non-positive numeric
+argument, switches to insert mode.  This command affects only
+\fBemacs\fP mode; \fBvi\fP mode does overwrite differently.
+Each call to \fIreadline()\fP starts in insert mode.
+In overwrite mode, characters bound to \fBself\-insert\fP replace   
+the text at point rather than pushing the text to the right.
+Characters bound to \fBbackward\-delete\-char\fP replace the character
+before point with a space.  By default, this command is unbound.
+.PD
+.SS Killing and Yanking
+.PP
+.PD 0
+.TP
+.B kill\-line (C\-k)
+Kill the text from point to the end of the line.
+.TP
+.B backward\-kill\-line (C\-x Rubout)
+Kill backward to the beginning of the line.
+.TP
+.B unix\-line\-discard (C\-u)
+Kill backward from point to the beginning of the line.
+The killed text is saved on the kill-ring.
+.\" There is no real difference between this and backward-kill-line
+.TP
+.B kill\-whole\-line
+Kill all characters on the current line, no matter where point is.
+.TP
+.B kill\-word  (M\-d)
+Kill from point to the end of the current word, or if between
+words, to the end of the next word.
+Word boundaries are the same as those used by \fBforward\-word\fP.
+.TP
+.B backward\-kill\-word (M\-Rubout)
+Kill the word behind point.
+Word boundaries are the same as those used by \fBbackward\-word\fP.
+.TP
+.B unix\-word\-rubout (C\-w)
+Kill the word behind point, using white space as a word boundary.
+The killed text is saved on the kill-ring.
+.TP
+.B unix\-filename\-rubout
+Kill the word behind point, using white space and the slash character
+as the word boundaries.
+The killed text is saved on the kill-ring.
+.TP
+.B delete\-horizontal\-space (M\-\e)
+Delete all spaces and tabs around point.
+.TP
+.B kill\-region
+Kill the text in the current region.
+.TP
+.B copy\-region\-as\-kill
+Copy the text in the region to the kill buffer.
+.TP
+.B copy\-backward\-word
+Copy the word before point to the kill buffer.
+The word boundaries are the same as \fBbackward\-word\fP.
+.TP
+.B copy\-forward\-word
+Copy the word following point to the kill buffer.
+The word boundaries are the same as \fBforward\-word\fP.
+.TP
+.B yank (C\-y)
+Yank the top of the kill ring into the buffer at point.
+.TP
+.B yank\-pop (M\-y)
+Rotate the kill ring, and yank the new top.  Only works following
+.B yank
+or
+.BR yank\-pop .
+.PD
+.SS Numeric Arguments
+.PP
+.PD 0
+.TP
+.B digit\-argument (M\-0, M\-1, ..., M\-\-)
+Add this digit to the argument already accumulating, or start a new
+argument.  M\-\- starts a negative argument.
+.TP
+.B universal\-argument
+This is another way to specify an argument.
+If this command is followed by one or more digits, optionally with a
+leading minus sign, those digits define the argument.
+If the command is followed by digits, executing
+.B universal\-argument
+again ends the numeric argument, but is otherwise ignored.
+As a special case, if this command is immediately followed by a
+character that is neither a digit or minus sign, the argument count
+for the next command is multiplied by four.
+The argument count is initially one, so executing this function the
+first time makes the argument count four, a second time makes the
+argument count sixteen, and so on.
+.PD
+.SS Completing
+.PP
+.PD 0
+.TP
+.B complete (TAB)
+Attempt to perform completion on the text before point.
+.B Bash
+attempts completion treating the text as a variable (if the
+text begins with \fB$\fP), username (if the text begins with
+\fB~\fP), hostname (if the text begins with \fB@\fP), or
+command (including aliases and functions) in turn.  If none
+of these produces a match, filename completion is attempted.
+.TP
+.B possible\-completions (M\-?)
+List the possible completions of the text before point.
+.TP
+.B insert\-completions (M\-*)
+Insert all completions of the text before point
+that would have been generated by
+\fBpossible\-completions\fP.
+.TP
+.B menu\-complete
+Similar to \fBcomplete\fP, but replaces the word to be completed
+with a single match from the list of possible completions.
+Repeated execution of \fBmenu\-complete\fP steps through the list
+of possible completions, inserting each match in turn.
+At the end of the list of completions, the bell is rung
+(subject to the setting of \fBbell\-style\fP)
+and the original text is restored.
+An argument of \fIn\fP moves \fIn\fP positions forward in the list
+of matches; a negative argument may be used to move backward
+through the list.
+This command is intended to be bound to \fBTAB\fP, but is unbound
+by default.
+.TP
+.B delete\-char\-or\-list
+Deletes the character under the cursor if not at the beginning or
+end of the line (like \fBdelete\-char\fP).
+If at the end of the line, behaves identically to
+\fBpossible\-completions\fP.
+This command is unbound by default.
+.TP
+.B complete\-filename (M\-/)
+Attempt filename completion on the text before point.
+.TP
+.B possible\-filename\-completions (C\-x /)
+List the possible completions of the text before point,
+treating it as a filename.
+.TP
+.B complete\-username (M\-~)
+Attempt completion on the text before point, treating
+it as a username.
+.TP
+.B possible\-username\-completions (C\-x ~)
+List the possible completions of the text before point,
+treating it as a username.
+.TP
+.B complete\-variable (M\-$)
+Attempt completion on the text before point, treating
+it as a shell variable.
+.TP
+.B possible\-variable\-completions (C\-x $)
+List the possible completions of the text before point,
+treating it as a shell variable.
+.TP
+.B complete\-hostname (M\-@)
+Attempt completion on the text before point, treating
+it as a hostname.
+.TP
+.B possible\-hostname\-completions (C\-x @)
+List the possible completions of the text before point,
+treating it as a hostname.
+.TP
+.B complete\-command (M\-!)
+Attempt completion on the text before point, treating
+it as a command name.  Command completion attempts to
+match the text against aliases, reserved words, shell
+functions, shell builtins, and finally executable filenames,
+in that order.
+.TP
+.B possible\-command\-completions (C\-x !)
+List the possible completions of the text before point,
+treating it as a command name.
+.TP
+.B dynamic\-complete\-history (M\-TAB)
+Attempt completion on the text before point, comparing
+the text against lines from the history list for possible
+completion matches.
+.TP
+.B complete\-into\-braces (M\-{)
+Perform filename completion and insert the list of possible completions
+enclosed within braces so the list is available to the shell (see
+.B Brace Expansion
+above).
+.PD
+.SS Keyboard Macros
+.PP
+.PD 0
+.TP
+.B start\-kbd\-macro (C\-x (\^)
+Begin saving the characters typed into the current keyboard macro.
+.TP
+.B end\-kbd\-macro (C\-x )\^)
+Stop saving the characters typed into the current keyboard macro
+and store the definition.
+.TP
+.B call\-last\-kbd\-macro (C\-x e)
+Re-execute the last keyboard macro defined, by making the characters
+in the macro appear as if typed at the keyboard.
+.PD
+.SS Miscellaneous
+.PP
+.PD 0
+.TP
+.B re\-read\-init\-file (C\-x C\-r)
+Read in the contents of the \fIinputrc\fP file, and incorporate
+any bindings or variable assignments found there.
+.TP
+.B abort (C\-g)
+Abort the current editing command and
+ring the terminal's bell (subject to the setting of
+.BR bell\-style ).
+.TP
+.B do\-uppercase\-version (M\-a, M\-b, M\-\fIx\fP, ...)
+If the metafied character \fIx\fP is lowercase, run the command
+that is bound to the corresponding uppercase character.
+.TP
+.B prefix\-meta (ESC)
+Metafy the next character typed.
+.SM
+.B ESC
+.B f
+is equivalent to
+.BR Meta\-f .
+.TP
+.B undo (C\-_, C\-x C\-u)
+Incremental undo, separately remembered for each line.
+.TP
+.B revert\-line (M\-r)
+Undo all changes made to this line.  This is like executing the
+.B undo
+command enough times to return the line to its initial state.
+.TP
+.B tilde\-expand (M\-&)
+Perform tilde expansion on the current word.
+.TP
+.B set\-mark (C\-@, M\-<space>)
+Set the mark to the point.  If a
+numeric argument is supplied, the mark is set to that position.
+.TP
+.B exchange\-point\-and\-mark (C\-x C\-x)
+Swap the point with the mark.  The current cursor position is set to
+the saved position, and the old cursor position is saved as the mark.
+.TP
+.B character\-search (C\-])
+A character is read and point is moved to the next occurrence of that
+character.  A negative count searches for previous occurrences.
+.TP
+.B character\-search\-backward (M\-C\-])
+A character is read and point is moved to the previous occurrence of that
+character.  A negative count searches for subsequent occurrences.
+.TP
+.B insert\-comment (M\-#)
+Without a numeric argument, the value of the readline
+.B comment\-begin
+variable is inserted at the beginning of the current line.
+If a numeric argument is supplied, this command acts as a toggle:  if
+the characters at the beginning of the line do not match the value
+of \fBcomment\-begin\fP, the value is inserted, otherwise
+the characters in \fBcomment-begin\fP are deleted from the beginning of 
+the line.
+In either case, the line is accepted as if a newline had been typed.
+The default value of
+\fBcomment\-begin\fP causes this command to make the current line
+a shell comment.
+If a numeric argument causes the comment character to be removed, the line
+will be executed by the shell.
+.TP
+.B glob\-complete\-word (M\-g)
+The word before point is treated as a pattern for pathname expansion,
+with an asterisk implicitly appended.  This pattern is used to
+generate a list of matching file names for possible completions.
+.TP
+.B glob\-expand\-word (C\-x *)
+The word before point is treated as a pattern for pathname expansion,
+and the list of matching file names is inserted, replacing the word.
+If a numeric argument is supplied, an asterisk is appended before
+pathname expansion.
+.TP
+.B glob\-list\-expansions (C\-x g)
+The list of expansions that would have been generated by
+.B glob\-expand\-word
+is displayed, and the line is redrawn.
+If a numeric argument is supplied, an asterisk is appended before
+pathname expansion.
+.TP
+.B dump\-functions
+Print all of the functions and their key bindings to the
+readline output stream.  If a numeric argument is supplied,
+the output is formatted in such a way that it can be made part
+of an \fIinputrc\fP file.
+.TP
+.B dump\-variables
+Print all of the settable readline variables and their values to the
+readline output stream.  If a numeric argument is supplied,
+the output is formatted in such a way that it can be made part
+of an \fIinputrc\fP file.
+.TP
+.B dump\-macros
+Print all of the readline key sequences bound to macros and the
+strings they ouput.  If a numeric argument is supplied,
+the output is formatted in such a way that it can be made part
+of an \fIinputrc\fP file.
+.TP
+.B display\-shell\-version (C\-x C\-v)
+Display version information about the current instance of
+.BR bash .
+.PD
+.SS Programmable Completion
+.PP
+When word completion is attempted for an argument to a command for
+which a completion specification (a \fIcompspec\fP) has been defined
+using the \fBcomplete\fP builtin (see
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below), the programmable completion facilities are invoked.
+.PP
+First, the command name is identified.
+If a compspec has been defined for that command, the
+compspec is used to generate the list of possible completions for the word.
+If the command word is a full pathname, a compspec for the full
+pathname is searched for first.
+If no compspec is found for the full pathname, an attempt is made to
+find a compspec for the portion following the final slash.
+.PP
+Once a compspec has been found, it is used to generate the list of
+matching words.
+If a compspec is not found, the default \fBbash\fP completion as
+described above under \fBCompleting\fP is performed.
+.PP
+First, the actions specified by the compspec are used.
+Only matches which are prefixed by the word being completed are
+returned.
+When the
+.B \-f
+or
+.B \-d
+option is used for filename or directory name completion, the shell
+variable
+.SM
+.B FIGNORE
+is used to filter the matches.
+.PP
+Any completions specified by a filename expansion pattern to the
+\fB\-G\fP option are generated next.
+The words generated by the pattern need not match the word
+being completed.
+The
+.SM
+.B GLOBIGNORE
+shell variable is not used to filter the matches, but the
+.SM
+.B FIGNORE
+variable is used.
+.PP
+Next, the string specified as the argument to the \fB\-W\fP option
+is considered.
+The string is first split using the characters in the
+.SM
+.B IFS
+special variable as delimiters.
+Shell quoting is honored.
+Each word is then expanded using
+brace expansion, tilde expansion, parameter and variable expansion,
+command substitution, arithmetic expansion, and pathname expansion,
+as described above under 
+.SM
+.BR EXPANSION .
+The results are split using the rules described above under
+\fBWord Splitting\fP.
+The results of the expansion are prefix-matched against the word being
+completed, and the matching words become the possible completions.
+.PP
+After these matches have been generated, any shell function or command
+specified with the \fB\-F\fP and \fB\-C\fP options is invoked.
+When the command or function is invoked, the
+.SM
+.B COMP_LINE
+and
+.SM
+.B COMP_POINT
+variables are assigned values as described above under
+\fBShell Variables\fP.
+If a shell function is being invoked, the 
+.SM
+.B COMP_WORDS
+and
+.SM
+.B COMP_CWORD
+variables are also set.
+When the function or command is invoked, the first argument is the
+name of the command whose arguments are being completed, the
+second argument is the word being completed, and the third argument
+is the word preceding the word being completed on the current command line.
+No filtering of the generated completions against the word being completed
+is performed; the function or command has complete freedom in generating
+the matches.
+.PP
+Any function specified with \fB\-F\fP is invoked first.
+The function may use any of the shell facilities, including the
+\fBcompgen\fP builtin described below, to generate the matches.
+It must put the possible completions in the
+.SM
+.B COMPREPLY
+array variable.
+.PP
+Next, any command specified with the \fB\-C\fP option is invoked
+in an environment equivalent to command substitution.
+It should print a list of completions, one per line, to the
+standard output.
+Backslash may be used to escape a newline, if necessary.
+.PP
+After all of the possible completions are generated, any filter
+specified with the \fB\-X\fP option is applied to the list.
+The filter is a pattern as used for pathname expansion; a \fB&\fP
+in the pattern is replaced with the text of the word being completed.
+A literal \fB&\fP may be escaped with a backslash; the backslash
+is removed before attempting a match.
+Any completion that matches the pattern will be removed from the list.
+A leading \fB!\fP negates the pattern; in this case any completion
+not matching the pattern will be removed.
+.PP
+Finally, any prefix and suffix specified with the \fB\-P\fP and \fB\-S\fP
+options are added to each member of the completion list, and the result is
+returned to the readline completion code as the list of possible
+completions.
+.PP
+If the previously-applied actions do not generate any matches, and the
+\fB\-o dirnames\fP option was supplied to \fBcomplete\fP when the
+compspec was defined, directory name completion is attempted.
+.PP
+If the \fB\-o plusdirs\fP option was supplied to \fBcomplete\fP when the
+compspec was defined, directory name completion is attempted and any
+matches are added to the results of the other actions.
+.PP
+By default, if a compspec is found, whatever it generates is returned
+to the completion code as the full set of possible completions.
+The default \fBbash\fP completions are not attempted, and the readline
+default of filename completion is disabled.
+If the \fB\-o bashdefault\fP option was supplied to \fBcomplete\fP when
+the compspec was defined, the \fBbash\fP default completions are attempted
+if the compspec generates no matches.
+If the \fB\-o default\fP option was supplied to \fBcomplete\fP when the
+compspec was defined, readline's default completion will be performed
+if the compspec (and, if attempted, the default \fBbash\fP completions)
+generate no matches.
+.PP
+When a compspec indicates that directory name completion is desired,
+the programmable completion functions force readline to append a slash
+to completed names which are symbolic links to directories, subject to  
+the value of the \fBmark\-directories\fP readline variable, regardless
+of the setting of the \fBmark-symlinked\-directories\fP readline variable.
+.SH HISTORY
+When the
+.B \-o history
+option to the
+.B set
+builtin is enabled, the shell provides access to the
+\fIcommand history\fP,
+the list of commands previously typed.
+The value of the \fBHISTSIZE\fP variable is used as the
+number of commands to save in a history list.
+The text of the last
+.SM
+.B HISTSIZE
+commands (default 500) is saved.  The shell
+stores each command in the history list prior to parameter and
+variable expansion (see
+.SM
+.B EXPANSION
+above) but after history expansion is performed, subject to the
+values of the shell variables
+.SM
+.B HISTIGNORE
+and
+.SM
+.BR HISTCONTROL .
+.PP
+On startup, the history is initialized from the file named by
+the variable
+.SM
+.B HISTFILE
+(default \fI~/.bash_history\fP).
+The file named by the value of
+.SM
+.B HISTFILE
+is truncated, if necessary, to contain no more than
+the number of lines specified by the value of
+.SM
+.BR HISTFILESIZE .
+When an interactive shell exits, the last
+.SM
+.B $HISTSIZE
+lines are copied from the history list to
+.SM
+.BR $HISTFILE .
+If the
+.B histappend
+shell option is enabled
+(see the description of
+.B shopt
+under
+.SM
+.B "SHELL BUILTIN COMMANDS"
+below), the lines are appended to the history file,
+otherwise the history file is overwritten.
+If
+.SM
+.B HISTFILE
+is unset, or if the history file is unwritable, the history is
+not saved.  After saving the history, the history file is truncated
+to contain no more than
+.SM
+.B HISTFILESIZE
+lines.  If
+.SM
+.B HISTFILESIZE
+is not set, no truncation is performed.
+.PP
+The builtin command
+.B fc
+(see
+.SM
+.B SHELL BUILTIN COMMANDS
+below) may be used to list or edit and re-execute a portion of
+the history list.
+The
+.B history
+builtin may be used to display or modify the history list and
+manipulate the history file.
+When using command-line editing, search commands
+are available in each editing mode that provide access to the
+history list.
+.PP
+The shell allows control over which commands are saved on the history
+list.  The
+.SM
+.B HISTCONTROL
+and
+.SM
+.B HISTIGNORE
+variables may be set to cause the shell to save only a subset of the
+commands entered.
+The
+.B cmdhist
+shell option, if enabled, causes the shell to attempt to save each
+line of a multi-line command in the same history entry, adding
+semicolons where necessary to preserve syntactic correctness.
+The
+.B lithist
+shell option causes the shell to save the command with embedded newlines
+instead of semicolons.  See the description of the
+.B shopt
+builtin below under
+.SM
+.B "SHELL BUILTIN COMMANDS"
+for information on setting and unsetting shell options.
+.SH "HISTORY EXPANSION"
+.PP
+The shell supports a history expansion feature that
+is similar to the history expansion in
+.BR csh.
+This section describes what syntax features are available.  This
+feature is enabled by default for interactive shells, and can be
+disabled using the
+.B \+H
+option to the
+.B set
+builtin command (see
+.SM
+.B SHELL BUILTIN COMMANDS
+below).  Non-interactive shells do not perform history expansion
+by default.
+.PP
+History expansions introduce words from the history list into
+the input stream, making it easy to repeat commands, insert the
+arguments to a previous command into the current input line, or
+fix errors in previous commands quickly.
+.PP
+History expansion is performed immediately after a complete line
+is read, before the shell breaks it into words.
+It takes place in two parts.
+The first is to determine which line from the history list
+to use during substitution.
+The second is to select portions of that line for inclusion into
+the current one.
+The line selected from the history is the \fIevent\fP,
+and the portions of that line that are acted upon are \fIwords\fP.
+Various \fImodifiers\fP are available to manipulate the selected words.
+The line is broken into words in the same fashion as when reading input,
+so that several \fImetacharacter\fP-separated words surrounded by
+quotes are considered one word.
+History expansions are introduced by the appearance of the
+history expansion character, which is \^\fB!\fP\^ by default.
+Only backslash (\^\fB\e\fP\^) and single quotes can quote
+the history expansion character.
+.PP
+Several characters inhibit history expansion if found immediately
+following the history expansion character, even if it is unquoted:
+space, tab, newline, carriage return, and \fB=\fP.
+If the \fBextglob\fP shell option is enabled, \fB(\fP will also
+inhibit expansion.
+.PP
+Several shell options settable with the
+.B shopt
+builtin may be used to tailor the behavior of history expansion.
+If the
+.B histverify
+shell option is enabled (see the description of the
+.B shopt
+builtin), and
+.B readline
+is being used, history substitutions are not immediately passed to
+the shell parser.
+Instead, the expanded line is reloaded into the
+.B readline
+editing buffer for further modification.
+If
+.B readline
+is being used, and the
+.B histreedit
+shell option is enabled, a failed history substitution will be reloaded
+into the
+.B readline
+editing buffer for correction.
+The
+.B \-p
+option to the
+.B history
+builtin command may be used to see what a history expansion will
+do before using it.
+The
+.B \-s
+option to the
+.B history
+builtin may be used to add commands to the end of the history list
+without actually executing them, so that they are available for
+subsequent recall.
+.PP
+The shell allows control of the various characters used by the
+history expansion mechanism (see the description of
+.B histchars
+above under
+.BR "Shell Variables" ).
+.SS Event Designators
+.PP
+An event designator is a reference to a command line entry in the
+history list.
+.PP
+.PD 0
+.TP
+.B !
+Start a history substitution, except when followed by a
+.BR blank ,
+newline, carriage return, =
+or ( (when the \fBextglob\fP shell option is enabled using
+the \fBshopt\fP builtin).
+.TP
+.B !\fIn\fR
+Refer to command line
+.IR n .
+.TP
+.B !\-\fIn\fR
+Refer to the current command line minus
+.IR n .
+.TP
+.B !!
+Refer to the previous command.  This is a synonym for `!\-1'.
+.TP
+.B !\fIstring\fR
+Refer to the most recent command starting with 
+.IR string .
+.TP
+.B !?\fIstring\fR\fB[?]\fR
+Refer to the most recent command containing
+.IR string .
+The trailing \fB?\fP may be omitted if
+.I string
+is followed immediately by a newline.
+.TP
+.B \d\s+2^\s-2\u\fIstring1\fP\d\s+2^\s-2\u\fIstring2\fP\d\s+2^\s-2\u
+Quick substitution.  Repeat the last command, replacing
+.I string1
+with
+.IR string2 .
+Equivalent to
+``!!:s/\fIstring1\fP/\fIstring2\fP/''
+(see \fBModifiers\fP below).
+.TP
+.B !#
+The entire command line typed so far.
+.PD
+.SS Word Designators
+.PP
+Word designators are used to select desired words from the event.
+A 
+.B :
+separates the event specification from the word designator.
+It may be omitted if the word designator begins with a
+.BR ^ ,
+.BR $ ,
+.BR * ,
+.BR \- ,
+or
+.BR % .
+Words are numbered from the beginning of the line,
+with the first word being denoted by 0 (zero).
+Words are inserted into the current line separated by single spaces.
+.PP
+.PD 0
+.TP
+.B 0 (zero)
+The zeroth word.  For the shell, this is the command
+word.
+.TP
+.I n
+The \fIn\fRth word.
+.TP
+.B ^
+The first argument.  That is, word 1.
+.TP
+.B $
+The last argument.
+.TP
+.B %
+The word matched by the most recent `?\fIstring\fR?' search.
+.TP
+.I x\fB\-\fPy
+A range of words; `\-\fIy\fR' abbreviates `0\-\fIy\fR'.
+.TP
+.B *
+All of the words but the zeroth.  This is a synonym
+for `\fI1\-$\fP'.  It is not an error to use
+.B *
+if there is just one
+word in the event; the empty string is returned in that case.
+.TP
+.B x*
+Abbreviates \fIx\-$\fP.
+.TP
+.B x\-
+Abbreviates \fIx\-$\fP like \fBx*\fP, but omits the last word.
+.PD
+.PP
+If a word designator is supplied without an event specification, the
+previous command is used as the event.
+.SS Modifiers
+.PP
+After the optional word designator, there may appear a sequence of
+one or more of the following modifiers, each preceded by a `:'.
+.PP
+.PD 0
+.PP
+.TP
+.B h
+Remove a trailing file name component, leaving only the head.
+.TP
+.B t
+Remove all leading file name components, leaving the tail.
+.TP
+.B r
+Remove a trailing suffix of the form \fI.xxx\fP, leaving the
+basename.
+.TP
+.B e
+Remove all but the trailing suffix.
+.TP
+.B p
+Print the new command but do not execute it.
+.TP
+.B q
+Quote the substituted words, escaping further substitutions.
+.TP
+.B x
+Quote the substituted words as with
+.BR q ,
+but break into words at
+.B blanks
+and newlines.
+.TP
+.B s/\fIold\fP/\fInew\fP/
+Substitute
+.I new
+for the first occurrence of
+.I old
+in the event line.  Any delimiter can be used in place of /.  The
+final delimiter is optional if it is the last character of the
+event line.  The delimiter may be quoted in
+.I old
+and
+.I new
+with a single backslash.  If & appears in
+.IR new ,
+it is replaced by
+.IR old .
+A single backslash will quote the &.  If
+.I old
+is null, it is set to the last
+.I old
+substituted, or, if no previous history substitutions took place,
+the last
+.I string
+in a
+.B !?\fIstring\fR\fB[?]\fR
+search.
+.TP
+.B &
+Repeat the previous substitution.
+.TP
+.B g
+Cause changes to be applied over the entire event line.  This is
+used in conjunction with `\fB:s\fP' (e.g., `\fB:gs/\fIold\fP/\fInew\fP/\fR')
+or `\fB:&\fP'.  If used with
+`\fB:s\fP', any delimiter can be used
+in place of /, and the final delimiter is optional
+if it is the last character of the event line.
+An \fBa\fP may be used as a synonym for \fBg\fP.
+.TP
+.B G
+Apply the following `\fBs\fP' modifier once to each word in the event line.
+.PD
+.SH "SHELL BUILTIN COMMANDS"
+.\" start of bash_builtins
+.zZ
+.PP
+Unless otherwise noted, each builtin command documented in this
+section as accepting options preceded by
+.B \-
+accepts
+.B \-\-
+to signify the end of the options.
+.sp .5
+.PD 0
+.TP
+\fB:\fP [\fIarguments\fP]
+.PD
+No effect; the command does nothing beyond expanding
+.I arguments
+and performing any specified
+redirections.  A zero exit code is returned.
+.TP
+\fB .\| \fP \fIfilename\fP [\fIarguments\fP]
+.PD 0
+.TP
+\fBsource\fP \fIfilename\fP [\fIarguments\fP]
+.PD
+Read and execute commands from
+.I filename
+in the current
+shell environment and return the exit status of the last command
+executed from
+.IR filename .
+If
+.I filename
+does not contain a slash, file names in
+.SM
+.B PATH
+are used to find the directory containing
+.IR filename .
+The file searched for in
+.SM
+.B PATH
+need not be executable.
+When \fBbash\fP is not in \fIposix mode\fP, the current directory is
+searched if no file is found in
+.SM
+.BR PATH .
+If the
+.B sourcepath
+option to the
+.B shopt
+builtin command is turned off, the
+.SM
+.B PATH
+is not searched.
+If any \fIarguments\fP are supplied, they become the positional
+parameters when \fIfilename\fP is executed.  Otherwise the positional
+parameters are unchanged.
+The return status is the status of the last command exited within
+the script (0 if no commands are executed), and false if
+.I filename
+is not found or cannot be read.
+.TP
+\fBalias\fP [\fB\-p\fP] [\fIname\fP[=\fIvalue\fP] ...]
+\fBAlias\fP with no arguments or with the
+.B \-p
+option prints the list of aliases in the form
+\fBalias\fP \fIname\fP=\fIvalue\fP on standard output.
+When arguments are supplied, an alias is defined for
+each \fIname\fP whose \fIvalue\fP is given.
+A trailing space in  \fIvalue\fP causes the next word to be
+checked for alias substitution when the alias is expanded.
+For each \fIname\fP in the argument list for which no \fIvalue\fP
+is supplied, the name and value of the alias is printed.
+\fBAlias\fP returns true unless a \fIname\fP is given for which
+no alias has been defined.
+.TP
+\fBbg\fP [\fIjobspec\fP]
+Resume the suspended job \fIjobspec\fP in the background, as if it
+had been started with
+.BR & .
+If \fIjobspec\fP is not present, the shell's notion of the
+\fIcurrent job\fP is used.
+.B bg
+.I jobspec
+returns 0 unless run when job control is disabled or, when run with
+job control enabled, if \fIjobspec\fP was not found or started without
+job control.
+.TP
+\fBbind\fP [\fB\-m\fP \fIkeymap\fP] [\fB\-lpsvPSV\fP]
+.PD 0
+.TP
+\fBbind\fP [\fB\-m\fP \fIkeymap\fP] [\fB\-q\fP \fIfunction\fP] [\fB\-u\fP \fIfunction\fP] [\fB\-r\fP \fIkeyseq\fP]
+.TP
+\fBbind\fP [\fB\-m\fP \fIkeymap\fP] \fB\-f\fP \fIfilename\fP
+.TP
+\fBbind\fP [\fB\-m\fP \fIkeymap\fP] \fB\-x\fP \fIkeyseq\fP:\fIshell\-command\fP
+.TP
+\fBbind\fP [\fB\-m\fP \fIkeymap\fP] \fIkeyseq\fP:\fIfunction\-name\fP
+.TP
+\fBbind\fP \fIreadline\-command\fP
+.PD
+Display current
+.B readline
+key and function bindings, bind a key sequence to a
+.B readline
+function or macro, or set a
+.B readline
+variable.
+Each non-option argument is a command as it would appear in
+.IR .inputrc ,
+but each binding or command must be passed as a separate argument;
+e.g., '"\eC\-x\eC\-r": re\-read\-init\-file'.
+Options, if supplied, have the following meanings:
+.RS
+.PD 0
+.TP
+.B \-m \fIkeymap\fP
+Use
+.I keymap
+as the keymap to be affected by the subsequent bindings.
+Acceptable
+.I keymap
+names are
+\fIemacs, emacs\-standard, emacs\-meta, emacs\-ctlx, vi,
+vi\-move, vi\-command\fP, and
+.IR vi\-insert .
+\fIvi\fP is equivalent to \fIvi\-command\fP; \fIemacs\fP is
+equivalent to \fIemacs\-standard\fP.
+.TP
+.B \-l
+List the names of all \fBreadline\fP functions.
+.TP
+.B \-p
+Display \fBreadline\fP function names and bindings in such a way
+that they can be re-read.
+.TP
+.B \-P
+List current \fBreadline\fP function names and bindings.
+.TP
+.B \-v
+Display \fBreadline\fP variable names and values in such a way that they
+can be re-read.
+.TP
+.B \-V
+List current \fBreadline\fP variable names and values.
+.TP
+.B \-s
+Display \fBreadline\fP key sequences bound to macros and the strings
+they output in such a way that they can be re-read.
+.TP
+.B \-S
+Display \fBreadline\fP key sequences bound to macros and the strings
+they output.
+.TP
+.B \-f \fIfilename\fP
+Read key bindings from \fIfilename\fP.
+.TP
+.B \-q \fIfunction\fP
+Query about which keys invoke the named \fIfunction\fP.
+.TP
+.B \-u \fIfunction\fP
+Unbind all keys bound to the named \fIfunction\fP.
+.TP
+.B \-r \fIkeyseq\fP
+Remove any current binding for \fIkeyseq\fP.
+.TP
+.B \-x \fIkeyseq\fP:\fIshell\-command\fP
+Cause \fIshell\-command\fP to be executed whenever \fIkeyseq\fP is
+entered.
+.PD
+.PP
+The return value is 0 unless an unrecognized option is given or an
+error occurred.
+.RE
+.TP
+\fBbreak\fP [\fIn\fP]
+Exit from within a
+.BR for ,
+.BR while ,
+.BR until ,
+or
+.B select
+loop.  If \fIn\fP is specified, break \fIn\fP levels.
+.I n
+must be \(>= 1.  If
+.I n
+is greater than the number of enclosing loops, all enclosing loops
+are exited.  The return value is 0 unless the shell is not executing
+a loop when
+.B break
+is executed.
+.TP
+\fBbuiltin\fP \fIshell\-builtin\fP [\fIarguments\fP]
+Execute the specified shell builtin, passing it
+.IR arguments ,
+and return its exit status.
+This is useful when defining a
+function whose name is the same as a shell builtin,
+retaining the functionality of the builtin within the function.
+The \fBcd\fP builtin is commonly redefined this way.
+The return status is false if
+.I shell\-builtin
+is not a shell builtin command.
+.TP
+\fBcd\fP [\fB\-L|-P\fP] [\fIdir\fP]
+Change the current directory to \fIdir\fP.  The variable
+.SM
+.B HOME
+is the
+default
+.IR dir .
+The variable
+.SM
+.B CDPATH
+defines the search path for the directory containing
+.IR dir .
+Alternative directory names in
+.SM
+.B CDPATH
+are separated by a colon (:).  A null directory name in
+.SM
+.B CDPATH
+is the same as the current directory, i.e., ``\fB.\fP''.  If
+.I dir
+begins with a slash (/),
+then
+.SM
+.B CDPATH
+is not used. The
+.B \-P
+option says to use the physical directory structure instead of
+following symbolic links (see also the
+.B \-P
+option to the
+.B set
+builtin command); the
+.B \-L
+option forces symbolic links to be followed.  An argument of
+.B \-
+is equivalent to
+.SM
+.BR $OLDPWD .
+If a non-empty directory name from \fBCDPATH\fP is used, or if
+\fB\-\fP is the first argument, and the directory change is
+successful, the absolute pathname of the new working directory is
+written to the standard output.
+The return value is true if the directory was successfully changed;
+false otherwise.
+.TP
+\fBcaller\fP [\fIexpr\fP]
+Returns the context of any active subroutine call (a shell function or
+a script executed with the \fB.\fP or \fBsource\fP builtins.
+Without \fIexpr\fP, \fBcaller\fP displays the line number and source
+filename of the current subroutine call.
+If a non-negative integer is supplied as \fIexpr\fP, \fBcaller\fP 
+displays the line number, subroutine name, and source file corresponding
+to that position in the current execution call stack.  This extra
+information may be used, for example, to print a stack trace.  The
+current frame is frame 0.
+The return value is 0 unless the shell is not executing a subroutine
+call or \fIexpr\fP does not correspond to a valid position in the
+call stack.
+.TP
+\fBcommand\fP [\fB\-pVv\fP] \fIcommand\fP [\fIarg\fP ...]
+Run
+.I command
+with
+.I args
+suppressing the normal shell function lookup. Only builtin
+commands or commands found in the
+.SM
+.B PATH
+are executed.  If the
+.B \-p
+option is given, the search for
+.I command
+is performed using a default value for
+.B PATH
+that is guaranteed to find all of the standard utilities.
+If either the
+.B \-V
+or
+.B \-v
+option is supplied, a description of
+.I command
+is printed.  The
+.B \-v
+option causes a single word indicating the command or file name
+used to invoke
+.I command
+to be displayed; the
+.B \-V
+option produces a more verbose description.
+If the
+.B \-V
+or
+.B \-v
+option is supplied, the exit status is 0 if
+.I command
+was found, and 1 if not.  If neither option is supplied and
+an error occurred or
+.I command
+cannot be found, the exit status is 127.  Otherwise, the exit status of the
+.B command
+builtin is the exit status of
+.IR command .
+.TP
+\fBcompgen\fP [\fIoption\fP] [\fIword\fP]
+Generate possible completion matches for \fIword\fP according to
+the \fIoption\fPs, which may be any option accepted by the
+.B complete
+builtin with the exception of \fB\-p\fP and \fB\-r\fP, and write
+the matches to the standard output.
+When using the \fB\-F\fP or \fB\-C\fP options, the various shell variables
+set by the programmable completion facilities, while available, will not
+have useful values.
+.sp 1
+The matches will be generated in the same way as if the programmable
+completion code had generated them directly from a completion specification
+with the same flags.
+If \fIword\fP is specified, only those completions matching \fIword\fP
+will be displayed.
+.sp 1
+The return value is true unless an invalid option is supplied, or no
+matches were generated.
+.TP
+\fBcomplete\fP [\fB\-abcdefgjksuv\fP] [\fB\-o\fP \fIcomp-option\fP] [\fB\-A\fP \fIaction\fP] [\fB\-G\fP \fIglobpat\fP] [\fB\-W\fP \fIwordlist\fP] [\fB\-P\fP \fIprefix\fP] [\fB\-S\fP \fIsuffix\fP]
+.br
+[\fB\-X\fP \fIfilterpat\fP] [\fB\-F\fP \fIfunction\fP] [\fB\-C\fP \fIcommand\fP] \fIname\fP [\fIname ...\fP]
+.PD 0
+.TP
+\fBcomplete\fP \fB\-pr\fP [\fIname\fP ...]
+.PD
+Specify how arguments to each \fIname\fP should be completed.
+If the \fB\-p\fP option is supplied, or if no options are supplied,
+existing completion specifications are printed in a way that allows
+them to be reused as input.
+The \fB\-r\fP option removes a completion specification for
+each \fIname\fP, or, if no \fIname\fPs are supplied, all
+completion specifications.
+.sp 1
+The process of applying these completion specifications when word completion
+is attempted is described above under \fBProgrammable Completion\fP.
+.sp 1
+Other options, if specified, have the following meanings.
+The arguments to the \fB\-G\fP, \fB\-W\fP, and \fB\-X\fP options
+(and, if necessary, the \fB\-P\fP and \fB\-S\fP options)
+should be quoted to protect them from expansion before the
+.B complete
+builtin is invoked.
+.RS
+.PD 0
+.TP 8
+\fB\-o\fP \fIcomp-option\fP
+The \fIcomp-option\fP controls several aspects of the compspec's behavior
+beyond the simple generation of completions.
+\fIcomp-option\fP may be one of:
+.RS
+.TP 8
+.B bashdefault
+Perform the rest of the default \fBbash\fP completions if the compspec
+generates no matches.
+.TP 8
+.B default
+Use readline's default filename completion if the compspec generates
+no matches.
+.TP 8
+.B dirnames
+Perform directory name completion if the compspec generates no matches.
+.TP 8
+.B filenames
+Tell readline that the compspec generates filenames, so it can perform any
+filename\-specific processing (like adding a slash to directory names or
+suppressing trailing spaces).  Intended to be used with shell functions.
+.TP 8
+.B nospace
+Tell readline not to append a space (the default) to words completed at
+the end of the line.
+.RE
+.TP 8
+\fB\-A\fP \fIaction\fP
+The \fIaction\fP may be one of the following to generate a list of possible
+completions:
+.RS
+.TP 8
+.B alias
+Alias names.  May also be specified as \fB\-a\fP.
+.TP 8
+.B arrayvar
+Array variable names.
+.TP 8
+.B binding
+\fBReadline\fP key binding names.
+.TP 8
+.B builtin
+Names of shell builtin commands.  May also be specified as \fB\-b\fP.
+.TP 8
+.B command
+Command names.  May also be specified as \fB\-c\fP.
+.TP 8
+.B directory
+Directory names.  May also be specified as \fB\-d\fP.
+.TP 8
+.B disabled
+Names of disabled shell builtins.
+.TP 8
+.B enabled
+Names of enabled shell builtins.
+.TP 8
+.B export
+Names of exported shell variables.  May also be specified as \fB\-e\fP.
+.TP 8
+.B file
+File names.  May also be specified as \fB\-f\fP.
+.TP 8
+.B function
+Names of shell functions.
+.TP 8
+.B group
+Group names.  May also be specified as \fB\-g\fP.
+.TP 8
+.B helptopic
+Help topics as accepted by the \fBhelp\fP builtin.
+.TP 8
+.B hostname
+Hostnames, as taken from the file specified by the
+.SM
+.B HOSTFILE
+shell variable.
+.TP 8
+.B job
+Job names, if job control is active.  May also be specified as \fB\-j\fP.
+.TP 8
+.B keyword
+Shell reserved words.  May also be specified as \fB\-k\fP.
+.TP 8
+.B running
+Names of running jobs, if job control is active.
+.TP 8
+.B service
+Service names.  May also be specified as \fB\-s\fP.
+.TP 8
+.B setopt
+Valid arguments for the \fB\-o\fP option to the \fBset\fP builtin.
+.TP 8
+.B shopt
+Shell option names as accepted by the \fBshopt\fP builtin.
+.TP 8
+.B signal
+Signal names.
+.TP 8
+.B stopped
+Names of stopped jobs, if job control is active.
+.TP 8
+.B user
+User names.  May also be specified as \fB\-u\fP.
+.TP 8
+.B variable
+Names of all shell variables.  May also be specified as \fB\-v\fP.
+.RE
+.TP 8
+\fB\-G\fP \fIglobpat\fP
+The filename expansion pattern \fIglobpat\fP is expanded to generate
+the possible completions.
+.TP 8
+\fB\-W\fP \fIwordlist\fP
+The \fIwordlist\fP is split using the characters in the
+.SM
+.B IFS
+special variable as delimiters, and each resultant word is expanded.
+The possible completions are the members of the resultant list which
+match the word being completed.
+.TP 8
+\fB\-C\fP \fIcommand\fP
+\fIcommand\fP is executed in a subshell environment, and its output is
+used as the possible completions.
+.TP 8
+\fB\-F\fP \fIfunction\fP
+The shell function \fIfunction\fP is executed in the current shell
+environment.
+When it finishes, the possible completions are retrieved from the value
+of the
+.SM
+.B COMPREPLY
+array variable.
+.TP 8
+\fB\-X\fP \fIfilterpat\fP
+\fIfilterpat\fP is a pattern as used for filename expansion.
+It is applied to the list of possible completions generated by the
+preceding options and arguments, and each completion matching
+\fIfilterpat\fP is removed from the list.
+A leading \fB!\fP in \fIfilterpat\fP negates the pattern; in this
+case, any completion not matching \fIfilterpat\fP is removed.
+.TP 8
+\fB\-P\fP \fIprefix\fP
+\fIprefix\fP is added at the beginning of each possible completion
+after all other options have been applied.
+.TP 8
+\fB\-S\fP \fIsuffix\fP
+\fIsuffix\fP is appended to each possible completion
+after all other options have been applied.
+.PD
+.PP
+The return value is true unless an invalid option is supplied, an option
+other than \fB\-p\fP or \fB\-r\fP is supplied without a \fIname\fP
+argument, an attempt is made to remove a completion specification for
+a \fIname\fP for which no specification exists, or
+an error occurs adding a completion specification.
+.RE
+.TP
+\fBcontinue\fP [\fIn\fP]
+Resume the next iteration of the enclosing
+.BR for ,
+.BR while ,
+.BR until ,
+or
+.B select
+loop.
+If
+.I n
+is specified, resume at the \fIn\fPth enclosing loop.
+.I n
+must be \(>= 1.  If
+.I n
+is greater than the number of enclosing loops, the last enclosing loop
+(the ``top-level'' loop) is resumed.  The return value is 0 unless the
+shell is not executing a loop when
+.B continue
+is executed.
+.TP
+\fBdeclare\fP [\fB\-afFirtx\fP] [\fB\-p\fP] [\fIname\fP[=\fIvalue\fP] ...]
+.PD 0
+.TP
+\fBtypeset\fP [\fB\-afFirtx\fP] [\fB\-p\fP] [\fIname\fP[=\fIvalue\fP] ...]
+.PD
+Declare variables and/or give them attributes.
+If no \fIname\fPs are given then display the values of variables.
+The
+.B \-p
+option will display the attributes and values of each
+.IR name .
+When
+.B \-p
+is used, additional options are ignored.
+The
+.B \-F
+option inhibits the display of function definitions; only the
+function name and attributes are printed.
+If the \fBextdebug\fP shell option is enabled using \fBshopt\fP,
+the source file name and line number where the function is defined
+are displayed as well.  The
+.B \-F
+option implies
+.BR \-f .
+The following options can
+be used to restrict output to variables with the specified attribute or
+to give variables attributes:
+.RS
+.PD 0
+.TP
+.B \-a
+Each \fIname\fP is an array variable (see
+.B Arrays
+above).
+.TP
+.B \-f
+Use function names only.
+.TP
+.B \-i
+The variable is treated as an integer; arithmetic evaluation (see
+.SM
+.B "ARITHMETIC EVALUATION" ") "
+is performed when the variable is assigned a value.
+.TP
+.B \-r
+Make \fIname\fPs readonly.  These names cannot then be assigned values
+by subsequent assignment statements or unset.
+.TP
+.B \-t
+Give each \fIname\fP the \fItrace\fP attribute.
+Traced functions inherit the \fBDEBUG\fP trap from the calling shell.
+The trace attribute has no special meaning for variables.
+.TP
+.B \-x
+Mark \fIname\fPs for export to subsequent commands via the environment.
+.PD
+.PP
+Using `+' instead of `\-'
+turns off the attribute instead, with the exception that \fB+a\fP
+may not be used to destroy an array variable.  When used in a function,
+makes each
+\fIname\fP local, as with the 
+.B local
+command.
+If a variable name is followed by =\fIvalue\fP, the value of
+the variable is set to \fIvalue\fP.
+The return value is 0 unless an invalid option is encountered,
+an attempt is made to define a function using
+.if n ``\-f foo=bar'',
+.if t \f(CW\-f foo=bar\fP,
+an attempt is made to assign a value to a readonly variable,
+an attempt is made to assign a value to an array variable without
+using the compound assignment syntax (see
+.B Arrays
+above), one of the \fInames\fP is not a valid shell variable name,
+an attempt is made to turn off readonly status for a readonly variable,
+an attempt is made to turn off array status for an array variable,
+or an attempt is made to display a non-existent function with \fB\-f\fP.
+.RE
+.TP
+.B dirs [\fB\-clpv\fP] [+\fIn\fP] [\-\fIn\fP]
+Without options, displays the list of currently remembered directories.
+The default display is on a single line with directory names separated
+by spaces.
+Directories are added to the list with the 
+.B pushd
+command; the
+.B popd
+command removes entries from the list.
+.RS
+.PD 0
+.TP
+\fB+\fP\fIn\fP
+Displays the \fIn\fPth entry counting from the left of the list
+shown by
+.B dirs
+when invoked without options, starting with zero.
+.TP
+\fB\-\fP\fIn\fP
+Displays the \fIn\fPth entry counting from the right of the list
+shown by
+.B dirs
+when invoked without options, starting with zero.
+.TP
+.B \-c
+Clears the directory stack by deleting all of the entries.
+.TP
+.B \-l
+Produces a longer listing; the default listing format uses a 
+tilde to denote the home directory.
+.TP
+.B \-p
+Print the directory stack with one entry per line.
+.TP
+.B \-v
+Print the directory stack with one entry per line,
+prefixing each entry with its index in the stack.
+.PD
+.PP
+The return value is 0 unless an
+invalid option is supplied or \fIn\fP indexes beyond the end
+of the directory stack.
+.RE
+.TP
+\fBdisown\fP [\fB\-ar\fP] [\fB\-h\fP] [\fIjobspec\fP ...]
+Without options, each
+.I jobspec
+is removed from the table of active jobs.
+If the \fB\-h\fP option is given, each
+.I jobspec
+is not removed from the table, but is marked so that
+.SM
+.B SIGHUP
+is not sent to the job if the shell receives a
+.SM
+.BR SIGHUP .
+If no
+.I jobspec
+is present, and neither the
+.B \-a
+nor the
+.B \-r
+option is supplied, the \fIcurrent job\fP is used.
+If no
+.I jobspec
+is supplied, the
+.B \-a
+option means to remove or mark all jobs; the
+.B \-r
+option without a
+.I jobspec
+argument restricts operation to running jobs.
+The return value is 0 unless a
+.I jobspec
+does not specify a valid job.
+.TP
+\fBecho\fP [\fB\-neE\fP] [\fIarg\fP ...]
+Output the \fIarg\fPs, separated by spaces, followed by a newline.
+The return status is always 0.
+If \fB\-n\fP is specified, the trailing newline is
+suppressed.  If the \fB\-e\fP option is given, interpretation of
+the following backslash-escaped characters is enabled.  The
+.B \-E
+option disables the interpretation of these escape characters,
+even on systems where they are interpreted by default.
+The \fBxpg_echo\fP shell option may be used to
+dynamically determine whether or not \fBecho\fP expands these
+escape characters by default.
+.B echo
+does not interpret
+.B \-\-
+to mean the end of options.
+.B echo
+interprets the following escape sequences:
+.RS
+.PD 0
+.TP
+.B \ea
+alert (bell)
+.TP
+.B \eb
+backspace
+.TP
+.B \ec
+suppress trailing newline
+.TP
+.B \ee
+an escape character
+.TP
+.B \ef
+form feed
+.TP
+.B \en
+new line
+.TP
+.B \er
+carriage return
+.TP
+.B \et
+horizontal tab
+.TP
+.B \ev
+vertical tab
+.TP
+.B \e\e
+backslash
+.TP
+.B \e0\fInnn\fP
+the eight-bit character whose value is the octal value \fInnn\fP
+(zero to three octal digits)
+.TP
+.B \e\fInnn\fP
+the eight-bit character whose value is the octal value \fInnn\fP
+(one to three octal digits)
+.TP
+.B \ex\fIHH\fP
+the eight-bit character whose value is the hexadecimal value \fIHH\fP
+(one or two hex digits)
+.PD
+.RE
+.TP
+\fBenable\fP [\fB\-adnps\fP] [\fB\-f\fP \fIfilename\fP] [\fIname\fP ...]
+Enable and disable builtin shell commands.
+Disabling a builtin allows a disk command which has the same name
+as a shell builtin to be executed without specifying a full pathname,
+even though the shell normally searches for builtins before disk commands.
+If \fB\-n\fP is used, each \fIname\fP
+is disabled; otherwise,
+\fInames\fP are enabled.  For example, to use the
+.B test
+binary found via the
+.SM
+.B PATH
+instead of the shell builtin version, run
+.if t \f(CWenable -n test\fP.
+.if n ``enable -n test''.
+The
+.B \-f
+option means to load the new builtin command
+.I name
+from shared object
+.IR filename ,
+on systems that support dynamic loading.  The
+.B \-d
+option will delete a builtin previously loaded with
+.BR \-f .
+If no \fIname\fP arguments are given, or if the
+.B \-p
+option is supplied, a list of shell builtins is printed.
+With no other option arguments, the list consists of all enabled
+shell builtins.
+If \fB\-n\fP is supplied, only disabled builtins are printed.
+If \fB\-a\fP is supplied, the list printed includes all builtins, with an
+indication of whether or not each is enabled.
+If \fB\-s\fP is supplied, the output is restricted to the POSIX
+\fIspecial\fP builtins.
+The return value is 0 unless a
+.I name
+is not a shell builtin or there is an error loading a new builtin
+from a shared object.
+.TP
+\fBeval\fP [\fIarg\fP ...]
+The \fIarg\fPs are read and concatenated together into a single
+command.  This command is then read and executed by the shell, and
+its exit status is returned as the value of
+.BR eval .
+If there are no
+.IR args ,
+or only null arguments,
+.B eval
+returns 0.
+.TP
+\fBexec\fP [\fB\-cl\fP] [\fB\-a\fP \fIname\fP] [\fIcommand\fP [\fIarguments\fP]]
+If
+.I command
+is specified, it replaces the shell.
+No new process is created.  The
+.I arguments
+become the arguments to \fIcommand\fP.
+If the
+.B \-l
+option is supplied,
+the shell places a dash at the beginning of the zeroth arg passed to 
+.IR command .
+This is what
+.IR login (1)
+does.  The
+.B \-c
+option causes
+.I command
+to be executed with an empty environment.  If
+.B \-a
+is supplied, the shell passes
+.I name
+as the zeroth argument to the executed command.  If
+.I command
+cannot be executed for some reason, a non-interactive shell exits,
+unless the shell option
+.B execfail
+is enabled, in which case it returns failure.
+An interactive shell returns failure if the file cannot be executed.
+If
+.I command
+is not specified, any redirections take effect in the current shell,
+and the return status is 0.  If there is a redirection error, the
+return status is 1.
+.TP
+\fBexit\fP [\fIn\fP]
+Cause the shell to exit
+with a status of \fIn\fP.  If
+.I n
+is omitted, the exit status
+is that of the last command executed.
+A trap on
+.SM
+.B EXIT
+is executed before the shell terminates.
+.TP
+\fBexport\fP [\fB\-fn\fP\^] [\fIname\fP[=\fIword\fP]] ...
+.PD 0
+.TP
+.B export \-p
+.PD
+The supplied
+.I names
+are marked for automatic export to the environment of
+subsequently executed commands.  If the 
+.B \-f
+option is given,
+the 
+.I names
+refer to functions.
+If no
+.I names
+are given, or if the
+.B \-p
+option is supplied, a list
+of all names that are exported in this shell is printed.
+The
+.B \-n
+option causes the export property to be removed from each
+\fIname\fP.
+If a variable name is followed by =\fIword\fP, the value of
+the variable is set to \fIword\fP.
+.B export
+returns an exit status of 0 unless an invalid option is
+encountered,
+one of the \fInames\fP is not a valid shell variable name, or
+.B \-f
+is supplied with a
+.I name
+that is not a function.
+.TP
+\fBfc\fP [\fB\-e\fP \fIename\fP] [\fB\-nlr\fP] [\fIfirst\fP] [\fIlast\fP]
+.PD 0
+.TP
+\fBfc\fP \fB\-s\fP [\fIpat\fP=\fIrep\fP] [\fIcmd\fP]
+.PD
+Fix Command.  In the first form, a range of commands from
+.I first
+to
+.I last
+is selected from the history list.
+.I First
+and
+.I last
+may be specified as a string (to locate the last command beginning
+with that string) or as a number (an index into the history list,
+where a negative number is used as an offset from the current
+command number).  If 
+.I last
+is not specified it is set to
+the current command for listing (so that
+.if n ``fc \-l \-10''
+.if t \f(CWfc \-l \-10\fP
+prints the last 10 commands) and to
+.I first
+otherwise.
+If
+.I first
+is not specified it is set to the previous
+command for editing and \-16 for listing.
+.sp 1
+The
+.B \-n
+option suppresses
+the command numbers when listing.  The
+.B \-r
+option reverses the order of
+the commands.  If the
+.B \-l
+option is given,
+the commands are listed on
+standard output.  Otherwise, the editor given by
+.I ename
+is invoked
+on a file containing those commands.  If
+.I ename
+is not given, the
+value of the
+.SM
+.B FCEDIT
+variable is used, and
+the value of
+.SM
+.B EDITOR
+if
+.SM
+.B FCEDIT
+is not set.  If neither variable is set,
+.FN vi
+is used.  When editing is complete, the edited commands are
+echoed and executed.
+.sp 1
+In the second form, \fIcommand\fP is re-executed after each instance
+of \fIpat\fP is replaced by \fIrep\fP.
+A useful alias to use with this is
+.if n ``r="fc -s"'',
+.if t \f(CWr='fc \-s'\fP,
+so that typing
+.if n ``r cc''
+.if t \f(CWr cc\fP
+runs the last command beginning with
+.if n ``cc''
+.if t \f(CWcc\fP
+and typing
+.if n ``r''
+.if t \f(CWr\fP
+re-executes the last command.
+.sp 1
+If the first form is used, the return value is 0 unless an invalid
+option is encountered or
+.I first
+or
+.I last
+specify history lines out of range.
+If the
+.B \-e
+option is supplied, the return value is the value of the last
+command executed or failure if an error occurs with the temporary
+file of commands.  If the second form is used, the return status
+is that of the command re-executed, unless
+.I cmd
+does not specify a valid history line, in which case
+.B fc
+returns failure.
+.TP
+\fBfg\fP [\fIjobspec\fP]
+Resume
+.I jobspec
+in the foreground, and make it the current job.
+If
+.I jobspec
+is not present, the shell's notion of the \fIcurrent job\fP is used.
+The return value is that of the command placed into the foreground,
+or failure if run when job control is disabled or, when run with
+job control enabled, if
+.I jobspec
+does not specify a valid job or
+.I jobspec
+specifies a job that was started without job control.
+.TP
+\fBgetopts\fP \fIoptstring\fP \fIname\fP [\fIargs\fP]
+.B getopts
+is used by shell procedures to parse positional parameters.
+.I optstring
+contains the option characters to be recognized; if a character
+is followed by a colon, the option is expected to have an
+argument, which should be separated from it by white space.
+The colon and question mark characters may not be used as
+option characters.
+Each time it is invoked,
+.B getopts
+places the next option in the shell variable
+.IR name ,
+initializing
+.I name
+if it does not exist,
+and the index of the next argument to be processed into the
+variable
+.SM
+.BR OPTIND .
+.SM
+.B OPTIND
+is initialized to 1 each time the shell or a shell script
+is invoked.  When an option requires an argument,
+.B getopts
+places that argument into the variable
+.SM
+.BR OPTARG .
+The shell does not reset
+.SM
+.B OPTIND
+automatically; it must be manually reset between multiple
+calls to
+.B getopts
+within the same shell invocation if a new set of parameters
+is to be used.
+.sp 1
+When the end of options is encountered, \fBgetopts\fP exits with a
+return value greater than zero.
+\fBOPTIND\fP is set to the index of the first non-option argument,
+and \fBname\fP is set to ?.
+.sp 1
+.B getopts
+normally parses the positional parameters, but if more arguments are
+given in
+.IR args ,
+.B getopts
+parses those instead.
+.sp 1
+.B getopts
+can report errors in two ways.  If the first character of
+.I optstring
+is a colon,
+.I silent
+error reporting is used.  In normal operation diagnostic messages
+are printed when invalid options or missing option arguments are
+encountered.
+If the variable
+.SM
+.B OPTERR
+is set to 0, no error messages will be displayed, even if the first
+character of 
+.I optstring
+is not a colon.
+.sp 1
+If an invalid option is seen,
+.B getopts
+places ? into
+.I name
+and, if not silent,
+prints an error message and unsets
+.SM
+.BR OPTARG .
+If
+.B getopts
+is silent,
+the option character found is placed in
+.SM
+.B OPTARG
+and no diagnostic message is printed.
+.sp 1
+If a required argument is not found, and
+.B getopts
+is not silent,
+a question mark (\^\fB?\fP\^) is placed in
+.IR name ,
+.SM
+.B OPTARG
+is unset, and a diagnostic message is printed.
+If
+.B getopts
+is silent, then a colon (\^\fB:\fP\^) is placed in
+.I name
+and
+.SM
+.B OPTARG
+is set to the option character found.
+.sp 1
+.B getopts
+returns true if an option, specified or unspecified, is found.
+It returns false if the end of options is encountered or an
+error occurs.
+.TP
+\fBhash\fP [\fB\-lr\fP] [\fB\-p\fP \fIfilename\fP] [\fB\-dt\fP] [\fIname\fP]
+For each
+.IR name ,
+the full file name of the command is determined by searching
+the directories in
+.B $PATH
+and remembered.
+If the
+.B \-p
+option is supplied, no path search is performed, and
+.I filename
+is used as the full file name of the command.
+The
+.B \-r
+option causes the shell to forget all
+remembered locations.
+The
+.B \-d
+option causes the shell to forget the remembered location of each \fIname\fP.
+If the
+.B \-t
+option is supplied, the full pathname to which each \fIname\fP corresponds
+is printed.  If multiple \fIname\fP arguments are supplied with \fB\-t\fP,
+the \fIname\fP is printed before the hashed full pathname.
+The
+.B \-l
+option causes output to be displayed in a format that may be reused as input.
+If no arguments are given, or if only \fB\-l\fP is supplied,
+information about remembered commands is printed.
+The return status is true unless a
+.I name
+is not found or an invalid option is supplied.
+.TP
+\fBhelp\fP [\fB\-s\fP] [\fIpattern\fP]
+Display helpful information about builtin commands.  If
+.I pattern
+is specified,
+.B help
+gives detailed help on all commands matching
+.IR pattern ;
+otherwise help for all the builtins and shell control structures
+is printed.
+The \fB\-s\fP option restricts the information displayed to a short
+usage synopsis.
+The return status is 0 unless no command matches
+.IR pattern .
+.TP
+\fBhistory [\fIn\fP]
+.PD 0
+.TP
+\fBhistory\fP \fB\-c\fP
+.TP
+\fBhistory \-d\fP \fIoffset\fP
+.TP
+\fBhistory\fP \fB\-anrw\fP [\fIfilename\fP]
+.TP
+\fBhistory\fP \fB\-p\fP \fIarg\fP [\fIarg ...\fP]
+.TP
+\fBhistory\fP \fB\-s\fP \fIarg\fP [\fIarg ...\fP]
+.PD
+With no options, display the command
+history list with line numbers.  Lines listed
+with a 
+.B *
+have been modified.  An argument of
+.I n
+lists only the last
+.I n
+lines.
+If the shell variable \fBHISTTIMEFORMAT\fP is set and not null,
+it is used as a format string for \fIstrftime\fP(3) to display
+the time stamp associated with each displayed history entry.
+No intervening blank is printed between the formatted time stamp
+and the history line.
+If \fIfilename\fP is supplied, it is used as the
+name of the history file; if not, the value of
+.SM
+.B HISTFILE
+is used.  Options, if supplied, have the following meanings:
+.RS
+.PD 0
+.TP
+.B \-c
+Clear the history list by deleting all the entries.
+.TP
+\fB\-d\fP \fIoffset\fP
+Delete the history entry at position \fIoffset\fP.
+.TP
+.B \-a
+Append the ``new'' history lines (history lines entered since the
+beginning of the current \fBbash\fP session) to the history file.
+.TP
+.B \-n
+Read the history lines not already read from the history
+file into the current history list.  These are lines
+appended to the history file since the beginning of the
+current \fBbash\fP session.
+.TP
+.B \-r
+Read the contents of the history file
+and use them as the current history.
+.TP
+.B \-w
+Write the current history to the history file, overwriting the
+history file's contents.
+.TP
+.B \-p
+Perform history substitution on the following \fIargs\fP and display
+the result on the standard output.
+Does not store the results in the history list.
+Each \fIarg\fP must be quoted to disable normal history expansion.
+.TP
+.B \-s
+Store the
+.I args
+in the history list as a single entry.  The last command in the
+history list is removed before the
+.I args
+are added.
+.PD
+.PP
+If the \fBHISTTIMEFORMAT\fP is set, the time stamp information
+associated with each history entry is written to the history file.
+The return value is 0 unless an invalid option is encountered, an
+error occurs while reading or writing the history file, an invalid
+\fIoffset\fP is supplied as an argument to \fB\-d\fP, or the
+history expansion supplied as an argument to \fB\-p\fP fails.
+.RE
+.TP
+\fBjobs\fP [\fB\-lnprs\fP] [ \fIjobspec\fP ... ]
+.PD 0
+.TP
+\fBjobs\fP \fB\-x\fP \fIcommand\fP [ \fIargs\fP ... ]
+.PD
+The first form lists the active jobs.  The options have the following
+meanings:
+.RS
+.PD 0
+.TP
+.B \-l
+List process IDs
+in addition to the normal information.
+.TP
+.B \-p
+List only the process ID of the job's process group
+leader.
+.TP
+.B \-n
+Display information only about jobs that have changed status since
+the user was last notified of their status.
+.TP
+.B \-r
+Restrict output to running jobs.
+.TP
+.B \-s
+Restrict output to stopped jobs.
+.PD
+.PP
+If
+.I jobspec
+is given, output is restricted to information about that job.
+The return status is 0 unless an invalid option is encountered
+or an invalid
+.I jobspec
+is supplied.
+.PP
+If the
+.B \-x
+option is supplied,
+.B jobs
+replaces any
+.I jobspec
+found in
+.I command
+or
+.I args
+with the corresponding process group ID, and executes
+.I command
+passing it
+.IR args ,
+returning its exit status.
+.RE
+.TP
+\fBkill\fP [\fB\-s\fP \fIsigspec\fP | \fB\-n\fP \fIsignum\fP | \fB\-\fP\fIsigspec\fP] [\fIpid\fP | \fIjobspec\fP] ...
+.PD 0
+.TP
+\fBkill\fP \fB\-l\fP [\fIsigspec\fP | \fIexit_status\fP]
+.PD
+Send the signal named by
+.I sigspec
+or
+.I signum
+to the processes named by
+.I pid
+or
+.IR jobspec .
+.I sigspec
+is either a case-insensitive signal name such as
+.SM
+.B SIGKILL
+(with or without the
+.SM
+.B SIG
+prefix) or a signal number;
+.I signum
+is a signal number.
+If
+.I sigspec
+is not present, then
+.SM
+.B SIGTERM
+is assumed.
+An argument of
+.B \-l
+lists the signal names.
+If any arguments are supplied when
+.B \-l
+is given, the names of the signals corresponding to the arguments are
+listed, and the return status is 0.
+The \fIexit_status\fP argument to
+.B \-l
+is a number specifying either a signal number or the exit status of
+a process terminated by a signal.
+.B kill
+returns true if at least one signal was successfully sent, or false
+if an error occurs or an invalid option is encountered.
+.TP
+\fBlet\fP \fIarg\fP [\fIarg\fP ...]
+Each
+.I arg
+is an arithmetic expression to be evaluated (see
+.SM
+.BR "ARITHMETIC EVALUATION" ).
+If the last
+.I arg
+evaluates to 0,
+.B let
+returns 1; 0 is returned otherwise.
+.TP
+\fBlocal\fP [\fIoption\fP] [\fIname\fP[=\fIvalue\fP] ...]
+For each argument, a local variable named
+.I name 
+is created, and assigned
+.IR value .
+The \fIoption\fP can be any of the options accepted by \fBdeclare\fP.
+When
+.B local
+is used within a function, it causes the variable
+.I name
+to have a visible scope restricted to that function and its children.
+With no operands,
+.B local
+writes a list of local variables to the standard output.  It is
+an error to use
+.B local
+when not within a function.  The return status is 0 unless
+.B local
+is used outside a function, an invalid
+.I name
+is supplied, or
+\fIname\fP is a readonly variable.
+.TP
+.B logout
+Exit a login shell.
+.TP
+\fBpopd\fP [\-\fBn\fP] [+\fIn\fP] [\-\fIn\fP]
+Removes entries from the directory stack.  With no arguments,
+removes the top directory from the stack, and performs a
+.B cd
+to the new top directory.
+Arguments, if supplied, have the following meanings:
+.RS
+.PD 0
+.TP
+\fB+\fP\fIn\fP
+Removes the \fIn\fPth entry counting from the left of the list
+shown by
+.BR dirs ,
+starting with zero.  For example:
+.if n ``popd +0''
+.if t \f(CWpopd +0\fP
+removes the first directory,
+.if n ``popd +1''
+.if t \f(CWpopd +1\fP
+the second.
+.TP
+\fB\-\fP\fIn\fP
+Removes the \fIn\fPth entry counting from the right of the list
+shown by
+.BR dirs ,
+starting with zero.  For example:
+.if n ``popd -0''
+.if t \f(CWpopd -0\fP
+removes the last directory,
+.if n ``popd -1''
+.if t \f(CWpopd -1\fP
+the next to last.
+.TP
+.B \-n
+Suppresses the normal change of directory when removing directories
+from the stack, so that only the stack is manipulated.
+.PD
+.PP
+If the
+.B popd
+command is successful, a 
+.B dirs
+is performed as well, and the return status is 0.
+.B popd
+returns false if an invalid option is encountered, the directory stack
+is empty, a non-existent directory stack entry is specified, or the
+directory change fails.
+.RE
+.TP
+\fBprintf\fP \fIformat\fP [\fIarguments\fP]
+Write the formatted \fIarguments\fP to the standard output under the
+control of the \fIformat\fP.
+The \fIformat\fP is a character string which contains three types of objects:
+plain characters, which are simply copied to standard output, character
+escape sequences, which are converted and copied to the standard output, and
+format specifications, each of which causes printing of the next successive
+\fIargument\fP.
+In addition to the standard \fIprintf\fP(1) formats, \fB%b\fP causes
+\fBprintf\fP to expand backslash escape sequences in the corresponding
+\fIargument\fP (except that \fB\ec\fP terminates output, backslashes in
+\fB\e'\fP, \fB\e"\fP, and \fB\e?\fP are not removed, and octal escapes
+beginning with \fB\e0\fP may contain up to four digits),
+and \fB%q\fP causes \fBprintf\fP to output the corresponding
+\fIargument\fP in a format that can be reused as shell input.
+.sp 1
+The \fIformat\fP is reused as necessary to consume all of the \fIarguments\fP.
+If the \fIformat\fP requires more \fIarguments\fP than are supplied, the
+extra format specifications behave as if a zero value or null string, as
+appropriate, had been supplied.  The return value is zero on success,
+non-zero on failure.
+.TP
+\fBpushd\fP [\fB\-n\fP] [\fIdir\fP]
+.PD 0
+.TP
+\fBpushd\fP [\fB\-n\fP] [+\fIn\fP] [\-\fIn\fP]
+.PD
+Adds a directory to the top of the directory stack, or rotates
+the stack, making the new top of the stack the current working
+directory.  With no arguments, exchanges the top two directories
+and returns 0, unless the directory stack is empty.
+Arguments, if supplied, have the following meanings:
+.RS
+.PD 0
+.TP
+\fB+\fP\fIn\fP
+Rotates the stack so that the \fIn\fPth directory
+(counting from the left of the list shown by
+.BR dirs ,
+starting with zero)
+is at the top.
+.TP
+\fB\-\fP\fIn\fP
+Rotates the stack so that the \fIn\fPth directory
+(counting from the right of the list shown by
+.BR dirs ,
+starting with zero) is at the top.
+.TP
+.B \-n
+Suppresses the normal change of directory when adding directories
+to the stack, so that only the stack is manipulated.
+.TP
+.I dir
+Adds
+.I dir
+to the directory stack at the top, making it the
+new current working directory.
+.PD
+.PP
+If the
+.B pushd
+command is successful, a 
+.B dirs
+is performed as well.
+If the first form is used,
+.B pushd
+returns 0 unless the cd to
+.I dir
+fails.  With the second form,
+.B pushd
+returns 0 unless the directory stack is empty,
+a non-existent directory stack element is specified,
+or the directory change to the specified new current directory
+fails.
+.RE
+.TP
+\fBpwd\fP [\fB\-LP\fP]
+Print the absolute pathname of the current working directory.
+The pathname printed contains no symbolic links if the
+.B \-P
+option is supplied or the 
+.B \-o physical
+option to the
+.B set
+builtin command is enabled.
+If the
+.B \-L
+option is used, the pathname printed may contain symbolic links.
+The return status is 0 unless an error occurs while
+reading the name of the current directory or an
+invalid option is supplied.
+.TP
+\fBread\fP [\fB\-ers\fP] [\fB\-u\fP \fIfd\fP] [\fB\-t\fP \fItimeout\fP] [\fB\-a\fP \fIaname\fP] [\fB\-p\fP \fIprompt\fP] [\fB\-n\fP \fInchars\fP] [\fB\-d\fP \fIdelim\fP] [\fIname\fP ...]
+One line is read from the standard input, or from the file descriptor
+\fIfd\fP supplied as an argument to the \fB\-u\fP option, and the first word
+is assigned to the first
+.IR name ,
+the second word to the second
+.IR name ,
+and so on, with leftover words and their intervening separators assigned
+to the last
+.IR name .
+If there are fewer words read from the input stream than names,
+the remaining names are assigned empty values.
+The characters in 
+.SM
+.B IFS
+are used to split the line into words.
+The backslash character (\fB\e\fP) may be used to remove any special
+meaning for the next character read and for line continuation.
+Options, if supplied, have the following meanings:
+.RS
+.PD 0
+.TP
+.B \-a \fIaname\fP
+The words are assigned to sequential indices
+of the array variable
+.IR aname ,
+starting at 0.
+.I aname
+is unset before any new values are assigned.
+Other \fIname\fP arguments are ignored.
+.TP
+.B \-d \fIdelim\fP
+The first character of \fIdelim\fP is used to terminate the input line,
+rather than newline.
+.TP
+.B \-e
+If the standard input
+is coming from a terminal,
+.B readline
+(see
+.SM
+.B READLINE
+above) is used to obtain the line.
+.TP
+.B \-n \fInchars\fP
+\fBread\fP returns after reading \fInchars\fP characters rather than
+waiting for a complete line of input.
+.TP
+.B \-p \fIprompt\fP
+Display \fIprompt\fP on standard error, without a
+trailing newline, before attempting to read any input.  The prompt
+is displayed only if input is coming from a terminal.
+.TP
+.B \-r
+Backslash does not act as an escape character.
+The backslash is considered to be part of the line.
+In particular, a backslash-newline pair may not be used as a line
+continuation.
+.TP
+.B \-s
+Silent mode.  If input is coming from a terminal, characters are
+not echoed.
+.TP
+.B \-t \fItimeout\fP
+Cause \fBread\fP to time out and return failure if a complete line of
+input is not read within \fItimeout\fP seconds.
+This option has no effect if \fBread\fP is not reading input from the
+terminal or a pipe.
+.TP
+.B \-u \fIfd\FP
+Read input from file descriptor \fIfd\fP.
+.PD
+.PP
+If no
+.I names
+are supplied, the line read is assigned to the variable
+.SM
+.BR REPLY .
+The return code is zero, unless end-of-file is encountered, \fBread\fP
+times out, or an invalid file descriptor is supplied as the argument to
+\fB\-u\fP.
+.RE
+.TP
+\fBreadonly\fP [\fB\-apf\fP] [\fIname\fP[=\fIword\fP] ...]
+.PD
+The given
+\fInames\fP are marked readonly; the values of these
+.I names
+may not be changed by subsequent assignment.
+If the
+.B \-f
+option is supplied, the functions corresponding to the
+\fInames\fP are so
+marked.
+The
+.B \-a
+option restricts the variables to arrays.
+If no
+.I name
+arguments are given, or if the
+.B \-p
+option is supplied, a list of all readonly names is printed.
+The
+.B \-p
+option causes output to be displayed in a format that
+may be reused as input.
+If a variable name is followed by =\fIword\fP, the value of
+the variable is set to \fIword\fP.
+The return status is 0 unless an invalid option is encountered,
+one of the
+.I names
+is not a valid shell variable name, or
+.B \-f
+is supplied with a
+.I name
+that is not a function.
+.TP
+\fBreturn\fP [\fIn\fP]
+Causes a function to exit with the return value specified by
+.IR n .
+If 
+.I n
+is omitted, the return status is that of the last command
+executed in the function body.  If used outside a function,
+but during execution of a script by the 
+.B .
+(\fBsource\fP) command, it causes the shell to stop executing
+that script and return either
+.I n
+or the exit status of the last command executed within the
+script as the exit status of the script.  If used outside a
+function and not during execution of a script by \fB.\fP\^,
+the return status is false.
+Any command associated with the \fBRETURN\fP trap is executed
+before execution resumes after the function or script.
+.TP
+\fBset\fP [\fB\-\-abefhkmnptuvxBCHP\fP] [\fB\-o\fP \fIoption\fP] [\fIarg\fP ...]
+Without options, the name and value of each shell variable are displayed
+in a format that can be reused as input.
+The output is sorted according to the current locale.
+When options are specified, they set or unset shell attributes.
+Any arguments remaining after the options are processed are treated
+as values for the positional parameters and are assigned, in order, to 
+.BR $1 ,
+.BR $2 ,
+.B ...
+.BR $\fIn\fP .
+Options, if specified, have the following meanings:
+.RS
+.PD 0
+.TP 8
+.B \-a
+Automatically mark variables and functions which are modified or
+created for export to the environment of subsequent commands.
+.TP 8
+.B \-b
+Report the status of terminated background jobs
+immediately, rather than before the next primary prompt.  This is
+effective only when job control is enabled.
+.TP 8
+.B \-e
+Exit immediately if a \fIsimple command\fP (see
+.SM
+.B SHELL GRAMMAR
+above) exits with a non-zero status.
+The shell does not exit if the
+command that fails is part of the command list immediately following a
+.B while
+or
+.B until
+keyword, 
+part of the test in an
+.I if
+statement, part of a
+.B &&
+or
+.B \(bv\(bv
+list, or if the command's return value is
+being inverted via
+.BR ! .
+A trap on \fBERR\fP, if set, is executed before the shell exits.
+.TP 8
+.B \-f
+Disable pathname expansion.
+.TP 8 
+.B \-h
+Remember the location of commands as they are looked up for execution.
+This is enabled by default.
+.TP 8
+.B \-k
+All arguments in the form of assignment statements
+are placed in the environment for a command, not just
+those that precede the command name.
+.TP 8
+.B \-m
+Monitor mode.  Job control is enabled.  This option is on
+by default for interactive shells on systems that support
+it (see
+.SM
+.B JOB CONTROL
+above).  Background processes run in a separate process
+group and a line containing their exit status is printed
+upon their completion.
+.TP 8
+.B \-n
+Read commands but do not execute them.  This may be used to 
+check a shell script for syntax errors.  This is ignored by
+interactive shells.
+.TP 8
+.B \-o \fIoption\-name\fP
+The \fIoption\-name\fP can be one of the following:
+.RS
+.TP 8
+.B allexport
+Same as
+.BR \-a .
+.TP 8
+.B braceexpand
+Same as
+.BR \-B .
+.TP 8
+.B emacs
+Use an emacs-style command line editing interface.  This is enabled
+by default when the shell is interactive, unless the shell is started
+with the
+.B \-\-noediting
+option.
+.TP 8
+.B errtrace
+Same as
+.BR \-E .
+.TP 8
+.B functrace
+Same as
+.BR \-T .
+.TP 8
+.B errexit
+Same as
+.BR \-e .
+.TP 8
+.B hashall
+Same as
+.BR \-h .
+.TP 8
+.B histexpand
+Same as
+.BR \-H .
+.TP 8
+.B history
+Enable command history, as described above under
+.SM
+.BR HISTORY .
+This option is on by default in interactive shells.
+.TP 8
+.B ignoreeof
+The effect is as if the shell command
+.if t \f(CWIGNOREEOF=10\fP
+.if n ``IGNOREEOF=10''
+had been executed
+(see
+.B Shell Variables
+above).
+.TP 8
+.B keyword
+Same as
+.BR \-k .
+.TP 8
+.B monitor
+Same as
+.BR \-m .
+.TP 8
+.B noclobber
+Same as
+.BR \-C .
+.TP 8
+.B noexec
+Same as
+.BR \-n .
+.TP 8
+.B noglob
+Same as
+.BR \-f .
+.B nolog
+Currently ignored.
+.TP 8
+.B notify
+Same as
+.BR \-b .
+.TP 8
+.B nounset
+Same as
+.BR \-u .
+.TP 8
+.B onecmd
+Same as
+.BR \-t .
+.TP 8
+.B physical
+Same as
+.BR \-P .
+.TP 8
+.B pipefail
+If set, the return value of a pipeline is the value of the last
+(rightmost) command to exit with a non-zero status, or zero if all
+commands in the pipeline exit successfully.
+This option is disabled by default.
+.TP 8
+.B posix
+Change the behavior of
+.B bash
+where the default operation differs
+from the POSIX 1003.2 standard to match the standard (\fI`posix mode\fP).
+.TP 8
+.B privileged
+Same as
+.BR \-p .
+.TP 8
+.B verbose
+Same as
+.BR \-v .
+.TP 8
+.B vi
+Use a vi-style command line editing interface.
+.TP 8
+.B xtrace
+Same as
+.BR \-x .
+.sp .5
+.PP
+If
+.B \-o
+is supplied with no \fIoption\-name\fP, the values of the current options are
+printed.
+If
+.B +o
+is supplied with no \fIoption\-name\fP, a series of
+.B set
+commands to recreate the current option settings is displayed on
+the standard output.
+.RE
+.TP 8
+.B \-p
+Turn on
+.I privileged
+mode.  In this mode, the
+.SM
+.B $ENV
+and
+.SM
+.B $BASH_ENV
+files are not processed, shell functions are not inherited from the
+environment, and the
+.SM
+.B SHELLOPTS
+variable, if it appears in the environment, is ignored.
+If the shell is started with the effective user (group) id not equal to the
+real user (group) id, and the \fB\-p\fP option is not supplied, these actions
+are taken and the effective user id is set to the real user id.
+If the \fB\-p\fP option is supplied at startup, the effective user id is
+not reset.
+Turning this option off causes the effective user
+and group ids to be set to the real user and group ids.
+.TP 8
+.B \-t
+Exit after reading and executing one command.
+.TP 8
+.B \-u
+Treat unset variables as an error when performing
+parameter expansion.  If expansion is attempted on an
+unset variable, the shell prints an error message, and,
+if not interactive, exits with a non-zero status.
+.TP 8
+.B \-v
+Print shell input lines as they are read.
+.TP 8
+.B \-x
+After expanding each \fIsimple command\fP,
+\fBfor\fP command, \fBcase\fP command, \fBselect\fP command, or
+arithmetic \fBfor\fP command, display the expanded value of
+.SM
+.BR PS4 ,
+followed by the command and its expanded arguments
+or associated word list.
+.TP 8
+.B \-B
+The shell performs brace expansion (see
+.B Brace Expansion
+above).  This is on by default.
+.TP 8
+.B \-C
+If set,
+.B bash
+does not overwrite an existing file with the
+.BR > ,
+.BR >& ,
+and
+.B <>
+redirection operators.  This may be overridden when 
+creating output files by using the redirection operator
+.B >|
+instead of
+.BR > .
+.TP 8
+.B \-E
+If set, any trap on \fBERR\fP is inherited by shell functions, command
+substitutions, and commands executed in a subshell environment.
+The \fBERR\fP trap is normally not inherited in such cases.
+.TP 8
+.B \-H
+Enable
+.B !
+style history substitution.  This option is on by
+default when the shell is interactive.
+.TP 8
+.B \-P
+If set, the shell does not follow symbolic links when executing
+commands such as
+.B cd
+that change the current working directory.  It uses the
+physical directory structure instead.  By default,
+.B bash
+follows the logical chain of directories when performing commands
+which change the current directory.
+.TP 8
+.B \-T
+If set, any trap on \fBDEBUG\fP is inherited by shell functions, command
+substitutions, and commands executed in a subshell environment.
+The \fBDEBUG\fP trap is normally not inherited in such cases.
+.TP 8
+.B \-\-
+If no arguments follow this option, then the positional parameters are
+unset.  Otherwise, the positional parameters are set to the
+\fIarg\fPs, even if some of them begin with a
+.BR \- .
+.TP 8
+.B \-
+Signal the end of options, cause all remaining \fIarg\fPs to be
+assigned to the positional parameters.  The
+.B \-x
+and
+.B \-v
+options are turned off.
+If there are no \fIarg\fPs,
+the positional parameters remain unchanged.
+.PD
+.PP
+The options are off by default unless otherwise noted.
+Using + rather than \- causes these options to be turned off.
+The options can also be specified as arguments to an invocation of
+the shell.
+The current set of options may be found in
+.BR $\- .
+The return status is always true unless an invalid option is encountered.
+.RE
+.TP
+\fBshift\fP [\fIn\fP]
+The positional parameters from \fIn\fP+1 ... are renamed to
+.B $1
+.B ....
+Parameters represented by the numbers \fB$#\fP
+down to \fB$#\fP\-\fIn\fP+1 are unset.
+.I n
+must be a non-negative number less than or equal to \fB$#\fP.
+If
+.I n
+is 0, no parameters are changed.
+If
+.I n 
+is not given, it is assumed to be 1.
+If
+.I n
+is greater than \fB$#\fP, the positional parameters are not changed.
+The return status is greater than zero if
+.I n
+is greater than
+.B $#
+or less than zero; otherwise 0.
+.TP
+\fBshopt\fP [\fB\-pqsu\fP] [\fB\-o\fP] [\fIoptname\fP ...]
+Toggle the values of variables controlling optional shell behavior.
+With no options, or with the
+.B \-p
+option, a list of all settable options is displayed, with
+an indication of whether or not each is set.
+The \fB\-p\fP option causes output to be displayed in a form that
+may be reused as input.
+Other options have the following meanings:
+.RS
+.PD 0
+.TP
+.B \-s
+Enable (set) each \fIoptname\fP.
+.TP
+.B \-u
+Disable (unset) each \fIoptname\fP.
+.TP
+.B \-q
+Suppresses normal output (quiet mode); the return status indicates
+whether the \fIoptname\fP is set or unset.
+If multiple \fIoptname\fP arguments are given with
+.BR \-q ,
+the return status is zero if all \fIoptnames\fP are enabled; non-zero
+otherwise.
+.TP
+.B \-o
+Restricts the values of \fIoptname\fP to be those defined for the
+.B \-o
+option to the
+.B set
+builtin.
+.PD
+.PP
+If either
+.B \-s
+or
+.B \-u
+is used with no \fIoptname\fP arguments, the display is limited to
+those options which are set or unset, respectively.
+Unless otherwise noted, the \fBshopt\fP options are disabled (unset)
+by default.
+.PP
+The return status when listing options is zero if all \fIoptnames\fP
+are enabled, non-zero otherwise.  When setting or unsetting options,
+the return status is zero unless an \fIoptname\fP is not a valid shell
+option.
+.PP
+The list of \fBshopt\fP options is:
+.if t .sp .5v
+.if n .sp 1v
+.PD 0
+.TP 8
+.B cdable_vars
+If set, an argument to the
+.B cd
+builtin command that
+is not a directory is assumed to be the name of a variable whose
+value is the directory to change to.
+.TP 8
+.B cdspell
+If set, minor errors in the spelling of a directory component in a
+.B cd
+command will be corrected.
+The errors checked for are transposed characters,
+a missing character, and one character too many.
+If a correction is found, the corrected file name is printed,
+and the command proceeds.
+This option is only used by interactive shells.
+.TP 8
+.B checkhash
+If set, \fBbash\fP checks that a command found in the hash
+table exists before trying to execute it.  If a hashed command no
+longer exists, a normal path search is performed.
+.TP 8
+.B checkwinsize
+If set, \fBbash\fP checks the window size after each command
+and, if necessary, updates the values of
+.SM
+.B LINES
+and
+.SM
+.BR COLUMNS .
+.TP 8
+.B cmdhist
+If set,
+.B bash
+attempts to save all lines of a multiple-line
+command in the same history entry.  This allows
+easy re-editing of multi-line commands.
+.TP 8
+.B dotglob
+If set, 
+.B bash
+includes filenames beginning with a `.' in the results of pathname
+expansion.
+.TP 8
+.B execfail
+If set, a non-interactive shell will not exit if
+it cannot execute the file specified as an argument to the
+.B exec
+builtin command.  An interactive shell does not exit if
+.B exec
+fails.
+.TP 8
+.B expand_aliases
+If set, aliases are expanded as described above under
+.SM
+.BR ALIASES .
+This option is enabled by default for interactive shells.
+.TP 8
+.B extdebug
+If set, behavior intended for use by debuggers is enabled:
+.RS
+.TP
+.B 1.
+The \fB\-F\fP option to the \fBdeclare\fP builtin displays the source
+file name and line number corresponding to each function name supplied
+as an argument.
+.TP
+.B 2.
+If the command run by the \fBDEBUG\fP trap returns a non-zero value, the
+next command is skipped and not executed.
+.TP
+.B 3.
+If the command run by the \fBDEBUG\fP trap returns a value of 2, and the
+shell is executing in a subroutine (a shell function or a shell script
+executed by the \fB.\fP or \fBsource\fP builtins), a call to
+\fBreturn\fP is simulated.
+.RE
+.TP 8
+.B extglob
+If set, the extended pattern matching features described above under
+\fBPathname Expansion\fP are enabled.
+.TP 8
+.B extquote
+If set, \fB$\fP'\fIstring\fP' and \fB$\fP"\fIstring\fP" quoting is
+performed within \fB${\fP\fIparameter\fP\fB}\fP expansions
+enclosed in double quotes.  This option is enabled by default.
+.TP 8
+.B failglob
+If set, patterns which fail to match filenames during pathname expansion
+result in an expansion error.
+.TP 8
+.B force_fignore
+If set, the suffixes specified by the \fBFIGNORE\fP shell variable
+cause words to be ignored when performing word completion even if
+the ignored words are the only possible completions.
+See
+.SM
+\fBSHELL VARIABLES\fP
+above for a description of \fBFIGNORE\fP.
+This option is enabled by default.
+.TP 8
+.B gnu_errfmt
+If set, shell error messages are written in the standard GNU error
+message format.
+.TP 8
+.B histappend
+If set, the history list is appended to the file named by the value
+of the
+.B HISTFILE
+variable when the shell exits, rather than overwriting the file.
+.TP 8
+.B histreedit
+If set, and
+.B readline
+is being used, a user is given the opportunity to re-edit a
+failed history substitution.
+.TP 8
+.B histverify
+If set, and 
+.B readline
+is being used, the results of history substitution are not immediately
+passed to the shell parser.  Instead, the resulting line is loaded into
+the \fBreadline\fP editing buffer, allowing further modification.
+.TP 8
+.B hostcomplete
+If set, and
+.B readline
+is being used, \fBbash\fP will attempt to perform hostname completion when a
+word containing a \fB@\fP is being completed (see
+.B Completing
+under
+.SM
+.B READLINE
+above).
+This is enabled by default.
+.TP 8
+.B huponexit
+If set, \fBbash\fP will send
+.SM
+.B SIGHUP
+to all jobs when an interactive login shell exits.
+.TP 8
+.B interactive_comments
+If set, allow a word beginning with
+.B #
+to cause that word and all remaining characters on that
+line to be ignored in an interactive shell (see
+.SM
+.B COMMENTS
+above).  This option is enabled by default.
+.TP 8
+.B lithist
+If set, and the
+.B cmdhist
+option is enabled, multi-line commands are saved to the history with
+embedded newlines rather than using semicolon separators where possible.
+.TP 8
+.B login_shell
+The shell sets this option if it is started as a login shell (see
+.SM
+.B "INVOCATION"
+above).
+The value may not be changed.
+.TP 8
+.B mailwarn
+If set, and a file that \fBbash\fP is checking for mail has been  
+accessed since the last time it was checked, the message ``The mail in
+\fImailfile\fP has been read'' is displayed.
+.TP 8
+.B no_empty_cmd_completion
+If set, and
+.B readline
+is being used,
+.B bash
+will not attempt to search the \fBPATH\fP for possible completions when
+completion is attempted on an empty line.
+.TP 8
+.B nocaseglob
+If set,
+.B bash
+matches filenames in a case\-insensitive fashion when performing pathname
+expansion (see
+.B Pathname Expansion
+above).
+.TP 8
+.B nullglob
+If set,
+.B bash
+allows patterns which match no
+files (see
+.B Pathname Expansion
+above)
+to expand to a null string, rather than themselves.
+.TP 8
+.B progcomp
+If set, the programmable completion facilities (see
+\fBProgrammable Completion\fP above) are enabled.
+This option is enabled by default.
+.TP 8
+.B promptvars
+If set, prompt strings undergo
+parameter expansion, command substitution, arithmetic
+expansion, and quote removal after being expanded as described in
+.SM
+.B PROMPTING
+above.  This option is enabled by default.
+.TP 8
+.B restricted_shell
+The shell sets this option if it is started in restricted mode (see
+.SM
+.B "RESTRICTED SHELL"
+below).
+The value may not be changed.
+This is not reset when the startup files are executed, allowing
+the startup files to discover whether or not a shell is restricted.
+.TP 8
+.B shift_verbose
+If set, the
+.B shift
+builtin prints an error message when the shift count exceeds the
+number of positional parameters.
+.TP 8
+.B sourcepath
+If set, the
+\fBsource\fP (\fB.\fP) builtin uses the value of
+.SM
+.B PATH
+to find the directory containing the file supplied as an argument.
+This option is enabled by default.
+.TP 8
+.B xpg_echo
+If set, the \fBecho\fP builtin expands backslash-escape sequences
+by default.
+.RE
+.TP
+\fBsuspend\fP [\fB\-f\fP]
+Suspend the execution of this shell until it receives a
+.SM
+.B SIGCONT
+signal.  The
+.B \-f
+option says not to complain if this is 
+a login shell; just suspend anyway.  The return status is 0 unless
+the shell is a login shell and
+.B \-f
+is not supplied, or if job control is not enabled.
+.TP
+\fBtest\fP \fIexpr\fP
+.PD 0
+.TP
+\fB[\fP \fIexpr\fP \fB]\fP
+Return a status of 0 or 1 depending on
+the evaluation of the conditional expression
+.IR expr .
+Each operator and operand must be a separate argument.
+Expressions are composed of the primaries described above under
+.SM
+.BR "CONDITIONAL EXPRESSIONS" .
+.if t .sp 0.5
+.if n .sp 1
+Expressions may be combined using the following operators, listed
+in decreasing order of precedence.
+.RS
+.PD 0
+.TP
+.B ! \fIexpr\fP
+True if
+.I expr
+is false.
+.TP
+.B ( \fIexpr\fP )
+Returns the value of \fIexpr\fP.
+This may be used to override the normal precedence of operators.
+.TP
+\fIexpr1\fP \-\fBa\fP \fIexpr2\fP
+True if both
+.I expr1
+and
+.I expr2
+are true.
+.TP
+\fIexpr1\fP \-\fBo\fP \fIexpr2\fP
+True if either
+.I expr1
+or
+.I expr2
+is true.
+.PD
+.PP
+\fBtest\fP and \fB[\fP evaluate conditional
+expressions using a set of rules based on the number of arguments.
+.if t .sp 0.5
+.if n .sp 1
+.PD 0
+.TP
+0 arguments
+The expression is false.
+.TP
+1 argument
+The expression is true if and only if the argument is not null.
+.TP
+2 arguments
+If the first argument is \fB!\fP, the expression is true if and
+only if the second argument is null.
+If the first argument is one of the unary conditional operators listed above
+under
+.SM
+.BR "CONDITIONAL EXPRESSIONS" ,
+the expression is true if the unary test is true.
+If the first argument is not a valid unary conditional operator, the expression
+is false.
+.TP
+3 arguments
+If the second argument is one of the binary conditional operators listed above
+under
+.SM
+.BR "CONDITIONAL EXPRESSIONS" ,
+the result of the expression is the result of the binary test using
+the first and third arguments as operands.
+If the first argument is \fB!\fP, the value is the negation of
+the two-argument test using the second and third arguments.
+If the first argument is exactly \fB(\fP and the third argument is
+exactly \fB)\fP, the result is the one-argument test of the second
+argument.
+Otherwise, the expression is false.
+The \fB\-a\fP and \fB\-o\fP operators are considered binary operators
+in this case.  
+.TP
+4 arguments
+If the first argument is \fB!\fP, the result is the negation of
+the three-argument expression composed of the remaining arguments.
+Otherwise, the expression is parsed and evaluated according to 
+precedence using the rules listed above.
+.TP
+5 or more arguments
+The expression is parsed and evaluated according to precedence
+using the rules listed above.
+.RE
+.PD
+.TP
+.B times
+Print the accumulated user and system times for the shell and
+for processes run from the shell.  The return status is 0.
+.TP
+\fBtrap\fP [\fB\-lp\fP] [[\fIarg\fP] \fIsigspec\fP ...]
+The command
+.I arg
+is to be read and executed when the shell receives
+signal(s)
+.IR sigspec .
+If
+.I arg
+is absent (and there is a single \fIsigspec\fP) or
+.BR \- ,
+each specified signal is
+reset to its original disposition (the value it had
+upon entrance to the shell).
+If 
+.I arg
+is the null string the signal specified by each
+.I sigspec
+is ignored by the shell and by the commands it invokes.
+If
+.I arg
+is not present and
+.B \-p
+has been supplied, then the trap commands associated with each
+.I sigspec
+are displayed.
+If no arguments are supplied or if only
+.B \-p
+is given,
+.B trap
+prints the list of commands associated with each signal.
+The
+.B \-l
+option causes the shell to print a list of signal names and
+their corresponding numbers.
+Each
+.I sigspec
+is either
+a signal name defined in <\fIsignal.h\fP>, or a signal number.
+Signal names are case insensitive and the SIG prefix is optional.
+If a
+.I sigspec
+is
+.SM
+.B EXIT
+(0) the command
+.I arg
+is executed on exit from the shell.
+If a
+.I sigspec
+is
+.SM
+.BR DEBUG ,
+the command
+.I arg
+is executed before every \fIsimple command\fP, \fIfor\fP command,
+\fIcase\fP command, \fIselect\fP command, every arithmetic \fIfor\fP
+command, and before the first command executes in a shell function (see
+.SM
+.B SHELL GRAMMAR
+above).
+Refer to the description of the \fBextglob\fP option to the
+\fBshopt\fP builtin for details of its effect on the \fBDEBUG\fP trap.
+If a
+.I sigspec
+is
+.SM
+.BR ERR ,
+the command
+.I arg
+is executed whenever a simple command has a non\-zero exit status,
+subject to the following conditions.
+The
+.SM
+.B ERR
+trap is not executed if the failed
+command is part of the command list immediately following a
+.B while
+or
+.B until
+keyword, 
+part of the test in an
+.I if
+statement, part of a
+.B &&
+or
+.B \(bv\(bv
+list, or if the command's return value is
+being inverted via
+.BR ! .
+These are the same conditions obeyed by the \fBerrexit\fP option.
+If a
+.I sigspec
+is
+.SM
+.BR RETURN ,
+the command
+.I arg
+is executed each time a shell function or a script executed with the
+\fB.\fP or \fBsource\fP builtins finishes executing.
+Signals ignored upon entry to the shell cannot be trapped or reset.
+Trapped signals are reset to their original values in a child
+process when it is created.
+The return status is false if any
+.I sigspec
+is invalid; otherwise
+.B trap
+returns true.
+.TP
+\fBtype\fP [\fB\-aftpP\fP] \fIname\fP [\fIname\fP ...]
+With no options, 
+indicate how each
+.I name
+would be interpreted if used as a command name.
+If the
+.B \-t
+option is used,
+.B type
+prints a string which is one of
+.IR alias ,
+.IR keyword ,
+.IR function ,
+.IR builtin ,
+or
+.I file 
+if
+.I name
+is an alias, shell reserved word, function, builtin, or disk file,
+respectively.
+If the
+.I name
+is not found, then nothing is printed, and an exit status of false
+is returned.
+If the
+.B \-p
+option is used,
+.B type
+either returns the name of the disk file
+that would be executed if
+.I name
+were specified as a command name,
+or nothing if
+.if t \f(CWtype -t name\fP
+.if n ``type -t name''
+would not return
+.IR file .
+The
+.B \-P
+option forces a
+.SM
+.B PATH
+search for each \fIname\fP, even if
+.if t \f(CWtype -t name\fP
+.if n ``type -t name''
+would not return
+.IR file .
+If a command is hashed,
+.B \-p
+and
+.B \-P
+print the hashed value, not necessarily the file that appears
+first in 
+.SM
+.BR PATH .
+If the
+.B \-a
+option is used, 
+.B type
+prints all of the places that contain
+an executable named 
+.IR name .
+This includes aliases and functions,
+if and only if the 
+.B \-p
+option is not also used.
+The table of hashed commands is not consulted
+when using
+.BR \-a .
+The
+.B \-f
+option suppresses shell function lookup, as with the \fBcommand\fP builtin.
+.B type
+returns true if any of the arguments are found, false if
+none are found.
+.TP
+\fBulimit\fP [\fB\-SHacdflmnpstuv\fP [\fIlimit\fP]]
+Provides control over the resources available to the shell and to
+processes started by it, on systems that allow such control.
+The \fB\-H\fP and \fB\-S\fP options specify that the hard or soft limit is
+set for the given resource.  A hard limit cannot be increased once it
+is set; a soft limit may be increased up to the value of the hard limit.
+If neither \fB\-H\fP nor \fB\-S\fP is specified, both the soft and hard
+limits are set.
+The value of
+.I limit
+can be a number in the unit specified for the resource
+or one of the special values
+.BR hard ,
+.BR soft ,
+or
+.BR unlimited ,
+which stand for the current hard limit, the current soft limit, and
+no limit, respectively.
+If
+.I limit
+is omitted, the current value of the soft limit of the resource is
+printed, unless the \fB\-H\fP option is given.  When more than one
+resource is specified, the limit name and unit are printed before the value.
+Other options are interpreted as follows:
+.RS
+.PD 0
+.TP
+.B \-a
+All current limits are reported
+.TP
+.B \-c
+The maximum size of core files created
+.TP
+.B \-d
+The maximum size of a process's data segment
+.TP
+.B \-f
+The maximum size of files created by the shell
+.TP
+.B \-l
+The maximum size that may be locked into memory
+.TP
+.B \-m
+The maximum resident set size
+.TP
+.B \-n
+The maximum number of open file descriptors (most systems do not
+allow this value to be set)
+.TP
+.B \-p
+The pipe size in 512-byte blocks (this may not be set)
+.TP
+.B \-s
+The maximum stack size
+.TP
+.B \-t
+The maximum amount of cpu time in seconds
+.TP
+.B \-u
+The maximum number of processes available to a single user
+.TP
+.B \-v
+The maximum amount of virtual memory available to the shell
+.PD
+.PP
+If
+.I limit
+is given, it is the new value of the specified resource (the
+.B \-a
+option is display only).
+If no option is given, then
+.B \-f
+is assumed.  Values are in 1024-byte increments, except for
+.BR \-t ,
+which is in seconds,
+.BR \-p ,
+which is in units of 512-byte blocks,
+and
+.B \-n
+and
+.BR \-u ,
+which are unscaled values.
+The return status is 0 unless an invalid option or argument is supplied,
+or an error occurs while setting a new limit.
+.RE
+.TP
+\fBumask\fP [\fB\-p\fP] [\fB\-S\fP] [\fImode\fP]
+The user file-creation mask is set to 
+.IR mode .
+If
+.I mode
+begins with a digit, it
+is interpreted as an octal number; otherwise
+it is interpreted as a symbolic mode mask similar
+to that accepted by
+.IR chmod (1).
+If
+.I mode
+is omitted, the current value of the mask is printed.
+The
+.B \-S
+option causes the mask to be printed in symbolic form; the
+default output is an octal number.
+If the
+.B \-p
+option is supplied, and
+.I mode
+is omitted, the output is in a form that may be reused as input.
+The return status is 0 if the mode was successfully changed or if
+no \fImode\fP argument was supplied, and false otherwise.
+.TP
+\fBunalias\fP [\-\fBa\fP] [\fIname\fP ...]
+Remove each \fIname\fP from the list of defined aliases.  If
+.B \-a
+is supplied, all alias definitions are removed.  The return
+value is true unless a supplied
+.I name
+is not a defined alias.
+.TP
+\fBunset\fP [\-\fBfv\fP] [\fIname\fP ...]
+For each
+.IR name ,
+remove the corresponding variable or function.
+If no options are supplied, or the
+.B \-v
+option is given, each
+.I name
+refers to a shell variable.
+Read-only variables may not be unset.
+If
+.B \-f
+is specifed, 
+each
+.I name
+refers to a shell function, and the function definition
+is removed.
+Each unset variable or function is removed from the environment
+passed to subsequent commands.
+If any of
+.SM
+.BR RANDOM ,
+.SM
+.BR SECONDS ,
+.SM
+.BR LINENO ,
+.SM
+.BR HISTCMD ,
+.SM
+.BR FUNCNAME ,
+.SM
+.BR GROUPS ,
+or
+.SM
+.B DIRSTACK
+are unset, they lose their special properties, even if they are
+subsequently reset.  The exit status is true unless a
+.I name
+is readonly.
+.TP
+\fBwait\fP [\fIn\fP]
+Wait for the specified process and return its termination
+status.
+.I n
+may be a process
+ID or a job specification; if a job spec is given, all processes
+in that job's pipeline are waited for.  If
+.I n
+is not given, all currently active child processes
+are waited for, and the return status is zero.  If
+.I n
+specifies a non-existent process or job, the return status is
+127.  Otherwise, the return status is the exit status of the last
+process or job waited for.
+.\" bash_builtins
+.if \n(zZ=1 .ig zZ
+.SH "RESTRICTED SHELL"
+.\" rbash.1
+.zY
+.PP
+If
+.B bash
+is started with the name
+.BR rbash ,
+or the
+.B \-r
+option is supplied at invocation,
+the shell becomes restricted.
+A restricted shell is used to
+set up an environment more controlled than the standard shell.
+It behaves identically to
+.B bash
+with the exception that the following are disallowed or not performed:
+.IP \(bu
+changing directories with \fBcd\fP
+.IP \(bu
+setting or unsetting the values of
+.BR SHELL ,
+.BR PATH ,
+.BR ENV ,
+or
+.B BASH_ENV
+.IP \(bu
+specifying command names containing
+.B /
+.IP \(bu
+specifying a file name containing a
+.B /
+as an argument to the
+.B .
+builtin command
+.IP \(bu
+Specifying a filename containing a slash as an argument to the
+.B \-p
+option to the
+.B hash
+builtin command
+.IP \(bu
+importing function definitions from the shell environment at startup
+.IP \(bu
+parsing the value of \fBSHELLOPTS\fP from the shell environment at startup
+.IP \(bu
+redirecting output using the >, >|, <>, >&, &>, and >> redirection operators
+.IP \(bu
+using the
+.B exec
+builtin command to replace the shell with another command
+.IP \(bu
+adding or deleting builtin commands with the
+.B \-f
+and
+.B \-d
+options to the
+.B enable
+builtin command
+.IP \(bu
+Using the \fBenable\fP builtin command to enable disabled shell builtins
+.IP \(bu
+specifying the
+.B \-p
+option to the
+.B command
+builtin command
+.IP \(bu
+turning off restricted mode with
+\fBset +r\fP or \fBset +o restricted\fP.
+.PP
+These restrictions are enforced after any startup files are read.
+.PP
+.ie \n(zY=1 When a command that is found to be a shell script is executed,
+.el \{ When a command that is found to be a shell script is executed
+(see
+.SM
+.B "COMMAND EXECUTION"
+above),
+\}
+.B rbash
+turns off any restrictions in the shell spawned to execute the
+script.
+.\" end of rbash.1
+.if \n(zY=1 .ig zY
+.SH "SEE ALSO"
+.PD 0
+.TP
+\fIBash Reference Manual\fP, Brian Fox and Chet Ramey
+.TP
+\fIThe Gnu Readline Library\fP, Brian Fox and Chet Ramey
+.TP
+\fIThe Gnu History Library\fP, Brian Fox and Chet Ramey
+.TP
+\fIPortable Operating System Interface (POSIX) Part 2: Shell and Utilities\fP, IEEE
+.TP
+\fIsh\fP(1), \fIksh\fP(1), \fIcsh\fP(1)
+.TP
+\fIemacs\fP(1), \fIvi\fP(1)
+.TP
+\fIreadline\fP(3)
+.PD
+.SH FILES
+.PD 0
+.TP
+.FN /bin/bash
+The \fBbash\fP executable
+.TP
+.FN /etc/profile
+The systemwide initialization file, executed for login shells
+.TP
+.FN ~/.bash_profile
+The personal initialization file, executed for login shells
+.TP
+.FN ~/.bashrc
+The individual per-interactive-shell startup file
+.TP
+.FN ~/.bash_logout
+The individual login shell cleanup file, executed when a login shell exits
+.TP
+.FN ~/.inputrc
+Individual \fIreadline\fP initialization file
+.PD
+.SH AUTHORS
+Brian Fox, Free Software Foundation
+.br
+bfox@gnu.org
+.PP
+Chet Ramey, Case Western Reserve University
+.br
+chet@po.CWRU.Edu
+.SH BUG REPORTS
+If you find a bug in
+.B bash,
+you should report it.  But first, you should
+make sure that it really is a bug, and that it appears in the latest
+version of
+.BR bash .
+The latest version is always available from
+\fIftp://ftp.gnu.org/pub/bash/\fP.
+.PP
+Once you have determined that a bug actually exists, use the
+.I bashbug
+command to submit a bug report.
+If you have a fix, you are encouraged to mail that as well!
+Suggestions and `philosophical' bug reports may be mailed
+to \fIbug-bash@gnu.org\fP or posted to the Usenet
+newsgroup
+.BR gnu.bash.bug .
+.PP
+ALL bug reports should include:
+.PP
+.PD 0
+.TP 20
+The version number of \fBbash\fR
+.TP
+The hardware and operating system
+.TP
+The compiler used to compile
+.TP
+A description of the bug behaviour
+.TP
+A short script or `recipe' which exercises the bug
+.PD
+.PP
+.I bashbug
+inserts the first three items automatically into the template
+it provides for filing a bug report.
+.PP
+Comments and bug reports concerning
+this manual page should be directed to
+.IR chet@po.CWRU.Edu .
+.SH BUGS
+.PP
+It's too big and too slow.
+.PP
+There are some subtle differences between 
+.B bash
+and traditional versions of
+.BR sh ,
+mostly because of the
+.SM
+.B POSIX
+specification.
+.PP
+Aliases are confusing in some uses.
+.PP
+Shell builtin commands and functions are not stoppable/restartable.
+.PP
+Compound commands and command sequences of the form `a ; b ; c'
+are not handled gracefully when process suspension is attempted.
+When a process is stopped, the shell immediately executes the next
+command in the sequence.
+It suffices to place the sequence of commands between
+parentheses to force it into a subshell, which may be stopped as
+a unit.
+.PP
+Commands inside of \fB$(\fP...\fB)\fP command substitution are not
+parsed until substitution is attempted.  This will delay error
+reporting until some time after the command is entered.  For example,
+unmatched parentheses, even inside shell comments, will result in
+error messages while the construct is being read.
+.PP
+Array variables may not (yet) be exported.
+.zZ
+.zY
index 017958ea2f6708977775b45eb0766422b2e775ee..2bcb4ad2e1a89677e86e4e9b320c62999b3e56bd 100644 (file)
@@ -6002,6 +6002,11 @@ The @code{type} and @code{command} builtins will not report a non-executable
 file as having been found, though the shell will attempt to execute such a
 file if it is the only so-named file found in @code{$PATH}.
 
+@item
+When the @code{xpg_echo} option is enabled, Bash does not attempt to interpret
+any arguments to @code{echo} as options.  Each argument is displayed, after
+escape characters are converted.
+
 @end enumerate
 
 There is other @sc{posix} 1003.2 behavior that Bash does not implement.
@@ -6145,15 +6150,15 @@ Bash does not print another warning, and the stopped jobs are terminated.
 @item bg
 @btindex bg
 @example
-bg [@var{jobspec}]
+bg [@var{jobspec} @dots{}]
 @end example
-Resume the suspended job @var{jobspec} in the background, as if it
+Resume each suspended job @var{jobspec} in the background, as if it
 had been started with @samp{&}.
 If @var{jobspec} is not supplied, the current job is used.
 The return status is zero unless it is run when job control is not
-enabled, or, when run with job control enabled, if @var{jobspec} was
-not found or @var{jobspec} specifies a job that was started without
-job control.
+enabled, or, when run with job control enabled, if the last
+@var{jobspec} was not found or the last @var{jobspec} specifies a job
+that was started without job control.
 
 @item fg
 @btindex fg
index 6edef623af3ab5d60d3fb43ccf917c48d669a587..98cf521bf656b4483695ffdf91c52d1fc085a117 100644 (file)
@@ -5997,6 +5997,16 @@ indication of whether or not a history entry has been modified.
 @item
 The default editor used by @code{fc} is @code{ed}.
 
+@item
+The @code{type} and @code{command} builtins will not report a non-executable
+file as having been found, though the shell will attempt to execute such a
+file if it is the only so-named file found in @code{$PATH}.
+
+@item
+When the @code{xpg_echo} option is enabled, Bash does not attempt to interpret
+any arguments to @code{echo} as options.  Each argument is displayed, after
+escape characters are converted.
+
 @end enumerate
 
 There is other @sc{posix} 1003.2 behavior that Bash does not implement.
index 5d1cfa75bfbf209e2f7e94a9c5ca2a19143919ff..441d091377baf66b558492cce9c9fe9c3136c340 100644 (file)
@@ -4,7 +4,7 @@ Copyright (C) 1988-2004 Free Software Foundation, Inc.
 
 @set EDITION 3.0
 @set VERSION 3.0
-@set UPDATED 2 August 2004
+@set UPDATED 16 August 2004
 @set UPDATED-MONTH August 2004
 
-@set LASTCHANGE Mon Aug  2 22:45:05 EDT 2004
+@set LASTCHANGE Mon Aug 16 23:09:57 EDT 2004
index ae5b6ad8420802f1834cff8e1ae0fea8dbb247d5..5d1cfa75bfbf209e2f7e94a9c5ca2a19143919ff 100644 (file)
@@ -4,7 +4,7 @@ Copyright (C) 1988-2004 Free Software Foundation, Inc.
 
 @set EDITION 3.0
 @set VERSION 3.0
-@set UPDATED 1 August 2004
+@set UPDATED 2 August 2004
 @set UPDATED-MONTH August 2004
 
-@set LASTCHANGE Sun Aug  1 14:48:46 EDT 2004
+@set LASTCHANGE Mon Aug  2 22:45:05 EDT 2004
index 60cbfabd04d1ef947c89ee80fe9f6b129fb1d84e..67c95554e30ba39459429a223b6dee8e9d5f04f8 100644 (file)
@@ -246,7 +246,7 @@ static unsigned long binsizes[NBUCKETS] = {
 static PTR_T internal_malloc __P((size_t, const char *, int, int));
 static PTR_T internal_realloc __P((PTR_T, size_t, const char *, int, int));
 static void internal_free __P((PTR_T, const char *, int, int));
-static PTR_T internal_memalign __P((unsigned int, size_t, const char *, int, int));
+static PTR_T internal_memalign __P((size_t, size_t, const char *, int, int));
 #ifndef NO_CALLOC
 static PTR_T internal_calloc __P((size_t, size_t, const char *, int, int));
 static void internal_cfree __P((PTR_T, const char *, int, int));
@@ -1026,7 +1026,7 @@ internal_realloc (mem, n, file, line, flags)
 
 static PTR_T
 internal_memalign (alignment, size, file, line, flags)
-     unsigned int alignment;
+     size_t alignment;
      size_t size;
      const char *file;
      int line, flags;
@@ -1145,7 +1145,7 @@ sh_free (mem, file, line)
 
 PTR_T
 sh_memalign (alignment, size, file, line)
-     unsigned int alignment;
+     size_t alignment;
      size_t size;
      const char *file;
      int line;
@@ -1212,7 +1212,7 @@ free (mem)
 
 PTR_T
 memalign (alignment, size)
-     unsigned int alignment;
+     size_t alignment;
      size_t size;
 {
   return internal_memalign (alignment, size, (char *)NULL, 0, 0);
diff --git a/lib/malloc/malloc.c~ b/lib/malloc/malloc.c~
new file mode 100644 (file)
index 0000000..60cbfab
--- /dev/null
@@ -0,0 +1,1244 @@
+/* malloc.c - dynamic memory allocation for bash. */
+
+/*  Copyright (C) 1985-2003 Free Software Foundation, Inc.
+
+    This program is free software; you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation; either version 2, or (at your option)
+    any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program; if not, write to the Free Software
+    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA.
+
+In other words, you are welcome to use, share and improve this program.
+You are forbidden to forbid anyone else to use, share and improve
+what you give them.   Help stamp out software-hoarding!  */
+
+/*
+ * @(#)nmalloc.c 1 (Caltech) 2/21/82
+ *
+ *     U of M Modified: 20 Jun 1983 ACT: strange hacks for Emacs
+ *
+ *     Nov 1983, Mike@BRL, Added support for 4.1C/4.2 BSD.
+ *
+ * This is a very fast storage allocator.  It allocates blocks of a small 
+ * number of different sizes, and keeps free lists of each size.  Blocks
+ * that don't exactly fit are passed up to the next larger size.  In this 
+ * implementation, the available sizes are (2^n)-4 (or -16) bytes long.
+ * This is designed for use in a program that uses vast quantities of
+ * memory, but bombs when it runs out.  To make it a little better, it
+ * warns the user when he starts to get near the end.
+ *
+ * June 84, ACT: modified rcheck code to check the range given to malloc,
+ * rather than the range determined by the 2-power used.
+ *
+ * Jan 85, RMS: calls malloc_warning to issue warning on nearly full.
+ * No longer Emacs-specific; can serve as all-purpose malloc for GNU.
+ * You should call malloc_init to reinitialize after loading dumped Emacs.
+ * Call malloc_stats to get info on memory stats if MALLOC_STATS turned on.
+ * realloc knows how to return same block given, just changing its size,
+ * if the power of 2 is correct.
+ */
+
+/*
+ * nextf[i] is the pointer to the next free block of size 2^(i+3).  The
+ * smallest allocatable block is 8 bytes.  The overhead information will
+ * go in the first int of the block, and the returned pointer will point
+ * to the second.
+ */
+
+/* Define MEMSCRAMBLE to have free() write 0xcf into memory as it's freed, to
+   uncover callers that refer to freed memory, and to have malloc() write 0xdf
+   into memory as it's allocated to avoid referring to previous contents. */
+
+/* SCO 3.2v4 getcwd and possibly other libc routines fail with MEMSCRAMBLE;
+   handled by configure. */
+
+#if defined (HAVE_CONFIG_H)
+#  include <config.h>
+#endif /* HAVE_CONFIG_H */
+
+#if defined (SHELL)
+#  include "bashtypes.h"
+#  include "stdc.h"
+#else
+#  include <sys/types.h>
+#endif
+
+#if defined (HAVE_UNISTD_H)
+#  include <unistd.h>
+#endif
+
+/* Determine which kind of system this is.  */
+#include <signal.h>
+
+#if defined (HAVE_STRING_H)
+#  include <string.h>
+#else
+#  include <strings.h>
+#endif
+
+#include <stdio.h>
+
+/* Define getpagesize () if the system does not.  */
+#ifndef HAVE_GETPAGESIZE
+#  include "getpagesize.h"
+#endif
+
+#include "imalloc.h"
+#ifdef MALLOC_STATS
+#  include "mstats.h"
+#endif
+#ifdef MALLOC_REGISTER
+#  include "table.h"
+#endif
+#ifdef MALLOC_WATCH
+#  include "watch.h"
+#endif
+
+/* System-specific omissions. */
+#ifdef HPUX
+#  define NO_VALLOC
+#endif
+
+#define NBUCKETS       30
+
+#define ISALLOC ((char) 0xf7)  /* magic byte that implies allocation */
+#define ISFREE ((char) 0x54)   /* magic byte that implies free block */
+                               /* this is for error checking only */
+#define ISMEMALIGN ((char) 0xd6)  /* Stored before the value returned by
+                                    memalign, with the rest of the word
+                                    being the distance to the true
+                                    beginning of the block.  */
+
+
+/* We have a flag indicating whether memory is allocated, an index in
+   nextf[], a size field, and a sentinel value to determine whether or
+   not a caller wrote before the start of allocated memory; to realloc()
+   memory we either copy mh_nbytes or just change mh_nbytes if there is
+   enough room in the block for the new size.  Range checking is always
+   done. */
+union mhead {
+  bits64_t mh_align;                                           /* 8 */
+  struct {
+    char mi_alloc;             /* ISALLOC or ISFREE */         /* 1 */
+    char mi_index;             /* index in nextf[] */          /* 1 */
+    /* Remainder are valid only when block is allocated */
+    u_bits16_t mi_magic2;      /* should be == MAGIC2 */       /* 2 */
+    u_bits32_t mi_nbytes;      /* # of bytes allocated */      /* 4 */
+  } minfo;
+};
+#define mh_alloc       minfo.mi_alloc
+#define mh_index       minfo.mi_index
+#define mh_nbytes      minfo.mi_nbytes
+#define mh_magic2      minfo.mi_magic2
+
+#define MOVERHEAD      sizeof(union mhead)
+#define MALIGN_MASK    7       /* one less than desired alignment */
+
+typedef union _malloc_guard {
+  char s[4];
+  u_bits32_t i;
+} mguard_t;
+
+/* Access free-list pointer of a block.
+   It is stored at block + sizeof (char *).
+   This is not a field in the minfo structure member of union mhead
+   because we want sizeof (union mhead)
+   to describe the overhead for when the block is in use,
+   and we do not want the free-list pointer to count in that.  */
+
+#define CHAIN(a) \
+  (*(union mhead **) (sizeof (char *) + (char *) (a)))
+
+/* To implement range checking, we write magic values in at the beginning
+   and end of each allocated block, and make sure they are undisturbed
+   whenever a free or a realloc occurs. */
+
+/* Written in the 2 bytes before the block's real space (-4 bytes) */
+#define MAGIC2 0x5555
+#define MSLOP  4               /* 4 bytes extra for u_bits32_t size */
+
+/* How many bytes are actually allocated for a request of size N --
+   rounded up to nearest multiple of 8 after accounting for malloc
+   overhead. */
+#define ALLOCATED_BYTES(n) \
+       (((n) + MOVERHEAD + MSLOP + MALIGN_MASK) & ~MALIGN_MASK)
+
+#define ASSERT(p) \
+  do \
+    { \
+      if (!(p)) xbotch((PTR_T)0, ERR_ASSERT_FAILED, __STRING(p), file, line); \
+    } \
+  while (0)
+
+/* Minimum and maximum bucket indices for block splitting (and to bound
+   the search for a block to split). */
+#define SPLIT_MIN      2       /* XXX - was 3 */
+#define SPLIT_MID      11
+#define SPLIT_MAX      14
+
+/* Minimum and maximum bucket indices for block coalescing. */
+#define COMBINE_MIN    2
+#define COMBINE_MAX    (pagebucket - 1)        /* XXX */
+
+#define LESSCORE_MIN   10
+#define LESSCORE_FRC   13
+
+#define STARTBUCK      1
+
+/* Flags for the internal functions. */
+#define MALLOC_WRAPPER 0x01    /* wrapper function */
+#define MALLOC_INTERNAL        0x02    /* internal function calling another */
+#define MALLOC_NOTRACE 0x04    /* don't trace this allocation or free */
+#define MALLOC_NOREG   0x08    /* don't register this allocation or free */
+
+/* Future use. */
+#define ERR_DUPFREE            0x01
+#define ERR_UNALLOC            0x02
+#define ERR_UNDERFLOW          0x04    
+#define ERR_ASSERT_FAILED      0x08
+
+/* Evaluates to true if NB is appropriate for bucket NU.  NB is adjusted
+   appropriately by the caller to account for malloc overhead.  This only
+   checks that the recorded size is not too big for the bucket.  We
+   can't check whether or not it's in between NU and NU-1 because we
+   might have encountered a busy bucket when allocating and moved up to
+   the next size. */
+#define IN_BUCKET(nb, nu)      ((nb) <= binsizes[(nu)])
+
+/* Use this when we want to be sure that NB is in bucket NU. */
+#define RIGHT_BUCKET(nb, nu) \
+       (((nb) > binsizes[(nu)-1]) && ((nb) <= binsizes[(nu)]))
+
+/* nextf[i] is free list of blocks of size 2**(i + 3)  */
+
+static union mhead *nextf[NBUCKETS];
+
+/* busy[i] is nonzero while allocation of block size i is in progress.  */
+
+static char busy[NBUCKETS];
+
+static int pagesz;     /* system page size. */
+static int pagebucket; /* bucket for requests a page in size */
+static int maxbuck;    /* highest bucket receiving allocation request. */
+
+static char *memtop;   /* top of heap */
+
+static unsigned long binsizes[NBUCKETS] = {
+       8UL, 16UL, 32UL, 64UL, 128UL, 256UL, 512UL, 1024UL, 2048UL, 4096UL,
+       8192UL, 16384UL, 32768UL, 65536UL, 131072UL, 262144UL, 524288UL,
+       1048576UL, 2097152UL, 4194304UL, 8388608UL, 16777216UL, 33554432UL,
+       67108864UL, 134217728UL, 268435456UL, 536870912UL, 1073741824UL,
+       2147483648UL, 4294967295UL
+};
+
+/* binsizes[x] == (1 << ((x) + 3)) */
+#define binsize(x)     binsizes[(x)]
+
+/* Declarations for internal functions */
+static PTR_T internal_malloc __P((size_t, const char *, int, int));
+static PTR_T internal_realloc __P((PTR_T, size_t, const char *, int, int));
+static void internal_free __P((PTR_T, const char *, int, int));
+static PTR_T internal_memalign __P((unsigned int, size_t, const char *, int, int));
+#ifndef NO_CALLOC
+static PTR_T internal_calloc __P((size_t, size_t, const char *, int, int));
+static void internal_cfree __P((PTR_T, const char *, int, int));
+#endif
+#ifndef NO_VALLOC
+static PTR_T internal_valloc __P((size_t, const char *, int, int));
+#endif
+
+#if defined (botch)
+extern void botch ();
+#else
+static void botch __P((const char *, const char *, int));
+#endif
+static void xbotch __P((PTR_T, int, const char *, const char *, int));
+
+#if !HAVE_DECL_SBRK
+extern char *sbrk ();
+#endif /* !HAVE_DECL_SBRK */
+
+#ifdef SHELL
+extern int interrupt_immediately;
+extern int signal_is_trapped __P((int));
+#endif
+
+#ifdef MALLOC_STATS
+struct _malstats _mstats;
+#endif /* MALLOC_STATS */
+
+/* Debugging variables available to applications. */
+int malloc_flags = 0;  /* future use */
+int malloc_trace = 0;  /* trace allocations and frees to stderr */
+int malloc_register = 0;       /* future use */
+
+#ifdef MALLOC_TRACE
+char _malloc_trace_buckets[NBUCKETS];
+
+/* These should really go into a header file. */
+extern void mtrace_alloc __P((const char *, PTR_T, size_t, const char *, int));
+extern void mtrace_free __P((PTR_T, int, const char *, int));
+#endif
+
+#if !defined (botch)
+static void
+botch (s, file, line)
+     const char *s;
+     const char *file;
+     int line;
+{
+  fprintf (stderr, _("malloc: failed assertion: %s\n"), s);
+  (void)fflush (stderr);
+  abort ();
+}
+#endif
+
+/* print the file and line number that caused the assertion failure and
+   call botch() to do whatever the application wants with the information */
+static void
+xbotch (mem, e, s, file, line)
+     PTR_T mem;
+     int e;
+     const char *s;
+     const char *file;
+     int line;
+{
+  fprintf (stderr, _("\r\nmalloc: %s:%d: assertion botched\r\n"),
+                       file ? file : "unknown", line);
+#ifdef MALLOC_REGISTER
+  if (mem != NULL && malloc_register)
+    mregister_describe_mem (mem, stderr);
+#endif
+  (void)fflush (stderr);
+  botch(s, file, line);
+}
+
+/* Coalesce two adjacent free blocks off the free list for size NU - 1,
+   as long as we can find two adjacent free blocks.  nextf[NU -1] is
+   assumed to not be busy; the caller (morecore()) checks for this. */
+static void
+bcoalesce (nu)
+     register int nu;
+{
+  register union mhead *mp, *mp1, *mp2;
+  register int nbuck;
+  unsigned long siz;
+
+  nbuck = nu - 1;
+  if (nextf[nbuck] == 0)
+    return;
+
+  siz = binsize (nbuck);
+
+  mp2 = mp1 = nextf[nbuck];
+  mp = CHAIN (mp1);
+  while (mp && mp != (union mhead *)((char *)mp1 + siz))
+    {
+      mp2 = mp1;
+      mp1 = mp;
+      mp = CHAIN (mp);
+    }
+  if (mp == 0)
+    return;
+
+  /* OK, now we have mp1 pointing to the block we want to add to nextf[NU].
+     CHAIN(mp2) must equal mp1.  Check that mp1 and mp are adjacent. */
+  if (mp2 != mp1 && CHAIN(mp2) != mp1)
+    xbotch ((PTR_T)0, 0, "bcoalesce: CHAIN(mp2) != mp1", (char *)NULL, 0);
+
+#ifdef MALLOC_DEBUG
+  if (CHAIN (mp1) != (union mhead *)((char *)mp1 + siz))
+    return;    /* not adjacent */
+#endif
+
+#ifdef MALLOC_STATS
+  _mstats.tbcoalesce++;
+  _mstats.ncoalesce[nbuck]++;
+#endif
+
+  /* Since they are adjacent, remove them from the free list */
+  if (mp1 == nextf[nbuck])
+    nextf[nbuck] = CHAIN (mp);
+  else
+    CHAIN (mp2) = CHAIN (mp);
+
+  /* And add the combined two blocks to nextf[NU]. */
+  mp1->mh_alloc = ISFREE;
+  mp1->mh_index = nu;
+  CHAIN (mp1) = nextf[nu];
+  nextf[nu] = mp1;
+}
+
+/* Split a block at index > NU (but less than SPLIT_MAX) into a set of
+   blocks of the correct size, and attach them to nextf[NU].  nextf[NU]
+   is assumed to be empty.  Must be called with signals blocked (e.g.,
+   by morecore()). */
+static void
+bsplit (nu)
+     register int nu;
+{
+  register union mhead *mp;
+  int nbuck, nblks, split_max;
+  unsigned long siz;
+
+  split_max = (maxbuck > SPLIT_MAX) ? maxbuck : SPLIT_MAX;
+
+  if (nu >= SPLIT_MID)
+    {
+      for (nbuck = split_max; nbuck > nu; nbuck--)
+       {
+         if (busy[nbuck] || nextf[nbuck] == 0)
+           continue;
+         break;
+       }
+    }
+  else
+    {
+      for (nbuck = nu + 1; nbuck <= split_max; nbuck++)
+       {
+         if (busy[nbuck] || nextf[nbuck] == 0)
+           continue;
+         break;
+       }
+    }
+
+  if (nbuck > split_max || nbuck <= nu)
+    return;
+
+  /* XXX might want to split only if nextf[nbuck] has >= 2 blocks free
+     and nbuck is below some threshold. */
+
+#ifdef MALLOC_STATS
+  _mstats.tbsplit++;
+  _mstats.nsplit[nbuck]++;
+#endif
+
+  /* Figure out how many blocks we'll get. */
+  siz = binsize (nu);
+  nblks = binsize (nbuck) / siz;
+
+  /* Remove the block from the chain of larger blocks. */
+  mp = nextf[nbuck];
+  nextf[nbuck] = CHAIN (mp);
+
+  /* Split the block and put it on the requested chain. */
+  nextf[nu] = mp;
+  while (1)
+    {
+      mp->mh_alloc = ISFREE;
+      mp->mh_index = nu;
+      if (--nblks <= 0) break;
+      CHAIN (mp) = (union mhead *)((char *)mp + siz);
+      mp = (union mhead *)((char *)mp + siz);
+    }
+  CHAIN (mp) = 0;
+}
+
+static void
+block_signals (setp, osetp)
+     sigset_t *setp, *osetp;
+{
+#ifdef HAVE_POSIX_SIGNALS
+  sigfillset (setp);
+  sigemptyset (osetp);
+  sigprocmask (SIG_BLOCK, setp, osetp);
+#else
+#  if defined (HAVE_BSD_SIGNALS)
+  *osetp = sigsetmask (-1);
+#  endif
+#endif
+}
+
+static void
+unblock_signals (setp, osetp)
+     sigset_t *setp, *osetp;
+{
+#ifdef HAVE_POSIX_SIGNALS
+  sigprocmask (SIG_SETMASK, osetp, (sigset_t *)NULL);
+#else
+#  if defined (HAVE_BSD_SIGNALS)
+  sigsetmask (*osetp);
+#  endif
+#endif
+}
+
+/* Return some memory to the system by reducing the break.  This is only
+   called with NU > pagebucket, so we're always assured of giving back
+   more than one page of memory. */  
+static void
+lesscore (nu)                  /* give system back some memory */
+     register int nu;          /* size index we're discarding  */
+{
+  long siz;
+
+  siz = binsize (nu);
+  /* Should check for errors here, I guess. */
+  sbrk (-siz);
+  memtop -= siz;
+
+#ifdef MALLOC_STATS
+  _mstats.nsbrk++;
+  _mstats.tsbrk -= siz;
+  _mstats.nlesscore[nu]++;
+#endif
+}
+  
+static void
+morecore (nu)                  /* ask system for more memory */
+     register int nu;          /* size index to get more of  */
+{
+  register union mhead *mp;
+  register int nblks;
+  register long siz;
+  long sbrk_amt;               /* amount to get via sbrk() */
+  sigset_t set, oset;
+  int blocked_sigs;
+
+  /* Block all signals in case we are executed from a signal handler. */
+  blocked_sigs = 0;
+#ifdef SHELL
+  if (interrupt_immediately || signal_is_trapped (SIGINT) || signal_is_trapped (SIGCHLD))
+#endif
+    {
+      block_signals (&set, &oset);
+      blocked_sigs = 1;
+    }
+
+  siz = binsize (nu);  /* size of desired block for nextf[nu] */
+
+  if (siz < 0)
+    goto morecore_done;                /* oops */
+
+#ifdef MALLOC_STATS
+  _mstats.nmorecore[nu]++;
+#endif
+
+  /* Try to split a larger block here, if we're within the range of sizes
+     to split. */
+  if (nu >= SPLIT_MIN)
+    {
+      bsplit (nu);
+      if (nextf[nu] != 0)
+       goto morecore_done;
+    }
+
+  /* Try to coalesce two adjacent blocks from the free list on nextf[nu - 1],
+     if we can, and we're withing the range of the block coalescing limits. */
+  if (nu >= COMBINE_MIN && nu < COMBINE_MAX && busy[nu - 1] == 0 && nextf[nu - 1])
+    {
+      bcoalesce (nu);
+      if (nextf[nu] != 0)
+       goto morecore_done;
+    }
+
+  /* Take at least a page, and figure out how many blocks of the requested
+     size we're getting. */
+  if (siz <= pagesz)
+    {
+      sbrk_amt = pagesz;
+      nblks = sbrk_amt / siz;
+    }
+  else
+    {
+      /* We always want to request an integral multiple of the page size
+        from the kernel, so let's compute whether or not `siz' is such
+        an amount.  If it is, we can just request it.  If not, we want
+        the smallest integral multiple of pagesize that is larger than
+        `siz' and will satisfy the request. */
+      sbrk_amt = siz & (pagesz - 1);
+      if (sbrk_amt == 0)
+       sbrk_amt = siz;
+      else
+       sbrk_amt = siz + pagesz - sbrk_amt;
+      nblks = 1;
+    }
+
+#ifdef MALLOC_STATS
+  _mstats.nsbrk++;
+  _mstats.tsbrk += sbrk_amt;
+#endif
+
+  mp = (union mhead *) sbrk (sbrk_amt);
+
+  /* Totally out of memory. */
+  if ((long)mp == -1)
+    goto morecore_done;
+
+  memtop += sbrk_amt;
+
+  /* shouldn't happen, but just in case -- require 8-byte alignment */
+  if ((long)mp & MALIGN_MASK)
+    {
+      mp = (union mhead *) (((long)mp + MALIGN_MASK) & ~MALIGN_MASK);
+      nblks--;
+    }
+
+  /* save new header and link the nblks blocks together */
+  nextf[nu] = mp;
+  while (1)
+    {
+      mp->mh_alloc = ISFREE;
+      mp->mh_index = nu;
+      if (--nblks <= 0) break;
+      CHAIN (mp) = (union mhead *)((char *)mp + siz);
+      mp = (union mhead *)((char *)mp + siz);
+    }
+  CHAIN (mp) = 0;
+
+morecore_done:
+  if (blocked_sigs)
+    unblock_signals (&set, &oset);
+}
+
+static void
+malloc_debug_dummy ()
+{
+  write (1, "malloc_debug_dummy\n", 19);
+}
+
+#define PREPOP_BIN     2
+#define PREPOP_SIZE    32
+
+static int
+pagealign ()
+{
+  register int nunits;
+  register union mhead *mp;
+  long sbrk_needed;
+  char *curbrk;
+
+  pagesz = getpagesize ();
+  if (pagesz < 1024)
+    pagesz = 1024;
+
+  /* OK, how much do we need to allocate to make things page-aligned?
+     Some of this partial page will be wasted space, but we'll use as
+     much as we can.  Once we figure out how much to advance the break
+     pointer, go ahead and do it. */
+  memtop = curbrk = sbrk (0);
+  sbrk_needed = pagesz - ((long)curbrk & (pagesz - 1));        /* sbrk(0) % pagesz */
+  if (sbrk_needed < 0)
+    sbrk_needed += pagesz;
+
+  /* Now allocate the wasted space. */
+  if (sbrk_needed)
+    {
+#ifdef MALLOC_STATS
+      _mstats.nsbrk++;
+      _mstats.tsbrk += sbrk_needed;
+#endif
+      curbrk = sbrk (sbrk_needed);
+      if ((long)curbrk == -1)
+       return -1;
+      memtop += sbrk_needed;
+
+      /* Take the memory which would otherwise be wasted and populate the most
+        popular bin (2 == 32 bytes) with it.  Add whatever we need to curbrk
+        to make things 32-byte aligned, compute how many 32-byte chunks we're
+        going to get, and set up the bin. */
+      curbrk += sbrk_needed & (PREPOP_SIZE - 1);
+      sbrk_needed -= sbrk_needed & (PREPOP_SIZE - 1);
+      nunits = sbrk_needed / PREPOP_SIZE;
+
+      if (nunits > 0)
+       {
+         mp = (union mhead *)curbrk;
+
+         nextf[PREPOP_BIN] = mp;
+         while (1)
+           {
+             mp->mh_alloc = ISFREE;
+             mp->mh_index = PREPOP_BIN;
+             if (--nunits <= 0) break;
+             CHAIN(mp) = (union mhead *)((char *)mp + PREPOP_SIZE);
+             mp = (union mhead *)((char *)mp + PREPOP_SIZE);
+           }
+         CHAIN(mp) = 0;
+       }
+    }
+
+  /* compute which bin corresponds to the page size. */
+  for (nunits = 7; nunits < NBUCKETS; nunits++)
+    if (pagesz <= binsize(nunits))
+      break;
+  pagebucket = nunits;
+
+  return 0;
+}
+    
+static PTR_T
+internal_malloc (n, file, line, flags)         /* get a block */
+     size_t n;
+     const char *file;
+     int line, flags;
+{
+  register union mhead *p;
+  register int nunits;
+  register char *m, *z;
+  long nbytes;
+  mguard_t mg;
+
+  /* Get the system page size and align break pointer so future sbrks will
+     be page-aligned.  The page size must be at least 1K -- anything
+     smaller is increased. */
+  if (pagesz == 0)
+    if (pagealign () < 0)
+      return ((PTR_T)NULL);
+  /* Figure out how many bytes are required, rounding up to the nearest
+     multiple of 8, then figure out which nextf[] area to use.  Try to
+     be smart about where to start searching -- if the number of bytes
+     needed is greater than the page size, we can start at pagebucket. */
+  nbytes = ALLOCATED_BYTES(n);
+  nunits = (nbytes <= (pagesz >> 1)) ? STARTBUCK : pagebucket;
+  for ( ; nunits < NBUCKETS; nunits++)
+    if (nbytes <= binsize(nunits))
+      break;
+
+  /* Silently reject too-large requests. */
+  if (nunits >= NBUCKETS)
+    return ((PTR_T) NULL);
+
+  /* In case this is reentrant use of malloc from signal handler,
+     pick a block size that no other malloc level is currently
+     trying to allocate.  That's the easiest harmless way not to
+     interfere with the other level of execution.  */
+#ifdef MALLOC_STATS
+  if (busy[nunits]) _mstats.nrecurse++;
+#endif
+  while (busy[nunits]) nunits++;
+  busy[nunits] = 1;
+
+  if (nunits > maxbuck)
+    maxbuck = nunits;
+
+  /* If there are no blocks of the appropriate size, go get some */
+  if (nextf[nunits] == 0)
+    morecore (nunits);
+
+  /* Get one block off the list, and set the new list head */
+  if ((p = nextf[nunits]) == NULL)
+    {
+      busy[nunits] = 0;
+      return NULL;
+    }
+  nextf[nunits] = CHAIN (p);
+  busy[nunits] = 0;
+
+  /* Check for free block clobbered */
+  /* If not for this check, we would gobble a clobbered free chain ptr
+     and bomb out on the NEXT allocate of this size block */
+  if (p->mh_alloc != ISFREE || p->mh_index != nunits)
+    xbotch ((PTR_T)(p+1), 0, _("malloc: block on free list clobbered"), file, line);
+
+  /* Fill in the info, and set up the magic numbers for range checking. */
+  p->mh_alloc = ISALLOC;
+  p->mh_magic2 = MAGIC2;
+  p->mh_nbytes = n;
+
+  /* End guard */
+  mg.i = n;
+  z = mg.s;
+  m = (char *) (p + 1) + n;
+  *m++ = *z++, *m++ = *z++, *m++ = *z++, *m++ = *z++;
+
+#ifdef MEMSCRAMBLE
+  if (n)
+    MALLOC_MEMSET ((char *)(p + 1), 0xdf, n);  /* scramble previous contents */
+#endif
+#ifdef MALLOC_STATS
+  _mstats.nmalloc[nunits]++;
+  _mstats.tmalloc[nunits]++;
+  _mstats.nmal++;
+  _mstats.bytesreq += n;
+#endif /* MALLOC_STATS */
+
+#ifdef MALLOC_TRACE
+  if (malloc_trace && (flags & MALLOC_NOTRACE) == 0)
+    mtrace_alloc ("malloc", p + 1, n, file, line);
+  else if (_malloc_trace_buckets[nunits])
+    mtrace_alloc ("malloc", p + 1, n, file, line);
+#endif
+
+#ifdef MALLOC_REGISTER
+  if (malloc_register && (flags & MALLOC_NOREG) == 0)
+    mregister_alloc ("malloc", p + 1, n, file, line);
+#endif
+
+#ifdef MALLOC_WATCH
+  if (_malloc_nwatch > 0)
+    _malloc_ckwatch (p + 1, file, line, W_ALLOC, n);
+#endif
+
+  return (PTR_T) (p + 1);
+}
+
+static void
+internal_free (mem, file, line, flags)
+     PTR_T mem;
+     const char *file;
+     int line, flags;
+{
+  register union mhead *p;
+  register char *ap, *z;
+  register int nunits;
+  register unsigned int nbytes;
+  int ubytes;          /* caller-requested size */
+  mguard_t mg;
+
+  if ((ap = (char *)mem) == 0)
+    return;
+
+  p = (union mhead *) ap - 1;
+
+  if (p->mh_alloc == ISMEMALIGN)
+    {
+      ap -= p->mh_nbytes;
+      p = (union mhead *) ap - 1;
+    }
+
+#if defined (MALLOC_TRACE) || defined (MALLOC_REGISTER)
+  if (malloc_trace || malloc_register)
+    ubytes = p->mh_nbytes;
+#endif
+
+  if (p->mh_alloc != ISALLOC)
+    {
+      if (p->mh_alloc == ISFREE)
+       xbotch (mem, ERR_DUPFREE,
+               _("free: called with already freed block argument"), file, line);
+      else
+       xbotch (mem, ERR_UNALLOC,
+               _("free: called with unallocated block argument"), file, line);
+    }
+
+  ASSERT (p->mh_magic2 == MAGIC2);
+
+  nunits = p->mh_index;
+  nbytes = ALLOCATED_BYTES(p->mh_nbytes);
+  /* Since the sizeof(u_bits32_t) bytes before the memory handed to the user
+     are now used for the number of bytes allocated, a simple check of
+     mh_magic2 is no longer sufficient to catch things like p[-1] = 'x'.
+     We sanity-check the value of mh_nbytes against the size of the blocks
+     in the appropriate bucket before we use it.  This can still cause problems
+     and obscure errors if mh_nbytes is wrong but still within range; the
+     checks against the size recorded at the end of the chunk will probably
+     fail then.  Using MALLOC_REGISTER will help here, since it saves the
+     original number of bytes requested. */
+
+  if (IN_BUCKET(nbytes, nunits) == 0)
+    xbotch (mem, ERR_UNDERFLOW,
+           _("free: underflow detected; mh_nbytes out of range"), file, line);
+
+  ap += p->mh_nbytes;
+  z = mg.s;
+  *z++ = *ap++, *z++ = *ap++, *z++ = *ap++, *z++ = *ap++;  
+  if (mg.i != p->mh_nbytes)
+    xbotch (mem, ERR_ASSERT_FAILED, _("free: start and end chunk sizes differ"), file, line);
+
+#if 1
+  if (nunits >= LESSCORE_MIN && ((char *)p + binsize(nunits) == memtop))
+#else
+  if (((char *)p + binsize(nunits) == memtop) && nunits >= LESSCORE_MIN)
+#endif
+    {
+      /* If above LESSCORE_FRC, give back unconditionally.  This should be set
+        high enough to be infrequently encountered.  If between LESSCORE_MIN
+        and LESSCORE_FRC, call lesscore if the bucket is marked as busy (in
+        which case we would punt below and leak memory) or if there's already
+        a block on the free list. */
+      if ((nunits >= LESSCORE_FRC) || busy[nunits] || nextf[nunits] != 0)
+       {
+         lesscore (nunits);
+         /* keeps the tracing and registering code in one place */
+         goto free_return;
+       }
+    }
+
+#ifdef MEMSCRAMBLE
+  if (p->mh_nbytes)
+    MALLOC_MEMSET (mem, 0xcf, p->mh_nbytes);
+#endif
+
+  ASSERT (nunits < NBUCKETS);
+  p->mh_alloc = ISFREE;
+
+  if (busy[nunits] == 1)
+    return;    /* this is bogus, but at least it won't corrupt the chains */
+
+  /* Protect against signal handlers calling malloc.  */
+  busy[nunits] = 1;
+  /* Put this block on the free list.  */
+  CHAIN (p) = nextf[nunits];
+  nextf[nunits] = p;
+  busy[nunits] = 0;
+
+free_return:
+  ;            /* Empty statement in case this is the end of the function */
+
+#ifdef MALLOC_STATS
+  _mstats.nmalloc[nunits]--;
+  _mstats.nfre++;
+#endif /* MALLOC_STATS */
+
+#ifdef MALLOC_TRACE
+  if (malloc_trace && (flags & MALLOC_NOTRACE) == 0)
+    mtrace_free (mem, ubytes, file, line);
+  else if (_malloc_trace_buckets[nunits])
+    mtrace_free (mem, ubytes, file, line);
+#endif
+
+#ifdef MALLOC_REGISTER
+  if (malloc_register && (flags & MALLOC_NOREG) == 0)
+    mregister_free (mem, ubytes, file, line);
+#endif
+
+#ifdef MALLOC_WATCH
+  if (_malloc_nwatch > 0)
+    _malloc_ckwatch (mem, file, line, W_FREE, ubytes);
+#endif
+}
+
+static PTR_T
+internal_realloc (mem, n, file, line, flags)
+     PTR_T mem;
+     register size_t n;
+     const char *file;
+     int line, flags;
+{
+  register union mhead *p;
+  register u_bits32_t tocopy;
+  register unsigned int nbytes;
+  register int nunits;
+  register char *m, *z;
+  mguard_t mg;
+
+#ifdef MALLOC_STATS
+  _mstats.nrealloc++;
+#endif
+
+  if (n == 0)
+    {
+      internal_free (mem, file, line, MALLOC_INTERNAL);
+      return (NULL);
+    }
+  if ((p = (union mhead *) mem) == 0)
+    return internal_malloc (n, file, line, MALLOC_INTERNAL);
+
+  p--;
+  nunits = p->mh_index;
+  ASSERT (nunits < NBUCKETS);
+
+  if (p->mh_alloc != ISALLOC)
+    xbotch (mem, ERR_UNALLOC,
+           _("realloc: called with unallocated block argument"), file, line);
+
+  ASSERT (p->mh_magic2 == MAGIC2);
+  nbytes = ALLOCATED_BYTES(p->mh_nbytes);
+  /* Since the sizeof(u_bits32_t) bytes before the memory handed to the user
+     are now used for the number of bytes allocated, a simple check of
+     mh_magic2 is no longer sufficient to catch things like p[-1] = 'x'.
+     We sanity-check the value of mh_nbytes against the size of the blocks
+     in the appropriate bucket before we use it.  This can still cause problems
+     and obscure errors if mh_nbytes is wrong but still within range; the
+     checks against the size recorded at the end of the chunk will probably
+     fail then.  Using MALLOC_REGISTER will help here, since it saves the
+     original number of bytes requested. */
+  if (IN_BUCKET(nbytes, nunits) == 0)
+    xbotch (mem, ERR_UNDERFLOW,
+           _("realloc: underflow detected; mh_nbytes out of range"), file, line);
+
+  m = (char *)mem + (tocopy = p->mh_nbytes);
+  z = mg.s;
+  *z++ = *m++, *z++ = *m++, *z++ = *m++, *z++ = *m++;
+  if (mg.i != p->mh_nbytes)
+    xbotch (mem, ERR_ASSERT_FAILED, _("realloc: start and end chunk sizes differ"), file, line);
+
+#ifdef MALLOC_WATCH
+  if (_malloc_nwatch > 0)
+    _malloc_ckwatch (p + 1, file, line, W_REALLOC, n);
+#endif
+#ifdef MALLOC_STATS
+  _mstats.bytesreq += (n < tocopy) ? 0 : n - tocopy;
+#endif
+
+  /* See if desired size rounds to same power of 2 as actual size. */
+  nbytes = ALLOCATED_BYTES(n);
+
+  /* If ok, use the same block, just marking its size as changed.  */
+  if (RIGHT_BUCKET(nbytes, nunits))
+    {
+#if 0
+      m = (char *)mem + p->mh_nbytes;
+#else
+      /* Compensate for increment above. */
+      m -= 4;
+#endif
+      *m++ = 0;  *m++ = 0;  *m++ = 0;  *m++ = 0;
+      m = (char *)mem + (p->mh_nbytes = n);
+
+      mg.i = n;
+      z = mg.s;
+      *m++ = *z++, *m++ = *z++, *m++ = *z++, *m++ = *z++;      
+
+      return mem;
+    }
+
+  if (n < tocopy)
+    tocopy = n;
+
+#ifdef MALLOC_STATS
+  _mstats.nrcopy++;
+#endif
+
+  if ((m = internal_malloc (n, file, line, MALLOC_INTERNAL|MALLOC_NOTRACE|MALLOC_NOREG)) == 0)
+    return 0;
+  FASTCOPY (mem, m, tocopy);
+  internal_free (mem, file, line, MALLOC_INTERNAL);
+
+#ifdef MALLOC_TRACE
+  if (malloc_trace && (flags & MALLOC_NOTRACE) == 0)
+    mtrace_alloc ("realloc", m, n, file, line);
+  else if (_malloc_trace_buckets[nunits])
+    mtrace_alloc ("realloc", m, n, file, line);
+#endif
+
+#ifdef MALLOC_REGISTER
+  if (malloc_register && (flags & MALLOC_NOREG) == 0)
+    mregister_alloc ("realloc", m, n, file, line);
+#endif
+
+#ifdef MALLOC_WATCH
+  if (_malloc_nwatch > 0)
+    _malloc_ckwatch (m, file, line, W_RESIZED, n);
+#endif
+
+  return m;
+}
+
+static PTR_T
+internal_memalign (alignment, size, file, line, flags)
+     unsigned int alignment;
+     size_t size;
+     const char *file;
+     int line, flags;
+{
+  register char *ptr;
+  register char *aligned;
+  register union mhead *p;
+
+  ptr = internal_malloc (size + alignment, file, line, MALLOC_INTERNAL);
+
+  if (ptr == 0)
+    return 0;
+  /* If entire block has the desired alignment, just accept it.  */
+  if (((long) ptr & (alignment - 1)) == 0)
+    return ptr;
+  /* Otherwise, get address of byte in the block that has that alignment.  */
+#if 0
+  aligned = (char *) (((long) ptr + alignment - 1) & -alignment);
+#else
+  aligned = (char *) (((long) ptr + alignment - 1) & (~alignment + 1));
+#endif
+
+  /* Store a suitable indication of how to free the block,
+     so that free can find the true beginning of it.  */
+  p = (union mhead *) aligned - 1;
+  p->mh_nbytes = aligned - ptr;
+  p->mh_alloc = ISMEMALIGN;
+
+  return aligned;
+}
+
+#if !defined (NO_VALLOC)
+/* This runs into trouble with getpagesize on HPUX, and Multimax machines.
+   Patching out seems cleaner than the ugly fix needed.  */
+static PTR_T
+internal_valloc (size, file, line, flags)
+     size_t size;
+     const char *file;
+     int line, flags;
+{
+  return internal_memalign (getpagesize (), size, file, line, flags|MALLOC_INTERNAL);
+}
+#endif /* !NO_VALLOC */
+
+#ifndef NO_CALLOC
+static PTR_T
+internal_calloc (n, s, file, line, flags)
+     size_t n, s;
+     const char *file;
+     int line, flags;
+{
+  size_t total;
+  PTR_T result;
+
+  total = n * s;
+  result = internal_malloc (total, file, line, flags|MALLOC_INTERNAL);
+  if (result)
+    memset (result, 0, total);
+  return result;  
+}
+
+static void
+internal_cfree (p, file, line, flags)
+     PTR_T p;
+     const char *file;
+     int line, flags;
+{
+  internal_free (p, file, line, flags|MALLOC_INTERNAL);
+}
+#endif /* !NO_CALLOC */
+
+#ifdef MALLOC_STATS
+int
+malloc_free_blocks (size)
+     int size;
+{
+  int nfree;
+  register union mhead *p;
+
+  nfree = 0;
+  for (p = nextf[size]; p; p = CHAIN (p))
+    nfree++;
+
+  return nfree;
+}
+#endif
+
+#if defined (MALLOC_WRAPFUNCS)
+PTR_T
+sh_malloc (bytes, file, line)
+     size_t bytes;
+     const char *file;
+     int line;
+{
+  return internal_malloc (bytes, file, line, MALLOC_WRAPPER);
+}
+
+PTR_T
+sh_realloc (ptr, size, file, line)
+     PTR_T ptr;
+     size_t size;
+     const char *file;
+     int line;
+{
+  return internal_realloc (ptr, size, file, line, MALLOC_WRAPPER);
+}
+
+void
+sh_free (mem, file, line)
+     PTR_T mem;
+     const char *file;
+     int line;
+{
+  internal_free (mem, file, line, MALLOC_WRAPPER);
+}
+
+PTR_T
+sh_memalign (alignment, size, file, line)
+     unsigned int alignment;
+     size_t size;
+     const char *file;
+     int line;
+{
+  return internal_memalign (alignment, size, file, line, MALLOC_WRAPPER);
+}
+
+#ifndef NO_CALLOC
+PTR_T
+sh_calloc (n, s, file, line)
+     size_t n, s;
+     const char *file;
+     int line;
+{
+  return internal_calloc (n, s, file, line, MALLOC_WRAPPER);
+}
+
+void
+sh_cfree (mem, file, line)
+     PTR_T mem;
+     const char *file;
+     int line;
+{
+  internal_cfree (mem, file, line, MALLOC_WRAPPER);
+}
+#endif
+
+#ifndef NO_VALLOC
+PTR_T
+sh_valloc (size, file, line)
+     size_t size;
+     const char *file;
+     int line;
+{
+  return internal_valloc (size, file, line, MALLOC_WRAPPER);
+}
+#endif /* !NO_VALLOC */
+
+#endif /* MALLOC_WRAPFUNCS */
+
+/* Externally-available functions that call their internal counterparts. */
+
+PTR_T
+malloc (size)
+     size_t size;
+{
+  return internal_malloc (size, (char *)NULL, 0, 0);
+}
+
+PTR_T
+realloc (mem, nbytes)
+     PTR_T mem;
+     size_t nbytes;
+{
+  return internal_realloc (mem, nbytes, (char *)NULL, 0, 0);
+}
+
+void
+free (mem)
+     PTR_T mem;
+{
+  internal_free (mem,  (char *)NULL, 0, 0);
+}
+
+PTR_T
+memalign (alignment, size)
+     unsigned int alignment;
+     size_t size;
+{
+  return internal_memalign (alignment, size, (char *)NULL, 0, 0);
+}
+
+#ifndef NO_VALLOC
+PTR_T
+valloc (size)
+     size_t size;
+{
+  return internal_valloc (size, (char *)NULL, 0, 0);
+}
+#endif
+
+#ifndef NO_CALLOC
+PTR_T
+calloc (n, s)
+     size_t n, s;
+{
+  return internal_calloc (n, s, (char *)NULL, 0, 0);
+}
+
+void
+cfree (mem)
+     PTR_T mem;
+{
+  internal_cfree (mem, (char *)NULL, 0, 0);
+}
+#endif
index 812bb419309997717de0fe8d0c4f6b213d62bbf2..e51e92bed24cff1f9bdea0d6e86381a49fb5bf72 100644 (file)
@@ -43,7 +43,7 @@ extern PTR_T sh_malloc __P((size_t, const char *, int));
 extern PTR_T sh_realloc __P((PTR_T, size_t, const char *, int));
 extern void sh_free __P((PTR_T, const char *, int));
 
-extern PTR_T sh_memalign __P((unsigned int, size_t, const char *, int));
+extern PTR_T sh_memalign __P((size_t, size_t, const char *, int));
 
 extern PTR_T sh_calloc __P((size_t, size_t, const char *, int));
 extern void sh_cfree __P((PTR_T, const char *, int));
diff --git a/lib/malloc/shmalloc.h~ b/lib/malloc/shmalloc.h~
new file mode 100644 (file)
index 0000000..812bb41
--- /dev/null
@@ -0,0 +1,68 @@
+/* Functions (currently) for use by the shell to do malloc debugging and
+   tracking. */
+/* Copyright (C) 2001-2003 Free Software Foundation, Inc.
+
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program; if not, write to the Free Software
+Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA.  */
+
+#ifndef _SH_MALLOC_H
+#define _SH_MALLOC_H
+
+#ifndef __P
+#  if defined (__STDC__) || defined (__GNUC__) || defined (__cplusplus)
+#    define __P(protos) protos
+#  else
+#    define __P(protos) ()
+#  endif
+#endif
+
+/* Generic pointer type. */
+#ifndef PTR_T
+
+#if defined (__STDC__)
+#  define PTR_T void *
+#else
+#  define PTR_T char *
+#endif
+
+#endif /* PTR_T */
+
+
+extern PTR_T sh_malloc __P((size_t, const char *, int));
+extern PTR_T sh_realloc __P((PTR_T, size_t, const char *, int));
+extern void sh_free __P((PTR_T, const char *, int));
+
+extern PTR_T sh_memalign __P((unsigned int, size_t, const char *, int));
+
+extern PTR_T sh_calloc __P((size_t, size_t, const char *, int));
+extern void sh_cfree __P((PTR_T, const char *, int));
+
+extern PTR_T sh_valloc __P((size_t, const char *, int));
+
+/* trace.c */
+extern int malloc_set_trace __P((int));
+extern void malloc_set_tracefp ();     /* full prototype requires stdio.h */
+extern void malloc_set_tracefn __P((char *, char *));
+
+/* table.c */
+extern void mregister_dump_table __P((void));
+extern void mregister_table_init __P((void));
+extern int malloc_set_register __P((int));
+
+/* stats.c */
+extern void print_malloc_stats __P((char *));
+extern void fprint_malloc_stats ();    /* full prototype requires stdio.h */
+extern void trace_malloc_stats __P((char *, char *));
+
+#endif
index 2badaa140b1bda8e96c4612ea85ddc1dd47c0365..de723a1d3d8dbf6aa6989da87993306f8e762810 100644 (file)
@@ -692,7 +692,7 @@ _rl_vi_change_mbchar_case (count)
 {
   wchar_t wc;
   char mb[MB_LEN_MAX+1];
-  int mblen;
+  int mblen, p;
   mbstate_t ps;
 
   memset (&ps, 0, sizeof (mbstate_t));
@@ -715,11 +715,14 @@ _rl_vi_change_mbchar_case (count)
       /* Vi is kind of strange here. */
       if (wc)
        {
+         p = rl_point;
          mblen = wcrtomb (mb, wc, &ps);
          if (mblen >= 0)
            mb[mblen] = '\0';
          rl_begin_undo_group ();
-         rl_delete (1, 0);
+         rl_vi_delete (1, 0);
+         if (rl_point < p)     /* Did we retreat at EOL? */
+           rl_point++; /* XXX - should we advance more than 1 for mbchar? */
          rl_insert_text (mb);
          rl_end_undo_group ();
          rl_vi_check ();
index 2badaa140b1bda8e96c4612ea85ddc1dd47c0365..797aa499db9db84a92f6911afee4f20754fb2784 100644 (file)
@@ -692,7 +692,7 @@ _rl_vi_change_mbchar_case (count)
 {
   wchar_t wc;
   char mb[MB_LEN_MAX+1];
-  int mblen;
+  int mblen, p;
   mbstate_t ps;
 
   memset (&ps, 0, sizeof (mbstate_t));
@@ -715,11 +715,14 @@ _rl_vi_change_mbchar_case (count)
       /* Vi is kind of strange here. */
       if (wc)
        {
+         p = rl_point;
          mblen = wcrtomb (mb, wc, &ps);
          if (mblen >= 0)
            mb[mblen] = '\0';
          rl_begin_undo_group ();
-         rl_delete (1, 0);
+         rl_vi_delete (1, 0);
+         if (rl_point < p)     /* Did we retreat at EOL? */
+           rl_point++;
          rl_insert_text (mb);
          rl_end_undo_group ();
          rl_vi_check ();
index 4cb542f5b4bf3efa9fb8893c282d46d2c8b6b115..451d0569f092ec11e054662324f636031499afea 100644 (file)
 
 #undef strchr  /* avoid AIX weirdness */
 
+#if defined (SHELL)
+extern char *get_string_value (const char *);
+#endif
+
 extern void tzset(void);
 static int weeknumber(const struct tm *timeptr, int firstweekday);
 static int iso8601wknum(const struct tm *timeptr);
@@ -98,8 +102,12 @@ extern int daylight;
 #if defined(SOLARIS) || defined(mips) || defined (M_UNIX)
 extern long int timezone, altzone;
 #else
+#  if defined (HPUX)
+extern long int timezone;
+#  else
 extern int timezone, altzone;
-#endif
+#  endif /* !HPUX */
+#endif /* !SOLARIS && !mips && !M_UNIX */
 #endif
 
 #undef min     /* just in case */
@@ -480,8 +488,13 @@ strftime(char *s, size_t maxsize, const char *format, const struct tm *timeptr)
                         * Systems with tzname[] probably have timezone as
                         * secs west of GMT.  Convert to mins east of GMT.
                         */
+#  ifdef HPUX
+                       off = -timezone / 60;
+#  else
                        off = -(daylight ? timezone : altzone) / 60;
+#  endif /* !HPUX */
 #else /* !HAVE_TZNAME */
+                       gettimeofday(& tv, & zone);
                        off = -zone.tz_minuteswest;
 #endif /* !HAVE_TZNAME */
 #endif /* !HAVE_TM_ZONE */
diff --git a/lib/sh/strftime.c~ b/lib/sh/strftime.c~
new file mode 100644 (file)
index 0000000..8ea2087
--- /dev/null
@@ -0,0 +1,868 @@
+/*
+ * Modified slightly by Chet Ramey for inclusion in Bash
+ */
+
+/*
+ * strftime.c
+ *
+ * Public-domain implementation of ISO C library routine.
+ *
+ * If you can't do prototypes, get GCC.
+ *
+ * The C99 standard now specifies just about all of the formats
+ * that were additional in the earlier versions of this file.
+ *
+ * For extensions from SunOS, add SUNOS_EXT.
+ * For extensions from HP/UX, add HPUX_EXT.
+ * For VMS dates, add VMS_EXT.
+ * For complete POSIX semantics, add POSIX_SEMANTICS.
+ *
+ * The code for %c, %x, and %X follows the C99 specification for
+ * the "C" locale.
+ *
+ * This version ignores LOCALE information.
+ * It also doesn't worry about multi-byte characters.
+ * So there.
+ *
+ * This file is also shipped with GAWK (GNU Awk), gawk specific bits of
+ * code are included if GAWK is defined.
+ *
+ * Arnold Robbins
+ * January, February, March, 1991
+ * Updated March, April 1992
+ * Updated April, 1993
+ * Updated February, 1994
+ * Updated May, 1994
+ * Updated January, 1995
+ * Updated September, 1995
+ * Updated January, 1996
+ * Updated July, 1997
+ * Updated October, 1999
+ * Updated September, 2000
+ *
+ * Fixes from ado@elsie.nci.nih.gov,
+ * February 1991, May 1992
+ * Fixes from Tor Lillqvist tml@tik.vtt.fi,
+ * May 1993
+ * Further fixes from ado@elsie.nci.nih.gov,
+ * February 1994
+ * %z code from chip@chinacat.unicom.com,
+ * Applied September 1995
+ * %V code fixed (again) and %G, %g added,
+ * January 1996
+ * %v code fixed, better configuration,
+ * July 1997
+ * Moved to C99 specification.
+ * September 2000
+ */
+#include <config.h>
+
+#ifndef GAWK
+#include <stdio.h>
+#include <ctype.h>
+#include <time.h>
+#endif
+#if defined(TM_IN_SYS_TIME)
+#include <sys/types.h>
+#include <sys/time.h>
+#endif
+
+#include <stdlib.h>
+#include <string.h>
+
+/* defaults: season to taste */
+#define SUNOS_EXT      1       /* stuff in SunOS strftime routine */
+#define VMS_EXT                1       /* include %v for VMS date format */
+#define HPUX_EXT       1       /* non-conflicting stuff in HP-UX date */
+#ifndef GAWK
+#define POSIX_SEMANTICS        1       /* call tzset() if TZ changes */
+#endif
+
+#undef strchr  /* avoid AIX weirdness */
+
+extern void tzset(void);
+static int weeknumber(const struct tm *timeptr, int firstweekday);
+static int iso8601wknum(const struct tm *timeptr);
+
+#ifdef __GNUC__
+#define inline __inline__
+#else
+#define inline /**/
+#endif
+
+#define range(low, item, hi)   max(low, min(item, hi))
+
+#if !defined(OS2) && !defined(MSDOS) && defined(HAVE_TZNAME)
+extern char *tzname[2];
+extern int daylight;
+#if defined(SOLARIS) || defined(mips) || defined (M_UNIX)
+extern long int timezone, altzone;
+#else
+#  if defined (HPUX)
+extern long int timezone;
+#  else
+extern int timezone, altzone;
+#  endif /* !HPUX */
+#endif /* !SOLARIS && !mips && !M_UNIX */
+#endif
+
+#undef min     /* just in case */
+
+/* min --- return minimum of two numbers */
+
+static inline int
+min(int a, int b)
+{
+       return (a < b ? a : b);
+}
+
+#undef max     /* also, just in case */
+
+/* max --- return maximum of two numbers */
+
+static inline int
+max(int a, int b)
+{
+       return (a > b ? a : b);
+}
+
+/* strftime --- produce formatted time */
+
+size_t
+strftime(char *s, size_t maxsize, const char *format, const struct tm *timeptr)
+{
+       char *endp = s + maxsize;
+       char *start = s;
+       auto char tbuf[100];
+       long off;
+       int i, w, y;
+       static short first = 1;
+#ifdef POSIX_SEMANTICS
+       static char *savetz = NULL;
+       static int savetzlen = 0;
+       char *tz;
+#endif /* POSIX_SEMANTICS */
+#ifndef HAVE_TM_ZONE
+#ifndef HAVE_TM_NAME
+#ifndef HAVE_TZNAME
+       extern char *timezone();
+       struct timeval tv;
+       struct timezone zone;
+#endif /* HAVE_TZNAME */
+#endif /* HAVE_TM_NAME */
+#endif /* HAVE_TM_ZONE */
+
+       /* various tables, useful in North America */
+       static const char *days_a[] = {
+               "Sun", "Mon", "Tue", "Wed",
+               "Thu", "Fri", "Sat",
+       };
+       static const char *days_l[] = {
+               "Sunday", "Monday", "Tuesday", "Wednesday",
+               "Thursday", "Friday", "Saturday",
+       };
+       static const char *months_a[] = {
+               "Jan", "Feb", "Mar", "Apr", "May", "Jun",
+               "Jul", "Aug", "Sep", "Oct", "Nov", "Dec",
+       };
+       static const char *months_l[] = {
+               "January", "February", "March", "April",
+               "May", "June", "July", "August", "September",
+               "October", "November", "December",
+       };
+       static const char *ampm[] = { "AM", "PM", };
+
+       if (s == NULL || format == NULL || timeptr == NULL || maxsize == 0)
+               return 0;
+
+       /* quick check if we even need to bother */
+       if (strchr(format, '%') == NULL && strlen(format) + 1 >= maxsize)
+               return 0;
+
+#ifndef POSIX_SEMANTICS
+       if (first) {
+               tzset();
+               first = 0;
+       }
+#else  /* POSIX_SEMANTICS */
+#if defined (SHELL)
+       tz = get_string_value ("TZ");
+#else
+       tz = getenv("TZ");
+#endif
+       if (first) {
+               if (tz != NULL) {
+                       int tzlen = strlen(tz);
+
+                       savetz = (char *) malloc(tzlen + 1);
+                       if (savetz != NULL) {
+                               savetzlen = tzlen + 1;
+                               strcpy(savetz, tz);
+                       }
+               }
+               tzset();
+               first = 0;
+       }
+       /* if we have a saved TZ, and it is different, recapture and reset */
+       if (tz && savetz && (tz[0] != savetz[0] || strcmp(tz, savetz) != 0)) {
+               i = strlen(tz) + 1;
+               if (i > savetzlen) {
+                       savetz = (char *) realloc(savetz, i);
+                       if (savetz) {
+                               savetzlen = i;
+                               strcpy(savetz, tz);
+                       }
+               } else
+                       strcpy(savetz, tz);
+               tzset();
+       }
+#endif /* POSIX_SEMANTICS */
+
+       for (; *format && s < endp - 1; format++) {
+               tbuf[0] = '\0';
+               if (*format != '%') {
+                       *s++ = *format;
+                       continue;
+               }
+       again:
+               switch (*++format) {
+               case '\0':
+                       *s++ = '%';
+                       goto out;
+
+               case '%':
+                       *s++ = '%';
+                       continue;
+
+               case 'a':       /* abbreviated weekday name */
+                       if (timeptr->tm_wday < 0 || timeptr->tm_wday > 6)
+                               strcpy(tbuf, "?");
+                       else
+                               strcpy(tbuf, days_a[timeptr->tm_wday]);
+                       break;
+
+               case 'A':       /* full weekday name */
+                       if (timeptr->tm_wday < 0 || timeptr->tm_wday > 6)
+                               strcpy(tbuf, "?");
+                       else
+                               strcpy(tbuf, days_l[timeptr->tm_wday]);
+                       break;
+
+               case 'b':       /* abbreviated month name */
+               short_month:
+                       if (timeptr->tm_mon < 0 || timeptr->tm_mon > 11)
+                               strcpy(tbuf, "?");
+                       else
+                               strcpy(tbuf, months_a[timeptr->tm_mon]);
+                       break;
+
+               case 'B':       /* full month name */
+                       if (timeptr->tm_mon < 0 || timeptr->tm_mon > 11)
+                               strcpy(tbuf, "?");
+                       else
+                               strcpy(tbuf, months_l[timeptr->tm_mon]);
+                       break;
+
+               case 'c':       /* appropriate date and time representation */
+                       /*
+                        * This used to be:
+                        *
+                        * strftime(tbuf, sizeof tbuf, "%a %b %e %H:%M:%S %Y", timeptr);
+                        *
+                        * Now, per the ISO 1999 C standard, it this:
+                        */
+                       strftime(tbuf, sizeof tbuf, "%A %B %d %T %Y", timeptr);
+                       break;
+
+               case 'C':
+               century:
+                       sprintf(tbuf, "%02d", (timeptr->tm_year + 1900) / 100);
+                       break;
+
+               case 'd':       /* day of the month, 01 - 31 */
+                       i = range(1, timeptr->tm_mday, 31);
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 'D':       /* date as %m/%d/%y */
+                       strftime(tbuf, sizeof tbuf, "%m/%d/%y", timeptr);
+                       break;
+
+               case 'e':       /* day of month, blank padded */
+                       sprintf(tbuf, "%2d", range(1, timeptr->tm_mday, 31));
+                       break;
+
+               case 'E':
+                       /* POSIX (now C99) locale extensions, ignored for now */
+                       goto again;
+
+               case 'F':       /* ISO 8601 date representation */
+                       strftime(tbuf, sizeof tbuf, "%Y-%m-%d", timeptr);
+                       break;
+
+               case 'g':
+               case 'G':
+                       /*
+                        * Year of ISO week.
+                        *
+                        * If it's December but the ISO week number is one,
+                        * that week is in next year.
+                        * If it's January but the ISO week number is 52 or
+                        * 53, that week is in last year.
+                        * Otherwise, it's this year.
+                        */
+                       w = iso8601wknum(timeptr);
+                       if (timeptr->tm_mon == 11 && w == 1)
+                               y = 1900 + timeptr->tm_year + 1;
+                       else if (timeptr->tm_mon == 0 && w >= 52)
+                               y = 1900 + timeptr->tm_year - 1;
+                       else
+                               y = 1900 + timeptr->tm_year;
+
+                       if (*format == 'G')
+                               sprintf(tbuf, "%d", y);
+                       else
+                               sprintf(tbuf, "%02d", y % 100);
+                       break;
+
+               case 'h':       /* abbreviated month name */
+                       goto short_month;
+
+               case 'H':       /* hour, 24-hour clock, 00 - 23 */
+                       i = range(0, timeptr->tm_hour, 23);
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 'I':       /* hour, 12-hour clock, 01 - 12 */
+                       i = range(0, timeptr->tm_hour, 23);
+                       if (i == 0)
+                               i = 12;
+                       else if (i > 12)
+                               i -= 12;
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 'j':       /* day of the year, 001 - 366 */
+                       sprintf(tbuf, "%03d", timeptr->tm_yday + 1);
+                       break;
+
+               case 'm':       /* month, 01 - 12 */
+                       i = range(0, timeptr->tm_mon, 11);
+                       sprintf(tbuf, "%02d", i + 1);
+                       break;
+
+               case 'M':       /* minute, 00 - 59 */
+                       i = range(0, timeptr->tm_min, 59);
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 'n':       /* same as \n */
+                       tbuf[0] = '\n';
+                       tbuf[1] = '\0';
+                       break;
+
+               case 'O':
+                       /* POSIX (now C99) locale extensions, ignored for now */
+                       goto again;
+
+               case 'p':       /* am or pm based on 12-hour clock */
+                       i = range(0, timeptr->tm_hour, 23);
+                       if (i < 12)
+                               strcpy(tbuf, ampm[0]);
+                       else
+                               strcpy(tbuf, ampm[1]);
+                       break;
+
+               case 'r':       /* time as %I:%M:%S %p */
+                       strftime(tbuf, sizeof tbuf, "%I:%M:%S %p", timeptr);
+                       break;
+
+               case 'R':       /* time as %H:%M */
+                       strftime(tbuf, sizeof tbuf, "%H:%M", timeptr);
+                       break;
+
+#if defined(HAVE_MKTIME) || defined(GAWK)
+               case 's':       /* time as seconds since the Epoch */
+               {
+                       struct tm non_const_timeptr;
+
+                       non_const_timeptr = *timeptr;
+                       sprintf(tbuf, "%ld", mktime(& non_const_timeptr));
+                       break;
+               }
+#endif /* defined(HAVE_MKTIME) || defined(GAWK) */
+
+               case 'S':       /* second, 00 - 60 */
+                       i = range(0, timeptr->tm_sec, 60);
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 't':       /* same as \t */
+                       tbuf[0] = '\t';
+                       tbuf[1] = '\0';
+                       break;
+
+               case 'T':       /* time as %H:%M:%S */
+               the_time:
+                       strftime(tbuf, sizeof tbuf, "%H:%M:%S", timeptr);
+                       break;
+
+               case 'u':
+               /* ISO 8601: Weekday as a decimal number [1 (Monday) - 7] */
+                       sprintf(tbuf, "%d", timeptr->tm_wday == 0 ? 7 :
+                                       timeptr->tm_wday);
+                       break;
+
+               case 'U':       /* week of year, Sunday is first day of week */
+                       sprintf(tbuf, "%02d", weeknumber(timeptr, 0));
+                       break;
+
+               case 'V':       /* week of year according ISO 8601 */
+                       sprintf(tbuf, "%02d", iso8601wknum(timeptr));
+                       break;
+
+               case 'w':       /* weekday, Sunday == 0, 0 - 6 */
+                       i = range(0, timeptr->tm_wday, 6);
+                       sprintf(tbuf, "%d", i);
+                       break;
+
+               case 'W':       /* week of year, Monday is first day of week */
+                       sprintf(tbuf, "%02d", weeknumber(timeptr, 1));
+                       break;
+
+               case 'x':       /* appropriate date representation */
+                       strftime(tbuf, sizeof tbuf, "%A %B %d %Y", timeptr);
+                       break;
+
+               case 'X':       /* appropriate time representation */
+                       goto the_time;
+                       break;
+
+               case 'y':       /* year without a century, 00 - 99 */
+               year:
+                       i = timeptr->tm_year % 100;
+                       sprintf(tbuf, "%02d", i);
+                       break;
+
+               case 'Y':       /* year with century */
+               fullyear:
+                       sprintf(tbuf, "%d", 1900 + timeptr->tm_year);
+                       break;
+
+               /*
+                * From: Chip Rosenthal <chip@chinacat.unicom.com>
+                * Date: Sun, 19 Mar 1995 00:33:29 -0600 (CST)
+                * 
+                * Warning: the %z [code] is implemented by inspecting the
+                * timezone name conditional compile settings, and
+                * inferring a method to get timezone offsets. I've tried
+                * this code on a couple of machines, but I don't doubt
+                * there is some system out there that won't like it.
+                * Maybe the easiest thing to do would be to bracket this
+                * with an #ifdef that can turn it off. The %z feature
+                * would be an admittedly obscure one that most folks can
+                * live without, but it would be a great help to those of
+                * us that muck around with various message processors.
+                */
+               case 'z':       /* time zone offset east of GMT e.g. -0600 */
+#ifdef HAVE_TM_NAME
+                       /*
+                        * Systems with tm_name probably have tm_tzadj as
+                        * secs west of GMT.  Convert to mins east of GMT.
+                        */
+                       off = -timeptr->tm_tzadj / 60;
+#else /* !HAVE_TM_NAME */
+#ifdef HAVE_TM_ZONE
+                       /*
+                        * Systems with tm_zone probably have tm_gmtoff as
+                        * secs east of GMT.  Convert to mins east of GMT.
+                        */
+                       off = timeptr->tm_gmtoff / 60;
+#else /* !HAVE_TM_ZONE */
+#if HAVE_TZNAME
+                       /*
+                        * Systems with tzname[] probably have timezone as
+                        * secs west of GMT.  Convert to mins east of GMT.
+                        */
+#  ifdef HPUX
+                       off = -timezone / 60;
+#  else
+                       off = -(daylight ? timezone : altzone) / 60;
+#  endif /* !HPUX */
+#else /* !HAVE_TZNAME */
+                       gettimeofday(& tv, & zone);
+                       off = -zone.tz_minuteswest;
+#endif /* !HAVE_TZNAME */
+#endif /* !HAVE_TM_ZONE */
+#endif /* !HAVE_TM_NAME */
+                       if (off < 0) {
+                               tbuf[0] = '-';
+                               off = -off;
+                       } else {
+                               tbuf[0] = '+';
+                       }
+                       sprintf(tbuf+1, "%02d%02d", off/60, off%60);
+                       break;
+
+               case 'Z':       /* time zone name or abbrevation */
+#ifdef HAVE_TZNAME
+                       i = (daylight && timeptr->tm_isdst > 0); /* 0 or 1 */
+                       strcpy(tbuf, tzname[i]);
+#else
+#ifdef HAVE_TM_ZONE
+                       strcpy(tbuf, timeptr->tm_zone);
+#else
+#ifdef HAVE_TM_NAME
+                       strcpy(tbuf, timeptr->tm_name);
+#else
+                       gettimeofday(& tv, & zone);
+                       strcpy(tbuf, timezone(zone.tz_minuteswest,
+                                               timeptr->tm_isdst > 0));
+#endif /* HAVE_TM_NAME */
+#endif /* HAVE_TM_ZONE */
+#endif /* HAVE_TZNAME */
+                       break;
+
+#ifdef SUNOS_EXT
+               case 'k':       /* hour, 24-hour clock, blank pad */
+                       sprintf(tbuf, "%2d", range(0, timeptr->tm_hour, 23));
+                       break;
+
+               case 'l':       /* hour, 12-hour clock, 1 - 12, blank pad */
+                       i = range(0, timeptr->tm_hour, 23);
+                       if (i == 0)
+                               i = 12;
+                       else if (i > 12)
+                               i -= 12;
+                       sprintf(tbuf, "%2d", i);
+                       break;
+#endif
+
+#ifdef HPUX_EXT
+               case 'N':       /* Emperor/Era name */
+                       /* this is essentially the same as the century */
+                       goto century;   /* %C */
+
+               case 'o':       /* Emperor/Era year */
+                       goto year;      /* %y */
+#endif /* HPUX_EXT */
+
+
+#ifdef VMS_EXT
+               case 'v':       /* date as dd-bbb-YYYY */
+                       sprintf(tbuf, "%2d-%3.3s-%4d",
+                               range(1, timeptr->tm_mday, 31),
+                               months_a[range(0, timeptr->tm_mon, 11)],
+                               timeptr->tm_year + 1900);
+                       for (i = 3; i < 6; i++)
+                               if (islower(tbuf[i]))
+                                       tbuf[i] = toupper(tbuf[i]);
+                       break;
+#endif
+
+               default:
+                       tbuf[0] = '%';
+                       tbuf[1] = *format;
+                       tbuf[2] = '\0';
+                       break;
+               }
+               i = strlen(tbuf);
+               if (i) {
+                       if (s + i < endp - 1) {
+                               strcpy(s, tbuf);
+                               s += i;
+                       } else
+                               return 0;
+               }
+       }
+out:
+       if (s < endp && *format == '\0') {
+               *s = '\0';
+               return (s - start);
+       } else
+               return 0;
+}
+
+/* isleap --- is a year a leap year? */
+
+static int
+isleap(int year)
+{
+       return ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0);
+}
+
+
+/* iso8601wknum --- compute week number according to ISO 8601 */
+
+static int
+iso8601wknum(const struct tm *timeptr)
+{
+       /*
+        * From 1003.2:
+        *      If the week (Monday to Sunday) containing January 1
+        *      has four or more days in the new year, then it is week 1;
+        *      otherwise it is the highest numbered week of the previous
+        *      year (52 or 53), and the next week is week 1.
+        *
+        * ADR: This means if Jan 1 was Monday through Thursday,
+        *      it was week 1, otherwise week 52 or 53.
+        *
+        * XPG4 erroneously included POSIX.2 rationale text in the
+        * main body of the standard. Thus it requires week 53.
+        */
+
+       int weeknum, jan1day, diff;
+
+       /* get week number, Monday as first day of the week */
+       weeknum = weeknumber(timeptr, 1);
+
+       /*
+        * With thanks and tip of the hatlo to tml@tik.vtt.fi
+        *
+        * What day of the week does January 1 fall on?
+        * We know that
+        *      (timeptr->tm_yday - jan1.tm_yday) MOD 7 ==
+        *              (timeptr->tm_wday - jan1.tm_wday) MOD 7
+        * and that
+        *      jan1.tm_yday == 0
+        * and that
+        *      timeptr->tm_wday MOD 7 == timeptr->tm_wday
+        * from which it follows that. . .
+        */
+       jan1day = timeptr->tm_wday - (timeptr->tm_yday % 7);
+       if (jan1day < 0)
+               jan1day += 7;
+
+       /*
+        * If Jan 1 was a Monday through Thursday, it was in
+        * week 1.  Otherwise it was last year's highest week, which is
+        * this year's week 0.
+        *
+        * What does that mean?
+        * If Jan 1 was Monday, the week number is exactly right, it can
+        *      never be 0.
+        * If it was Tuesday through Thursday, the weeknumber is one
+        *      less than it should be, so we add one.
+        * Otherwise, Friday, Saturday or Sunday, the week number is
+        * OK, but if it is 0, it needs to be 52 or 53.
+        */
+       switch (jan1day) {
+       case 1:         /* Monday */
+               break;
+       case 2:         /* Tuesday */
+       case 3:         /* Wednesday */
+       case 4:         /* Thursday */
+               weeknum++;
+               break;
+       case 5:         /* Friday */
+       case 6:         /* Saturday */
+       case 0:         /* Sunday */
+               if (weeknum == 0) {
+#ifdef USE_BROKEN_XPG4
+                       /* XPG4 (as of March 1994) says 53 unconditionally */
+                       weeknum = 53;
+#else
+                       /* get week number of last week of last year */
+                       struct tm dec31ly;      /* 12/31 last year */
+                       dec31ly = *timeptr;
+                       dec31ly.tm_year--;
+                       dec31ly.tm_mon = 11;
+                       dec31ly.tm_mday = 31;
+                       dec31ly.tm_wday = (jan1day == 0) ? 6 : jan1day - 1;
+                       dec31ly.tm_yday = 364 + isleap(dec31ly.tm_year + 1900);
+                       weeknum = iso8601wknum(& dec31ly);
+#endif
+               }
+               break;
+       }
+
+       if (timeptr->tm_mon == 11) {
+               /*
+                * The last week of the year
+                * can be in week 1 of next year.
+                * Sigh.
+                *
+                * This can only happen if
+                *      M   T  W
+                *      29  30 31
+                *      30  31
+                *      31
+                */
+               int wday, mday;
+
+               wday = timeptr->tm_wday;
+               mday = timeptr->tm_mday;
+               if (   (wday == 1 && (mday >= 29 && mday <= 31))
+                   || (wday == 2 && (mday == 30 || mday == 31))
+                   || (wday == 3 &&  mday == 31))
+                       weeknum = 1;
+       }
+
+       return weeknum;
+}
+
+/* weeknumber --- figure how many weeks into the year */
+
+/* With thanks and tip of the hatlo to ado@elsie.nci.nih.gov */
+
+static int
+weeknumber(const struct tm *timeptr, int firstweekday)
+{
+       int wday = timeptr->tm_wday;
+       int ret;
+
+       if (firstweekday == 1) {
+               if (wday == 0)  /* sunday */
+                       wday = 6;
+               else
+                       wday--;
+       }
+       ret = ((timeptr->tm_yday + 7 - wday) / 7);
+       if (ret < 0)
+               ret = 0;
+       return ret;
+}
+
+#if 0
+/* ADR --- I'm loathe to mess with ado's code ... */
+
+Date:         Wed, 24 Apr 91 20:54:08 MDT
+From: Michal Jaegermann <audfax!emory!vm.ucs.UAlberta.CA!NTOMCZAK>
+To: arnold@audiofax.com
+
+Hi Arnold,
+in a process of fixing of strftime() in libraries on Atari ST I grabbed
+some pieces of code from your own strftime.  When doing that it came
+to mind that your weeknumber() function compiles a little bit nicer
+in the following form:
+/*
+ * firstweekday is 0 if starting in Sunday, non-zero if in Monday
+ */
+{
+    return (timeptr->tm_yday - timeptr->tm_wday +
+           (firstweekday ? (timeptr->tm_wday ? 8 : 1) : 7)) / 7;
+}
+How nicer it depends on a compiler, of course, but always a tiny bit.
+
+   Cheers,
+   Michal
+   ntomczak@vm.ucs.ualberta.ca
+#endif
+
+#ifdef TEST_STRFTIME
+
+/*
+ * NAME:
+ *     tst
+ *
+ * SYNOPSIS:
+ *     tst
+ *
+ * DESCRIPTION:
+ *     "tst" is a test driver for the function "strftime".
+ *
+ * OPTIONS:
+ *     None.
+ *
+ * AUTHOR:
+ *     Karl Vogel
+ *     Control Data Systems, Inc.
+ *     vogelke@c-17igp.wpafb.af.mil
+ *
+ * BUGS:
+ *     None noticed yet.
+ *
+ * COMPILE:
+ *     cc -o tst -DTEST_STRFTIME strftime.c
+ */
+
+/* ADR: I reformatted this to my liking, and deleted some unneeded code. */
+
+#ifndef NULL
+#include       <stdio.h>
+#endif
+#include       <sys/time.h>
+#include       <string.h>
+
+#define                MAXTIME         132
+
+/*
+ * Array of time formats.
+ */
+
+static char *array[] =
+{
+       "(%%A)      full weekday name, var length (Sunday..Saturday)  %A",
+       "(%%B)       full month name, var length (January..December)  %B",
+       "(%%C)                                               Century  %C",
+       "(%%D)                                       date (%%m/%%d/%%y)  %D",
+       "(%%E)                           Locale extensions (ignored)  %E",
+       "(%%F)       full month name, var length (January..December)  %F",
+       "(%%H)                          hour (24-hour clock, 00..23)  %H",
+       "(%%I)                          hour (12-hour clock, 01..12)  %I",
+       "(%%M)                                       minute (00..59)  %M",
+       "(%%N)                                      Emporer/Era Name  %N",
+       "(%%O)                           Locale extensions (ignored)  %O",
+       "(%%R)                                 time, 24-hour (%%H:%%M)  %R",
+       "(%%S)                                       second (00..60)  %S",
+       "(%%T)                              time, 24-hour (%%H:%%M:%%S)  %T",
+       "(%%U)    week of year, Sunday as first day of week (00..53)  %U",
+       "(%%V)                    week of year according to ISO 8601  %V",
+       "(%%W)    week of year, Monday as first day of week (00..53)  %W",
+       "(%%X)     appropriate locale time representation (%H:%M:%S)  %X",
+       "(%%Y)                           year with century (1970...)  %Y",
+       "(%%Z) timezone (EDT), or blank if timezone not determinable  %Z",
+       "(%%a)          locale's abbreviated weekday name (Sun..Sat)  %a",
+       "(%%b)            locale's abbreviated month name (Jan..Dec)  %b",
+       "(%%c)           full date (Sat Nov  4 12:02:33 1989)%n%t%t%t  %c",
+       "(%%d)                             day of the month (01..31)  %d",
+       "(%%e)               day of the month, blank-padded ( 1..31)  %e",
+       "(%%h)                                should be same as (%%b)  %h",
+       "(%%j)                            day of the year (001..366)  %j",
+       "(%%k)               hour, 24-hour clock, blank pad ( 0..23)  %k",
+       "(%%l)               hour, 12-hour clock, blank pad ( 0..12)  %l",
+       "(%%m)                                        month (01..12)  %m",
+       "(%%o)                                      Emporer/Era Year  %o",
+       "(%%p)              locale's AM or PM based on 12-hour clock  %p",
+       "(%%r)                   time, 12-hour (same as %%I:%%M:%%S %%p)  %r",
+       "(%%u) ISO 8601: Weekday as decimal number [1 (Monday) - 7]   %u",
+       "(%%v)                                VMS date (dd-bbb-YYYY)  %v",
+       "(%%w)                       day of week (0..6, Sunday == 0)  %w",
+       "(%%x)                appropriate locale date representation  %x",
+       "(%%y)                      last two digits of year (00..99)  %y",
+       "(%%z)      timezone offset east of GMT as HHMM (e.g. -0500)  %z",
+       (char *) NULL
+};
+
+/* main routine. */
+
+int
+main(argc, argv)
+int argc;
+char **argv;
+{
+       long time();
+
+       char *next;
+       char string[MAXTIME];
+
+       int k;
+       int length;
+
+       struct tm *tm;
+
+       long clock;
+
+       /* Call the function. */
+
+       clock = time((long *) 0);
+       tm = localtime(&clock);
+
+       for (k = 0; next = array[k]; k++) {
+               length = strftime(string, MAXTIME, next, tm);
+               printf("%s\n", string);
+       }
+
+       exit(0);
+}
+#endif /* TEST_STRFTIME */
index 72ec06a2c1fd8dde92acea5e8ac773e35f1d061b..3efcf32d68e9722024b6ca9d67f9e81b2aa5ac04 100755 (executable)
@@ -1,4 +1,4 @@
-BUILD_DIR=/usr/local/build/bash/bash-current
+BUILD_DIR=/usr/local/build/chet/bash/bash-current
 THIS_SH=$BUILD_DIR/bash
 PATH=$PATH:$BUILD_DIR