Reputation: 1535
In Make it's possible to compute variable names in runtime using double-evaluation, like $($(var))
.
I'm interested if it's possible somehow to make this work:
one.js_DEPS=a b
two.js_DEPS=c b
all: one.js two.js
%.js: $(%.js_DEPS)
cat $^ > $@
I can make this work by declaring two rules with explicit dependencies, like this:
one.js: $(one.js_DEPS)
But this seems a bit anti-DRY. So I'm wondering if I miss something because make doesn't seem to understand me. I use GNU Make 3.81.
Upvotes: 1
Views: 2222
Reputation: 25493
This could be done using Secondary Expansion.
JS := one.js two.js
all: $(JS)
.SECONDEXPANSION:
one.js_DEPS := a b
two.js_DEPS := c b
$(JS) : $$($$(@F)_DEPS)
cat $^ > $@
But in fact, the goal can be achieved much simply, without using any GNU Make extensions, as thiton has suggested in his answer:
all: one.js two.js
one.js : a b
two.js : c b
%.js :
cat $^ > $@
Upvotes: 1
Reputation: 36049
%
and implicit rules are somewhat second-class citizens in make
, since variable expansion seems to happen before implicit rule expansion. So, in your above Makefile, $(%.js_DEPS)
is expanded to the empty string before %
is substituted.
Alternative:
%.js: %.js_DEPS
cat $^ > $@
%.js_DEPS :
cat $^ > $@
.INTERMEDIATE: one.js_DEPS two.js_DEPS
or simply:
one.js : a b
two.js : c d
%.js :
cat $^ > $@
Upvotes: 2