在开始之前,我会提到我在这种情况下不使用GNU Make来构建C / C ++项目。
生成文件:
DEST_DIR = build/
SRC_DIR = src/
$(SRC_DIR)a/ : $(SOMETHING_ELSE)
$(DO_SOMETHING_TO_GENERATE_A_DIR)
$(DEST_DIR)% : $(SRC_DIR)%
cp -r $^ $@
ALL_DEPS += <SOMETHING>
... more code which appends to ALL_DEPS ...
.PHONY: all
all : $(ALL_DEPS)
我在$(SRC_DIR)中通过Make规则生成了一些 not 文件。 (为了这个例子,假设有一个目录$(SRC_DIR)b /和一个文件$(SRC_DIR)c。)
我想向ALL_DEPS追加代表$(DEST_DIR)中文件或目录的所有目标,以便“make all”将运行所有的可用$(DEST_DIR)%规则。
我想做这样的事情:
ALL_DEPS += $(addprefix $(DEST_DIR),$(notdir $(wildcard $(SRC_DIR)*)))
但是,当然,这并没有抓住任何尚未制造的东西。 (即它不会将$(DEST_DIR)附加到列表中,因为$(SRC_DIR)a /在评估$(通配符...)调用时尚不存在,并且shell不包含它$(通配符...)调用返回的结果。)
因此,我找到一个找到匹配模式的所有目标的函数,而不是找到匹配模式的所有(当前存在的)文件的函数。然后,我可以这样做:
ALL_DEPS += $(addprefix $(DEST_DIR),$(notdir $(targetwildcard $(SRC_DIR)*)))
如果重要的是,我已经将大部分GNU Make代码拆分为多个文件,并由“master”Makefile包含。 ALL_DEPS变量附加到任何要添加到其中的文件中。这是为了保持构建过程的模块化,而不是将它全部放在一个怪物Makefile中。
我当然还在学习GNU Make,所以我不太可能错过一些相当明显的东西。如果我只是想解决这个问题,请告诉我。
谢谢!
答案 0 :(得分:2)
根本不可能做你想做的事情;你试图让make识别出不存在的东西。
这就是为什么通常情况下,通配符很糟糕的原因之一(另一方面是你最终可能包含你不想要的东西)。这里要做的是明确创建source
文件列表(ls -1 | sed -e 's/\(.*\)/sources+=\1/' > dir.mk
)并在该列表上执行patsubst
转换。
如果您有其他文件作为构建的一部分生成,那么您可以将它们附加到该列表中,并且可以按照您的预期找到它们的规则。