makefile - make: *** 没有规则可以生成目标 all'。停止。

9
我一直在尝试制作一个正确的makefile,但是我一直收到以下错误信息:
“make: *** 没有可以制作目标“all”的规则。停止。”
我的主程序是mpasswdsort.c,还有一个被mpasswdsort使用的c文件,它也带有一个头文件:list.c和list.h。
我的makefile如下:
CC=gcc
CFLAGS=-Wall -pedantic -ansi
all: mpasswdsort
server: mpasswdsort.o list.o
    $(CC) mpasswdsort.o list.o -o mpasswdsort
mpasswdsort.o: mpasswdsort.cpp
    $(CC) $(CFLAGS) mpasswdsort.cpp
list.o: list.cpp
     $(CC) $(CFLAGS) list.cpp
clean:
    rm -f server client *.o core

我不确定是makefile出错了还是makefile本身就不应该是一个.txt文件。


1
此外,你的 makefile 文件中说 all 包含 mpasswdsort,但是你没有为 mpasswdsort 定义规则。 - KevinDTimm
这很可能是一个错误,@KevinDTimm,但不一定是。如果make可以通过其内置规则之一找到构建mpasswdsort的方法,则无需提供显式规则。在这种情况下,它将尝试从mpasswdsort.o构建它,而它确实有一个明确的构建规则。我猜那可能会链接失败,但诊断结果与问题中呈现的结果大不相同。 - John Bollinger
1
@JohnBollinger - 我提醒一下,这样可以使OP编写一个正确、明确的Makefile,而不是目前这个。特别是因为当下一个新手来排除故障时,他们会迷失方向。最后,考虑到诊断结果,我怀疑这是否真的是正在使用的Makefile。 - KevinDTimm
1
如果你输入 make server (并且 all 目标的 makefile 问题已经解决),那么每次运行 make server 时,mpasswdsort 程序将从两个目标文件重新链接,因为 server 目标的规则不会创建名为 server 的文件。如果你运行 make mpasswdsort,那么 make 将尝试从单个文件构建程序——从 mpasswdsort.cpp 构建的 mpasswdsort.o 文件——并且可能会失败,因为没有包含 list.o。你最终需要解决这个问题(因为 make all 将尝试使用单个文件构建 mpasswdsort)。 - Jonathan Leffler
1
我并没有看到批评@JohnBollinger - 我看到的是教学。现在我只希望原帖发布者对他们所发布的问题感兴趣...... - KevinDTimm
显示剩余2条评论
4个回答

12
您提供的错误信息表明make没有看到构建目标"all"的任何规则。这正是GNU make在根本没有makefile时发出的诊断信息。由于您提供的makefile内容确实包含针对目标"all"的规则,我认为 make 没有看到它们。
可能是因为makefile位于不同的目录中,其名称与默认情况下 make 尝试的名称(约定俗成的是 Makefile 或 makefile ; GNU版本的 make 还检查 GNUmakefile )不同,或者因为访问控制问题防止 make 读取文件。由于您的备注:

我不确定makefile是否有误或该makefile是否应该是.txt文件。

因此最可能的结论是至少文件名错误。Makefiles是文本文件,但文本文件名不一定以".txt"结尾。实际上,在Linux和其他UNIX上,大部分文件没有这样的扩展名。虽然技术上可以使用-f选项告诉 make 要使用的makefile的名称,但makefiles不应该具有此类扩展名。

所有标准版本的 make 根据原始 Unix make 程序的行为(参见 POSIX make)查找 makefileMakefile(按该顺序)。当然,在不区分大小写的文件系统(Mac、Windows)上,它们之间没有区别。 - Jonathan Leffler
谢谢,@JonathanLeffler,我已经根据您的评论更新了答案。 - John Bollinger

1
我使用的是MAC,所以将 "MakeFile" 重命名为 "Makefile" 就解决了问题。另外,我在解决上一个问题后遇到了这个错误:

Makefile:3: *** 缺少分隔符。 停止。

将四个空格替换为制表符就解决了这个问题!只需删除“Makefile”中命令前面的空格并在它们后面放置一个制表符即可。

1
对我来说,很简单,我在目标目录之外启动了make init命令,而我希望创建Makefile的目录是在目标目录内。希望这能帮助到某些人。

0
对我来说,我有一个名为"project1_src"的文件夹,里面包含了项目文件和makefile,还有一个同名的父文件夹("project1_src")。一旦我将实际包含文件的文件夹取出并删除了父文件夹,makefile就可以正常工作了。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接