- Modify access of config and gnulib Savannah modules to use GIT

- Fix Savannah bug #24655.
- Fix Savannah bug #24588.
- Fix Savannah bug #24277.
- Fix Savannah bug #25697.
- Fix Savannah bug #25694.
- Fix Savannah bug #25460.
- Fix Savannah bug #26207.
- Fix Savannah bug #25712.
- Fix Savannah bug #26593.
- Fix various doc issues.
This commit is contained in:
Paul Smith 2009-06-04 06:30:27 +00:00
parent 5b4d419476
commit 81f3e4babd
20 changed files with 523 additions and 437 deletions

View file

@ -1,3 +1,67 @@
2009-06-04 Paul Smith <psmith@gnu.org>
* maintMakefile: Modify access of config and gnulib Savannah
modules to use GIT instead of CVS.
* main.c (main): Initialize the LENGTH field in SHELL_VAR.
Fixes Savannah bug #24655.
* read.c (eval_buffer): Don't dereference reading_file if it's NULL;
this can happen during some invocations of $(eval ...) for example.
Fixes Savannah bug #24588. Patch by Lars Jessen <ljessen@ljessen.dk>
2009-06-02 Paul Smith <psmith@gnu.org>
* configure.in: Check for fileno()
* read.c (eval_makefile): If fileno() is available, set CLOSE_ON_EXEC
for the makefile file so invocations of $(shell ...) don't inherit it.
Fixes Savannah bug #24277.
2009-06-01 Paul Smith <psmith@gnu.org>
* main.c (main): The previous fix for .DEFAULT_GOAL had issues;
expansion was handled incorrectly. Rework the default goal
handling to save the variable only. Remove default_goal_file and
default_goal_name.
* read.c (eval): Check default_goal_var, not default_goal_name.
* read.c (record_target_var): Don't check default_goal_file here.
2009-05-31 Paul Smith <psmith@gnu.org>
* main.c (main): Expand the .DEFAULT_GOAL variable before using
it, and if the multi_glob() returns nothing (say it expanded to
nothing but spaces) then don't crash. Fixes Savannah bug #25697.
* doc/make.texi (Quick Reference): Add $(if ..), $(or ..), and
$(and ..) to the reference. Fixes Savannah bug #25694.
* make.1: Be clear that some recipes will be executed even with -n.
* doc/make.texi: Ditto. Fixes Savannah bug #25460.
* doc/make.texi (Override Directive): Make more clear how
overrides and appends interact.
Elucidates part of Savannah bug #26207.
* read.c (record_target_var): Don't reset the origin on
target-specific variables; try_variable_definition() will handle
this correctly. Fixes Savannah bug #26207.
* maintMakefile (do-po-update): Copy PO files into $(top_srcdir).
Fixes Savannah bug #25712.
* implicit.c (pattern_search): Keep a pointer to the beginning of
the filename and save that instead of the constructed pointer.
Fixes Savannah bug #26593.
Patch by Mark Seaborn <mrs@mythic-beasts.com>
2009-05-30 Paul Smith <psmith@gnu.org>
* doc/make.texi (Multi-Line): Add a description of the new abilities
of define/endef. Rename "Sequences" to "Multi-Line" and fix some
"command sequence" vs. "recipe" syntax.
* read.c (do_define): Modify to allow assignment tokens (=, :=, etc.)
after a define, to create variables with those flavors.
2009-05-25 Paul Smith <psmith@gnu.org>
Reworked the parser for variable assignments to allow multiple

View file

@ -147,7 +147,7 @@ if test "$ac_cv_func_gettimeofday" = yes; then
[Define to 1 if you have a standard gettimeofday function])
fi
AC_CHECK_FUNCS( strdup strndup mkstemp mktemp fdopen \
AC_CHECK_FUNCS( strdup strndup mkstemp mktemp fdopen fileno \
bsd_signal dup2 getcwd realpath sigsetmask sigaction \
getgroups seteuid setegid setlinebuf setreuid setregid \
getrlimit setrlimit setvbuf pipe strerror strsignal \

View file

@ -25,8 +25,8 @@ and issues the commands to recompile them.
This is Edition @value{EDITION}, last updated @value{UPDATED},
of @cite{The GNU Make Manual}, for GNU @code{make} version @value{VERSION}.
Copyright @copyright{} 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
1996, 1997, 1998, 1999, 2000, 2002, 2003, 2004, 2005, 2006, 2007
Copyright @copyright{} 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996,
1997, 1998, 1999, 2000, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
Free Software Foundation, Inc.
@quotation
@ -38,8 +38,8 @@ and with the Back-Cover Texts as in (a) below. A copy of the
license is included in the section entitled ``GNU Free Documentation
License.''
(a) The FSF's Back-Cover Text is: ``You are free to copy and modify
this GNU Manual. Buying copies from GNU Press supports the FSF in
(a) The FSF's Back-Cover Text is: ``You have the freedom to copy and
modify this GNU manual. Buying copies from the FSF supports it in
developing GNU and promoting software freedom.''
@end quotation
@end copying
@ -201,7 +201,7 @@ Writing Recipes in Rules
* Errors:: What happens after a recipe execution error.
* Interrupts:: What happens when a recipe is interrupted.
* Recursion:: Invoking @code{make} from makefiles.
* Sequences:: Defining canned recipes.
* Canned Recipes:: Defining canned recipes.
* Empty Recipes:: Defining useful, do-nothing recipes.
Recipe Syntax
@ -233,8 +233,8 @@ How to Use Variables
of a variable.
* Override Directive:: How to set a variable in the makefile even if
the user has set it with a command argument.
* Defining:: An alternate way to set a variable
to a verbatim string.
* Multi-Line:: An alternate way to set a variable
to a multi-line string.
* Environment:: Variable values can come from the environment.
* Target-specific:: Variable values can be defined on a per-target
basis.
@ -996,7 +996,7 @@ ignore a part of the makefile (@pxref{Conditionals, ,Conditional Parts of Makefi
@item
Defining a variable from a verbatim string containing multiple lines
(@pxref{Defining, ,Defining Variables Verbatim}).
(@pxref{Multi-Line, ,Defining Multi-Line Variables}).
@end itemize
@cindex comments, in makefile
@ -1269,7 +1269,7 @@ that it is not an error if @code{make} cannot find or make any makefile;
a makefile is not always necessary.@refill
When you use the @samp{-t} or @samp{--touch} option
(@pxref{Instead of Execution, ,Instead of Executing the Recipe}),
(@pxref{Instead of Execution, ,Instead of Executing Recipes}),
you would not want to use an out-of-date makefile to decide which
targets to touch. So the @samp{-t} option has no effect on updating
makefiles; they are really updated even if @samp{-t} is specified.
@ -1388,6 +1388,22 @@ Variable definitions are parsed as follows:
define @var{immediate}
@var{deferred}
endef
define @var{immediate} =
@var{deferred}
endef
define @var{immediate} ?=
@var{deferred}
endef
define @var{immediate} :=
@var{immediate}
endef
define @var{immediate} +=
@var{deferred} or @var{immediate}
endef
@end example
For the append operator, @samp{+=}, the right-hand side is considered
@ -3361,7 +3377,7 @@ otherwise. @xref{Execution, ,Command Execution}.
* Errors:: What happens after a recipe execution error.
* Interrupts:: What happens when a recipe is interrupted.
* Recursion:: Invoking @code{make} from makefiles.
* Sequences:: Defining canned recipes.
* Canned Recipes:: Defining canned recipes.
* Empty Recipes:: Defining useful, do-nothing recipes.
@end menu
@ -3629,12 +3645,12 @@ the makefile:
@cindex @code{--just-print}
@cindex @code{--dry-run}
@cindex @code{--recon}
When @code{make} is given the flag @samp{-n} or @samp{--just-print}
it only echoes recipes, it won't execute them. @xref{Options Summary,
,Summary of Options}. In this case and only this case, even the
recipe lines starting with @samp{@@} are printed. This flag is useful for
finding out which recipes @code{make} thinks are necessary without
actually doing them.
When @code{make} is given the flag @samp{-n} or @samp{--just-print} it
only echoes most recipes, without executing them. @xref{Options
Summary, ,Summary of Options}. In this case even the recipe lines
starting with @samp{@@} are printed. This flag is useful for finding
out which recipes @code{make} thinks are necessary without actually
doing them.
@cindex @code{-s}
@cindex @code{--silent}
@ -4014,7 +4030,7 @@ target is updated in some atomic fashion, or exists only to record a
modification-time (its contents do not matter), or must exist at all
times to prevent other sorts of trouble.
@node Recursion, Sequences, Interrupts, Recipes
@node Recursion, Canned Recipes, Interrupts, Recipes
@section Recursive Use of @code{make}
@cindex recursion
@cindex subdirectories, recursion for
@ -4360,7 +4376,7 @@ supports it (most any UNIX system will; others typically won't), the
parent @code{make} and all the sub-@code{make}s will communicate to
ensure that there are only @samp{N} jobs running at the same time
between them all. Note that any job that is marked recursive
(@pxref{Instead of Execution, ,Instead of Executing the Recipes})
(@pxref{Instead of Execution, ,Instead of Executing Recipes})
doesn't count against the total jobs (otherwise we could get @samp{N}
sub-@code{make}s running and have no slots left over for any real work!)
@ -4496,7 +4512,7 @@ automatically turn on @samp{-w} if you also use @samp{-s}, which says to
be silent, or if you use @samp{--no-print-directory} to explicitly
disable it.
@node Sequences, Empty Recipes, Recursion, Recipes
@node Canned Recipes, Empty Recipes, Recursion, Recipes
@section Defining Canned Recipes
@cindex canned recipes
@cindex recipes, canned
@ -4509,10 +4525,10 @@ directive, and refer to the canned sequence from the recipes for those
targets. The canned sequence is actually a variable, so the name must
not conflict with other variable names.
Here is an example of defining a canned recipes:
Here is an example of defining a canned recipe:
@example
define run-yacc
define run-yacc =
yacc $(firstword $^)
mv y.tab.c $@@
endef
@ -4526,7 +4542,7 @@ commands. The @code{define} directive does not expand variable references
and function calls in the canned sequence; the @samp{$} characters,
parentheses, variable names, and so on, all become part of the value of the
variable you are defining.
@xref{Defining, ,Defining Variables Verbatim},
@xref{Multi-Line, ,Defining Multi-Line Variables},
for a complete explanation of @code{define}.
The first command in this example runs Yacc on the first prerequisite of
@ -4567,7 +4583,7 @@ can use the special prefix characters that affect command lines
For example, using this canned sequence:
@example
define frobnicate
define frobnicate =
@@echo "frobnicating target $@@"
frob-step-1 $< -o $@@-step-1
frob-step-2 $@@-step-1 -o $@@
@ -4590,7 +4606,7 @@ frob.out: frob.in
does not echo @emph{any} recipe lines.
(@xref{Echoing, ,Recipe Echoing}, for a full explanation of @samp{@@}.)
@node Empty Recipes, , Sequences, Recipes
@node Empty Recipes, , Canned Recipes, Recipes
@section Using Empty Recipes
@cindex empty recipes
@cindex recipes, empty
@ -4685,8 +4701,8 @@ they have particular specialized uses. @xref{Automatic Variables}.
of a variable.
* Override Directive:: How to set a variable in the makefile even if
the user has set it with a command argument.
* Defining:: An alternate way to set a variable
to a verbatim string.
* Multi-Line:: An alternate way to set a variable
to a multi-line string.
* Environment:: Variable values can come from the environment.
* Target-specific:: Variable values can be defined on a per-target
basis.
@ -4762,7 +4778,7 @@ distinguished in how they are defined and in what they do when expanded.
The first flavor of variable is a @dfn{recursively expanded} variable.
Variables of this sort are defined by lines using @samp{=}
(@pxref{Setting, ,Setting Variables}) or by the @code{define} directive
(@pxref{Defining, ,Defining Variables Verbatim}). The value you specify
(@pxref{Multi-Line, ,Defining Multi-Line Variables}). The value you specify
is installed verbatim; if it contains references to other variables,
these references are expanded whenever this variable is substituted (in
the course of expanding some other string). When this happens, it is
@ -5189,7 +5205,7 @@ variable assignment, or in a @code{define} directive, as in:
@example
dir = foo
$(dir)_sources := $(wildcard $(dir)/*.c)
define $(dir)_print
define $(dir)_print =
lpr $($(dir)_sources)
endef
@end example
@ -5218,7 +5234,7 @@ You can specify an overriding value when you run @code{make}.
@item
You can specify a value in the makefile, either
with an assignment (@pxref{Setting, ,Setting Variables}) or with a
verbatim definition (@pxref{Defining, ,Defining Variables Verbatim}).@refill
verbatim definition (@pxref{Multi-Line, ,Defining Multi-Line Variables}).@refill
@item
Variables in the environment become @code{make} variables.
@ -5426,7 +5442,7 @@ the reference to @code{includes}, so if that variable gets defined at
any later point, a reference like @samp{$(CFLAGS)} still uses its
value.
@node Override Directive, Defining, Appending, Using Variables
@node Override Directive, Multi-Line, Appending, Using Variables
@section The @code{override} Directive
@findex override
@cindex overriding with @code{override}
@ -5459,6 +5475,11 @@ override @var{variable} += @var{more text}
@noindent
@xref{Appending, ,Appending More Text to Variables}.
Variable assignments marked with the @code{override} flag have a
higher priority than all other assignments, except another
@code{override}. Subsequent assignments or appends to this variable
which are not marked @code{override} will be ignored.
The @code{override} directive was not invented for escalation in the war
between makefiles and command arguments. It was invented so you can alter
and add to values that the user specifies with command arguments.
@ -5476,7 +5497,7 @@ You can also use @code{override} directives with @code{define} directives.
This is done as you might expect:
@example
override define foo
override define foo =
bar
endef
@end example
@ -5486,43 +5507,52 @@ endef
See the next section for information about @code{define}.
@end iftex
@ifnottex
@xref{Defining, ,Defining Variables Verbatim}.
@xref{Multi-Line, ,Defining Multi-Line Variables}.
@end ifnottex
@node Defining, Environment, Override Directive, Using Variables
@section Defining Variables Verbatim
@node Multi-Line, Environment, Override Directive, Using Variables
@section Defining Multi-Line Variables
@findex define
@findex endef
@cindex multi-line variable definition
@cindex variables, multi-line
@cindex verbatim variable definition
@cindex defining variables verbatim
@cindex variables, defining verbatim
Another way to set the value of a variable is to use the @code{define}
directive. This directive has an unusual syntax which allows newline
characters to be included in the value, which is convenient for defining
both canned sequences of commands
(@pxref{Sequences, ,Defining Canned Command Sequences}), and also
sections of makefile syntax to use with @code{eval} (@pxref{Eval Function}).
characters to be included in the value, which is convenient for
defining both canned sequences of commands (@pxref{Canned Recipes,
,Defining Canned Recipes}), and also sections of makefile syntax to
use with @code{eval} (@pxref{Eval Function}).@refill
The @code{define} directive is followed on the same line by the name of the
variable and nothing more. The value to give the variable appears on the
following lines. The end of the value is marked by a line containing just
the word @code{endef}. Aside from this difference in syntax, @code{define}
works just like @samp{=}: it creates a recursively-expanded variable
(@pxref{Flavors, ,The Two Flavors of Variables}).
The variable name may contain function and variable references, which
are expanded when the directive is read to find the actual variable name
The @code{define} directive is followed on the same line by the name
of the variable being defined and an (optional) assignment operator,
and nothing more. The value to give the variable appears on the
following lines. The end of the value is marked by a line containing
just the word @code{endef}. Aside from this difference in syntax,
@code{define} works just like any other variable definition. The
variable name may contain function and variable references, which are
expanded when the directive is read to find the actual variable name
to use.
You may omit the variable assignment operator if you prefer. If
omitted, @code{make} assumes it to be @samp{=} and creates a
recursively-expanded variable (@pxref{Flavors, ,The Two Flavors of Variables}).
When using a @samp{+=} operator, the value is appended to the previous
value as with any other append operation: with a single space
separating the old and new values.
You may nest @code{define} directives: @code{make} will keep track of
nested directives and report an error if they are not all properly
closed with @code{endef}. Note that lines beginning with the recipe
prefix character are considered part of a recipe, so any @code{define}
or @code{endef} strings appearing on such a line will not be
considered @code{make} operators.
considered @code{make} directives.
@example
define two-lines
define two-lines =
echo foo
echo $(bar)
endef
@ -5552,7 +5582,7 @@ precedence over command-line variable definitions, you can use the
@code{override} directive together with @code{define}:
@example
override define two-lines
override define two-lines =
foo
$(bar)
endef
@ -5561,7 +5591,7 @@ endef
@noindent
@xref{Override Directive, ,The @code{override} Directive}.
@node Environment, Target-specific, Defining, Using Variables
@node Environment, Target-specific, Multi-Line, Using Variables
@section Variables from the Environment
@cindex variables, environment
@ -7193,7 +7223,7 @@ client_LIBS = protocol
.PHONY: all
all: $(PROGRAMS)
define PROGRAM_template
define PROGRAM_template =
$(1): $$($(1)_OBJS) $$($(1)_LIBS:%=-l%)
ALL_OBJS += $$($(1)_OBJS)
endef
@ -7246,14 +7276,15 @@ function will return the origin of the later definition.
@item environment
if @var{variable} was defined as an environment variable and the
@samp{-e} option is @emph{not} turned on (@pxref{Options Summary, ,Summary of Options}).
if @var{variable} was inherited from the environment provided to
@code{make}.
@item environment override
if @var{variable} was defined as an environment variable and the
@w{@samp{-e}} option @emph{is} turned on (@pxref{Options Summary,
,Summary of Options}).@refill
if @var{variable} was inherited from the environment provided to
@code{make}, and is overriding a setting for @var{variable} in the
makefile as a result of the @w{@samp{-e}} option (@pxref{Options
Summary, ,Summary of Options}).@refill
@item file
@ -7494,7 +7525,7 @@ It will print messages describing the particular errors.
@item 1
The exit status is one if you use the @samp{-q} flag and @code{make}
determines that some target is not already up to date.
@xref{Instead of Execution, ,Instead of Executing the Recipes}.
@xref{Instead of Execution, ,Instead of Executing Recipes}.
@end table
@menu
@ -7671,7 +7702,7 @@ Perform self tests on the program this makefile builds.
@end table
@node Instead of Execution, Avoiding Compilation, Goals, Running
@section Instead of Executing the Recipes
@section Instead of Executing Recipes
@cindex execution, instead of
@cindex recipes, instead of executing
@ -7691,7 +7722,8 @@ what you want. Certain options specify other activities for @code{make}.
@cindex @code{-n}
``No-op''. The activity is to print what recipe would be used to make
the targets up to date, but not actually execute it.
the targets up to date, but not actually execute it. Some recipes are
still executed, even with this flag (@pxref{MAKE Variable, ,How the @code{MAKE} Variable Works}).
@item -t
@itemx --touch
@ -7733,7 +7765,7 @@ to see what would happen if you were to modify specific files.@refill
@end table
With the @samp{-n} flag, @code{make} prints the recipe that it would
normally execute but does not execute it.
normally execute but usually does not execute it.
With the @samp{-t} flag, @code{make} ignores the recipes in the rules
and uses (in effect) the command @code{touch} for each target that needs to
@ -8108,8 +8140,9 @@ links is taken as the modification time for this target file.
@cindex @code{--recon}
@c Extra blank line here makes the table look better.
Print the recipe that would be executed, but do not execute it.
@xref{Instead of Execution, ,Instead of Executing the Recipes}.
Print the recipe that would be executed, but do not execute it (except
in certain circumstances).
@xref{Instead of Execution, ,Instead of Executing Recipes}.
@item -o @var{file}
@cindex @code{-o}
@ -8146,7 +8179,7 @@ in complex environments.
``Question mode''. Do not run any recipes, or print anything; just
return an exit status that is zero if the specified targets are already
up to date, one if any remaking is required, or two if an error is
encountered. @xref{Instead of Execution, ,Instead of Executing the
encountered. @xref{Instead of Execution, ,Instead of Executing
Recipes}.@refill
@item -r
@ -8208,7 +8241,7 @@ or if you set @samp{-k} in @code{MAKEFLAGS} in your environment.@refill
Touch files (mark them up to date without really changing them)
instead of running their recipes. This is used to pretend that the
recipes were done, in order to fool future invocations of
@code{make}. @xref{Instead of Execution, ,Instead of Executing the Recipes}.
@code{make}. @xref{Instead of Execution, ,Instead of Executing Recipes}.
@item -v
@cindex @code{-v}
@ -8249,7 +8282,7 @@ to modify that file. Without @samp{-n}, it is almost the same as
running a @code{touch} command on the given file before running
@code{make}, except that the modification time is changed only in the
imagination of @code{make}.
@xref{Instead of Execution, ,Instead of Executing the Recipes}.
@xref{Instead of Execution, ,Instead of Executing Recipes}.
@item --warn-undefined-variables
@cindex @code{--warn-undefined-variables}
@ -10102,7 +10135,7 @@ did. @xref{Automatic Variables}. The automatic variable
@item
The ``what if'' flag (@samp{-W} in GNU @code{make}) was (as far as we know)
invented by Andrew Hume in @code{mk}.
@xref{Instead of Execution, ,Instead of Executing the Recipes}.
@xref{Instead of Execution, ,Instead of Executing Recipes}.
@item
The concept of doing several things at once (parallelism) exists in
@ -10120,7 +10153,7 @@ inspired whom, since GNU @code{make} had @code{patsubst} before SunOS
@item
The special significance of @samp{+} characters preceding recipe lines
(@pxref{Instead of Execution, ,Instead of Executing the Recipes}) is
(@pxref{Instead of Execution, ,Instead of Executing Recipes}) is
mandated by @cite{IEEE Standard 1003.2-1992} (POSIX.2).
@item
@ -10165,7 +10198,7 @@ directory. @xref{Options Summary, ,Summary of Options}.
@item
Make verbatim variable definitions with @code{define}.
@xref{Defining, ,Defining Variables Verbatim}.
@xref{Multi-Line, ,Defining Multi-Line Variables}.
@item
Declare phony targets with the special target @code{.PHONY}.
@ -10373,10 +10406,13 @@ Here is a summary of the directives GNU @code{make} recognizes:
@table @code
@item define @var{variable}
@itemx define @var{variable} =
@itemx define @var{variable} :=
@itemx define @var{variable} +=
@itemx define @var{variable} ?=
@itemx endef
Define a multi-line, recursively-expanded variable.@*
@xref{Sequences}.
Define multi-line variables.@*
@xref{Multi-Line}.
@item ifdef @var{variable}
@itemx ifndef @var{variable}
@ -10388,43 +10424,35 @@ Define a multi-line, recursively-expanded variable.@*
@itemx ifneq '@var{a}' '@var{b}'
@itemx else
@itemx endif
Conditionally evaluate part of the makefile.@*
@xref{Conditionals}.
@item include @var{file}
@itemx -include @var{file}
@itemx sinclude @var{file}
Include another makefile.@*
@xref{Include, ,Including Other Makefiles}.
@item override @var{variable} = @var{value}
@itemx override @var{variable} := @var{value}
@itemx override @var{variable} += @var{value}
@itemx override @var{variable} ?= @var{value}
@itemx override define @var{variable}
@itemx endef
@item override @var{variable-assignment}
Define a variable, overriding any previous definition, even one from
the command line.@*
@xref{Override Directive, ,The @code{override} Directive}.
@item export
Tell @code{make} to export all variables to child processes by default.@*
@xref{Variables/Recursion, , Communicating Variables to a Sub-@code{make}}.
@item export @var{variable}
@itemx export @var{variable} = @var{value}
@itemx export @var{variable} := @var{value}
@itemx export @var{variable} += @var{value}
@itemx export @var{variable} ?= @var{value}
@itemx export @var{variable-assignment}
@itemx unexport @var{variable}
Tell @code{make} whether or not to export a particular variable to child
processes.@*
@xref{Variables/Recursion, , Communicating Variables to a Sub-@code{make}}.
@item private @var{variable-assignment}
Do not allow this variable assignment to be inherited by prerequisites.@*
@xref{Suppressing Inheritance}.
@item vpath @var{pattern} @var{path}
Specify a search path for files matching a @samp{%} pattern.@*
@xref{Selective Search, , The @code{vpath} Directive}.
@ -10533,54 +10561,64 @@ symlinks.@*
@xref{File Name Functions, ,Functions for File Names}.
@item $(error @var{text}@dots{})
When this function is evaluated, @code{make} generates a fatal error
with the message @var{text}.@*
@xref{Make Control Functions, ,Functions That Control Make}.
@item $(warning @var{text}@dots{})
When this function is evaluated, @code{make} generates a warning with
the message @var{text}.@*
@xref{Make Control Functions, ,Functions That Control Make}.
@item $(shell @var{command})
Execute a shell command and return its output.@*
@xref{Shell Function, , The @code{shell} Function}.
@item $(origin @var{variable})
Return a string describing how the @code{make} variable @var{variable} was
defined.@*
@xref{Origin Function, , The @code{origin} Function}.
@item $(flavor @var{variable})
Return a string describing the flavor of the @code{make} variable
@var{variable}.@*
@xref{Flavor Function, , The @code{flavor} Function}.
@item $(foreach @var{var},@var{words},@var{text})
Evaluate @var{text} with @var{var} bound to each word in @var{words},
and concatenate the results.@*
@xref{Foreach Function, ,The @code{foreach} Function}.
@item $(call @var{var},@var{param},@dots{})
@item $(if @var{condition},@var{then-part}[,@var{else-part}])
Evaluate the condition @var{condition}; if it's non-empty substitute
the expansion of the @var{then-part} otherwise substitute the
expansion of the @var{else-part}.@*
@xref{Conditional Functions, ,Functions for Conditionals}.
@item $(or @var{condition1}[,@var{condition2}[,@var{condition3}@dots{}]])
Evaluate each condition @var{conditionN} one at a time; substitute the
first non-empty expansion. If all expansions are empty, substitute
the empty string.@*
@xref{Conditional Functions, ,Functions for Conditionals}.
@item $(and @var{condition1}[,@var{condition2}[,@var{condition3}@dots{}]])
Evaluate each condition @var{conditionN} one at a time; if any
expansion results in the empty string substitute the empty string. If
all expansions result in a non-empty string, substitute the expansion
of the last @var{condition}.@*
@xref{Conditional Functions, ,Functions for Conditionals}.
@item $(call @var{var},@var{param},@dots{})
Evaluate the variable @var{var} replacing any references to @code{$(1)},
@code{$(2)} with the first, second, etc.@: @var{param} values.@*
@xref{Call Function, ,The @code{call} Function}.
@item $(eval @var{text})
Evaluate @var{text} then read the results as makefile commands.
Expands to the empty string.@*
@xref{Eval Function, ,The @code{eval} Function}.
@item $(value @var{var})
Evaluates to the contents of the variable @var{var}, with no expansion
performed on it.@*
@xref{Value Function, ,The @code{value} Function}.

3
file.c
View file

@ -738,7 +738,8 @@ snap_deps (void)
*/
#endif
/* Remember that we've done this. */
/* Remember that we've done this. Once done we can no longer define
new targets. */
snapped_deps = 1;
}

View file

@ -97,8 +97,7 @@ struct file
};
extern struct file *default_goal_file, *suffix_file, *default_file;
extern char **default_goal_name;
extern struct file *suffix_file, *default_file;
struct file *lookup_file (const char *name);

View file

@ -917,7 +917,8 @@ pattern_search (struct file *file, int archive,
for (ri = 0; ri < rule->num; ++ri)
if (ri != matches[foundrule])
{
char *p = alloca (rule->lens[ri] + fullstemlen + 1);
char *nm = alloca (rule->lens[ri] + fullstemlen + 1);
char *p = nm;
struct file *f;
struct dep *new = alloc_dep ();
@ -929,7 +930,7 @@ pattern_search (struct file *file, int archive,
p += fullstemlen;
memcpy (p, rule->suffixes[ri],
rule->lens[ri] - (rule->suffixes[ri] - rule->targets[ri])+1);
new->name = strcache_add (p);
new->name = strcache_add (nm);
new->file = enter_file (new->name);
new->next = file->also_make;

137
main.c
View file

@ -468,15 +468,13 @@ char *starting_directory;
unsigned int makelevel;
/* First file defined in the makefile whose name does not
start with `.'. This is the default to remake if the
command line does not specify. */
/* Pointer to the value of the .DEFAULT_GOAL special variable.
The value will be the name of the goal to remake if the command line
does not override it. It can be set by the makefile, or else it's
the first target defined in the makefile whose name does not start
with '.'. */
struct file *default_goal_file;
/* Pointer to the value of the .DEFAULT_GOAL special
variable. */
char ** default_goal_name;
struct variable * default_goal_var;
/* Pointer to structure for the file .DEFAULT
whose commands are used for any file that has none of its own.
@ -945,7 +943,6 @@ main (int argc, char **argv, char **envp)
/* Needed for OS/2 */
initialize_main(&argc, &argv);
default_goal_file = 0;
reading_file = 0;
#if defined (__MSDOS__) && !defined (_POSIX_SOURCE)
@ -1186,6 +1183,7 @@ main (int argc, char **argv, char **envp)
v->export = v_noexport;
#endif
shell_var.name = "SHELL";
shell_var.length = 5;
shell_var.value = xstrdup (ep + 1);
}
@ -1603,10 +1601,7 @@ main (int argc, char **argv, char **envp)
default_file = enter_file (strcache_add (".DEFAULT"));
{
struct variable *v = define_variable (".DEFAULT_GOAL", 13, "", o_file, 0);
default_goal_name = &v->value;
}
default_goal_var = define_variable (".DEFAULT_GOAL", 13, "", o_file, 0);
/* Read all the makefiles. */
@ -2159,62 +2154,72 @@ main (int argc, char **argv, char **envp)
if (stdin_nm && unlink (stdin_nm) < 0 && errno != ENOENT)
perror_with_name (_("unlink (temporary file): "), stdin_nm);
/* If there were no command-line goals, use the default. */
if (goals == 0)
{
char *p;
if (default_goal_var->recursive)
p = variable_expand (default_goal_var->value);
else
{
p = variable_buffer_output (variable_buffer, default_goal_var->value,
strlen (default_goal_var->value));
*p = '\0';
p = variable_buffer;
}
if (*p != '\0')
{
struct file *f = lookup_file (p);
/* If .DEFAULT_GOAL is a non-existent target, enter it into the
table and let the standard logic sort it out. */
if (f == 0)
{
struct nameseq *ns;
ns = multi_glob (parse_file_seq (&p, '\0', sizeof (struct nameseq), 1),
sizeof (struct nameseq));
if (ns)
{
/* .DEFAULT_GOAL should contain one target. */
if (ns->next != 0)
fatal (NILF, _(".DEFAULT_GOAL contains more than one target"));
f = enter_file (strcache_add (ns->name));
ns->name = 0; /* It was reused by enter_file(). */
free_ns_chain (ns);
}
}
if (f)
{
goals = alloc_dep ();
goals->file = f;
}
}
}
else
lastgoal->next = 0;
if (!goals)
{
if (read_makefiles == 0)
fatal (NILF, _("No targets specified and no makefile found"));
fatal (NILF, _("No targets"));
}
/* Update the goals. */
DB (DB_BASIC, (_("Updating goal targets....\n")));
{
int status;
/* If there were no command-line goals, use the default. */
if (goals == 0)
{
if (**default_goal_name != '\0')
{
if (default_goal_file == 0 ||
strcmp (*default_goal_name, default_goal_file->name) != 0)
{
default_goal_file = lookup_file (*default_goal_name);
/* In case user set .DEFAULT_GOAL to a non-existent target
name let's just enter this name into the table and let
the standard logic sort it out. */
if (default_goal_file == 0)
{
struct nameseq *ns;
char *p = *default_goal_name;
ns = multi_glob (
parse_file_seq (&p, '\0', sizeof (struct nameseq), 1),
sizeof (struct nameseq));
/* .DEFAULT_GOAL should contain one target. */
if (ns->next != 0)
fatal (NILF, _(".DEFAULT_GOAL contains more than one target"));
default_goal_file = enter_file (strcache_add (ns->name));
ns->name = 0; /* It was reused by enter_file(). */
free_ns_chain (ns);
}
}
goals = alloc_dep ();
goals->file = default_goal_file;
}
}
else
lastgoal->next = 0;
if (!goals)
{
if (read_makefiles == 0)
fatal (NILF, _("No targets specified and no makefile found"));
fatal (NILF, _("No targets"));
}
/* Update the goals. */
DB (DB_BASIC, (_("Updating goal targets....\n")));
switch (update_goal_chain (goals))
{
case -1:

View file

@ -143,14 +143,12 @@ do-po-update:
&& mkdir "$$tmppo" \
&& (cd "$$tmppo" \
&& $(WGET) -r -l1 -nd --no-parent -A '*.po' $(po_repo)) \
&& cp "$$tmppo"/*.po po && rm -rf "$$tmppo"
&& cp "$$tmppo"/*.po $(top_srcdir)/po && rm -rf "$$tmppo"
cd po && $(MAKE) update-po
$(MAKE) po-check
po-update:
if test -d "po"; then \
$(MAKE) do-po-update; \
fi
[ -d "po" ] && $(MAKE) do-po-update
# -------------------------- #
# Updating GNU build files. #
@ -160,29 +158,30 @@ po-update:
# with each of the files that belongs to some other package and is
# regularly updated from the specified URL.
savannah-url = http://savannah.gnu.org/cgi-bin/viewcvs/~checkout~
cvs-url = http://savannah.gnu.org/cgi-bin/viewcvs/~checkout~
git-url = http://git.savannah.gnu.org/cgit
target = $(patsubst get-%,%,$@)
config-url = $(savannah-url)/config/config/$(patsubst get-config/%,%,$@)
config-url = $(git-url)/config.git/plain/$(patsubst get-config/%,%,$@)
get-config/config.guess get-config/config.sub:
@echo $(WGET) $(config-url) -O $(target) \
&& $(WGET) $(config-url) -O $(target).t \
&& $(move_if_change)
gnulib-url = $(savannah-url)/gnulib/gnulib/build-aux/$(patsubst get-config/%,%,$@)
gnulib-url = $(git-url)/gnulib.git/plain/build-aux/$(patsubst get-config/%,%,$@)
get-config/texinfo.tex:
@echo $(WGET) $(gnulib-url) -O $(target) \
&& $(WGET) $(gnulib-url) -O $(target).t \
&& $(move_if_change)
gnustandards-url = $(savannah-url)/gnustandards/gnustandards/$(patsubst get-doc/%,%,$@)
gnustandards-url = $(cvs-url)/gnustandards/gnustandards/$(patsubst get-doc/%,%,$@)
get-doc/make-stds.texi get-doc/fdl.texi:
@echo $(WGET) $(gnustandards-url) -O $(target) \
&& $(WGET) $(gnustandards-url) -O $(target).t \
&& $(move_if_change)
.PHONY: cvs-update
cvs-update: get-config/texinfo.tex get-config/config.guess get-config/config.sub get-doc/make-stds.texi get-doc/fdl.texi
.PHONY: scm-update
scm-update: get-config/texinfo.tex get-config/config.guess get-config/config.sub get-doc/make-stds.texi get-doc/fdl.texi
# --------------------- #
@ -190,7 +189,7 @@ cvs-update: get-config/texinfo.tex get-config/config.guess get-config/config.sub
# --------------------- #
.PHONY: update
update: po-update cvs-update
update: po-update scm-update
## --------------- ##
@ -204,7 +203,7 @@ local-check: po-check changelog-check
# copyright-check writable-files
changelog-check:
if head ChangeLog | grep 'Version $(VERSION)' >/dev/null; then \
if head $(top_srcdir)/ChangeLog | grep 'Version $(VERSION)' >/dev/null; then \
:; \
else \
echo "$(VERSION) not in ChangeLog" 1>&2; \

3
make.1
View file

@ -223,7 +223,8 @@ With no argument, removes a previous load limit.
Use the latest mtime between symlinks and target.
.TP 0.5i
.BR \-n , " \-\-just\-print" , " \-\-dry\-run" , " \-\-recon"
Print the commands that would be executed, but do not execute them.
Print the commands that would be executed, but do not execute them (except in
certain circumstances).
.TP 0.5i
\fB\-o\fR \fIfile\fR, \fB\-\-old\-file\fR=\fIfile\fR, \fB\-\-assume\-old\fR=\fIfile\fR
Do not remake the file

6
misc.c
View file

@ -112,11 +112,13 @@ collapse_continuations (char *line)
/* Skip the newline. */
++in;
/* If the newline is quoted, discard following whitespace
and any preceding whitespace; leave just one space. */
/* If the newline is escaped, discard following whitespace leaving just
one space. POSIX requires that each backslash/newline/following
whitespace sequence be reduced to a single space. */
if (backslash)
{
in = next_token (in);
/* Removing this loop will fix Savannah bug #16670: do we want to? */
while (out > line && isblank ((unsigned char)out[-1]))
--out;
*out++ = ' ';

136
read.c
View file

@ -136,8 +136,7 @@ static int eval_makefile (const char *filename, int flags);
static int eval (struct ebuffer *buffer, int flags);
static long readline (struct ebuffer *ebuf);
static struct variable *do_define (char *name, unsigned int namelen,
enum variable_origin origin,
static struct variable *do_define (char *name, enum variable_origin origin,
struct ebuffer *ebuf);
static int conditional_line (char *line, int len, const struct floc *flocp);
static void record_files (struct nameseq *filenames, const char *pattern,
@ -400,6 +399,12 @@ eval_makefile (const char *filename, int flags)
return 0;
}
/* Set close-on-exec to avoid leaking the makefile to children, such as
$(shell ...). */
#ifdef HAVE_FILENO
CLOSE_ON_EXEC (fileno (ebuf.fp));
#endif
/* Add this makefile to the list. */
do_variable_definition (&ebuf.floc, "MAKEFILE_LIST", filename, o_file,
f_append, 0);
@ -438,7 +443,10 @@ eval_buffer (char *buffer)
ebuf.buffer = ebuf.bufnext = ebuf.bufstart = buffer;
ebuf.fp = NULL;
ebuf.floc = *reading_file;
if (reading_file)
ebuf.floc = *reading_file;
else
ebuf.floc.filenm = NULL;
curfile = reading_file;
reading_file = &ebuf.floc;
@ -688,26 +696,12 @@ eval (struct ebuffer *ebuf, int set_default)
continue;
}
/* If it's a multi-line define / endef, manage that. */
if (vmod.define_v)
{
if (*p == '\0')
fatal (fstart, _("empty variable name"));
/* Let the variable name be the whole rest of the line,
with trailing blanks stripped (comments have already been
removed), so it could be a complex variable/function
reference that might contain blanks. */
p2 = p + strlen (p);
while (isblank ((unsigned char)p2[-1]))
--p2;
v = do_define (p, p2 - p, origin, ebuf);
}
v = do_define (p, origin, ebuf);
else
{
v = try_variable_definition (fstart, p, origin, 0);
assert (v != NULL);
}
v = try_variable_definition (fstart, p, origin, 0);
assert (v != NULL);
if (vmod.export_v)
v->export = v_export;
@ -1205,10 +1199,9 @@ eval (struct ebuffer *ebuf, int set_default)
Because the target is not recorded until after ifeq directive is
evaluated the .DEFAULT_GOAL does not contain foo yet as one
would expect. Because of this we have to move some of the logic
here. */
would expect. Because of this we have to move the logic here. */
if (**default_goal_name == '\0' && set_default)
if (set_default && default_goal_var->value[0] == '\0')
{
const char *name;
struct dep *d;
@ -1314,45 +1307,60 @@ remove_comments (char *line)
the variable to be defined. The following lines remain to be read. */
static struct variable *
do_define (char *name, unsigned int namelen,
enum variable_origin origin, struct ebuffer *ebuf)
do_define (char *name, enum variable_origin origin, struct ebuffer *ebuf)
{
struct variable *v;
enum variable_flavor flavor;
struct floc defstart;
long nlines = 0;
int nlevels = 1;
unsigned int length = 100;
char *definition = xmalloc (length);
unsigned int idx = 0;
char *p;
/* Expand the variable name. */
char *var = alloca (namelen + 1);
memcpy (var, name, namelen);
var[namelen] = '\0';
var = variable_expand (var);
char *p, *var;
defstart = ebuf->floc;
p = parse_variable_definition (name, &flavor);
if (p == NULL)
/* No assignment token, so assume recursive. */
flavor = f_recursive;
else
{
if (*(next_token (p)) != '\0')
error (&defstart, _("extraneous text after `define' directive"));
/* Chop the string before the assignment token to get the name. */
p[flavor == f_recursive ? -1 : -2] = '\0';
}
/* Expand the variable name and find the beginning (NAME) and end. */
var = allocated_variable_expand (name);
name = next_token (var);
if (*name == '\0')
fatal (&defstart, _("empty variable name"));
p = name + strlen (name) - 1;
while (p > name && isblank ((unsigned char)*p))
--p;
p[1] = '\0';
/* Now read the value of the variable. */
while (1)
{
unsigned int len;
char *line;
long nlines = readline (ebuf);
nlines = readline (ebuf);
ebuf->floc.lineno += nlines;
/* If there is nothing left to eval, we're done. */
/* If there is nothing left to be eval'd, there's no 'endef'!! */
if (nlines < 0)
break;
fatal (&defstart, _("missing `endef', unterminated `define'"));
ebuf->floc.lineno += nlines;
line = ebuf->buffer;
collapse_continuations (line);
/* If the line doesn't begin with a tab, test to see if it introduces
another define, or ends one. */
/* Stop if we find an 'endef' */
another define, or ends one. Stop if we find an 'endef' */
if (line[0] != cmd_prefix)
{
p = next_token (line);
@ -1370,30 +1378,16 @@ do_define (char *name, unsigned int namelen,
{
p += 5;
remove_comments (p);
if (*next_token (p) != '\0')
if (*(next_token (p)) != '\0')
error (&ebuf->floc,
_("Extraneous text after `endef' directive"));
_("extraneous text after `endef' directive"));
if (--nlevels == 0)
{
struct variable *v;
/* Define the variable. */
if (idx == 0)
definition[0] = '\0';
else
definition[idx - 1] = '\0';
/* Always define these variables in the global set. */
v = define_variable_global (var, strlen (var), definition,
origin, 1, &defstart);
free (definition);
return (v);
}
break;
}
}
/* Otherwise add this line to the variable definition. */
/* Add this line to the variable definition. */
len = strlen (line);
if (idx + len + 1 > length)
{
@ -1407,8 +1401,16 @@ do_define (char *name, unsigned int namelen,
definition[idx++] = '\n';
}
/* No `endef'!! */
fatal (&defstart, _("missing `endef', unterminated `define'"));
/* We've got what we need; define the variable. */
if (idx == 0)
definition[0] = '\0';
else
definition[idx - 1] = '\0';
v = do_variable_definition (&defstart, name, definition, origin, flavor, 0);
free (definition);
free (var);
return (v);
}
/* Interpret conditional commands "ifdef", "ifndef", "ifeq",
@ -1791,6 +1793,7 @@ record_target_var (struct nameseq *filenames, char *defn,
v = assign_variable_definition (&p->variable, defn);
assert (v != 0);
v->origin = origin;
if (v->flavor == f_simple)
v->value = allocated_variable_expand (v->value);
else
@ -1823,14 +1826,13 @@ record_target_var (struct nameseq *filenames, char *defn,
}
/* Set up the variable to be *-specific. */
v->origin = origin;
v->per_target = 1;
v->private_var = vmod->private_v;
v->export = vmod->export_v ? v_export : v_default;
/* If it's not an override, check to see if there was a command-line
setting. If so, reset the value. */
if (origin != o_override)
if (v->origin != o_override)
{
struct variable *gv;
int len = strlen(v->name);
@ -2097,12 +2099,6 @@ record_files (struct nameseq *filenames, const char *pattern,
}
name = f->name;
/* If this target is a default target, update DEFAULT_GOAL_FILE. */
if (streq (*default_goal_name, name)
&& (default_goal_file == 0
|| ! streq (default_goal_file->name, name)))
default_goal_file = f;
}
if (implicit)

View file

@ -1,5 +1,27 @@
2009-06-04 Paul Smith <psmith@gnu.org>
* scripts/features/se_explicit: Add tests for Savannah bug #24588.
2009-05-31 Paul Smith <psmith@gnu.org>
* scripts/variables/DEFAULT_GOAL: Add tests for Savannah bug #25697.
* scripts/features/targetvars: Add tests of overrides for Savannah
bug #26207.
* scripts/features/patspecific_vars: Ditto.
* scripts/features/patternrules: Add a test for Savannah bug #26593.
2009-05-30 Paul Smith <psmith@gnu.org>
* scripts/variables/flavors: Update with new variable flavor tests.
* scripts/variables/define: Create a new set of tests for
define/endef and move those aspects of the flavors suite here.
2009-05-25 Paul Smith <psmith@gnu.org>
* scripts/features/targetvars: Ditto.
* scripts/features/export: Test new variable parsing abilities.
2009-02-23 Ramon Garcia <ramon.garcia.f@gmail.com>

View file

@ -1,34 +1,45 @@
$description = "The following test creates a makefile to ...";
# -*-perl-*-
$description = "Test the override directive on variable assignments.";
$details = "";
open(MAKEFILE,"> $makefile");
# TEST 0: Basic override
# The Contents of the MAKEFILE ...
run_make_test('
X = start
override recur = $(X)
override simple := $(X)
X = end
all: ; @echo "$(recur) $(simple)"
',
'recur=I simple=J', "end start\n");
print MAKEFILE "override define foo\n"
."\@echo First comes the definition.\n"
."\@echo Then comes the override.\n"
."endef\n"
."all: \n"
."\t\$(foo)\n";
# TEST 1: Override with append
# END of Contents of MAKEFILE
run_make_test('
X += X1
override X += X2
override Y += Y1
Y += Y2
all: ; @echo "$(X) $(Y)"
',
'', "X1 X2 Y1\n");
close(MAKEFILE);
# TEST 2: Override with append to the command line
&run_make_with_options($makefile,"foo=Hello",&get_logfile);
run_make_test(undef, 'X=C Y=C', "C X2 C Y1\n");
# Create the answer to what should be produced by this Makefile
$answer = "First comes the definition.\n"
."Then comes the override.\n";
# Test override of define/endef
run_make_test('
override define foo
@echo First comes the definition.
@echo Then comes the override.
endef
all: ; $(foo)
',
'foo=Hello', "First comes the definition.\nThen comes the override.\n");
&compare_output($answer,&get_logfile(1));
1;

View file

@ -120,5 +120,15 @@ run_make_test(undef, # reuse previous makefile
'normal: global: new $t pattern: good $t inherit: good $t;
pattrn: global: new $t pattern: good $t inherit: good $t;');
# TEST #8: override in pattern-specific variables
run_make_test('
a%: override FOO += f1
a%: FOO += f2
ab: ; @echo "$(FOO)"
',
'', "f1\n");
run_make_test(undef, 'FOO=C', "C f1\n");
1;

View file

@ -145,5 +145,20 @@ echo foo.c foo.h >foo.o');
unlink('foo.in', 'foo.h', 'foo.c', 'foo.o');
# TEST #5: make sure both prefix and suffix patterns work with multiple
# target patterns (Savannah bug #26593).
#
run_make_test('
all: foo.s1 foo.s2 p1.foo p2.foo
p1.% p2.%: %.orig
@echo $@
%.s1 %.s2: %.orig
@echo $@
.PHONY: foo.orig
',
'', "foo.s1\np1.foo\n");
# This tells the test driver that the perl test script executed properly.
1;

View file

@ -123,5 +123,12 @@ baz.1
baz.2
');
# TEST #4: eval in a context where there is no reading_file
run_make_test('
.SECONDEXPANSION:
all : $$(eval $$(info test))
', '', "test\n#MAKE#: Nothing to be done for `all'.\n");
# This tells the test driver that the perl test script executed properly.
1;

View file

@ -219,12 +219,24 @@ rmdir('t1');
# Test appending to a simple variable containing a "$": avoid a
# double-expansion. See Savannah bug #15913.
run_make_test("
VAR := \$\$FOO
run_make_test('
VAR := $$FOO
foo: VAR += BAR
foo: ; \@echo '\$(VAR)'",
foo: ; @echo '."'".'$(VAR)'."'".'
',
'', '$FOO BAR');
# TEST #19: Override with append variables
run_make_test('
a: override FOO += f1
a: FOO += f2
a: ; @echo "$(FOO)"
',
'', "f1\n");
run_make_test(undef, 'FOO=C', "C f1\n");
# TEST #19: Test define/endef variables as target-specific vars
# run_make_test('

View file

@ -73,6 +73,15 @@ $(call make-rule)
'',
'foo');
# TEST #5: .DEFAULT_GOAL containing just whitespace (Savannah bug #25697)
run_make_test('
N =
.DEFAULT_GOAL = $N $N # Just whitespace
foo: ; @echo "boo"
',
'', "#MAKE#: *** No targets. Stop.\n", 512);
# This tells the test driver that the perl test script executed properly.
1;

View file

@ -4,180 +4,73 @@ $description = "Test various flavors of make variable setting.";
$details = "";
open(MAKEFILE, "> $makefile");
# TEST 0: Recursive
# The Contents of the MAKEFILE ...
print MAKEFILE <<'EOF';
run_make_test('
ugh = Goodbye
foo = $(bar)
bar = ${ugh}
ugh = Hello
all: ; @echo $(foo)
',
'', "Hello\n");
all: multi ; @echo $(foo)
multi: ; $(multi)
x := foo
y := $(x) bar
x := later
nullstring :=
space := $(nullstring) $(nullstring)
next: ; @echo $x$(space)$y
define multi
@echo hi
echo there
endef
ifdef BOGUS
define
@echo error
endef
endif
define outer
define inner
A = B
endef
endef
$(eval $(outer))
outer: ; @echo $(inner)
EOF
# END of Contents of MAKEFILE
close(MAKEFILE);
# TEST #1
# -------
&run_make_with_options($makefile, "", &get_logfile);
$answer = "hi\necho there\nthere\nHello\n";
&compare_output($answer, &get_logfile(1));
# TEST #2
# -------
&run_make_with_options($makefile, "next", &get_logfile);
$answer = "later foo bar\n";
&compare_output($answer, &get_logfile(1));
# TEST #3
# -------
&run_make_with_options($makefile, "BOGUS=true", &get_logfile, 512);
$answer = "$makefile:24: *** empty variable name. Stop.\n";
&compare_output($answer, &get_logfile(1));
# TEST #4
# -------
&run_make_with_options($makefile, "outer", &get_logfile);
$answer = "A = B\n";
&compare_output($answer, &get_logfile(1));
# Clean up from "old style" testing. If all the above tests are converted to
# run_make_test() syntax than this line can be removed.
$makefile = undef;
# -------------------------
# Make sure that prefix characters apply properly to define/endef values.
#
# There's a bit of oddness here if you try to use a variable to hold the
# prefix character for a define. Even though something like this:
#
# define foo
# echo bar
# endef
#
# all: ; $(V)$(foo)
#
# (where V=@) can be seen by the user to be obviously different than this:
#
# define foo
# $(V)echo bar
# endef
#
# all: ; $(foo)
#
# and the user thinks it should behave the same as when the "@" is literal
# instead of in a variable, that can't happen because by the time make
# expands the variables for the command line and sees it begins with a "@" it
# can't know anymore whether the prefix character came before the variable
# reference or was included in the first line of the variable reference.
# TEST #5
# -------
# TEST 1: Simple
run_make_test('
define FOO
$(V1)echo hello
$(V2)echo world
endef
all: ; @$(FOO)
', '', 'hello
world');
bar = Goodbye
foo := $(bar)
bar = ${ugh}
ugh = Hello
all: ; @echo $(foo)
',
'', "Goodbye\n");
# TEST #6
# -------
run_make_test(undef, 'V1=@ V2=@', 'hello
world');
# TEST #7
# -------
# TEST 2: Append to recursive
run_make_test('
define FOO
$(V1)echo hello
$(V2)echo world
endef
all: ; $(FOO)
', 'V1=@', 'hello
echo world
world');
foo = Hello
ugh = Goodbye
foo += $(bar)
bar = ${ugh}
ugh = Hello
all: ; @echo $(foo)
',
'', "Hello Hello\n");
# TEST #8
# -------
run_make_test(undef, 'V2=@', 'echo hello
hello
world');
# TEST #9
# -------
run_make_test(undef, 'V1=@ V2=@', 'hello
world');
# TEST #10
# -------
# Test the basics; a "@" internally to the variable applies to only one line.
# A "@" before the variable applies to the entire variable.
# TEST 3: Append to simple
run_make_test('
define FOO
@echo hello
echo world
endef
define BAR
echo hello
echo world
endef
foo := Hello
ugh = Goodbye
bar = ${ugh}
foo += $(bar)
ugh = Hello
all: ; @echo $(foo)
',
'', "Hello Goodbye\n");
all: foo bar
foo: ; $(FOO)
bar: ; @$(BAR)
', '', 'hello
echo world
world
hello
world
');
# TEST 4: Conditional pre-set
run_make_test('
foo = Hello
ugh = Goodbye
bar = ${ugh}
foo ?= $(bar)
ugh = Hello
all: ; @echo $(foo)
',
'', "Hello\n");
# TEST 5: Conditional unset
run_make_test('
ugh = Goodbye
bar = ${ugh}
foo ?= $(bar)
ugh = Hello
all: ; @echo $(foo)
',
'', "Hello\n");
1;

View file

@ -110,6 +110,7 @@ struct pattern_var
extern char *variable_buffer;
extern struct variable_set_list *current_variable_set_list;
extern struct variable *default_goal_var;
/* expand.c */
char *variable_buffer_output (char *ptr, const char *string, unsigned int length);