Makefile资料整理Word文件下载.docx
- 文档编号:4682922
- 上传时间:2023-05-03
- 格式:DOCX
- 页数:13
- 大小:24.55KB
Makefile资料整理Word文件下载.docx
《Makefile资料整理Word文件下载.docx》由会员分享,可在线阅读,更多相关《Makefile资料整理Word文件下载.docx(13页珍藏版)》请在冰点文库上搜索。
使用变量:
$(变量名)
(3)默认变量,也就是make不定义就可以使用的变量:
AR:
档案管理程序;
缺省为:
‘ar'
.
AS:
汇编编译程序;
‘as'
CC:
C语言编译程序;
‘cc'
CXX:
C++编译程序;
‘g++'
CPP:
带有标准输出的C语言预处理程序;
‘$(CC)-E'
RM:
删除文件的命令;
‘rm-f'
(4)自动变量,在写规则中的命令时使用,
比如
那么,以下符号出现在命令中时有特殊含义:
$@:
规则的目标文件名。
对于有多个目标的格式规则,它指导致规则命令运行的目标文件名。
$<
:
第一个依赖的文件名。
如果目标更新命令来源于隐含规则,该变量的值是隐含规则添加的第一个依赖。
$^:
所有依赖的名字,名字之间用空格隔开。
如果在依赖列表中,同一个文件名出现多次,则仅包含该文件名一次。
$*:
和隐含规则匹配的stem(径),stem的解释待会再说
(5)有以上的基本知识,可以看一个简单的Makefile:
===makefile开始===
OBJS=foo.obar.o
CC=gcc
CFLAGS=-Wall-O-g
myprog:
$(OBJS)
$(CC)$(OBJS)-omyprog
foo.o:
foo.cfoo.hbar.h
$(CC)$(CFLAGS)-cfoo.c-ofoo.o
bar.o:
bar.cbar.h
$(CC)$(CFLAGS)-c$<
-o$@
===makefile结束===
说明:
开始三行定义变量:
OBJS、CC、CFLAGS
这里有三条规则,而第一条一般作为默认规则,也就是说如果在shell命令行中只输入make的话就从这里开始
第一条规则是说:
要去编译foo.o和bar.o,编译完后再执行gccfoo.obar.o-omyprog从而生成myprog文件
4>
第二条规则是说如何编译foo.o,它执行命令:
gcc-Wall-O-g-cfoo.c-ofoo.o
5>
第三条规则比第二条复杂一点点:
$<
是指bar.c,$@是指bar.o,所以命令是:
gcc-Wall-O-g-cbar.cbar.o
二、较高级的知识
(1)什么时候更新目标文件?
Make程序根据Makefile文件中的数据和每个文件更改的时间戳决定哪些文件需要更新。
对于这些需要更新的文件,Make基于Makefile文件发布命令进行更新,进行更新的方式由提供的命令行参数控制。
比如上面那个简单的Makefile,make从最上面开始,把上面第一个目的,‘myprog’,做为它的主要目标(一个它需要保证其总是最新的最终目标)。
给出的规则说明只要文件‘myprog’比文件‘foo.o’或‘bar.o’中的任何一个旧,下一行的命令将会被执行。
但是,在检查文件foo.o和bar.o的时间戳之前,它会往下查找那些把foo.o或bar.o做为目标文件的规则。
它找到的关于foo.o的规则,该文件的依靠文件是foo.c,foo.h和bar.h。
它从下面再找不到生成这些依靠文件的规则,它就开始检查磁盘上这些依靠文件的时间戳。
如果这些文件中任何一个的时间戳比foo.o的新,命令'
gcc-ofoo.ofoo.c'
将会执行,从而更新文件foo.o。
(2)假想目标(PhonyTargets):
假想目标并不是一个真正的文件名,它仅仅是您制定的一个具体规则所执行的一些命令的名称。
应用一:
all:
exec1exec2
其中exec1和exec2是我们做为目的的两个可执行文件。
make把这个'
all'
做为它的主要目的,每次执行时都会尝试把'
更新。
但既然这行规则里没有哪个命令来作用在一个叫'
的实际文件(事实上all并不会在磁盘上实际产生),所以这个规则并不真的改变'
的状态。
可既然这个文件并不存在,所以make总会尝试更新all规则,因此就检查它的依靠exec1,exec2是否需要更新,如果需要,就把它们更新,从而达到我们的目的。
应用二:
clean:
rm*.otemp
那么,在shell下输入'
makeclean'
就会去执行rm*.otemp了,但如果你的磁盘上存在一个叫clean文件,会发生什么事?
这时因为在这个规则里没有任何依赖文件,所以这个目的文件一定是最新的了(所有的依赖文件都已经是最新的了),所以既使用户明确命令make重新产生它,也不会有任何事情发生。
解决方法是用.PHONY标明假想目标,这就告诉make不用检查它们是否存在于磁盘上,也不用查找任何隐含规则,直接假设指定的目的需要被更新。
在makefile里加入下面这行包含上面规则的规则:
.PHONY:
clean
(3)隐含规则
允许make对一个目标文件寻找传统的更新方法,您所有做的是避免指定任何命令。
可以编写没有命令行的规则或根本不编写任何规则。
这样,make将根据存在的源文件的类型或要生成的文件类型决定使用何种隐含规则。
例如,假设makefile文件是下面的格式:
foo:
foo.obar.o
cc-ofoofoo.obar.o$(CFLAGS)$(LDFLAGS)
因为您提及了文件‘foo.o’,但是您没有给出它的规则,make将自动寻找一条隐含规则,该规则能够告诉make怎样更新该文件。
无论文件‘foo.o’存在与否,make都会这样执行。
然后make就会找到如下规则生成'
foo.o'
:
CompilingCprograms(编译C程序)
‘n.o'
自动由‘n.c'
使用命令‘$(CC)-c$(CPPFLAGS)$(CFLAGS)'
生成。
所以,当使用隐含规则时,还要关注一下编译器额外标志变量,比较常用的有:
ASFLAGS:
用于汇编编译器的额外标志(当具体调用‘.s'
或‘.S'
文件时)。
CFLAGS:
用于C编译器的额外标志。
CXXFLAGS:
用于C++编译器的额外标志。
CPPFLAGS:
用于C预处理以及使用它的程序的额外标志(C和Fortran编译器)。
LDFLAGS:
用于调用linker(‘ld’)的编译器的额外标志。
(4)条件语句
一个条件语句可以导致根据变量的值执行或忽略makefile文件中一部分脚本。
条件语句可以将一个变量与其它变量的值相比较,或将一个变量与一字符串常量相比较。
条件语句用于控制make实际看见的makefile文件部分,不能用于在执行时控制shell命令。
下述的条件语句的例子告诉make如果变量CC的值是‘gcc’时使用一个数据库,如不是则使用其它数据库。
它通过控制选择两命令行之一作为该规则的命令来工作。
‘CC=gcc’作为make改变的参数的结果不仅用于决定使用哪一个编译器,而且决定连接哪一个数据库。
libs_for_gcc=-lgnu
normal_libs=
foo:
$(objects)
ifeq($(CC),gcc)
$(CC)-ofoo$(objects)$(libs_for_gcc)
else
$(CC)-ofoo$(objects)$(normal_libs)
endif
该条件语句使用三个指令:
ifeq、else和endif。
Ifeq指令是条件语句的开始,并指明条件。
它包含两个参数,它们被逗号分开,并被扩在圆括号内。
运行时首先对两个参数变量替换,然后进行比较。
在makefile中跟在ifeq后面的行是符合条件时执行的命令;
否则,它们将被忽略。
else指令指出:
如果前面的条件失败将导致跟在其后面的命令执行。
在上述例子中,意味着当第一个选项不执行时,和第二个选项连在一起的命令将执行。
在条件语句中,else指令是可选择使用的。
endif指令结束条件语句。
任何条件语句必须以endif指令结束,后跟makefile文件中的正常内容。
当变量CC的值是gcc,上例的效果为:
当变量CC的值不是gcc而是其它值的时候,上例的效果为:
上例表明条件语句工作在原文水平:
条件语句的行根据条件要么被处理成makefile文件的一部分或要么被忽略。
这是makefile文件重大的语法单位(例如规则)可以跨越条件语句的开始或结束的原因。
(5)在目录中搜寻依赖
变量VPATH(注意是大写的)的值指定了make搜寻的目录。
经常用到的是那些包含依赖的目录,并不是当前的目录;
但VPATH指定了make对所有文件都适用的目录搜寻序列,包括了规则的目标所需要的文件。
在VPATH变量定义中,目录的名字由冒号或空格分开。
目录列举的次序也是make搜寻的次序。
在MS-DOS、MS-WINDOWS系统中,VPATH变量定义中的目录的名字由分号分开,因为在这些系统中,冒号用为路径名的一部分(通常在驱动器字母后面)。
例如:
VPATH=src:
../headers
指定了两个目录,‘src’和‘…/headers’,make也按照这个次序进行搜寻。
vpath指令(注意字母是小写)和VPATH变量类似,但却更具灵活性。
vpath指令允许对符合一定格式类型的文件名指定一个搜寻路径。
这样您就可以对一种格式类型的文件名指定一个搜寻路径,对另外格式类型的文件名指定另外一个搜寻路径。
总共由三种形式的vpath指令:
vpathpatterndirectories对一定格式类型的文件名指定一个搜寻路径,搜寻的路径VPATH变量定义要搜寻的路径格式一样。
vpathpattern清除和一定类型格式相联系的搜寻路径。
vpath清除所有前面由vapth指令指定的搜寻路径。
(6)静态格式规则与径stem
静态格式规则的语法格式如下:
targets...:
target-pattern:
dep-patterns...
commands
...
目标列表指明该规则应用的目标。
目标可以含有通配符,具体使用和平常的目标规则基本一样
目标的格式和依赖的格式是说明如何计算每个目标依赖的方法。
从匹配目标格式的目标名中依据格式抽取部分字符串,这部分字符串称为径。
将径分配到每一个依赖格式中产生依赖名。
每一个格式通常包含字符‘%’。
目标格式匹配目标时,‘%’可以匹配目标名中的任何字符串;
这部分匹配的字符串称为径;
剩下的部分必须完全相同。
如目标‘foo.o’匹配格式‘%.o’,字符串‘foo’称为径。
而目标‘foo.c’和‘foo.out’不匹配格式。
每个目标的依赖名是使用径代替各个依赖中的‘%’产生。
如果一个依赖格式为‘%.c’,把径‘foo’代替依赖格式中的‘%’生成依赖的文件名‘foo.c’。
在依赖格式中不包含‘%’也是合法的,此时对所有目标来说,依赖是相同的。
如果一个目标为‘dir/a.foo.b'
,目标格式规则为:
‘a.%.b'
,则stem为‘dir/foo'
。
在构建相关文件名时stem十分有用。
在静态格式规则中,stem是匹配目标格式中字符‘%’的文件名中那一部分。
在一个没有stem具体规则中;
变量‘$*'
不能以该方法设置。
如果目标名以一种推荐的后缀结尾(参阅过时的后缀规则),变量‘$*'
设置为目标去掉该后缀后的部分。
例如,如果目标名是‘foo.c'
,则变量‘$*'
设置为‘foo'
因为‘.c'
是一个后缀。
GNUmake处理这样奇怪的事情是为了和其它版本的make兼容。
在隐含规则和静态格式规则以外,您应该尽量避免使用变量‘$*'
在具体规则中如果目标名不以推荐的后缀结尾,则变量‘$*’在该规则中设置为空值。
下面是两个例子:
例一:
files=foo.elcbar.olose.o
$(filter%.o,$(files)):
%.o:
%.c
$(CC)-c$(CFLAGS)$<
$(filter%.elc,$(files)):
%.elc:
%.el
emacs-fbatch-byte-compile$<
在这个例子中,‘$(filter%.o,$(files))'
的结果是‘bar.olose.o'
,第一个静态格式规则是将相应的C语言源文件编译更新为OBJ文件,‘$(filter%.elc,$(files))'
的结果是‘foo.elc'
,它由‘foo.el’构造。
例二:
在静态格式规则中使用‘$*’
bigoutputlittleoutput:
%output:
text.g
generatetext.g-$*>
$@
当命令generate执行时,$*扩展为径,即‘big’或‘little’二者之一。
(7)格式规则与径stem
格式规则是在目标中包含字符‘%’(只有一个)的规则,其它方面看起来和普通规则相同。
目标是可以匹配文件名的格式,字符‘%’可以匹配任何非空的字符串,而其它字符仅仅和它们自己相匹配。
例如‘%.c’匹配任何以‘.c’结尾的文件名;
‘s.%.c’匹配以‘s.’开始并且以‘.c’结尾的文件名,该文件名至少包含5个字符(因为‘%’至少匹配一个字符)。
匹配‘%’的子字符串称为stem(径)。
依赖中使用‘%’表示它们的名字中含有和目标名相同的stem。
要使用格式规则,文件名必须匹配目标的格式,而且符合依赖格式的文件必须存在或可以创建。
下面规则:
%.o:
%.c;
command...
表明要创建文件‘n.o’,使用‘n.c’作为它的依赖,而且文件‘n.c’必须存在或可以创建。
在格式规则中,依赖有时不含有‘%’。
这表明采用该格式规则创建的所有文件都是采用相同的依赖。
这种固定依赖的格式规则在有些场合十分有用。
格式规则的依赖不必都包含字符‘%’,这样的规则是一个有力的常规通配符,它为任何匹配该目标格式规则的文件提供创建方法。
(8)函数
函数调用和变量引用类似,它的格式如下:
$(functionarguments)
或这样:
${functionarguments}
'
function'
是函数名,是make内建函数列表中的一个。
当然您也可以使用创建函数call创建的您自己的函数。
arguments'
是该函数的参数。
参数和函数名之间是用空格或Tab隔开,如果有多个参数,它们之间用逗号隔开。
$(substfrom,to,text)
在文本‘text’中使用‘to’替换每一处‘from’。
$(substee,EE,feetonthestreet)结果为‘fEEtonthestreet’。
$(patsubstpattern,replacement,text)
寻找‘text’中符合格式‘pattern’的字,用‘replacement’替换它们。
这里‘pattern’中包含通配符‘%’,它和一个字中任意个数的字符相匹配。
如果‘replacement’中也含有通配符‘%’,则这个‘%’被和‘pattern’中通配符‘%’匹配的文本代替。
$(patsubst%.c,%.o,x.c.cbar.c)的结果为:
‘x.c.obar.o'
替换引用是实现函数patsubst功能一个简单方法:
$(var:
pattern=replacement)等同于:
$(patsubstpattern,replacement,$(var))
来看一个例子:
怎样使用函数subst和patsubst告诉C编译器在相同路径列表中搜寻头文件?
(假设变量VPATH=src:
../headers)
首先,函数subst将冒号变为空格:
$(subst:
,$(VPATH))这产生值‘src../headers'
然后,函数patsubst为每一个路径名加入‘-I’标志,$(patsubst%,-I%,$(subst:
,$(VPATH))),产生文本为‘-Isrc-I../headers’
最后,将这些路径加到变量CFLAGS中:
overrideCFLAGS+=$(patsubst%,-I%,$(subst:
,$(VPATH)))结果是在以前给定的变量CFLAGS的值后追加文本‘-Isrc-I../headers’。
Override指令的作用是即使以前使用命令参数指定变量CFLAGS的值,新值也能起作用。
$(filterpattern...,text)
返回在‘text’中由空格隔开且匹配格式‘pattern...’的字,对于不符合格式‘pattern...’的字移出。
格式用‘%’写出,和前面论述过的函数patsubst的格式相同。
函数filter可以用来变量分离类型不同的字符串。
sources:
=foo.cbar.cbaz.sugh.h
$(sources)
cc$(filter%.c%.s,$(sources))-ofoo
表明‘foo'
依靠‘foo.c'
‘bar.c'
‘baz.s'
和‘ugh.h'
;
但仅有‘foo.c'
和‘baz.s'
指明用命令编译。
$(filter-outpattern...,text)
返回在‘text’中由空格隔开且不匹配格式‘pattern...’的字,对于符合格式‘pattern...’的字移出,即函数filter的剩下的那些。
例如:
objects=main1.ofoo.omain2.obar.o
mains=main1.omain2.o
下面产生不包含在变量‘mains’中的OBJ文件的文件列表:
$(filter-out$(mains),$(objects))
$(wildcardpattern)
参数‘pattern’是一个文件名格式,典型的包含通配符(和shell中的文件名一样)。
函数wildcard的结果是一列和格式匹配的且文件存在的文件名,文件名之间用一个空格隔开。
如果没有和指定格式一致的文件,则函数wildcard的输出将会省略。
注意这和在规则中通配符扩展的方式不同,在规则中使用逐字扩展方式,而不是省略方式。
使用函数wildcard得到指定目录下所有的C语言源程序文件名:
$(wildcard*.c)
我们可以把所获得的C语言源程序文件名的字符串通过将‘.c’后缀变为‘.o’转换为OBJ文件名的字符串,其格式为:
$(patsubst%.c,%.o,$(wildcard*.c))
这样,一个编译特定目录下所有C语言源程序并把它们连接在一起的makefile文件可以写成如下格式:
objects:
=$(patsubst%.c,%.o,$(wildcard*.c))
foo:
cc-ofoo$(objects)
这里使用了编译C语言源程序的隐含规则,因此没有必要为每个文件写具体编译规则。
‘:
=’是‘=’的变异。
6>
$(addprefixprefix,names...)
参数‘names’作为一系列的文件名,文件名之间用空格隔开;
prefix作为一个单位。
将preffix(前缀)的值附加在每一个独立文件名的前面,完成后将文件名串联起来,它们之间用单个空格隔开。
$(addprefixsrc/,foobar)结果为‘src/foosrc/bar’。
(9)
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- Makefile 资料 整理