MAKE手册中的注意点之“静态模式”

4.12 静态模式

静态模式规则是这样一个规则:规则存在多个目标,并且不同的目标可以根据目标文件的名字来自动构造出依赖文件。静态模式规则比多目标规则更通用,它不需要多个目标具有相同的依赖。但是静态模式规则中的依赖文件必须是相类似的而不是完全相同的。

4.12.1 静态模式规则的语法

首先,我们来看一下静态模式规则的基本语法:

 

 

TARGETS ...: TARGET-PATTERN: PREREQ-PATTERNS ...

COMMANDS

...

 

“TAGETS”列出了此规则的一系列目标文件。像普通规则的目标一样可以包含通配符。关于通配符的使用可参考 3.4 文件名使用通配符一节

TAGET-PATTERN”和“PREREQ-PATTERNS”说明了如何为每一个目标文件生成依赖文件。从目标模式(TAGET-PATTERN)的目标名字中抽取一部分字符串(称为“茎”)。使用“茎”替代依赖模式(PREREQ-PATTERNS)中的相应部分来产生对应目标的依赖文件。下边详细说明这一替代的过程。

首先在目标模式和依赖模式中,一般需要包含模式字符“%”。在目标模式(TAGET-PATTERN)中“%”可以匹配目标文件的任何部分,模式字符“%”匹配的部分就是“茎”。目标文件和目标模式的其余部分必须精确的匹配。看一个例子:目标“foo.o”符合模式“%.o”,其“茎”为“foo”。而目标“foo.c”和“foo.out”就不符合此目标模式。

每一个目标的依赖文件是使用此目标的“茎”代替依赖模式(PREREQ-PATTERNS)中的模式字符“%”而得到。例如:上边的例子中依赖模式(PREREQ-PATTERNS)为“%.c”,那么使用“茎”“foo”替代依赖模式中的“%”得到的依赖文件就是“foo.c”。需要明确的一点是:在模式规则的依赖列表中使用不包含模式字符“%”也是合法的。代表这个文件是所有目标的依赖文件。

在模式规则中字符‘%’可以用前面加反斜杠“\”方法引用。引用“%”的反斜杠也可以由更多的反斜杠引用。引用“%”、“\”的反斜杠在和文件名比较或由“茎”代替它之前会从模式中被删除。反斜杠不会因为引用“%”而混乱。如,模式“the\%weird\\%pattern\\”是“the%weird\+%+pattern\\”构成。最后的两个反斜杠由于没有任何转义引用“%”所以保持不变。

我们来看一个例子,它根据相应的.c文件来编译生成“foo.o”和“bar.o”文件:

objects = foo.o bar.o

 

all: $(objects)

 

$(objects): %.o: %.c

         $(CC) -c $(CFLAGS) $< -o $@

 

例子中,规则描述了所有的.o文件的依赖文件为对应的.c文件,对于目标“foo.o”,取其茎“foo”替代对应的依赖模式“%.c”中的模式字符“%”之后可得到目标的依赖文件“foo.c”。这就是目标“foo.o”的依赖关系“foo.o: foo.c”,规则的命令行描述了如何完成由“foo.c”编译生成目标“foo.o”。命令行中“$<”和“$@”是自动化变量,“$<”表示规则中的第一个依赖文件,“$@”表示规则中的目标文件(可参考 3.14 自动产生依赖 一节)。以上的规则就是描述了以下两个具体的规则:

 

foo.o : foo.c

      $(CC) -c $(CFLAGS) foo.c -o foo.o

bar.o : bar.c

      $(CC) -c $(CFLAGS) bar.c -o bar.o

 

在使用静态模式规则时,指定的目标必须和目标模式相匹配,否则在执行make时将会得到一个错误提示。如果存在一个文件列表,其中一部分符合某一种模式而另外一部分符合另外一种模式,这种情况下我们可以使用“filter”函数(可参考 第七章 make的内嵌函数)来对这个文件列表进行分类,在分类之后对确定的某一类使用模式规则。例如:

 

files = foo.elc bar.o lose.o

$(filter %.o,$(files)): %.o: %.c

       $(CC) -c $(CFLAGS) $< -o $@

 

$(filter %.elc,$(files)): %.elc: %.el

       emacs -f batch-byte-compile $<

 

其中;$(filter %.o,$(files))的结果为“bar.o lose.o”。“filter”函数过滤不符合“%.o”模式的文件名而至返回所有符合此模式的文件列表。第一条静态模式规则描述了这些目标文件是通过编译对应的.c源文件来重建的。同样第二条规则也是使用这种方式。

我们通过另外一个例子来看一下自动环变量“$*”在静态模式规则中的使用方法:

 

bigoutput littleoutput : %output : text.g

       generate text.g -$* > $@

 

当执行此规则的命令时,自动环变量“$*”被展开为“茎”。在这里就是“big”和“little”。

静态模式规则在一个较大的工程中非常有用的。它可以对一个工程中的同类文件的重建规则进行一次定义,而实现对整个工程中此类文件指定相同的重建规则。比如,可以用来描述整个工程中所有的.o文件的依赖规则和编译命令。通常的做法是将生成同一类目标的模式定义在一个make.rules的文件中。在工程各个模块的Makefile中包含此文件。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值