Makefile工程管理
前文回顾:gcc编译器
课程截图如下:
demo文件如下:
sequence.h
#ifndef _SEQUENCE_H_
#define _SEQUENCE_H_
void sequence(unsigned char*sp,unsigned char num);
#endif
sequence.c
#include "sequence.h"void sequence(unsigned char *sp,unsigned char num)
{
unsigned char i,j;
unsigned char a;
for(j=0;j<num-1;i++)
{
for(i=j+1;i<num;i++)
{
if(sp[j]>sp[i])
{
a=sp[i];
sp[i]=sp[j];
sp[j]=a;
}
}
}
}
main.c
#include <stdio.h>
#include "sequence.h"
unsigned char dis_num[8] = {10,9,17,92,2,8,35,12};
int main(void)
{
unsigned char i;
sequence(dis_num,sizeof(dis_num));
for(i=0;i<8;i++)printf("%d ",dis_num[i]);
printf("
");
return 0;
}
针对模块化程序如何去编译:
处理如下:
gcc -o sequence.o -c sequence.c
gcc -o main.o -c main.c
gcc -o main sequence.o main.o
./main
假设 sequence.c 文件有修改了或者工程里面有很多的.c文件,按照上面的方式处理,工程量就很大,而且一旦有一个文件修改了,那么你就要重新再搞一遍。
针对上面的情况,咋们就用 makefile 进行工程管理。
- Makefile规则:
1)先创建一个名称为 makefile 或者 Makefile 的文档;
2)在文档里面输入相应的内容:
输入相应内容的时候,要遵循相应的规则。
规则:用于说明如何生成一个或多个目标文件; 规则格式: target:dependency_files //目标项:依赖项 <TAB>command //必须以tab开头,command编译命令
规则就是为了生成某一个文件的。
目标项:这个就是你要生成的文件名;
依赖项:要生成目标项需要的文件;
编译命令:如果有依赖项生成目标项;必须以TAB开头;
makefile 文件里面可以有很多规则,但是第一个规则是最终生成的文件规则。
编写规则如下:
main:main.c
gcc -o main main.c
3)如何运行这个 makefile 文件
make
main:main.o sequence.o gcc -o main main.o sequence.o main.o:main.c gcc -o main.o -c main.c sequence.o:sequence.c gcc -o sequence.o -c sequence.c
- Makefile的伪目标:
1)使用 .PHONY 这个makefile的关键字来定义你的伪目标;
.PHONY:clean rebuild
2)再编写对应的伪目标:
clean: rm -f main.o main sequence.o
rebuild:clean main
3)要想执行伪目标,直接 make 伪目标名就可以了。
make rebuild
make clean
- Makefile的变量:
变量类似C语言里面的宏定义。
变量分为:用户自定义变量,自动变量,预定义变量,环境变量;
1)自定义变量:
定义变量格式如下:
变量名:=变量值
如何引用变量:
$(变量名)=??? //赋值 ???=$(变量名) //引用
在 Makefine 体现如下:
SOURCE:=main.o sequence.o EXE:=main $(EXE):$(SOURCE) gcc -o $(EXE) $(SOURCE) main.o:main.c gcc -o main.o -c main.c sequence.o:sequence.c gcc -o sequence.o -c sequence.c .PHONY:clean rebuild clean: rm -f main.o main sequence.o rebuild:clean main
2)自动变量:
使用的时候,使用特定的值去替换。
自动变量,可以认为是 makefile 里面设定好的符号。
SOURCE:=main.o sequence.o EXE:=main $(EXE):$(SOURCE) gcc -o $@ $^ main.o:main.c gcc -o $@ -c $^ sequence.o:sequence.c gcc -o $@ -c $^ .PHONY:clean rebuild clean: rm -f main.o main sequence.o rebuild:clean main
3)预定义变量和环境变量:
都是系统里面设定好的自定义变量。
- Makefile的规则:
1)普通规则:
2)隐含规则:
*.o 文件自动依赖 *.c 或 *.cc 文件,所以可以省略 main.o:main.c等。
main:main.o sequence.o gcc -o main main.o sequence.o .PHONY:clean rebuild clean: rm -f main.o main sequence.o rebuild:clean main
3)模式规则:
main:main.o sequence.o gcc -o main main.o sequence.o %.o:%.c gcc -o $@ -c $^ #注意这里面不能再使用%.o来代替了 .PHONY:clean rebuild clean: rm -f main.o main sequence.o rebuild:clean main
- 把生成的目标存放到其他的文件夹里面:
DIR:=./debug/ ${DIR}main:${DIR}main.o ${DIR}sequence.o gcc -o ${DIR}main ${DIR}main.o ${DIR}sequence.o ${DIR}main.o:main.c gcc -o ${DIR}main.o -c main.c ${DIR}sequence.o:sequence.c gcc -o ${DIR}sequence.o -c sequence.c .PHONY:clean rebuild clean: rm -f ${DIR}main.o ${DIR}main ${DIR}sequence.o rebuild:clean main
改进
DIR:=./debug/ OBJS:=${DIR}main.o ${DIR}sequence.o ${DIR}main:${OBJS} gcc -o ${DIR}main ${OBJS} ${DIR}main.o:main.c gcc -o ${DIR}main.o -c main.c ${DIR}sequence.o:sequence.c gcc -o ${DIR}sequence.o -c sequence.c .PHONY:clean rebuild clean: rm -f ${DIR}main ${OBJS} rebuild:clean main
- Makefile里面的函数:
SOURCE = $(wildcard *.c) #SOURCE = main.c sequence.c OBJS = $(patsubst %.c,%.o,$(SOURCE)) #OBJS = main.o sequence.o main:$(OBJS) gcc -o main $(OBJS) main.o:main.c gcc -o main.o -c main.c sequence.o:sequence.c gcc -o sequence.o -c sequence.c .PHONY:clean rebuild clean: rm -f main.o main sequence.o rebuild:clean main
- 其他:
1)Makefile里面的注释使用#
2)命令如果不想显示到终端,在命令前加@
SOURCE = $(wildcard *.c) #SOURCE = main.c sequence.c OBJS = $(patsubst %.c,%.o,$(SOURCE)) #OBJS = main.o sequence.o main:$(OBJS) @gcc -o main $(OBJS) main.o:main.c @gcc -o main.o -c main.c sequence.o:sequence.c @gcc -o sequence.o -c sequence.c .PHONY:clean rebuild clean: @rm -f main.o main sequence.o rebuild:clean main
3)如果你命名的Makefile文档名并非Makefile,那么就要加上 -f
make -f Makefile1
这个老师的课程内容如下: