$mv makefile Makefile
$make
gcc -c main.c
gcc -c liu.c
gcc -c generatedatafile.c
gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz
rm -f *.o
Makefile文件格式
<Target 1>: depend <command 1> <command 2> |
Makefile文件格式--------以小节(rule)为基本结构
$cat Makefile LIBS=-L/usr/local/mysql/lib/mysql -lmysqlclient -lz all: liu clean all depend 两个小节 liu: main.o liu.o generatedatafile.o liu depend 三个小节 gcc -g $? -o $@ $(LIBS) main.o: main.c gcc -c $? 之前一定要有一个TAB(即TAB键) liu.o: liu.c gcc -c liu.c generatedatafile.o: generatedatafile.c gcc -c $? clean: $(RM) *.o |
命令行必须用TAB,不能用一串空格
TAB是command行的标志
[macg@localhost mysqltmp]$ more makefile liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu -L /usr/lib/mysql -l mysqlclient -lz main.o: main.c comm.h gcc -c main.c liu.o: liu.c /usr/include/mysql/mysql.h gcc -c liu.c generatedatafile.o: generatedatafile.c gcc -c generatedatafile.c |
只make单个小节
$make main.o gcc -c main.c |
main.o: main.c gcc -c $? |
#cat Makefile … install: … clean: … |
小节menu化
小节引用,直接在写在depend处
$vi Makefile LIBS=-L/usr/local/mysql/lib/mysql -lmysqlclient -lz liu: main.o liu.o generatedatafile.o clean gcc -g main.o liu.o generatedatafile.o -o liu $(LIBS) liu depend 4个小节:main.o liu.o generatedatafile.o clean main.o: main.c gcc -c main.c liu.o: liu.c gcc -c liu.c generatedatafile.o: generatedatafile.c gcc -c generatedatafile.c clean: $(RM) *.o |
$make gcc -c main.c gcc -c liu.c gcc -c generatedatafile.c rm -f *.o gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz gcc: main.o: No such file or directory gcc: liu.o: No such file or directory |
因为总的执行顺序: o depend 小结1, o depend 小结2, o depend 小结3, o depend 小结4(clean), o gcc -g main.o liu.o generatedatafile.o -o liu $(LIBS) 等于是在gcc link前,先把*.o又删掉了,所以出错 |
正确的做法 $vi Makefile LIBS=-L/usr/local/mysql/lib/mysql -lmysqlclient –lz all: liu clean 设一个总的menu小节 o 第一步进行编译和链接是编译 o 最后一步才删除 liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu $(LIBS) main.o: main.c gcc -c main.c liu.o: liu.c gcc -c liu.c generatedatafile.o: generatedatafile.c gcc -c generatedatafile.c clean: $(RM) *.o |
$make gcc -c main.c gcc -c liu.c gcc -c generatedatafile.c gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz rm -f *.o |
makefile的注释类似shell,在以"#"为开头的的文字皆为注释
小节(rule)的command里,就是普通的unix命令,可以是gcc命令,也可以是任何unix command
install: liu chmod 750 liu cp liu /usr/bin liu: liu.o gcc liu.o -o liu |
先执行depend liu小结,生成可执行文件liu 将生成的可执行文件改权限 将生成的可执行文件copy到适当的安装目录 |
clean: rm –f *.o 删除掉中间产生的*.o文件 |
通常在最后链接的小节加入删除语句,删除掉中间产生的*.o文件
$vi makefile LDFLAGS=-L/usr/local/mysql/lib/mysql -lmysqlclient -lz liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu $(LDFLAGS) rm -f *.o |
$make gcc -c main.c gcc -c liu.c gcc -c generatedatafile.c gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz rm -f *.o $ls comm.h generatedatafile.c liu.c makefile testm dataf liu main.c makefile.bak testm.c |
用make的内部宏$(RM)实现删除
vi Makefile liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu $(LDFLAGS) $(RM) *.o |
$make gcc -c main.c gcc -c liu.c gcc -c generatedatafile.c gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz rm -f *.o |
makefile文件中的宏变量替换、宏变量引用要带$()
$vi makefile LDFLAGS=-L/usr/local/mysql/lib/mysql -lmysqlclient -lz liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu $LDFLAGS $make gcc -c liu.c gcc -g main.o liu.o generatedatafile.o -o liu DFLAGS gcc: DFLAGS: No such file or directory *** Error code 1 |
$vi makefile liu: main.o liu.o generatedatafile.o gcc -g main.o liu.o generatedatafile.o -o liu $(LDFLAGS) $make gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz |
为什么make 引用变量要加$( )?
因为那根本不是变量,而是宏
Makefile中所有文件名都是路径名,可以带目录路径,如src/main.c
main.o: main.c comm.h
gcc -c main.c $(INC) 源文件在当前目录下
main.o: src/main.c include/comm.h
gcc -c src/main.c $(INC) 源文件在子目录下
$@ 和$? 的用法:
target:depend
$@ : $?
liu:
main.o liu.o generatedatafile.o gcc -g $? -o $@ $(LIBS) |
$? 可以代替多个(所有的)depend
$vi Makefile LIBS=-L/usr/local/mysql/lib/mysql -lmysqlclient -lz all: liu clean liu: main.o liu.o generatedatafile.o gcc -g $? -o $@ $(LIBS) main.o: main.c gcc -c $? liu.o: liu.c gcc -c liu.c generatedatafile.o: generatedatafile.c gcc -c $? clean: $(RM) *.o |
编译时,不用带.h文件
$vi makefile
main.o: main.c comm.h
gcc -c main.c
所谓“编译带不带.h"文件的实质----depend是做什么用的
depend的含义:如果target检查发现depend中有任何一个自己新,就重新编译。
<Target 1>: depend <command 1> <command 2> |
main.o: main.c comm.h gcc -c main.c |
其他如stdio.h之类的标准头文件,也没必要出现在depend中
liu.o: liu.c /usr/ /include/mysql/mysql.h gcc -c liu.c |
liu: main.o main.o:main.c |
depend xxx.h文件的缺憾,不能继续用$?了
main.o: main.c comm.h gcc -c $? |
$make gcc -c src/main.c include/comm.h –Iinclude 显然$?编译时把comm.h也编译进去了 |
正确的做法:直接用文件名,不用$? main.o: src/main.c include/comm.h gcc -c src/main.c $(INC) 只能直接用文件名了,不能用$?了 |
采用结构化编程的make
- 目录树
mysqltmp---src---main.c liu.c generatedatafile.c ---include--comm.h ---lib--libcomm.so或libcomm.a |
- 在顶层目录建立Makefile
vi Makefile LIBS=-L/usr/local/mysql/lib/mysql -L/export/home/macg/mysqltmp/lib -lmysqlclient -lz -lcomm INC=-Iinclude all: liu clean liu: main.o liu.o generatedatafile.o gcc -g $? -o $@ $(LIBS) main.o: src/main.c gcc -c $? $(INC) 自定义头文件不能重复include 建议在main.c中include(假设有多个文件使用) 或者在使用文件include(假设只有一个文件使用) liu.o: src/liu.c gcc -c $? generatedatafile.o: src/generatedatafile.c gcc -c $? clean: $(RM) *.o |
- make
$make gcc -c src/liu.c gcc -c src/generatedatafile.c gcc -g main.o liu.o generatedatafile.o -o liu -L/usr/local/mysql/lib/mysql -lmysqlclient -lz rm -f *.o |
[macg@machome]:/export/home/macg/mysqltmp>$ls -F Makefile dataf lib/ src/ liu* include/ [macg@machome]:/export/home/macg/mysqltmp>$ls src generatedatafile.c liu.c main.c [macg@machome]:/export/home/macg/mysqltmp>$ls include comm.h [macg@machome]:/export/home/macg/mysqltmp>$ls lib comm.c comm.o libcomm.so |
转自:http://blog.sina.com.cn/s/blog_6151984a0100er9a.html