C程序的Makefile

时间:2015-10-23 17:51:05

标签: c makefile

我正在尝试将此Makefile用于C程序。你能否跟我分享一下如何更好地理解Make实用程序?我正在尝试以下方法:

# stack/Makefile
CC := gcc
CFLAGS += -std=c99
CFLAGS += -Wall
CFLAGS += -Wextra
CFLAGS += -g
VPATH = main src

all: bin/main.exe clean run
bin/main.exe: bin/main.o bin/stack.o
    $(CC) -o $@ $^ $(LDFLAGS) $(LDLIBS)
bin/main.o: main.c
bin/stack.o: stack.c stack.h
bin/%.o: %.c
    $(CC) $(CFLAGS) -c -o $@ $<
demo:       
    ../bin/main.exe
clean:
    rm -f bin/*.o 
run:
    bin/main.exe
.PHONY: all clean run

我收到了这条消息:

gcc -std=c99 -Wall -Wextra -g -c -o bin/main.o main.c
error: unable to open output file 'bin/main.o': 'No such file or directory'
1 error generated.
make: *** [bin/main.o] Error 1

2 个答案:

答案 0 :(得分:2)

错误源于您的Makefile想要的事实 生成子目录bin中的可执行文件和目标文件但是它 不包含确保bin存在的规则 需要。正如@JonathanLeffler评论,你可以解决这个问题 只需自己手动创建bin

但通常希望Makefile本身能够确保 当它存在时,存在一个子目录或一些其他资源 需要,你可能假设模式规则

bin/%.o: %.c

会根据需要创建bin。它赢了。

如果你的话,你的Makefile可以确保bin的存在 像这样修改它:

all规则以下的某处,添加新目标:

bin:
    mkdir -p $@

这是为了bin子目录,如果它不存在。

然后更改规则:

bin/%.o: %.c
    $(CC) $(CFLAGS) -c -o $@ $<

为:

bin/%.o: %.c | bin
    $(CC) $(CFLAGS) -c -o $@ $<

其他| binorder-only prequisite的示例 这意味着:如果任何目标(bin/%.o事物)需要从之前的任何先决条件(|之前的那些,即%.c重新制作。 事情),然后必须先bin。因此,只要需要在bin中进行任何操作,bin将首先制作。

Makefile中还有另一个更基本的缺陷。 all取决于clean,因此每次成功构建时都是如此 你的程序删除了目标文件。我知道你打算这个,但它完全是 挫败make的目的,即避免重建所有(目标文件,可执行文件)的需要 相反,只需重建那些已经过时的先决条件。

所以all不应该依赖clean,然后只有当需要时才会重新编译目标文件 被重新编译,即比相应的源文件旧。如果你想要清理的话 目标文件,运行make clean

最后,您的demo规则:

demo:       
    ../bin/main.exe

与其他人不一致。其他人假设可执行文件所在的bin 被放在当前目录中。 demo规则假定它位于中 当前目录。如果您更正了demo规则,那么它将与之相同 run规则,所以它是多余的,但如果它不是多余的那么应该 将其添加到.PHONY目标。

答案 1 :(得分:-1)

学习使用makefile的正确方法的最佳方法是阅读manual。此外,您可以使用Google simple tutorials