многоцелевая цель в Makefile - PullRequest
       4

многоцелевая цель в Makefile

0 голосов
/ 21 сентября 2018

Просто простой Makefile:

a/% b/%:
    @echo $@

Когда я делаю

, создаю / ab / b

Все нормально, как и ожидалось, что:

a / a

b / b

Но когда я это сделаю

, сделайте / ab / a

Похоже, что:

a / a

make: Ничего не поделаешь для `b / a '.

Как получить ожидаемый доход

a / a

b / a

Протестировано с версией make как v3.81, так и v3.82в Linux и macOS

Ответы [ 2 ]

0 голосов
/ 24 сентября 2018

Если вы не хотите жестко закодировать возможные цели, как предложил GM, вы можете создать магию:

$ cat Makefile
define recipe
$(1):
    @echo $$@
endef

PATTERNS=a/% b/%
$(foreach pattern,$(PATTERNS),$(eval $(call recipe,$(pattern))))

Тестирование:

$ make a/a b/a
a/a
b/a
$ make a/a b/b
a/a
b/b

Наблюдаемое вами поведение описано в GNU make docs :

У шаблонных правил может быть несколько целей.В отличие от обычных правил, это не так много разных правил с одинаковыми предпосылками и рецептом.Если правило шаблона имеет несколько целей, make знает, что рецепт правила отвечает за создание всех целей.Рецепт выполняется только один раз, чтобы сделать все цели.

0 голосов
/ 21 сентября 2018

Учитывая ваше makefile ...

a/% b/%:
        @echo $@

Подумайте, что происходит, когда вы вызываете make a/a b/b.make замечает, что правило a/% b/%: совпадает с основанием a (т. Е. Встроенная переменная $* будет a) и запускает команду.Поскольку у вашего правила есть несколько целей, make теперь считает, что и a/a , и b/a были обновлены.

Make затем считает следующую цель, указанную в командной строке b/b,Это еще не было обновлено, поэтому make снова запускает то же правило, но со стеблем b.Таким образом, правило запускается дважды - по одному разу для каждого ствола шаблона a и b.

Теперь рассмотрим, что происходит при вызове make a/a b/a.На этот раз обе цели будут соответствовать одному и тому же правилу, но с одинаковым стволом a.Следовательно, make, запустив правило со стволом a, считает, что и a/a, и b/a были обновлены, и не видит необходимости перезапускать правило для второй цели командной строки b/a.

* 1033.* Не совсем понятно, какое поведение вам требуется, но если вы хотите, чтобы одно и то же правило вызывалось несколько раз для разных целей, даже если основа шаблона одинакова, вам может понадобиться что-то вроде ...
# Possible targets (for illustration purposes).
#
TARGETS := a/a a/b b/a b/b

$(TARGETS): %:
        @echo $@

Вышеприведенное дает ...

GM> make -f multi-wildcard-target-in-makefile.mk a / ab / b
a / a
b / b

GM> make -f multi-wildcard-target-in-makefile.mk a / ab / a
a / a
b / a

...