Re: 1.16.90 regression: configure now takes 7 seconds to start
Bruno Haible <[email protected]> Thu, 13 Jun 2024 14:23:23 +0200
| Newsgroups | gmane.comp.sysutils.automake.general |
|---|---|
| Message-ID | <3017686.aBcLfjPe96@nimes> |
Nick Bowler wrote:
> Maybe this is a silly question, but, is there a reason why this test
> needs to be performed in every single package that uses Automake?
Excellent point. The best optimization of a certain code is the one
that avoids executing the code entirely.
With Karl's newest patch, it's no longer a 7-seconds delay, but a
2-seconds delay. But if we can avoid executing it entirely, it would
be better.
Zack Weinberg wrote:
> The timestamp resolution is actually used by core automake code, namely
> the "ensuring generated files are newer than source" config.status step,
> which is necessary to make tarball builds work reliably on systems that
> don't have the `automake`, `autoconf`, `aclocal`, etc. tools already
> installed.
Right. And, more precisely, this test "ensuring generated files are newer
than source" makes sure that a newly created file is at least 0.01 or 0.1
or 1 or 2 seconds newer that the 'configure' file. Therefore the situations
where it is needed are:
(A) when a machine has a skewed time clock (like gcc111.fsffrance.org
often has),
(B) when a package creates a configure file in a subtree and then
_immediately_ runs that configure script.
Case (A) affects all packages, but it can usually not be fixed with a
'sleep 1' or 'sleep 2'; that's not what we are talking about.
Case (B) is why the Automake test suite needs this test to be in 'configure'.
This is the case where a 'sleep 1' or 'sleep 2' can help. Still, case (B)
can also occur in other packages (think of distros which — for ill-guided
reasons — routinely regenerate the configure script).
So, I agree with Karl that this code is needed for all packages.
But it is not needed in all configure runs! The 'sleep 1' or 'sleep 2'
is in _AM_FILESYSTEM_TIMESTAMP_RESOLUTION, whose sole purpose is to
determine a variable am_cv_filesystem_timestamp_resolution. The sole
use of this variable is in AM_SANITY_CHECK, in a loop whose structure is:
for (2 times)
Test whether the configure file is old enough (0.01 sec ... 2 sec —
it depends).
If yes:
break;
sleep $am_cv_filesystem_timestamp_resolution
end
In most cases, the test will already succeed in the first loop round,
and then there is *no need* for even determining
am_cv_filesystem_timestamp_resolution.
So, the fix is simply to delay determining am_cv_filesystem_timestamp_resolution
until we actually need it.
The attached patch does it. In my testing on NetBSD, which involves a few
seconds of transfer between creation and execution of a tarball, the 2-seconds
delay goes away, as expected.
Note: The redirection of AS_MESSAGE_FD may look ugly, but is portable.
Gnulib uses this idiom for three years already.
Bruno
0001-automake-Save-up-to-2-seconds-of-configure-time.patch
(text/x-patch, 1.4 KB)
From 3a7f1cb3ea4a51caf77cf6c06a1d9528764adc2b Mon Sep 17 00:00:00 2001 From: Bruno Haible <[email protected]> Date: Thu, 13 Jun 2024 13:47:49 +0200 Subject: [PATCH] automake: Save up to 2 seconds of configure time. * m4/sanity.m4 (AM_SANITY_CHECK): Don't require _AM_FILESYSTEM_TIMESTAMP_RESOLUTION. Instead, execute it only when it is actually needed. In most cases outside Automake's test suite, it is not needed. --- m4/sanity.m4 | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/m4/sanity.m4 b/m4/sanity.m4 index 68fbf36f7..e09bca69f 100644 --- a/m4/sanity.m4 +++ b/m4/sanity.m4 @@ -141,7 +141,7 @@ rm -f conftest.ts? # AM_SANITY_CHECK # --------------- AC_DEFUN([AM_SANITY_CHECK], -[AC_REQUIRE([_AM_FILESYSTEM_TIMESTAMP_RESOLUTION]) +[ # This check should not be cached, as it may vary across builds of # different projects. AC_MSG_CHECKING([whether build environment is sane]) @@ -179,6 +179,14 @@ for am_try in 1 2; do am_build_env_is_sane=yes break fi + # Determine am_cv_filesystem_timestamp_resolution. Do it only on the first + # loop round, since it is expensive. Do so without visible output, because + # we're already in a AC_MSG_CHECKING..AC_MSG_RESULT block. + if test $am_try = 1; then + exec 9>&AS_MESSAGE_FD AS_MESSAGE_FD>/dev/null + _AM_FILESYSTEM_TIMESTAMP_RESOLUTION + exec AS_MESSAGE_FD>&9 9>&- + fi # Just in case. sleep $am_cv_filesystem_timestamp_resolution am_has_slept=yes -- 2.34.1