Makefile是做Linux方向经常用到的文件,Makefile主要用来管理代码的编译,代码的编译顺序,以及在后期某个文件发生变动,就只编译该文件,而不用所有文件都编译一次;Makefile的编写基本是一劳永逸的,编写一次,后面基于该Makefile做相应的修改即可。
Makefile文件一般可以命名为Makefile或者makefile,在linux内核中一般是选用的前者命名的;
Makefile如果命名为其他名字也是可以的:比如makefile_demo,但是在make的时候需要使用如下命令:
make -f makefile_demo.
Makefile的格式一般是:
目标:依赖
规则
目标是make之后生成文件名字,依赖是生成目标文件所需要的文件,规则是指导怎么生成目标文件或者如何生成目标文件所需要的依赖。就好比:做一道菜:你需要知道做成一道什么样的菜<----->目标,做着道菜需要准备哪些蔬菜原料<------->依赖,做这道菜的过程是怎样的<------>规则。
Makefile在编译代码的时候,因为代码一般是有很多的.c文件组成的,所以在写Makefile的时候,放在Makefile最前面的目标是该工程的一个终极目标。而下面的目标是为终极目标服务的,一般是为了生成终极目标所需要的依赖。
Makefile在编译的时候的规则是这样的,首先检查目标文件的依赖是否是存在的,如果依赖的文件不存在,则继续向下找是否有对应的规则生成目标所需要的依赖。总结一下就是:在编译的过程从第一个目标往下先找对应的依赖,然后从下向上执行对应的命令。
Makefile文件中常用的自动变量:
$@ ---------->目标;
$< ------------>依赖中文件中的第一个依赖;
$^ -------------> 表示所有的依赖
例如:app:main.c test1.c test2.c
$^表示的是main.c test1.c test2.c;$<表示是main.c $@表示的是app.
Makefile中变量在直接赋值的时候就完成了变量的定义;
引用变量的值的时候 是在用()括起来改变量,然后在()前面加一个$符号。
在Makefile中经常还会用到%这个符号,在Makefile中%是通配符,经常用在模式规则中来匹配文件,所谓的模式规则就是:
在一个有main.c test1.c test2.c的工程里:
%.o:%.c
$(CC) -c $< -o $@
这个模式规则的作用就相当于以下命令:
main.o:main.c
gcc -c main.c -o main.o
test1.o:test1.c
gcc -c test1.c -o test1.o
test2.test2.c
gcc -c test2.c -o test2.o
最后说一下Makefile文件中经常使用的两个函数,在Makefile中所有的函数都是有返回值的:
wildcard:
用于查找指定目录下指定类型的文件,跟的参数就是目录+文件类型,比如:
src = $(wildcard ./src/*.c)
这句话表示:找到./src 目录下所有后缀为.c的文件,并赋给变量src。
命令执行完成后,src的值为:main.c func1.c fun2.c。
patsubst:
匹配替换,例如以下例子,用于从src目录中找到所有.c 结尾的文件,并将其替换为.o文件,并赋值给obj。
obj = $(patsubst %.c ,%.o ,$(src))
把src变量中所有后缀为.c的文件替换成.o。
命令执行完成后,obj的值为main.o func1.o func2.o
特别地,如果要把所有.o文件放在obj目录下,可用以下方法:
ob = $(patsubst ./src/%.c, ./obj/%.o, $(src))
注:主要参考yychuyu博主的分享,感谢!!