概念
makefile理解:
makefile关系到了整个工程的编译规则。一个工程的源文件不计其数,其按类型、功能、模块分别放在若干目录中,makefile定义了一系列的规则来指定,那些文件需要先编译,哪些文件需要后编译,哪些文件需要更新编译,甚至于进行更复杂的功能操作,因此makefile像shell脚本一样,其中可以执行系统操作的命令。
好处
自动化编译,一旦写好,只需要一个make命令,整个工程完全自动编译,极大地提高了软件开发效率,make是一个命令工具,是一个解释makefile中指令的命令工具,一般来说,大多数ide都有这样的命令。
简单的makefile书写介绍
1.简单的单文件生成对应的可执行文件
如:a.c -> a b.c->b c.c->c
src=$(wildfile *.c)
obj=$(patsubst %.c,%,$src)
target:$(obj)
%:%.c
gcc $< -o $@
.PHONY:clean
clean:
-rm -f $(obj)
2.数据库的编译
如: a.pc->a.c->a
通过proc a.pc -> a.c 中间生成a.lis
通过gcc a.c -> a
我们用gcc编译程序时,可能会用到“-I”(大写i),“-L”(大写l),“-l”(小写l)等参数,下面做个记录:
-I头文件
-L库文件目录
-l动态库文件
例:
gcc -o hello hello.c -I /home/hello/include -L /home/hello/lib -lworld
上面这句表示在编译hello.c时:
-I /home/hello/include表示将/home/hello/include目录作为第一个寻找头文件的目录,寻找的顺序是:/home/hello/include–>/usr/include–>/usr/local/include
-L /home/hello/lib表示将/home/hello/lib目录作为第一个寻找库文件的目录,寻找的顺序是:/home/hello/lib–>/lib–>/usr/lib–>/usr/local/lib
-lworld表示在上面的lib的路径中寻找libworld.so动态库文件(如果gcc编译选项中加入了“-static”表示寻找libworld.a静态库文件)
src=$(wildcard *.c)
obj1=$(patsubst %.pc,%.lis,$(src))
obj2=$(patsubst %.pc,%.c,$(src))
obj3=$(patsubst %.pc,%,$(src))
target:$(obj3)
$(obj3):%:%.c
gcc $< -L -l -I -o $@
%.c:%.pc
proc $<
.PHONY:clean
clean:
-rm -f $(obj1) $(obj2) $(obj3)
3.多文件编译
target=app
src=$(wildcard *.c)
obj=$(patsubst %.c,%.o,$(src))
$(target):$(obj)
gcc $(obj) -o $(target)
%.o:%.c
gcc $< -c $@
.PHONY:clean
clean:
-rm -f $(obj) $(target)
规则
gcc的四个编译阶段:E S C ->i o s
预处理器:头文件展开,宏替换,注释去掉 gcc -E a.c -o a.i
->编译器:c文件变成汇编文件 gcc -S a.i -o a.s
->汇编器:汇编文件转换成二进制文件 gcc -C a.s -o a.o
->链接器:函数库中相应代码组合到目标库中可执行文件 gcc a.c -o a
三要素:目标 依赖 命令
规则:
目标:依赖
gcc 依赖 -o 目标(命令)
两个函数:
wildcard 通配符
patsubst
三个变量:
$@ 目标
$< 依赖中的第一个
$^ 所有依赖
匹配
%.o:%.c
命令
通过命令将.c文件编译成.o文件