help-make
[Top][All Lists]
Advanced

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

Re: Copying Prerequisites / conditional remove Prerequisites


From: Paul Smith
Subject: Re: Copying Prerequisites / conditional remove Prerequisites
Date: Tue, 12 Oct 2010 16:27:11 -0400

On Tue, 2010-10-12 at 22:06 +0200, Erik Rull wrote:
> Do you have an idea how to get the list of all targets that are
> defined in a make call (after evaluating all rules)?

I had attempted to implement this with a .TARGETS variable, similar to
the .VARIABLES variable.

However, there were some gross technical details so I abandoned it and
haven't gotten back to it.

First, due to the way make parses rules, the target wasn't added to the
list until it was completely defined.  However, because of a makefile's
free-form syntax a target can't be completely defined until the next
target starts (or a variable is defined or the makefile ends).  This
means seemingly obvious and simple things like:

        foo:
                @echo hi

        ifeq (foo,$(filter foo,$(.TARGETS)))
        $(info found target foo!)
        endif

don't work.  In order to fix this we'd need to modify the way in which
make reads targets so they are defined early, when first detected,
before the rest of the rule is parsed.


The second thing is that make is recursive, which means that every file
is potentially a target, by make's lights.  The behavior I was going to
implement was that targets specifically called out AS TARGETS in the
makefile would be in the .TARGETS variable.

However, what about pattern rules?  With the above rule of "targets
specifically mentioned in the makefile", then with a makefile like this:

        foo: bar.o baz.o

        %.o : %.c ; $(CC) -o $@ -c $<

        baz.o: baz.c; $(CC) -o $@ -c $<

the .TARGETS variable would contain "foo baz.o", because bar.o is not
specifically mentioned as a target in the makefile.

And, if you did it the other way (anything make tries to build as a
target), then first the variable would change value as make built new
targets and resolved implicit rules, and second all kinds of other stuff
would get put in; in the above example the .TARGETS variable by the end
of the build would contain something like "foo bar.o bar.c baz.o baz.c"
plus whatever header files, etc. might be mentioned as prerequisites.

Ugh.

So I guess the short answer is no, there's no way to do this today.


I should point out that the traditional way very dynamic makefile
environments are constructed is NOT by users creating lots of rules.
Instead, makefiles contain virtually nothing but VARIABLE assignments,
and the rules are constructed dynamically from the values of the
variables (typically with a lot of very hairy make goo).  For example, a
makefile might say:

        PROGRAMS = foo bar

        foo_SOURCES = foo.c bar.c baz.c
        foo_LIBRARIES = libfoo.a

        bar_SOURCES = one.c two.cpp three.cpp

        LIBRARIES = libfoo.a

        libfoo.a_SOURCES = foo_lib.c

etc.

It's VERY easy to construct dynamic rules from this because make allows
recursive variable name construction.  And you can get a list of all the
stuff you want by deriving from these values.

-- 
-------------------------------------------------------------------------------
 Paul D. Smith <address@hidden>          Find some GNU make tips at:
 http://www.gnu.org                      http://make.mad-scientist.net
 "Please remain calm...I may be mad, but I am a professional." --Mad Scientist




reply via email to

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