summaryrefslogtreecommitdiff
path: root/lib/Automake/Variable.pm
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Automake/Variable.pm')
-rw-r--r--lib/Automake/Variable.pm277
1 files changed, 52 insertions, 225 deletions
diff --git a/lib/Automake/Variable.pm b/lib/Automake/Variable.pm
index c0be3f8a5..bdacb7e11 100644
--- a/lib/Automake/Variable.pm
+++ b/lib/Automake/Variable.pm
@@ -34,7 +34,7 @@ use vars '@ISA', '@EXPORT', '@EXPORT_OK';
@EXPORT = qw (err_var msg_var msg_cond_var reject_var
var rvar vardef rvardef
variables
- scan_variable_expansions check_variable_expansions
+ scan_variable_expansions
variable_delete
variables_dump
set_seen
@@ -55,7 +55,7 @@ Automake::Variable - support for variable definitions
# Defining a variable.
Automake::Variable::define($varname, $owner, $type,
$cond, $value, $comment,
- $where, $pretty)
+ $where)
# Looking up a variable.
my $var = var $varname;
@@ -129,11 +129,6 @@ non-object).
=cut
-my $_VARIABLE_CHARACTERS = '[.A-Za-z0-9_@]+';
-my $_VARIABLE_PATTERN = '^' . $_VARIABLE_CHARACTERS . "\$";
-my $_VARIABLE_RECURSIVE_PATTERN =
- '^([.A-Za-z0-9_@]|\$[({]' . $_VARIABLE_CHARACTERS . '[})]?)+' . "\$";
-
# The order in which variables should be output. (May contain
# duplicates -- only the first occurrence matters.)
my @_var_order;
@@ -284,25 +279,6 @@ sub reject_var ($$)
=over 4
-=item C<Automake::Variable::hook ($varname, $fun)>
-
-Declare a function to be called whenever a variable
-named C<$varname> is defined or redefined.
-
-C<$fun> should take two arguments: C<$type> and C<$value>.
-When type is C<''> or <':'>, C<$value> is the value being
-assigned to C<$varname>. When C<$type> is C<'+'>, C<$value>
-is the value being appended to C<$varname>.
-
-=cut
-
-use vars '%_hooks';
-sub hook ($$)
-{
- my ($var, $fun) = @_;
- $_hooks{$var} = $fun;
-}
-
=item C<variables ([$suffix])>
Returns the list of all L<Automake::Variable> instances. (I.e., all
@@ -445,7 +421,6 @@ sub _new ($$)
my ($class, $name) = @_;
my $self = Automake::Item::new ($class, $name);
$self->{'scanned'} = 0;
- $self->{'last-append'} = []; # helper variable for last conditional append.
$_variable_dict{$name} = $self;
if ($name =~ /_([[:alnum:]]+)$/)
{
@@ -469,7 +444,7 @@ sub _check_ambiguous_condition ($$$)
# We allow silent variables to be overridden silently,
# by either silent or non-silent variables.
my $def = $self->def ($ambig_cond);
- if ($message && $def->pretty != VAR_SILENT)
+ if ($message)
{
msg 'syntax', $where, "$message ...", partial => 1;
msg_var ('syntax', $var, "... '$var' previously defined here");
@@ -506,6 +481,16 @@ sub check_defined_unconditionally ($;$$)
}
}
+sub _has_line_too_long ($)
+{
+ my ($text) = @_;
+ foreach my $line (split "\n", $text)
+ {
+ return 1 if length ($line) >= 1000 ;
+ }
+ return 0;
+}
+
=item C<$str = $var-E<gt>output ([@conds])>
Format all the definitions of C<$var> if C<@cond> is not specified,
@@ -530,48 +515,32 @@ sub output ($@)
. $self->name . "'")
unless $def;
- next
- if $def->pretty == VAR_SILENT;
-
$res .= $def->comment;
my $val = $def->raw_value;
my $equals = $def->type eq ':' ? ':=' : '=';
my $str = $cond->subst_string;
-
-
- if ($def->pretty == VAR_ASIS)
- {
- my $output_var = "$name $equals $val";
- $output_var =~ s/^/$str/meg;
- $res .= "$output_var\n";
- }
- elsif ($def->pretty == VAR_PRETTY)
- {
- # Suppress escaped new lines. &makefile_wrap will
- # add them back, maybe at other places.
- $val =~ s/\\$//mg;
- my $wrap = makefile_wrap ("$str$name $equals", "$str\t",
- split (' ', $val));
-
- # If the last line of the definition is made only of
- # @substitutions@, append an empty variable to make sure it
- # cannot be substituted as a blank line (that would confuse
- # HP-UX Make).
- $wrap = makefile_wrap ("$str$name $equals", "$str\t",
- split (' ', $val), '$(am__empty)')
- if $wrap =~ /\n(\s*@\w+@)+\s*$/;
-
- $res .= $wrap;
- }
- else # ($def->pretty == VAR_SORTED)
- {
- # Suppress escaped new lines. &makefile_wrap will
- # add them back, maybe at other places.
- $val =~ s/\\$//mg;
- $res .= makefile_wrap ("$str$name $equals", "$str\t",
- sort (split (' ' , $val)));
- }
+ my $output_var;
+ # Definition of variables whose value contains unescaped newlines
+ # (likely as a result of a "+=" appending) cannot be output as-is;
+ # we need to wrap their definition. We also wrap the definition if
+ # the length of any line is too big, since POSIX-compliant systems
+ # are not required to support lines longer than 2048 bytes (most
+ # notably, some sed implementation are limited to 4000 bytes, and
+ # sed is used by config.status to rewrite Makefile.in into Makefile).
+ if (_has_line_too_long ($val) or $val =~ /(:?\\\\)*[^\\]\n./)
+ {
+ $val =~ s/\\$//mg;
+ $output_var = makefile_wrap ("$str$name $equals", "$str\t",
+ split (' ', $val));
+ }
+ else
+ {
+ $val =~ s/^[ \t]*//;
+ $output_var = "$name $equals $val";
+ $output_var =~ s/^/$str/meg;
+ }
+ $res .= "$output_var\n";
}
return $res;
}
@@ -725,74 +694,7 @@ sub dump ($)
=over 4
-=item C<@list = scan_variable_expansions ($text)>
-
-Return the list of variable names expanded in C<$text>. Note that
-unlike some other functions, C<$text> is not split on spaces before we
-check for subvariables.
-
-=cut
-
-sub scan_variable_expansions ($)
-{
- my ($text) = @_;
- my @result = ();
-
- # Strip comments.
- $text =~ s/#.*$//;
-
- # Record each use of ${stuff} or $(stuff) that does not follow a $.
- while ($text =~ /(?<!\$)\$(?:\{([^\}]*)\}|\(([^\)]*)\))/g)
- {
- my $var = $1 || $2;
- # The occurrence may look like $(string1[:subst1=[subst2]]) but
- # we want only 'string1'.
- $var =~ s/:[^:=]*=[^=]*$//;
- push @result, $var;
- }
-
- return @result;
-}
-
-=item C<check_variable_expansions ($text, $where)>
-
-Check variable expansions in C<$text> and warn about any name that
-does not conform to POSIX. C<$where> is the location of C<$text>
-for the error message.
-
-=cut
-
-sub check_variable_expansions ($$)
-{
- my ($text, $where) = @_;
- # Catch expansion of variables whose name does not conform to POSIX.
- foreach my $var (scan_variable_expansions ($text))
- {
- if ($var !~ /$_VARIABLE_PATTERN/o)
- {
- # If the variable name contains a space, it's likely
- # to be a GNU make extension (such as $(addsuffix ...)).
- # Mention this in the diagnostic.
- my $gnuext = "";
- $gnuext = "\n(probably a GNU make extension)" if $var =~ / /;
- # Accept recursive variable expansions if so desired
- # (we hope they are rather portable in practice).
- if ($var =~ /$_VARIABLE_RECURSIVE_PATTERN/o)
- {
- msg ('portability-recursive', $where,
- "$var: non-POSIX recursive variable expansion$gnuext");
- }
- else
- {
- msg ('portability', $where, "$var: non-POSIX variable name$gnuext");
- }
- }
- }
-}
-
-
-
-=item C<Automake::Variable::define($varname, $owner, $type, $cond, $value, $comment, $where, $pretty)>
+=item C<Automake::Variable::define($varname, $owner, $type, $cond, $value, $comment, $where)>
Define or append to a new variable.
@@ -816,20 +718,11 @@ assignment.
C<$where>: the C<Location> of the assignment.
-C<$pretty>: whether C<$value> should be pretty printed (one of
-C<VAR_ASIS>, C<VAR_PRETTY>, C<VAR_SILENT>, or C<VAR_SORTED>, defined
-by by L<Automake::VarDef>). C<$pretty> applies only to real
-assignments. I.e., it does not apply to a C<+=> assignment (except
-when part of it is being done as a conditional C<=> assignment).
-
-This function will all run any hook registered with the C<hook>
-function.
-
=cut
-sub define ($$$$$$$$)
+sub define ($$$$$$$)
{
- my ($var, $owner, $type, $cond, $value, $comment, $where, $pretty) = @_;
+ my ($var, $owner, $type, $cond, $value, $comment, $where) = @_;
prog_error "$cond is not a reference"
unless ref $cond;
@@ -837,24 +730,6 @@ sub define ($$$$$$$$)
prog_error "$where is not a reference"
unless ref $where;
- prog_error "pretty argument missing"
- unless defined $pretty && ($pretty == VAR_ASIS
- || $pretty == VAR_PRETTY
- || $pretty == VAR_SILENT
- || $pretty == VAR_SORTED);
-
- error $where, "bad characters in variable name '$var'"
- if $var !~ /$_VARIABLE_PATTERN/o;
-
- # ':='-style assignments are not acknowledged by POSIX. Moreover it
- # has multiple meanings. In GNU make or BSD make it means "assign
- # with immediate expansion", while in OSF make it is used for
- # conditional assignments.
- msg ('portability', $where, "':='-style assignments are not portable")
- if $type eq ':';
-
- check_variable_expansions ($value, $where);
-
# If there's a comment, make sure it is \n-terminated.
if ($comment)
{
@@ -911,9 +786,7 @@ sub define ($$$$$$$$)
# 1. append (+=) to a variable defined for current condition
if ($type eq '+' && ! $new_var)
{
- $def->append ($value, $comment);
- $self->{'last-append'} = [];
-
+ $def->append ($value, $comment, $cond);
# Only increase owners. A VAR_CONFIGURE variable augmented in a
# Makefile.am becomes a VAR_MAKEFILE variable.
$def->set_owner ($owner, $where->clone)
@@ -922,63 +795,24 @@ sub define ($$$$$$$$)
# 2. append (+=) to a variable defined for *another* condition
elsif ($type eq '+' && ! $self->conditions->false)
{
- # * Generally, $cond is not TRUE. For instance:
+ # * If we have an input like:
# FOO = foo
# if COND
# FOO += bar
# endif
- # In this case, we declare an helper variable conditionally,
- # and append it to FOO:
+ # we declare an helper variable conditionally, and append
+ # it to FOO:
# FOO = foo $(am__append_1)
# @COND_TRUE@am__append_1 = bar
# Of course if FOO is defined under several conditions, we add
# $(am__append_1) to each definitions.
- #
- # * If $cond is TRUE, we don't need the helper variable. E.g., in
- # if COND1
- # FOO = foo1
- # else
- # FOO = foo2
- # endif
- # FOO += bar
- # we can add bar directly to all definition of FOO, and output
- # @COND_TRUE@FOO = foo1 bar
- # @COND_FALSE@FOO = foo2 bar
-
- my $lastappend = [];
- # Do we need an helper variable?
- if ($cond != TRUE)
- {
- # Can we reuse the helper variable created for the previous
- # append? (We cannot reuse older helper variables because
- # we must preserve the order of items appended to the
- # variable.)
- my $condstr = $cond->string;
- my $key = "$var:$condstr";
- my ($appendvar, $appendvarcond) = @{$self->{'last-append'}};
- if ($appendvar && $condstr eq $appendvarcond)
- {
- # Yes, let's simply append to it.
- $var = $appendvar;
- $owner = VAR_AUTOMAKE;
- $self = var ($var);
- $def = $self->rdef ($cond);
- $new_var = 0;
- }
- else
- {
- # No, create it.
- my $num = ++$_appendvar;
- my $hvar = "am__append_$num";
- $lastappend = [$hvar, $condstr];
- &define ($hvar, VAR_AUTOMAKE, '+',
- $cond, $value, $comment, $where, $pretty);
-
- # Now HVAR is to be added to VAR.
- $comment = '';
- $value = "\$($hvar)";
- }
- }
+ my $num = ++$_appendvar;
+ my $hvar = "am__append_$num";
+ &define ($hvar, VAR_AUTOMAKE, '+',
+ $cond, $value, $comment, $where);
+ # Now HVAR is to be added to VAR.
+ $comment = '';
+ $value = "\$($hvar)";
# Add VALUE to all definitions of SELF.
foreach my $vcond ($self->conditions->conds)
@@ -1004,11 +838,9 @@ sub define ($$$$$$$$)
}
else
{
- &define ($var, $owner, '+', $vcond, $value, $comment,
- $where, $pretty);
+ &define ($var, $owner, '+', $vcond, $value, $comment, $where);
}
}
- $self->{'last-append'} = $lastappend;
}
# 3. first assignment (=, :=, or +=)
else
@@ -1028,16 +860,11 @@ sub define ($$$$$$$$)
# Assignments to a macro set its location. We don't adjust
# locations for '+='. Ideally I suppose we would associate
# line numbers with random bits of text.
- $def = new Automake::VarDef ($var, $value, $comment, $where->clone,
- $type, $owner, $pretty);
+ $def = new Automake::VarDef ($var, $value, $comment, $cond,
+ $where->clone, $type, $owner);
$self->set ($cond, $def);
push @_var_order, $var;
}
-
- # Call any defined hook. This helps to update some internal state
- # *while* parsing the file. For instance the handling of SUFFIXES
- # requires this (see var_SUFFIXES_trigger).
- &{$_hooks{$var}}($type, $value) if exists $_hooks{$var};
}
=item C<variable_delete ($varname, [@conds])>
@@ -1647,7 +1474,7 @@ sub transform_variable_recursively ($$$$$&;%)
foreach (@conds)
{
define ($varname, VAR_AUTOMAKE, '', $_, "@result",
- '', $where, VAR_PRETTY);
+ '', $where);
}
}
}