首页 > 代码库 > 写个简单的makefile(文件拆分篇)
写个简单的makefile(文件拆分篇)
# 两个特殊的字符,出现在命令之前
# - :告诉make命令忽略所有错误.
# @:告诉make在执行某条命令前不要将该命令显示在标准输出上
1.在makefile中使用宏
看一个例子:
edit : 1.o 2.o 3.o 4.o
cc -o edit 1.o 2.o 3.o 4.o
如果后面文件很多的话,就会导致管理不方便, 我们可以设置宏
例如:
OBJECTS = 1.o 2.o 3.o 4.o 那么上述的例子就变成
edit : $(OBJECTS)
cc -o edit $(OBJECTS)
2.文件搜寻 VPATH
如果指明VPATH ,make在当前目录下搜寻不到的时候就会去指定目录搜寻
e.g. VPATH = src : ../headers
上面的定义包含两个目录 一个是src 一个是../headers 中间用:隔开
make中还有一个vpath关键字(小写) 其用法如下:
1. vpath <pattern> <directories> 为符合<pattern>的文件指定搜索目录<directories>
2. vpath <pattern> 清除符合<pattern>的文件的搜索目录
3. vpath 清除所有已被设置好了的文件搜索目录
e.g. vpath %.h ../headers
3.伪目标
我们在使用clean目标的时候就是一个伪目标, 伪目标的取名不能和文件名重名,make无法生成伪目标的依赖关系,一直是过时的
e.g.
clean:
-rm *.o temp
可以显示的声明为伪目标
.PHONY: clean
clean:
-rm *.o temp
利用伪目标生成多个可执行文件 :
all : prog1 prog2 prog3
prog1 : balabalabala
prog2 : balabalabala
prog3 : balabalabala
这样省事多了 一个make搞定
常见的伪目标有:all, clean, install, print, tar, dist, TAGS, check, test
4. 静态模式
语法:
<targets...> : <target-pattern> : <prereq-patterns...>
<commands>
...
看个例子:
objects = 1.o 2.o
all : &(objects)
&(objects) : %.o : %.c
$(CC) -c $(CFLAGS) $< -o $@ ( $<和$@是自动化变量,$<是所有的依赖目标集,$@是目标集)
5.自动生成依赖
C/C++编译器的M参数可以输出头文件的依赖:
gcc会把标准库的文件包含进来,可以使用 gcc -MM xxxx.c 例如今天写的程序 如果gcc -MM main.c 输出 main.o : main.c stack.h 1016.h
GNU建议把编译器为每一个源文件的自动生成的依赖关系放在一个文件中,为每一个"name.c"的文件都生成一个"name.d"的Makefile文件
%.d: %c
@set -e; rm -f $@;\
$(CC) -MM $(CFLAGS) $< > $@.$$$$;\
sed ‘s,\($*\)\.o[:]*,\1.o $@:,g‘ <$@.$$$$> $@;\
rm -f $@.$$$$
6.重载内建隐含规则
例如:
%.o:%.c
$(CC) -c $(CFLAGS) -D $(date)
取消内建的隐含规则 后面不加命令即可
%.o:%.s
我今天的简单的makefile
2
3 CFLAGS= -g -Wall
4
5 INCLUDE= ./headers
6
7 vpath %.h ../headers
8 vpath %.c ./sources
9
10 OBJECTS= main.o stack.o computing.o
11
12 myprog: $(OBJECTS)
13 $(CC) -o myprog $(OBJECTS)
14
15 %.o:%.c
16 $(CC) -I$(INCLUDE) $(CFLAGS) -c $< -o $@
17
18 %.d:%.c
19 @set -e; rm -f $@;\
20 $(CC) -MM $(CFLAGS) $< > $@.$$$$;\
21 sed ‘s,\($*\)\.o[:]*,\1.o $@:,g‘ <$@.$$$$> $@;\
22 rm -f $@.$$$$
23
24 clean:
25 -rm *.o
写个简单的makefile(文件拆分篇)