makefile

来源:互联网 发布:sum服务器监控软件 编辑:程序博客网 时间:2024/06/03 20:06

make一些默认规则:

转载文章http://blog.csdn.net/xkq_lyx/article/details/17800791

一、两个阶段:

1.读取所有的makfile文件,(包括include字段),内建所有的变量和他们的值,隐式和显示规则,构建target和prerequisites的依赖关系

2.根据第1步中构造的依赖关系,来决定是否一些target是否需要进行重建工作。


二、变量赋值,按照官网的介绍,赋值有立即展开和延迟展开.

立即展开:意味着在第一阶段的时候,文件顺序被读取的时候,凡在该立即展开位置的变量都会被马上展开,而不会等待第二阶段,由全文来最终决定该变量的值

延迟展开:在第二阶段,由该变量在文件中的最后一个赋值关系进行最终展开。

如赋值:

immediate = deferredimmediate ?= deferredimmediate := immediateimmediate ::= immediateimmediate += deferred or immediateimmediate != immediatedefine immediate  deferredendefdefine immediate =  deferredendefdefine immediate ?=  deferredendefdefine immediate :=  immediateendefdefine immediate ::=  immediateendefdefine immediate +=  deferred or immediateendefdefine immediate !=  immediateendef

例子:

a=1test=xb$(test)=$(a)test=ya=3all:    @echo $(bx)    @echo $(by)    @echo $(test)a=4

输出结果: 

4


y
这里表示bx=4,by未定义空字符
首先根据b$(test)=$(a),其规则为immediate = deferred,
所以左边的b$(test)立即展开,而由于顺序读取文件时,其之前的test只能设值为x 
因此立即展开为bx
而后面的deferred为延迟展开,所以b$(test)=$(a)的表达式等价为bx=$(a)
而@echo $(bx)也为延迟展开,在第二阶段的时候,先展开$(bx)即a,再展开$(a),而a在文件中最终赋值为4,因此为4 
而@echo $(by)因为by实际并没有被定义,因此$(by)实际是空字符
而@echo $(test)因为test在中文件中最终赋值为y,则打印为y 
提示:其实可以通过查看make -f Makefile -p 来查看该Makefile在第一阶段的解析是怎样,如下片段
# makefile (从'Makefile_8',行 3)  
bx = $(a)


三、为了避免混淆(自己有点混淆),故可按照下面的方式进行解读: 
1.先查看需要定位的语句,在该语句的位置判断其立即展开和延迟展开的部分
2.对于其立即展开的部分,根据其位置以上的均为到达该位置时已设置且可用的变量,并以此为基础,进行立即展开,而无视其位置后面的变量定义
3.对于延迟展开的部分,将延迟展开的表达式保留下来,等待文件完整读取完后,考虑该变量最终被设置成什么变量关系,并最终推导该变量的值
4.以此最终确定该表达式


四、.PHONY
一个作用是使目标名不认为是文件

.PHONY clean
clean:
rm -rf ./
这样即使当前路径下存在clean文件,也会忽略,而继续执行rm -rf ./指令
相关文章:https://www.gnu.org/software/make/manual/html_node/Phony-Targets.html


五、自动变量
%@,target名字
%<第一依赖


六、搜索路径VPATH
vpath %.cpp ../src ../include


七、makefile的搜索路径与编译具体代码的搜索路径是两回事

如:

target ... : prerequisites ...    command    ...
target...:prerequisties是makefile的搜索的路径,可通过vpath设置

而command则是你具体代码的搜索路径了,不会收到vpath的影响,同时其设置的搜索路径也不会影响target...:prerequisties


八、函数

函数调用语法:
$(fun_name argument,,)
Make的内嵌函数列表:
文本处理函数
$(substFROM,TO,TEXT)           #把字串<text>中的<from>字符串替换成<to> 
$(patsubstPATTERN,REPLACEMENT,TEXT) #搜索“TEXT”中以空格分开的单词,将符合模式“PATTERN”替换为“REPLACEMENT”
$(stripSTRINT)       #去掉字串“STRINT”开头和结尾的空字符,并将其中多个连续空字符合并为一个空字符
$(findstringFIND,IN)     #如果在“IN”之中存在“FIND”,则返回“FIND”,否则返回空
$(filterPATTERN…,TEXT)     #过滤掉字串“TEXT”中所有不符合模式“PATTERN”的单词,保留所有符合此模式的单词
$(filter-outPATTERN...,TEXT)   #过滤掉字串“TEXT”中所有符合模式“PATTERN”的单词,保留所有不符合此模式的单词
$(sortLIST)       #给字串“LIST”中的单词以首字母为准进行排序(升序),并去掉重复的单词
$(wordN,TEXT)       #取字串“TEXT”中第“N”个单词(“N”的值从1开始)
$(wordlistS,E,TEXT)     #从字串“TEXT”中取出从“S”开始到“E”的单词串
$(wordsTEXT)       #计算字串“TEXT”中单词的数目
$(firstwordNAMES…)      #取字串“NAMES…”中的第一个单词

文件名处理函数
$(dirNAMES…)       #从文件名序列“Name1Name2 …”中取出各个文件名的目录部分
$(notdirNAMES…)      #从文件名序列“NAMES…”中取出非目录部分
$(suffixNAMES…)      #从文件名序列“NAMES…”中取出各个文件名的后缀
$(basenameNAMES…)      #从文件名序列“NAMES…”中取出各个文件名的前缀部分
$(addsuffixSUFFIX,NAMES…)    #为“NAMES…”中的每一个文件名添加后缀“SUFFIX” 
$(addprefixPREFIX,NAMES…)    #为“NAMES…”中的每一个文件名添加前缀“PREFIX”
$(joinLIST1,LIST2)      #将字串“LIST1”和字串“LIST2”各单词进行对应连接
$(wildcardPATTERN)      #列出当前目录下所有符合模式“PATTERN”格式的文件名
foreach 函数
$(foreachVAR,LIST,TEXT)    #它是一个循环函数。类似于Linux的shell中的for语句
if 函数
$(ifCONDITION,THEN-PART[,ELSE-PART]) #函数“if”提供了一个在函数上下文中实现条件判断的功能。就像make所支持的条件语句—ifeq一样
call函数
$(callVARIABLE,PARAM,PARAM,...)  #是唯一一个可以创建定制化参数函数的引用函数。使用这个函数可以实现对用户自己定义函数引用
value函数        
$(valueVARIABLE)      #提供了一种在不对变量进行展开的情况下获取变量值的方法
eval函数
$(evalPARAM,...)      #根据其参数的关系、结构,对它们进行替换展开。
origin函数
$(originVARIABLE)      #函数“origin”查询参数“VARIABLE”(一个变量名)的出处
shell函数 
$(shell catfoo)      #所实现的功能和shell中的引用(``)相同
make的控制函数
$(errorTEXT…)       #产生致命错误,并提示“TEXT…”信息给用户,并退出make的执行
$(warningTEXT…)      #它不会导致致命错误(make不退出),而只是提示“TEXT…”,make的执行过
转载地址:http://blog.sina.com.cn/s/blog_679daa6b0100k0wo.html

0 0
原创粉丝点击