#!/usr/bin/env perl
#
-# Copyright © 2011-2014, 2020-2022 Nick Bowler
+# Copyright © 2011-2014, 2020-2023 Nick Bowler
#
# Prepare the Gnulib tree for inclusion into a non-recursive automake build.
# While the output of gnulib-tool is "include"-able if the --makefile-name
# the value is always set to 1.
my (%allvars, %sourcevars);
+# Collected names of subdirectories that may need to be created at build time.
+# The keys are directory names, the values are targets.
+my %gl_dirstamps;
+
+# State to drop MKDIR_P lines that have been replaced by dirstamps.
+my ($have_dirstamp) = (0);
+
sub drop {
undef $_;
next;
@left = map(mangle_file($_), @left);
@right = map(mangle_file($_), @right);
- return join(" ", @left) . ": " . join(" ", @right) . "\n";
+ my @dirstamps = get_dirstamps(@left);
+
+ return join(" ", @left) . ": " . join(" ", @dirstamps, @right) . "\n";
+}
+
+sub get_dirstamps {
+ my %h;
+
+ foreach (@_) {
+ next unless $_[0] =~ m|^(lib(/.*)?)/[^/]*$|;
+
+ $h{$gl_dirstamps{$1} = "$1/\$(am__dirstamp)"} = 1;
+ }
+
+ return keys %h;
}
while (<STDIN>) {
# something actually depends on it (which is typically the case).
if (/^noinst_LIBRARIES.*libgnu.a/) {
s/^noinst/EXTRA/;
- $for_library //= 0;
+ $for_library = 0 unless defined $for_library;
$use_libtool = 0;
}
if (/^noinst_LTLIBRARIES.*libgnu.la/) {
s/^noinst/EXTRA/;
- $for_library //= 1;
+ $for_library = 1 unless defined $for_library;
$use_libtool = 1;
}
# useful for non-recursive builds. Strip them out.
drop if (/^(AM_CPPFLAGS|AM_CFLAGS)/);
+ # We don't care about upstream warning flags that just result in adding
+ # massive amounts of additional build rules for no reason.
+ if (/_CFLAGS/) {
+ s/ *\$\(GL_CFLAG_GNULIB_WARNINGS\)// if /_CFLAGS\s*=/;
+ }
+
+ # Drop superfluous CFLAGS assignments (which may be created by above
+ # transformation).
+ drop if /_CFLAGS\s*=\s*\$\(AM_CFLAGS\)\s*$/;
+
# Library dependencies are added automatically to libgnu.la by
# gnulib-tool. Unfortunately, this means that everything linking
# against libgnu.la is forced to pull in the same deps, even if they're
if (/^([[:word:]]+)[[:space:]]*\+?=/) {
$allvars{$1} = 1;
- if (/_SOURCES|CLEANFILES|EXTRA_DIST|[[:upper:]]+_H/) {
+ if ($1 =~ /(_SOURCES|CLEANFILES|EXTRA_DIST|[[:upper:]]+_H)$/) {
$_ = mangle_variable($_);
}
}
# Targets are similar to variables: the target and its dependencies
# need to be mangled.
- if (/^[^\t].*:/) {
+ if (/^([^\t:]*):/) {
$_ = mangle_target($_);
+ $have_dirstamp = /am__dirstamp/;
}
# MKDIR_P commands need to be fixed up; in principle Gnulib could also
# component.
s/t-\$@/\$\@-t/g;
- # Finally, references to $(srcdir) and $(builddir) need to be fixed up.
+ # $(srcdir), $(builddir) and %reldir% need to be fixed up.
s:\$\(srcdir\):\$\(top_srcdir\)/lib:g;
s:\$\(builddir\):\$\(top_builddir\)/lib:g;
+ s:%reldir%:lib:g;
+
+ # If we installed a dirstamp prerequisite for this target, don't
+ # emit the mkdir line which creates the output directory.
+ if ($have_dirstamp && m|\$[({]MKDIR_P[})][ '"]*lib/|) {
+ drop unless s/^(\t\$[({](AM_V_GEN|gl_V_at)[})]).*/\1:/;
+ }
+ undef $have_dirstamp if /^\t/;
} continue { s/(\n.)/\\\1/g; print; };
+# Define a bunch of fake programs which will ensure Automake produces the
+# necessary dirstamp rules, as unfortunately we cannot know in advance which
+# will be generated, and the usual Automake behaviour where generated rules
+# are suppressed by rules in Makefile.am doesn't actaully work for these.
+print <<EOF foreach (keys %gl_dirstamps);
+EXTRA_PROGRAMS += $_/gl-dirstamp
+${\(y|/|_|r)}_gl_dirstamp_SOURCES =
+EOF
+
print <<'EOF' if ($use_libtool);
gnulib_lt_objects = $(libgnu_la_OBJECTS) $(gl_LTLIBOBJS)
gnulib_objects = $(gnulib_lt_objects)