我的 Makefile 是空的,但 make 正在运行一些旧命令

我的 Makefile 是空的,但 make 正在运行一些旧命令

我有一个奇怪的错误,我设法将其减少到以下内容。我有一个只有两个空文件的文件夹:一个 Makefile 和一个 cpp 文件:

$ ls -la
total 8
drwxrwxr-x  2 erelsgl erelsgl 4096 Mar  3 20:12 .
drwxrwxr-x 13 erelsgl erelsgl 4096 Mar  3 20:10 ..
-rw-rw-r--  1 erelsgl erelsgl    0 Mar  3 20:12 Demo.cpp
-rw-rw-r--  1 erelsgl erelsgl    0 Mar  3 20:09 Makefile
$ cat Makefile 
$ cat Demo.cpp 

当我运行时,make我得到了预期的结果:

$ make
make: *** No targets.  Stop.

但当我跑步时,make Demo.o我得到了一个非常奇怪的结果:

$ make Demo.o
clang++-5.0 -std=c++17   -c -o Demo.o Demo.cpp
make: clang++-5.0: Command not found
<builtin>: recipe for target 'Demo.o' failed
make: *** [Demo.o] Error 127

命令“clang++-5.0 -std=c++17”实际上几天前就在 Makefile 中,但我很久以前就用 clang++-9 替换了它。现在,如您所见,Makefile 完全是空的。为什么make仍在运行这些旧命令?

编辑:当我更改 Makefile 以包含这两行时,会发生同样的事情:

%.o: %.cpp xxx.h
    clang++-9 --compile $< -o $@

当文件 xxx.h 不存在时。这非常令人困惑:我运行它make Demo.o,它是用 clang++-5.0 而不是 clang++-9 构建的!

答案1

这个 Makefile 是如何在不指定编译器的情况下生成 C 程序的?为背景。 Make 有内置规则告诉它如何构建各种文件;在这种特殊情况下,由于您要求一个目标文件,并且.cpp当前目录中有一个匹配的文件,因此它使用指定如何从.cpp文件构建目标文件的规则。

在 GNU Make 中,该规则的某些部分最终使用了变量;特别是CXX对于 C++ 编译器,以及CXXFLAGS编译 C++ 代码时使用的标志。如果环境包含这些变量的值,则这些值优先于内置默认值。由于CXX仍设置为clang++-5.0,Make 尝试使用它来构建Demo.o

使用两行 Makefile,您定义的配方不会被使用因为它的先决条件并不全部存在,也不可能全部实现。相反,再次使用通用模式规则,但仍CXX设置为clang++-5.0

-r您可以使用 选项完全禁用内置规则make。你也可以补充它们;因此

Demo.o: Demo.cpp xxx.h

没有配方将使用内置规则,但需要xxx.h添加Demo.cpp(并且正确地失败,因为xxx.h不存在且无法构建)。

相关内容