我正在做一个基于递归(有毒但无关紧要)制作的构建系统。我遇到的主要问题是,即使没有对* o文件进行任何更改,make也会重新创建我指示它执行的库。
以下是处理静态库创建的make文件的部分。
all: $(DEPS) $(OBJS) $(LIB_TARGET)
### Archive into a library file (.a)
%.a: $(OBJS)
@echo $(MSG_L)
@echo 'Adding $< to library $@'
$(AR) $(ARFLAGS) $(LIB_DIR)/$@ $^
@echo $(MSG_L)
在各自的makefile中的某些目录下,$(LIB_TARGET)是使用库名定义的,每个子目录使用前缀makefile来知道如何创建它的共享。 现在我最大的问题是,首先运行创建所有内容是正常的,但是在第二次运行时,或者每次后续运行而不对代码中的任何内容进行任何更改时,都会重新创建库(但不是* d或* o文件,它们不是重新创建,它们不会被删除,它们的时间戳不会改变,这是正常的。)
make -C modules all
make[3]: Entering directory `F:/automata/tmp/remake/src/modules'
make -C interface all
make[4]: Entering directory `F:/automata/tmp/remake/src/modules/interface'
make -C cli all
make[5]: Entering directory `F:/automata/tmp/remake/src/modules/interface/cli'
------- make Lib -------
Adding cli.o to library libInterface.a
avr-ar rcs F:/automata/tmp/remake//tmp/app/brick/lib/atmega328p/libInterface.a c
li.o
------- make Lib -------
注意:这是从第二次/第三次运行,在这里可以看出* d和* o没有重新创建
我创建了使用文件的规则,我能看到的唯一问题是我将库放在一个特殊的目录中,而不是它从它获取源的目录。 关于如何解决这个问题并且没有让系统重新创建库的任何想法?
谢谢。
答案 0 :(得分:2)
每当你看到一个创建目标文件的配方时, <{em> $@
,你知道这是错误的,你会遇到这个问题。
在这里,您告诉您要创建一个与模式%.a
匹配的目标。将该模式匹配到libInterface.a
并将$@
设置为libInterface.a
并调用您的食谱。
但你的食谱不构建$@
,它构建$(LIBDIR)/$@
这是一个完全不同的文件。因此,下次运行make
时,它会查找libInterface.a
作为all
的先决条件,看它不存在,并重新运行您提供的规则...它再次不会创建你告诉它的目标,$@
,而是创建一些其他文件make不知道任何事情。
您需要使用:
LIB_TARGET = $(LIB_DIR)/libInterface.a
....
### Archive into a library file (.a)
$(LIB_DIR)/%.a: $(OBJS)
@echo $(MSG_L)
@echo 'Adding $< to library $@'
$(AR) $(ARFLAGS) $@ $^
@echo $(MSG_L)