GUN make是一种代码维护工具。 make工具会根据makefile文件定义的规则和步骤,完成整个软件项目的代码维护工作。 一般用来简化编译工作,可以极大地提高软件开发地效率。 windows下一般由集成开发环境自动生成, linux下需要由我们按照其语法自己编写。

make主要解决两个问题

一、大量代码地关系维护
大项目中源代码比较多,手工维护、编译时间长而且编译命令复杂,难以记忆及维护。
把项目维护命令及编译命令写在makefile文件中,然后再用make工具解析此文件自动代码的合理编译。
二、减少重复编译时间
在改动其中一个文件的时候,能判断哪些文件被修改过,可以对该文件进行重新编译目标文件,节省编译时间。

makefile语法及其执行

makefile语法规则

目标:依赖文件列表
命令列表
1.目标:
通常是要产生的文件名称,目标可以是可执行文件或其它obj文件,也可是一个动作的名称
2.依赖文件:
是用来输入从而产生目标的文件
一个目标通常由几个依赖文件 3.命令:
make执行的动作,一个规则可以含几个命令
有多个命令时,每个命令占一行

简单的Makefile实例

在代码文件目录下,新建makefile文件进行编辑

假设这里有一个源文件名为main.c的代码文件,头文件main.h

main:main.c main.h      //主目标
    gcc main.c -o main
clean:                  //伪目标
    rm main -rf;

编辑好makefile,在命令行输入make命令即可执行主目标也就是代码编译。
伪目标需要make命令+次要目标名:make clean,执行批量删除操作

稍微复杂一点的makefile实例

假设现在有一个工程,需要编译多个源文件,有main.c 1.c 2.c main.h 1.h 2.h

main:main.o 1.o 2.o         //执行make命令找不到.o文件就会向下执行.o目标
    gcc main.o 1.o 2.o -o main
main.o:main.c main.h
    gcc main.c -o main.o
1.o:1.c 1.h
    gcc 1.c -o 1.o
2.o:2.c 2.h
    gcc 2.c -o 2.o
clean:
    rm main main.o 1.o 2.o -rf

分步编译为.o文件的好处在于一旦修改源文件,只会重新编译修改文件其他文件不会重新编译,在大型项目中就会大大节约编译时间。

假象目标

makefile中出现的文件称之为假想目标
假想目标并不是一个真正的文件名,通常是一个目标集合或者动作
可以没有依赖或者命令
一般需要显示的使用make+名字 显示调用
all:exec1 exec2
clean:
rm *.o exec install: mv main /home

all: 1.c 2.c    //有了这条语句,可以同时执行1.c 2.c

1.c: 1.c
    gcc 1.c -o 1
2.c: 2.c
    gcc 2.c -o 2
clean:
    rm -rf 1 2
install:
    mv 1 2 /home

makefile变量

当工程源文件过多时,以上方法依然过于麻烦,因此引出了makefile变量,通过变量大大的减少了工作量。

cc=gcc
#cc=arm-linux-gcc
obj=main.o 1.o 2.o
target=main
cfalgs=-Wall -g

$(target):$(obj)
    $(cc) $(obj) -o $(target) $(cfalgs)
main.o:main.c
    $(cc) -c main.c -o main.o $(cfalgs)
1.o:1.c
    $(cc) -c 1.c -o 1.o $(cfalgs)
2.o:2.c
    $(cc) -c 1.c -o 1.o $(cfalgs)
clean:
    rm -rf $(obj) $(target)

常用的自动变量

@ 表示目标名字
^ 表示所有依赖文件的名字
< 表示第一个依赖文件的名字

cc=gcc
obj=main.o 1.o 2.o
target=main
cfalgs=-Wall -g

$(target):$(obj)
    $(cc) $^ -o $@ $(cfalgs)
main.o:main.c
    $(cc) -c $< -o $@ $(cfalgs)
1.o:1.c
    $(cc) -c $< -o $@ $(cfalgs)
2.o:2.c
    $(cc) -c $< -o $@ $(cfalgs)
clean:
    rm -rf $(obj) $(target)

当源文件特别多时通常用通配符%代表一个单词中的若干字符
ex:%.c

cc=gcc
obj=main.o 1.o 2.o
target=main
cfalgs=-Wall -g

$(target):$(obj)
    $(cc) $^ -o $@ $(cfalgs)
%.o:%.c
    $(cc) -c $< -o $@ $(cfalgs)
clean:
    rm -rf *.o $(target)