Hi folks,
I'm trying to define new targets with eval during secondary expansion, but
apparently this is not allowed -- with make 4.2.1 I get an error like this:
Makefile:94: *** prerequisites cannot be defined in recipes. Stop.
I found bugs #24588 and #24622 related to this.
My use case is as follows. I have a bunch of targets which can be nested
arbitrarily deeply in subdirectories within my build directory. For each
target, I'd like to have an order-only prerequisite on the existence of
its parent directory. So something like this:
build/foo/bar/baz/mytarget: | build/foo/bar/baz
touch $@
build/foo/bar/baz:
mkdir -p $@
The issue is that if I have many targets in many different directories, then I
need to write lots of 'mkdir' rules like this. I can save some typing with a
template and a foreach/eval/call, but that's still a bit awkward because I have
to maintain a list of all the directories I need.
My current solution is to do something similar to this:
define mkdir_template
$(1):
mkdir -p $(1)
endef
mkdir_dep = $(eval $(call mkdir_template,$(1))) $(1)
build/foo/bar/baz/mytarget: | $(call mkdir_dep,build/foo/bar/baz)
This is a bit nicer but there's still some duplication. What I'd like to do
is replace the argument on the right hand side with $(dir $@). With secondary
expansion enabled I could write something like this:
mktargetdir = $(eval $(call mkdir_template,$(dir $@))) $(dir $@)
.SECONDEXPANSION:
build/foo/bar/baz/mytarget: | $$(mktargetdir)
Then I can just write the path for each target and all the duplication is gone.
But this doesn't work and I get the error above about prerequisites in recipes.
I spotted a comment in file.c that says "in the future it would be nice to
support this". Are there plans to allow defining targets during secondary
expansion in this way? Or is there an easy way to do what I'm trying to do
without too much duplication?
Thanks,
Ismail