help-make
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Evaluation of variables inside make rules' dependencies


From: Dmitry N. Mikushin
Subject: Re: Evaluation of variables inside make rules' dependencies
Date: Wed, 9 Mar 2011 14:10:35 +0300

Philip,

Thank you for you kind help,

.SECONDEXPANSION solves issue with $(OBJECTS). Interestingly,
$(INCLUDES) remains unmodified in object rules:

%.a: LIBNAME = $(shell echo $(notdir $(basename $@)) | sed s/lib// | \
        tr '[a-z]' '[A-Z]' | tr '/' '_')
%.a: SOURCES = $($(LIBNAME)_SOURCES)
%.a: OBJECTS = $(addprefix $(STORE)/, $(addsuffix .o, $(SOURCES)))
%.a: DEPLIBS = $($(LIBNAME)_DEPLIBS)
%.a: DEFINES += $($(LIBNAME)_DEFINES)
%.a: INCLUDES += $($(LIBNAME)_INCLUDES)               <--- (1)
%.a: dirs $$(OBJECTS)
        @echo Packing static library $@ ... $(INCLUDES)               <---(2)
        @$(AR) $(ARPARAMS) $@ $(OBJECTS)

$(STORE)/%.c.o: %.c
        @echo Creating object file for $< ...
        $(CCOMP) $(CPARAMS) $(DEFINES) $(INCLUDES) -c $< -o $@            <--- 
(3)

Here at (1) INCLUDES is expanded with library-specific values, and
changes are visible at (2), but not applied at (3). It turns all
variables defined in %.a are recomputed in %.c.o with respect to new
$@, and all information I need to pass from %.a to %.c.o via variables
is lost. Is there a workaround to deliver %.a's values to %.c.o?

Thanks,
- D.

2011/3/7 Philip Guenther <address@hidden>:
> On Sun, Mar 6, 2011 at 6:06 PM, Dmitry N. Mikushin <address@hidden> wrote:
>> I'm trying to understand the behavior of the following example:
>>
>> %.a: LIBNAME = $(shell echo $(notdir $(basename $@)) | sed s/lib// | \
>>        tr '[a-z]' '[A-Z]' | tr '/' '_')
>> %.a: SOURCES = $($(LIBNAME)_SOURCES)
>> %.a: OBJECTS = $(addprefix $(STORE)/, $(addsuffix .o, $(SOURCES)))
>> %.a: DEPLIBS = $($(LIBNAME)_DEPLIBS)
>> %.a: DEFINES += $($(shell echo $(1) | tr '[a-z]' '[A-Z]' | tr '/' 
>> '_')_DEFINES)
>> %.a: INCLUDES += $($(shell echo $(1) | tr '[a-z]' '[A-Z]' | tr '/'
>> '_')_INCLUDES)
>> %.a: dirs $(OBJECTS)
>>       address@hidden Packing static library $@ $(OBJECTS) ...
>>       address@hidden(AR) $(ARPARAMS) $@ $(OBJECTS)
>>
>> The result is:
>> ============
>>
>> $(OBJECTS) seems to be empty inside line %.a: dirs $(OBJECTS),
> ...
>> So what's the difference between evaluating variable in dependency
>> line and in command?
>
> There are several differences.  The first is that the former is
> expanded immediately while the latter is deferred until the rule is
> run.  There are others.  For example, to quote the manual:
>
> ----
> 6.11 Target-specific Variable Values
> ....
> This feature allows you to define different values for the same variable,
> based on the target that `make' is currently building.  As with
> automatic variables, these values are only available within the context
> of a target's recipe (and in other target-specific assignments).
> ----
>
> I.e., they aren't available for immediate expansion.  There's a
> workaround: turn on second-expansion and target-specific variables can
> be referenced during the second expansion (but not during the first,
> still).
>
> I.e., add the line
>  .SECONDEXPANSION:
>
> above this in the Makefile and then use $$(OBJECTS) instead of
> $(OBJECTS) in the dependency line.
>
> Beware: there may be other changes that you need to make when you add
> .SECONDEXPANSION.  Read the manual and then think about what variables
> contain and whether a second expansion will affect things...
>
>
> Philip Guenther
>



reply via email to

[Prev in Thread] Current Thread [Next in Thread]