bug-gnulib
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Bug in gnulib-tools prevents bison from bootstrapping


From: Bruno Haible
Subject: Re: Bug in gnulib-tools prevents bison from bootstrapping
Date: Sat, 23 Jun 2007 04:30:24 +0200
User-agent: KMail/1.5.4

Hello,

Fernando Ferreira wrote:
> I found out that gnulib-tools, 
> invoked by bootstrap to generate the gnulib-comp.m4 file, had a little 
> but vital bug that inserted these extraneous characters instead of the 
> desired behavior. The faulty lines are these, lines 2170 to 2180 on 
> gnulib/gnulib-tool, that is downloaded from the gnulib CVS by the 
> bootstrap script:
> 
>     if test "$auxdir" != "build-aux"; then
>       sed_replace_build_aux='
>         :a
>         /AC_CONFIG_FILES(.*:build-aux\/.*)/{
>           
> s|AC_CONFIG_FILES(\(.*\):build-aux/\(.*\))|AC_CONFIG_FILES(\1:'"$auxdir"'/\2)|
>           ba
>         }'
>       sed_replace_build_aux=`echo "$sed_replace_build_aux" | sed -e 1d 
> -e 's/^ *//'`
>     else
>       sed_replace_build_aux=
>     fi
> 
> 
> When it assigns sed_replace_build_aux with 'foo \1 bar \2', and then 
> echoes it, instead of the desired effect of keeping it as literal '\1' 
> and '\2' it changes it to the ASCII character 1 and 2.

It is generally impossible to write reliable shell-scripts using 'echo',
when this 'echo' commands interprets backslahes. I'm not inclined to check
or rewrite the 500 echo commands in gnulib-tool. Instead, I'm applying this
workaround. Tested with bash, zsh, ksh, and /bin/sh of Linux, MacOS X,
AIX, HP-UX, IRIX, Solaris, OSF/1.

libtool.m4 also tries other workarounds: searching for an 'echo' program
in $PATH:/usr/ucb (but how is this better than 'cat'?) or using a built-in
'print -r' command (which shells except ksh have this?) or using 'printf'
(is that portable nowadays?).


2007-06-22  Bruno Haible  <address@hidden>

        * gnulib-tool (echo): Ensure the echo primitive does not interpret
        backslashes.
        * tests/test-echo.sh: New file.

*** gnulib-tool 22 Jun 2007 18:16:40 -0000      1.234
--- gnulib-tool 23 Jun 2007 01:59:31 -0000
***************
*** 410,415 ****
--- 410,512 ----
    fi
  }
  
+ # Ensure an 'echo' command that does not interpret backslashes.
+ # Test cases:
+ #   echo '\n' | wc -l                 prints 1 when OK, 2 when KO
+ #   echo '\t' | grep t > /dev/null    has return code 0 when OK, 1 when KO
+ # This problem is a weird heritage from SVR4. BSD got it right.
+ # Nowadays the problem occurs in 4 situations:
+ # - in bash, when the shell option xpg_echo is set,
+ # - in zsh, when sh-emulation is not set,
+ # - in ksh (e.g. AIX /bin/sh and Solaris /usr/xpg4/bin/sh are ksh instances,
+ #           and HP-UX /bin/sh and IRIX /bin/sh behave similarly),
+ # - in Solaris /bin/sh and OSF/1 /bin/sh.
+ # We try the following workarounds:
+ # - for all: respawn using $CONFIG_SHELL if that is set and works.
+ # - for bash: unset the shell option xpg_echo.
+ # - for zsh: turn sh-emulation on.
+ # - for ksh: alias echo to a function that uses cat of a here document.
+ # - for Solaris /bin/sh: respawn using /bin/ksh and rely on the ksh 
workaround.
+ # - otherwise: respawn using /bin/sh and rely on the workarounds.
+ # When respawning, we pass --no-reexec as first argument, so as to avoid
+ # turning this script into a fork bomb in unlucky situations.
+ have_echo=
+ if echo '\t' | grep t > /dev/null; then
+   have_echo=yes # Lucky!
+ fi
+ # Try the workarounds.
+ # Respawn using $CONFIG_SHELL if that is set and works.
+ if test -z "$have_echo" \
+    && test "X$1" != "X--no-reexec" \
+    && test -n "$CONFIG_SHELL" \
+    && test -f "$CONFIG_SHELL" \
+    && $CONFIG_SHELL -c 'echo '\t' | grep t > /dev/null'; then
+   exec $CONFIG_SHELL "$0" --no-reexec "$@"
+   exit 127
+ fi
+ # For bash: unset the shell option xpg_echo.
+ if test -z "$have_echo" \
+    && test -n "$BASH_VERSION" \
+    && (shopt -o xpg_echo; echo '\t' | grep t > /dev/null) 2>/dev/null; then
+   shopt -o xpg_echo
+   have_echo=yes
+ fi
+ # For zsh: turn sh-emulation on.
+ if test -z "$have_echo" \
+    && test -n "$ZSH_VERSION" \
+    && (emulate sh) >/dev/null 2>&1; then
+   emulate sh
+ fi
+ # For ksh: alias echo to a function that uses cat of a here document.
+ # The ksh manual page says:
+ #   "Aliasing is performed when scripts are read, not while they are executed.
+ #    Therefore, for an alias to take effect, the alias definition command has
+ #    to be executed before the command which references the alias is read."
+ # Because of this, we have to play strange tricks with have_echo, to ensure
+ # that the top-level statement containing the test start after the 'alias'
+ # command.
+ if test -z "$have_echo"; then
+ bsd_echo ()
+ {
+ cat <<EOF
+ $*
+ EOF
+ }
+ alias echo=bsd_echo 2>/dev/null
+ fi
+ if test -z "$have_echo" \
+    && echo '\t' | grep t > /dev/null; then
+   have_echo=yes
+ fi
+ if test -z "$have_echo"; then
+   unalias echo 2>/dev/null
+ fi
+ # For Solaris /bin/sh and OSF/1 /bin/sh: respawn using /bin/ksh.
+ if test -z "$have_echo" \
+    && test "X$1" != "X--no-reexec" \
+    && test -f /bin/ksh; then
+   exec /bin/ksh "$0" --no-reexec "$@"
+   exit 127
+ fi
+ # Otherwise: respawn using /bin/sh.
+ if test -z "$have_echo" \
+    && test "X$1" != "X--no-reexec" \
+    && test -f /bin/sh; then
+   exec /bin/sh "$0" --no-reexec "$@"
+   exit 127
+ fi
+ if test -z "$have_echo"; then
+   func_fatal_error "Shell does not support 'echo' correctly. Please install 
GNU bash and set the environment variable CONFIG_SHELL to point to it."
+ fi
+ if echo '\t' | grep t > /dev/null; then
+   : # Works fine now.
+ else
+   func_fatal_error "Shell does not support 'echo' correctly. Workaround does 
not work. Please report this as a bug to address@hidden"
+ fi
+ if test "X$1" = "X--no-reexec"; then
+   shift
+ fi
+ 
  # Command-line option processing.
  # Removes the OPTIONS from the arguments. Sets the variables:
  # - mode            list or import or create-testdir or create-megatestdir





reply via email to

[Prev in Thread] Current Thread [Next in Thread]