makefile - 为什么 make 不检测 header 依赖项的变化

标签 makefile gnu-make

我不确定我在这里做错了什么。我试图让 make 弄清楚我的项目有哪些依赖项,不仅是源文件,还有非系统包含的头文件。我在这个网站上有很多与这个主题相关的资源。

如:Makefile header dependenciesMakefile, header dependencies

但是,当我这样做时

touch MyHeader.h

作为测试是否有效,我的 make 过程无法重建包含此 header 的源文件。所以,这就是我的 makefile 中的内容(相关)

CPP=g++
CPPFLAGS=-Iadditional/includes -MMD
CXXFLAGS=-std=c++0x -c 
# not every source file in this directory needs to be included in this build
# this is because of shared code with Windows
SOURCESFILTER = File1.cpp File2.cpp

OBJ_DIR=obj
SOURCES = $(filter-out $(SOURCEFILTER),$(wildcard *.cpp))
OBJECTS = $(addprefix $(OBJ_DIR)/,$(SOURCES:.cpp=.o))

DEPENDENCIES = $(OBJECTS:.o=.d)

.PHONY: archive

archive : $(OBJECTS)
    ar mylib.a obj/*.o

-include $(DEPENDENCIES)

$(OBJ_DIR)/%.o: $(SOURCES) $(DEPENDENCIES)
    $(CPP) $(CPPFLAGS) $(CXXFLAGS) $< -o $@

我已经验证上述过程确实生成了预期的 *.d 文件。我认为我正确地包含了它们。然而,正如前面提到的,作为一个测试,我做了: 触摸 MyHeader.h

与源文件位于同一目录中,然后重新运行 make,包含此 header 的源文件都不会被重新制作。我错过了什么?

安迪

最佳答案

首先,您不能在后缀规则中包含先决条件。即使可以,您也肯定不会想要包含 $(SOURCES)$(DEPENDENCIES),因为这会导致 每当任何源文件或依赖文件发生更改时,都会重建每个对象。

其次,您不能在与 make 期望的目录不同的目录中创建目标文件。 Make 会将要查找目标的位置放入变量 $@ 中,并且您必须将输出准确地写入该位置。如果您看到修改目标的规则(例如上面使用 obj/$@ 的规则),则该规则将不起作用。

很可能 GCC 将文件写入 obj/foo.d,但您的 include 试图包含 foo.d 但那不存在...但由于您使用了 -include make 不会提示。

我建议您首先将对象文件写入本地目录并使其与依赖项一起使用。一旦成功,请阅读如何将目标写入不同的目录和/或再次询问。

预计到达时间:

尝试这样的事情:

CXX := g++
CPPFLAGS := -Iadditional/includes -MMD
CXXFLAGS := -std=c++0x
# not every source file in this directory needs to be included in this build
# this is because of shared code with Windows
SOURCESFILTER := File1.cpp File2.cpp

OBJ_DIR := obj
SOURCES := $(filter-out $(SOURCEFILTER),$(wildcard *.cpp))
OBJECTS := $(addprefix $(OBJ_DIR)/,$(SOURCES:.cpp=.o))

DEPENDENCIES := $(OBJECTS:.o=.d)

.PHONY: archive

archive: mylib.a

mylib.a: $(OBJECTS)
        $(AR) $@ $^

-include $(DEPENDENCIES)

$(OBJ_DIR)/%.o: %.cpp
        $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $<

关于makefile - 为什么 make 不检测 header 依赖项的变化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16221805/

相关文章:

c++ - Eigen、make 和 cmake 之间的问题(可能是 cmake 错误)

makefile - 在每个子目录中运行make

c - Gnu 在先决条件列表中进行独占或(有点)?

Makefile 动态变量作为先决条件

c++ - 如何分离不同配置的 Makefile 构建输出?

c++ - Make with Autodependencies for C++

c 多个源文件返回错误值

macos - 在 Mac OS X 上使用 GYP 生成 Makefile?

makefile - 获取所有目录列表的通配符

makefile - 为什么 "make all"没有将 "all"添加到 .PHONY 目标就按预期工作?