Fix bug #940 (from the Savannah bug tracker): make sure that target-

specific variables work correctly in conjunction with double-colon
targets.
This commit is contained in:
Paul Smith 2002-09-17 21:52:45 +00:00
parent d7ebcadadb
commit dac7b49de4
5 changed files with 94 additions and 6 deletions

View File

@ -1,3 +1,18 @@
2002-09-17 Paul D. Smith <psmith@gnu.org>
Fix Bug #940 (plus another bug I found while looking at this):
* read.c (record_target_var): enter_file() will add a new entry if
it's a double-colon target: we don't want to do that in this
situation. Invoke lookup_file() and only enter_file() if it does
not already exist. If the file we get back is a double-colon then
add this variable to the "root" double-colon target.
* variable.c (initialize_file_variables): If this file is a
double-colon target but is not the "root" target, then initialize
the root and make the root's variable list the parent of our
variable list.
2002-09-12 Paul D. Smith <psmith@gnu.org> 2002-09-12 Paul D. Smith <psmith@gnu.org>
* Makefile.am (loadavg_SOURCES, loadavg.c): Tiptoe around automake * Makefile.am (loadavg_SOURCES, loadavg.c): Tiptoe around automake

12
read.c
View File

@ -1671,8 +1671,16 @@ record_target_var (filenames, defn, two_colon, origin, flocp)
{ {
struct file *f; struct file *f;
/* Get a file reference for this file, and initialize it. */ /* Get a file reference for this file, and initialize it.
f = enter_file (name); We don't want to just call enter_file() because that allocates a
new entry if the file is a double-colon, which we don't want in
this situation. */
f = lookup_file (name);
if (!f)
f = enter_file (name);
else if (f->double_colon)
f = f->double_colon;
initialize_file_variables (f, 1); initialize_file_variables (f, 1);
vlist = f->variables; vlist = f->variables;
fname = f->name; fname = f->name;

View File

@ -1,3 +1,9 @@
2002-09-17 Paul D. Smith <psmith@gnu.org>
* scripts/features/targetvars: Tests for Bug #940: test
target-specific and pattern-specific variables in conjunction with
double-colon targets.
2002-09-10 Paul D. Smith <psmith@gnu.org> 2002-09-10 Paul D. Smith <psmith@gnu.org>
* test_driver.pl (compare_output): Match the new format for time * test_driver.pl (compare_output): Match the new format for time

View File

@ -194,5 +194,50 @@ close(MAKEFILE);
$answer = "bar snafu bar\n"; $answer = "bar snafu bar\n";
&compare_output($answer, &get_logfile(1)); &compare_output($answer, &get_logfile(1));
# Test #13
# Test double-colon rules with target-specific variable values
$makefile6 = &get_tmpfile;
open(MAKEFILE, "> $makefile6");
print MAKEFILE <<'EOF';
W = bad
X = bad
foo: W = ok
foo:: ; @echo $(W) $(X) $(Y) $(Z)
foo:: ; @echo $(W) $(X) $(Y) $(Z)
foo: X = ok
Y = foo
bar: foo
bar: Y = bar
Z = nopat
ifdef PATTERN
fo% : Z = pat
endif
EOF
close(MAKEFILE);
&run_make_with_options("$makefile6", "foo", &get_logfile);
$answer = "ok ok foo nopat\nok ok foo nopat\n";
&compare_output($answer, &get_logfile(1));
# Test #14
# Test double-colon rules with target-specific variable values and
# inheritance
&run_make_with_options("$makefile6", "bar", &get_logfile);
$answer = "ok ok bar nopat\nok ok bar nopat\n";
&compare_output($answer, &get_logfile(1));
# Test #15
# Test double-colon rules with pattern-specific variable values
&run_make_with_options("$makefile6", "foo PATTERN=yes", &get_logfile);
$answer = "ok ok foo pat\nok ok foo pat\n";
&compare_output($answer, &get_logfile(1));
1; 1;

View File

@ -372,9 +372,12 @@ lookup_variable_in_set (name, length, set)
/* Initialize FILE's variable set list. If FILE already has a variable set /* Initialize FILE's variable set list. If FILE already has a variable set
list, the topmost variable set is left intact, but the the rest of the list, the topmost variable set is left intact, but the the rest of the
chain is replaced with FILE->parent's setlist. If we're READing a chain is replaced with FILE->parent's setlist. If FILE is a double-colon
makefile, don't do the pattern variable search now, since the pattern rule, then we will use the "root" double-colon target's variable set as the
variable might not have been defined yet. */ parent of FILE's variable set.
If we're READing a makefile, don't do the pattern variable search now,
since the pattern variable might not have been defined yet. */
void void
initialize_file_variables (file, reading) initialize_file_variables (file, reading)
@ -389,10 +392,21 @@ initialize_file_variables (file, reading)
xmalloc (sizeof (struct variable_set_list)); xmalloc (sizeof (struct variable_set_list));
l->set = (struct variable_set *) xmalloc (sizeof (struct variable_set)); l->set = (struct variable_set *) xmalloc (sizeof (struct variable_set));
hash_init (&l->set->table, PERFILE_VARIABLE_BUCKETS, hash_init (&l->set->table, PERFILE_VARIABLE_BUCKETS,
variable_hash_1, variable_hash_2, variable_hash_cmp); variable_hash_1, variable_hash_2, variable_hash_cmp);
file->variables = l; file->variables = l;
} }
/* If this is a double-colon, then our "parent" is the "root" target for
this double-colon rule. Since that rule has the same name, parent,
etc. we can just use its variables as the "next" for ours. */
if (file->double_colon && file->double_colon != file)
{
initialize_file_variables (file->double_colon, reading);
l->next = file->double_colon->variables;
return;
}
if (file->parent == 0) if (file->parent == 0)
l->next = &global_setlist; l->next = &global_setlist;
else else