help-make
[Top][All Lists]
Advanced

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

Re: Understanding Pattern Rules


From: james
Subject: Re: Understanding Pattern Rules
Date: Tue, 05 May 2015 10:10:44 -0700
User-agent: Roundcube Webmail/1.1-git

Thanks for the information!

Sorry, I did forget to state my desired behavior, but you did infer correctly what I am attempting to do.

First, based on the presence of the pattern "%.cached: %.src" in his
question, he would probably get equivalent results with a rule that
says "treat as prerequisites all the files '*.cached' for which a file
'*.src' exists", which we *can* do:
    SRCS = $(wildcard *.src)
    file.out: $(SRCS:.src=.cached)
            cat $^ >$@

That looks ideal for me, thank you! Now I'll have to go read up on those features to make sure I actually understand this snippet properly, but it's good to know that what I'm trying to achieve is doable :)

The other solution is to recognize that depending on pattern matching
means that filenames become magical, which can trip things up later.
Most build systems have chosen to require an explicit action to
include a file in a build; that lets developers use whatever filenames
they want without disturbing the build.  Using pattern matching means
you can't do a build if you have new, not-yet-working code, unless you
want to develop the file under some other name and rename it into
place when it's ready.

I will bear this in mind when I am building C projects, but the Makefile I am currently building is actually for just processing plain text files, so the introduction of a slightly errant or incomplete file won't throw build failures at me. I think this kind of wildcard prereqisite specification makes sense for what I am trying to do.

Thank you again, to everyone who helped clear up this issue for me!

On 2015-05-05 09:44, Philip Guenther wrote:
On Tue, May 5, 2015 at 9:25 AM, Paul Smith <address@hidden> wrote:
On Tue, 2015-05-05 at 07:49 -0700, address@hidden wrote:
file.out: %.cached
        cat $^ > file.out

This is not a pattern rule.  A pattern rule must have a pattern match
(the "%") in the TARGET, because it matches any of a set of targets.
Having a pattern in the prerequisite is optional, but there must be one
in the target, or else it's an explicit rule... and thus it depends on
the explicit prerequisite named, literally, '%.cached'.

To make this a pattern rule you'd need to write:

  %.out : %.cached
          cat $^ > $@

or similar.

The original poster didn't actually state what the desired behavior
was, but I'll *guess* that we wants a rule that says
   "treat as prerequisites all the files '*.cached' that make can
figure out how to build"

make has no way to express the "all the files that it figure out how
to build" part.  However, in this case, there are two other solutions.

First, based on the presence of the pattern "%.cached: %.src" in his
question, he would probably get equivalent results with a rule that
says "treat as prerequisites all the files '*.cached' for which a file
'*.src' exists", which we *can* do:
    SRCS = $(wildcard *.src)
    file.out: $(SRCS:.src=.cached)
            cat $^ >$@


The other solution is to recognize that depending on pattern matching
means that filenames become magical, which can trip things up later.
Most build systems have chosen to require an explicit action to
include a file in a build; that lets developers use whatever filenames
they want without disturbing the build.  Using pattern matching means
you can't do a build if you have new, not-yet-working code, unless you
want to develop the file under some other name and rename it into
place when it's ready.  But if you're going to require an explicit
action (renaming) to make a file for ready to include the build, why
not use an action that is simpler and clear to document by just
listing the files in the Makefile?  So, solution two:

   SRCS = foo.src bar.src baz.src quux.src..etc
   file.out: $(SRCS:.src=.cached)
           cat $^ >$@


Philip Guenther



reply via email to

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