makefile基础及实战

it2022-05-09  25

一、什么是make

make 是软件构造工具,make有多个版本,本文将基于GNU make,make会自动搜索当前目录下的makefile, Makefile或者GNUmakefile。

二、make核心规则

target ... : prerequisites ... command target是目标文件,实际是Object File,或执行文件,以及标签(Label)prerequisites是target依赖的文件或是目标。一个依赖关系可以附属有多个操作。

如果prerequisites的修改时间比target更新,或者target文件不存在,command被执行;首次执行make创建了target文件是因为target文件不存在,之后执行make会根据修改时间的属性进行判断,如更新了源码内容,那么command还会再次执行,这就是makefile的规则和核心。

三、实例介绍

测试c文件main.c:

#include <stdio.h> int main() { printf("Hello world!\n"); return 0; }

对应makefile如下:

# 宏 CC ?= gcc # main is a binary file main: main.o   $(CC) -o main main.o main.o: main.c   $(CC) -c -o main.o main.c

执行make后将会生产main可执行文件。

宏分为自定义宏和内部宏,比如我们上面使用的CC就是自定义宏,make会在运行时,使用宏的值(gcc)来替代 (CC); shell的环境变量可以直接作为宏调用,如果同一个自定义的宏同时也有同名环境环境变量,make将优先使用自定义宏。

内部宏

$? :比目标还要新的依赖文件列表$@ :当前依赖关系的目标文件名$< :表示当前目标的第一个依赖文件$* :当前依赖关系中的目标文件名,不包括后缀$^ :当前目标的所有依赖文件$$ :字符"$"

后缀依赖

可以在在makefile中使用

.SUFFIXES: .c .o .c.o: $(CC) -c -o $@ $^

来说明.c和.o是后缀,并编写后缀依赖关系**.c.o**。

其他

makefile的续行符为\@command表示不显示命令本身-command表示忽略命令报错makefile中经常会定义下面依赖关系: all:

如果make后没有跟随文件名,那么将执行该依赖关系。

clean:

常用于清理历史文件。

test:

用于编写make test测试用例。

dep:

用于自动生成依赖关系。

完整版makefile例子

# 宏 CC ?= gcc PACKNAME = main .SUFFIXES: .c .o .c.o: $(CC) -c -o $@ $^ all: main @echo "all" # main is a binary file main: main.o   $(CC) -o $@ $< main.o: main.c clean: -rm $(PACKNAME) *.o dep: $(CC) -MM *.c test: @echo "write test case"

如果到这里你都看懂,那么说明你已经掌握了makefile常用的语法了。


最新回复(0)