假设我有一些带有生成源规则的 makefile(简化示例)
SRCS = $(shell find src -name "*.c")
OBJS = $(patsubst src/%.c, build/%.o, $(SRCS))
generate-src:
@echo "int main() {return 0;}" > ./src/x.c
target: generate-src $(OBJS)
$(CC) -o target $(OBJS)
build/%.o: src/%.c
@mkdir -p $(@D)
$(CC) $(CFLAGS) $(CXXFLAGS) -c -o $@ $<
运行
make target
时,出现以下错误
cc -o target build/x.o
clang: error: no such file or directory: 'build/x.o'
clang: error: no input files
make: *** [target] Error 1
这是因为当我们调用
make target
时,$(OBJS)
的计算结果为空,因为 $(SRCS)
的计算结果为空。然后调用generate-src,创建src/x.c
。然后 $(CC) -o target $(OBJS)
被调用,但是这次 $(OBJS)
的计算结果为 build/x.o
,它没有被创建,因为它没有被识别为目标的依赖项。
有没有办法编写此 makefile,以便在运行
$(OBJS)
后评估 generate-srcs
?
这是执行此操作的一种方法。
SRCSX = $(shell find src -name "*.c") src/x.c
uniq = $(if $1,$(firstword $1) $(call uniq,$(filter-out $(firstword $1),$1)))
SRCS = $(call uniq, $(SRCSX))
(
uniq
的定义从这里盗来)