Имам много прост Makefile, който не прави това, което очаквам да направи. Крайната цел е той да се извиква рекурсивно, включително съответния файл всеки път, което води до компилация, специфична за това, което е включено (изграждам няколко проекта, които споделят една и съща кодова база, но използват различни комбинации от изходни файлове ). Никога не съм се занимавал с рекурсивни повиквания, така че трябва да пропускам нещо очевидно. В момента имам само един .mk
файл в същата папка като моя Makefile. Това е прост едноредов само за целите на този тест. В крайна сметка ще съдържа различни настройки за всеки проект.
Makefile:
SHELL = /bin/sh
ifdef MYFILE
include $(MYFILE)
PROGRAM = $(basename $(MYFILE))
endif
all: $(wildcard *.mk)
dummy:
@echo -- Entering dummy stub ... why do I need this?
%.mk: dummy
@echo Calling $(MAKE) MYFILE=$@ $*
$(MAKE) MYFILE=$@ $*
$(PROGRAM): objs
@echo Time to link!
objs:
@echo Building objs!
test.mk
SOMEVAR = SomeValue
Имам следните два проблема:
Проблем 1
Ако премахна предпоставката dummy
от моето правило за шаблон, правилото за шаблон никога не се извиква (получавам страховитата грешка „Нищо не трябва да се прави за всички“). Има ли начин да накарам рецептите под правилото %.mk
да се изпълняват, без да се нуждая от тази фиктивна предпоставка?
Проблем 2
Имайки предвид двата гореспоменати файла, бих очаквал make да направи следното:
- make[1] стартира и натиснете правилото
all
- make[1] скача надолу към правилото за шаблон
%.mk
- make[1] се извиква рекурсивно (извикването ще изглежда като
make MYFILE=test.mk test
) - make[2] стартира, включва файла test.mk и настройва променливата PROGRAM
- make[2] скача надолу към правилото $(PROGRAM) (тъй като бяхме изрично извикани с тази цел)
- make[2] прескача до правилото objs, изпълнява рецептите и се връща обратно по веригата
В действителност make се забива в правилото за шаблон %.mk
и влиза в безкраен цикъл. Не разбирам защо настоява да изпълни правилото за шаблон, когато изрично му казах да изгради test
в първото ми рекурсивно повикване (което трябва да съответства на целта $(PROGRAM)
). Какво ми липсва тук?
make
? Има ли значение? Второ,make
прави две преминавания през make-файла, за да разреши/оцени всички променливи. Ще съдържат ли това, което очаквате, когато влезете в рекурсивното повикване? - person HonkyTonk   schedule 04.05.2012