如何在 Linux 上为 gcc 制作一个简单的 makefile?
Posted
技术标签:
【中文标题】如何在 Linux 上为 gcc 制作一个简单的 makefile?【英文标题】:How do I make a simple makefile for gcc on Linux? 【发布时间】:2010-12-01 20:56:15 【问题描述】:我有三个文件:program.c
、program.h
和 headers.h
。
program.c
包括program.h
和headers.h
。
我需要在 Linux 上使用 gcc 编译器来编译它。我不知道该怎么做。 Netbeans 为我创建了一个,但它是空的。
【问题讨论】:
spin.atomicobject.com/2016/08/26/makefile-c-projects 有一个非常优雅(并且有据可查)的解决方案。 【参考方案1】:有趣的是,我不知道 make 会默认使用 C 编译器给定有关源文件的规则。
无论如何,演示简单 Makefile 概念的简单解决方案是:
HEADERS = program.h headers.h
default: program
program.o: program.c $(HEADERS)
gcc -c program.c -o program.o
program: program.o
gcc program.o -o program
clean:
-rm -f program.o
-rm -f program
(请记住,make 需要制表符而不是空格缩进,因此请务必在复制时修复该问题)
但是,要支持更多 C 文件,您必须为每个文件制定新规则。因此,要改进:
HEADERS = program.h headers.h
OBJECTS = program.o
default: program
%.o: %.c $(HEADERS)
gcc -c $< -o $@
program: $(OBJECTS)
gcc $(OBJECTS) -o $@
clean:
-rm -f $(OBJECTS)
-rm -f program
我试图通过省略通常在 makefile 中看到的 $(CC) 和 $(CFLAGS) 等变量来尽可能简单地做到这一点。如果您有兴趣弄清楚这一点,我希望我已经为您提供了一个良好的开端。
这是我喜欢用于 C 源代码的 Makefile。随意使用它:
TARGET = prog
LIBS = -lm
CC = gcc
CFLAGS = -g -Wall
.PHONY: default all clean
default: $(TARGET)
all: default
OBJECTS = $(patsubst %.c, %.o, $(wildcard *.c))
HEADERS = $(wildcard *.h)
%.o: %.c $(HEADERS)
$(CC) $(CFLAGS) -c $< -o $@
.PRECIOUS: $(TARGET) $(OBJECTS)
$(TARGET): $(OBJECTS)
$(CC) $(OBJECTS) -Wall $(LIBS) -o $@
clean:
-rm -f *.o
-rm -f $(TARGET)
它使用 make 实用程序的通配符和 patsubst 功能在当前目录中自动包含 .c 和 .h 文件,这意味着当您向目录中添加新代码文件时,您无需更新 Makefile。但是,如果要更改生成的可执行文件、库或编译器标志的名称,只需修改变量即可。
在任何一种情况下,请不要使用 autoconf。我求你! :)
【讨论】:
为了技术上正确,我相信您应该将.PHONY: clean all default
用于那些打算从命令行使用的目标。此外,Autoconf/Automake 也不错。当然,它们感觉很糟糕,习惯它们就像强迫你的头穿过一堵砖墙一样有趣,但它们确实有效,而且它们发展良好,它们将覆盖你的大部分基础,就便携性而言,一旦你习惯了他们糟糕的设计,最终会让你的生活变得更轻松。
我想这是可行的,但我想如果我在终端上输入“make”,程序应该会运行。这是我得到的: gcc statsh.o -Wall -lm -o prog 是否可以只输入 make 并执行程序?
为什么不使用 autoconf joey-adams ?
如果有人想知道为什么rm
前面有破折号:***.com/questions/2989465/rm-rf-versus-rm-rf
最好使用:=
而不是=
。使用:=
,wildcard
函数只运行一次,以后可以附加/扩展变量OBJS := $(OBJS) other.o
。使用=
这是不可能的,它会导致变量扩展的无限循环!请参阅:The Two Flavors of Variables。【参考方案2】:
例如这个简单的 Makefile 就足够了:
抄送=gcc CFLAGS=-墙 全部:程序 程序:program.o program.o:program.c program.h headers.h 干净的: rm -f 程序 program.o 运行:程序 。/程序注意清理运行后的下一行必须有<tab>
,而不是空格。
更新以下评论已应用
【讨论】:
@user69514:make
没有参数通常只构建你的软件。要运行它,要么使用make run
(在这个答案中可用,但不一定在所有Makefile
s),或者直接运行它:./program
【参考方案3】:
all: program
program.o: program.h headers.h
就够了。其余的都是隐含的
【讨论】:
如果你的整个程序是一个单一的.c
文件,那么只有program:
是必要的。甜:)
虽然这肯定很简单,但毫无疑问,匿名和@MestreLion,我是 C 新手,最近才将一个大型项目拆分为 2 个源文件和一个标头,我是 不使用makefile,而是一个非常简单的C程序,基本上只使用stdlib.h
中的system()
...这种方法没有缺点,有吗?
@APJo:对于简单的项目,您可以不用Makefile
直接调用gcc *.c *.h -o program
,可能添加-Wall -O2
等选项。【参考方案4】:
最简单的make文件可以是
all : test
test : test.o
gcc -o test test.o
test.o : test.c
gcc -c test.c
clean :
rm test *.o
【讨论】:
您可以添加更多细节来解释您的 Makefile 的作用 您实际上可以更简单。见@anonymous 1 班轮【参考方案5】:根据标头的数量和您的开发习惯,您可能需要研究 gccmakedep。该程序检查您的当前目录并将每个 .c/cpp 文件的头依赖项添加到 makefile 的末尾。当您有 2 个标头和一个程序文件时,这是矫枉过正的。但是,如果您有 5 个以上的小测试程序并且您正在编辑 10 个标头之一,那么您可以信任 make 来准确重建那些因您的修改而更改的程序。
【讨论】:
以上是关于如何在 Linux 上为 gcc 制作一个简单的 makefile?的主要内容,如果未能解决你的问题,请参考以下文章
如何在 Windows 上为 NetBeans 和 gcc 添加库包含路径?
如何在 iOS 8 上为 superview 制作 clearColor
markdown 在Windows上为GCC(MinGW)安装boost库