makefile笔记

4 篇文章 0 订阅
1 篇文章 0 订阅

看懂makefile文档

在GitHub上看到一个C++项目,想着模仿写一个,于是计划先从makefile文档看起,要看懂makefile文档,首先需要知道makefile的语法规则。而在了解makefile语法规则之前先回顾一下linux下从源程序到可执行程序的处理过程。

从源程序到可执行程序

如果已经对源程序到可执行程序的过程了如执掌,读者可以略过这段。
应用程序员使用程序编辑软件,得到hello.c文件,在计算机中以ASCII字符存放(不同操作系统编码方式不一样)。以下是hello.c的C语言源程序代码。

#include <stdio.h> 
int main(void){
     printf("hello,world\n");
}

应用程序员接着对程序进行预处理、编译、汇编、链接的操做,最终生成可执行的目标文件。

预处理

预处理阶段是对文件的宏定义进行展开的过程,这个宏定义的展开包括头文件的展开,预处理过程的输入为.c文件,输出为.i文件,执行程序为cpp,运行代码如下所示:

gcc -E hello.c -o hello.i

编译

编译过程是对预处理后的源程序进行编译,生成一个汇编语言源程序文件。其输入为.i文件,输出为.s文件,执行程序为cc1。无论什么样的高级语言,通过编译之后得到的汇编语言都将会变成同一种汇编语言。运行代码如下所示:

gcc -S hello.i -o hello.s

汇编

汇编过程是对汇编语言源程序进行汇编,生成一个可重定位的目标文件的过程。输入为.s文件,输出为.o文件,执行程序为as。此时生成的文件已经转换成二进制文件了,人是很难再读懂的。运行代码如下所示:

as hello.s -o hello.o

链接

链接过程时将多个可重定位的目标文件和标准库函数合并成一个可执行的目标文件,输入为.o文件,输出为hello可执行文件,执行程序为ld,运行代码如下所示:

gcc hello -o hello.o

make工程管理器的引入

如果一个项目包含了上百个代码文件,而每次项目更新只是更新了少数几个文件,如果每一次更新都对所有项目文件进行重新编译,编译步骤将会极其的繁琐。为此,引入了Make工程管理器的概念,工程管理器能够根据文件时间自动发现更新后的文件,未更新过的文件不必重新编译,从而减少了编译的工作量。工程管理器通过读取makefile文件来执行makefile中定义好的操做从而自动执行大量的编译工作。

makefile格式

target:dependency_files //target(目标项):denpendcy_files(依赖项)
<TAB>command //command(编译命令)开头必须以tab开头	

写command(命令行)时,必须在前面加入TAB键。
给定一个makefile文件实例,:

main.exe:main.o func.o
	g++ -o main.exe main.o func.o
main.o:main.cpp
	g++ -c main.cpp
func.o:func.cpp
	g++ -c func.cpp

假设我们更改了func.cpp文件,在命令行运行

make

make如何工作

1、make会在当前目录下找名字为"Makefile"或者"makefile"的文件。
2、如果找到,它会找到文件中的第一个目标文件(target),在上面的例子中,它首先找到main.exe这个文件,并把这个文件作为最终的目标文件。
3、如果main.exe文件不存在(首次执行),或者main.exe后面的依赖文件比main.exe文件要新,那么它将会执行后面的命令来生成main.exe文件。
4、如果main.exe所依赖的.o文件并不存在,那么make会在当前文件中查找.o文件的依赖文件,如果找到则根据这一规则生成.o文件。(先进后出栈模型)
5、最后找到的依赖文件再无依赖,于是make会生成.o文件,最后.o文件会根据依赖一层一层的生成可执行文件。

再makefile文件中设置clean命令的话,采用以下命令

make clean

会清除掉所有的目标文件,以方便重新编译。
如果func.cpp文件更新了,那么执行make命令之后,func.o文件更新时间会比main.exe文件更新时间更新,这会导致第二行命令的执行,最终会使得生成的main.exe文件更新。

Makefile里包含了什么东西?

Makefile包含了五种东西:显式规则、隐晦规则、变量定义、文件指示和注释。
1、显示规则。说明如何生成一个或者多个目标文件。由Makefile文件的编写者明确指出要生成的文件、文件的依赖文件和生成的命令。
2、隐晦规则。make具有自动推导的功能,隐晦规则可以让我们简略的书写Makefile。
3、变量的定义。在Makefile中定义一系列的变量,这些变量类似于C语言中的宏。当Makefile被执行时,其中的变量就会被扩展到相应的引用位置上去。
4、文件指示。分为三部分,一个是Makefile引用另一个Makefile,类似于include,另一个部分根据情况指定Makefile中的有效部分,就像预编译一样。最后是定义多行命令。
5、注释。Makefile中只有行注释,注释用**#**字符。

若干注意事项

1、伪目标
clean是一个伪目标

clean:
	rm *.o temp

伪目标不是一个文件,只是一个标签,我们可以使用“.PHONY”来显示指明一个目标是伪目标,向make 说明,不管是否存在这个文件,这个目标就是“伪目标”。

.PHONY : clean

makefile更多详细知识见以下链接:
https://seisman.github.io/how-to-write-makefile/introduction.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值