Fixes automake bug#8365.
* tests/aclocal6.test: Sleep before modifying m4 files that should
trigger remake rules. Remove incorrect/obsoleted comments.
* tests/subdir5.test: Likewise, and extend a bit.
* tests/subdir8.test: Likewise.
* tests/pr8365-remake-timing.test: New xfailing test.
* tests/Makefile.am (TESTS): Update.
Report from Sam Steingold.
+2011-04-02 Stefano Lattarini <stefano.lattarini@gmail.com>
+
+ tests: fix timestamp-related failures
+ Fixes automake bug#8365.
+ * tests/aclocal6.test: Sleep before modifying m4 files that should
+ trigger remake rules. Remove incorrect/obsoleted comments.
+ * tests/subdir5.test: Likewise, and extend a bit.
+ * tests/subdir8.test: Likewise.
+ * tests/pr8365-remake-timing.test: New xfailing test.
+ * tests/Makefile.am (TESTS): Update.
+ Report from Sam Steingold.
+
2011-04-02 Ralf Wildenhues <Ralf.Wildenhues@gmx.de>
Create subdirs for generated sources even when not dep tracking.
auxdir2.test \
cond17.test \
gcj6.test \
+pr8365-remake-timing.test \
txinfo5.test
include $(srcdir)/parallel-tests.am
remake5.test \
remake6.test \
remake7.test \
+pr8365-remake-timing.test \
regex.test \
req.test \
reqd.test \
auxdir2.test \
cond17.test \
gcj6.test \
+pr8365-remake-timing.test \
txinfo5.test
parallel_tests = \
remake5.test \
remake6.test \
remake7.test \
+pr8365-remake-timing.test \
regex.test \
req.test \
reqd.test \
../configure
$MAKE
+# Modified configure dependencies must be newer than config.status.
+$sleep
# Update an aclocal.m4 dependency, then make sure all Makefiles
# are updated, even from a sub-directory.
echo 'AC_DEFUN([SOME_DEFS], [MORE_DEFS])' > ../m4/somedefs.m4
--- /dev/null
+#! /bin/sh
+# Copyright (C) 2011 Free Software Foundation, Inc.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# Test for automake bug#8365, related to Makefile remake rules.
+# The bug is due to subtle timestamp issues and limitations in
+# make's behaviour, and is very unlikely to be triggered (we have
+# to resort to timestamp edit hacks to consistently expose it); in
+# any account, it is nigh to impossible to trigger it by running
+# make by hand. Thus, fixing it would not be worth the hassle, but
+# we prefer to keep it exposed anyway.
+
+. ./defs || Exit 1
+
+set -e
+
+# We'll use calls to stat to get debugging information.
+if stat /dev/null; then stat=stat; else stat=:; fi
+
+cat >> configure.in << 'END'
+FOOBAR=zardoz
+AC_OUTPUT
+END
+
+: > Makefile.am
+
+$ACLOCAL
+# Run automake *before* autoconf, because we want to ensure that
+# Makefile.in is not newer than configure.
+$AUTOMAKE
+$AUTOCONF
+
+./configure
+$MAKE Makefile
+$EGREP 'FOOBAR|zardoz' Makefile && Exit 99 # Sanity check.
+
+echo 'AC_SUBST([FOOBAR])' >> configure.in
+
+# Modified configure dependencies must have the same timestamp of
+# config.status and Makefile in order to trigger the bug.
+# We also re-touch config.status, because "touch -r" can truncate
+# timestamps on file systems with sub-second resolutions (see the
+# autoconf manual). Finally, we also sleep before touching, to ensure
+# that the (possibly truncated) timestamps of config.status etc. are
+# strictly newer than the non-truncated configure timestamp.
+$stat config.status Makefile configure.in
+$sleep
+touch config.status
+touch -r config.status config.status Makefile configure.in
+$stat config.status Makefile configure.in
+
+# Also, the race condition is triggered only when aclocal, automake
+# and aclocal run fast enough to keep the timestamp of the generated
+# aclocal.m4, Makefile.in and configure equal to the timestamp of
+# Makefile & config.status. To reproduce this race consistently, we
+# need the following hackish wrappers.
+
+save_AUTOCONF=$AUTOCONF
+
+cat > aclocal-wrap <<END
+#!/bin/sh
+set -ex
+# aclocal shouldn't use our autoconf wrapper when extracting
+# the races from configure.in.
+AUTOCONF='$save_AUTOCONF'; export AUTOCONF
+$ACLOCAL "\$@"
+touch -r config.status aclocal.m4
+$stat aclocal.m4
+END
+
+cat > automake-wrap <<END
+#!/bin/sh
+set -ex
+# automake shouldn't use our autoconf wrapper when extracting
+# the races from configure.in.
+AUTOCONF='$save_AUTOCONF'; export AUTOCONF
+$AUTOMAKE "\$@"
+touch -r config.status Makefile.in
+$stat Makefile.in
+END
+
+cat > autoconf-wrap <<END
+#!/bin/sh
+set -ex
+$AUTOCONF "\$@"
+touch -r config.status configure
+$stat configure
+END
+
+chmod a+x aclocal-wrap automake-wrap autoconf-wrap
+
+env \
+ ACLOCAL=./aclocal-wrap AUTOMAKE=./automake-wrap AUTOCONF=./autoconf-wrap \
+ $MAKE -e Makefile
+grep '^FOOBAR =' Makefile.in
+grep '^FOOBAR *= *zardoz *$' Makefile
+
+:
#! /bin/sh
-# Copyright (C) 2001, 2002, 2003, 2004, 2009, 2010 Free Software
+# Copyright (C) 2001, 2002, 2003, 2004, 2009, 2010, 2011 Free Software
# Foundation, Inc.
#
# This program is free software; you can redistribute it and/or modify
$MAKE
# Now add new directories.
-#
-# We shouldn't need to $sleep here: configure ensures that files
-# generated by it are newer than configure. Thus, even if
-# Makefile.in is newer than configure but the updated Makefile.am
-# below has the same timestamp as Makefile.in, the latter should
-# be rebuilt due to its dependency on configure.in.
# First we add a new directory by modifying configure.in directly.
# We update configure.in *before* updating sub/Makefile.am; subdir8.test
# does it in the other way: it updates confiles.m4 (which is m4_included
# by configure.in there) after Makefile.am.
+# Modified configure dependencies must be newer than config.status.
+$sleep
sed <configure.in >configure.tmp -e '/^AC_OUTPUT$/i\
AC_CONFIG_FILES([maude/Makefile])\
m4_include([confile.m4])\
# We want a simple rebuild to create maude/Makefile automatically.
$MAKE
+grep '^SUBDIRS = *maude *$' Makefile.in
+grep '^SUBDIRS = *maude *$' Makefile
test -f maude/Makefile
# Then we add a new directory by modifying a file included (through
# `m4_include') by configure.in.
mkdir maude2
+# Modified configure dependencies must be newer than config.status.
+$sleep
cat >> confile.m4 << 'END'
AC_CONFIG_FILES([maude2/Makefile])
AC_SUBST([GREPME])
# We want a simple rebuild to create maude2/Makefile and update
# all other Makefiles automatically.
$MAKE
-grep '^GREPME =' Makefile
-grep '^GREPME =' maude/Makefile
-grep '^GREPME =' maude2/Makefile
+grep '^SUBDIRS =.* maude2' Makefile.in
+grep '^SUBDIRS =.* maude2' Makefile
+
+for ext in '.in' ''; do
+ for d in . maude maude2; do
+ grep '^GREPME =' $d/Makefile$ext
+ done
+done
:
#! /bin/sh
-# Copyright (C) 2003, 2004, 2009, 2010 Free Software Foundation, Inc.
+# Copyright (C) 2003, 2004, 2009, 2010, 2011 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
$MAKE
# Now add new directories.
-#
-# We shouldn't need to $sleep here: configure ensures that files
-# generated by it are newer than configure. Thus, even if
-# Makefile.in is newer than configure but the updated Makefile.am
-# below has the same timestamp as Makefile.in, the latter should
-# be rebuilt due to its dependency on configure.in.
# The first step users typically do when adding a new subdir is
# editing configure.in. That is already tested by subdir5.test,
# Update confiles.m4 *after* updating sub/Makefile.am; subdir5.test do
# it in the other way: it updates configure.in before Makefile.am.
+# We sleep here because modified configure dependencies must be newer
+# than config.status.
+$sleep
echo 'AC_CONFIG_FILES([maude/Makefile sub/maude/Makefile])' >> confiles.m4
# We want a simple rebuild from sub/ to create sub/maude/Makefile
cd sub
$MAKE
cd ..
+grep '^SUBDIRS = *maude *$' sub/Makefile.in
+grep '^SUBDIRS = *maude *$' sub/Makefile
test -f maude/Makefile
test -f sub/maude/Makefile
echo 'AC_DEFUN([MORE_DEFS], [AC_SUBST([GREPME])])' > m4/moredefs.m4
$MAKE
-grep '^GREPME =' Makefile
-grep '^GREPME =' maude/Makefile
-grep '^GREPME =' sub/Makefile
-grep '^GREPME =' sub/maude/Makefile
+for ext in '.in' ''; do
+ for d in . maude sub sub/maude; do
+ grep '^GREPME =' $d/Makefile$ext
+ done
+done
: