【转】makefile的双冒号规则

摘要:
首先,需要明确的是,在Makefile中,一个目标可以出现在多个规则中。当同一个目标出现在多个双冒号规则中时,这些规则将以与普通规则相同的顺序执行,按照它们在Makefile中的写入顺序执行。GNUmake的双冒号规则为我们提供了一种机制,可以根据相关更新执行不同的命令来重建同一个目标。为了解决这两个问题,可以使用双冒号规则。

 在编译一个软件包时看见下面rules文件中出现“binary-predeb/gir1.0-unique-1.0::”,对这里的双冒号很是不解,经查阅资料,才明白一点儿。

#!/usr/bin/make -f


include /usr/share/cdbs/1/class/autotools.mk
include /usr/share/cdbs/1/rules/debhelper.mk
include /usr/share/cdbs/1/rules/simple-patchsys.mk
include /usr/share/cdbs/1/rules/utils.mk
include /usr/share/cdbs/1/class/gnome.mk
include /usr/share/gnome-pkg-tools/1/rules/uploaders.mk
-include /usr/share/gnome-pkg-tools/1/rules/gnome-get-source.mk

LDFLAGS += -Wl,-z,defs -Wl,-O1 -Wl,--as-needed

DEB_DH_MAKESHLIBS_ARGS_libunique-1.0-0 = -V 'libunique-1.0-0 (>= 1.0.2)' -- -c4

binary-predeb/gir1.0-unique-1.0::

    dh_girepository -p$(cdbs_curpkg)

双冒号规则就是使用“::”代替普通规则的“:”得到的规则。当同一个文件作为多个规则的目标时,双冒号规则的处理和普通规则的处理过程完全不同(双冒号规则允许在多个规则中为同一个目标指定不同的重建目标的命令)。

首先需要明确的是:Makefile中,一个目标可以出现在多个规则中。但是这些规则必须是同一类型的规则,要么都是普通规则,要么都是双冒号规则。而不允许一个目标同时出现在两种不同类型的规则中。双冒号规则和普通规则的处理的不同点表现在以下几个方面:

1.        双冒号规则中,当依赖文件比目标更新时。规则将会被执行。对于一个没有依赖而只有命令行的双冒号规则,当引用此目标时,规则的命令将会被无条件执行。而普通规则,当规则的目标文件存在时,此规则的命令永远不会被执行(目标文件永远是最新的)。

2.        当同一个文件作为多个双冒号规则的目标时。这些不同的规则会被独立的处理,而不是像普通规则那样合并所有的依赖到一个目标文件。这就意味着对这些规则的处理就像多个不同的普通规则一样。就是说多个双冒号规则中的每一个的依赖文件被改变之后,make只执行此规则定义的命令,而其它的以这个文件作为目标的双冒号规则将不会被执行。

我们来看一个例子,在我们的Makefile中包含以下两个规则:

 

Newprog :: foo.c

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

Newprog :: bar.c

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

 

如果“foo.c”文件被修改,执行make以后将根据“foo.c”文件重建目标“Newprog”。而如果“bar.c”被修改那么“Newprog”将根据“bar.c”被重建。回想一下,如果以上两个规则为普通规时出现的情况是什么?(make将会出错并提示错误信息)

当同一个目标出现在多个双冒号规则中时,规则的执行顺序和普通规则的执行顺序一样,按照其在Makefile中的书写顺序执行。

GNU make的双冒号规则给我们提供一种根据依赖的更新情况而执行不同的命令来重建同一目标的机制。一般这种需要的情况很少,所以双冒号规则的使用比较罕见。一般双冒号规则都需要定义命令,如果一个双冒号规则没有定义命令,在执行规则时将为其目标自动查找隐含规则。 

     看完这个,我猜想,此rules文件开头“include”了许多*.mk文件,这些文件中可能会出现与“binary-predeb/gir1.0-unique-1.0”同名的目标,如果此时使用普通冒号规则的话,一旦出现同名的目标,则rules文件就会出错(makefile不允许同名目标出现在多个普通冒号规则中),另外在此文件中,每当引用“binary-predeb/gir1.0-unique-1.0”目标时,如果使用普通冒号规则并且目标存在的情况下,规则命令就永远也不会执行。针对这两个问题,使用双冒号规则就能得到很好的解决。 
 

免责声明:文章转载自《【转】makefile的双冒号规则》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇PMBOK概要(九大知识体系与五个具体阶段)004.UDP--拼接UDP数据包,构造ip头和udp头通信(使用原始套接字)下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

【 linux编程 】 Makefile

Makefile:跟我一起写Makefile:https://seisman.github.io/how-to-write-makefile/overview.htmlMakefile中的include命令详解https://www.cnblogs.com/cuckoos/articles/5049984.html一 什么是makefile一个工程中的源文...

Ubuntu 如何编译安装第三方库

在工程应用中都会用到第三方库,标准库是在我们安装IDE环境或系统自带已经编译好的库,我们是可以直接调用的,而第三方库需要我们自己下载,编译和安装后才能使用,这里我们说的是Ubuntu如何使用cmake和make来实现第三方库的安装。 主要的步骤分为三步: 1.首先是需要下载第三方库文件。 2.将下载好的库解压,首先查看文件中是否有makefile或者cma...

Makefile简介

一、为什么要写Makefile         首先要确定我们的目标,Makefile是用来干嘛的?         曾经很长时间我都是在从事Windows环境下的开发,所以根本不知道Makefile是个什么东西。因为早已经习惯了使用VS、Eclipse等等优秀的IDE做开发,只要点一个按钮,程序就可以运行啦。但是进入公司以后,从事的是Unix环境下的开发...

转:openwrt 框架分析

本文是本人对OpenWrt的Makefile的理解,并非转载。OpenWrt是一个典型的嵌入式Linux工程,了解OpenWrt的Makefile的工作过程对提高嵌入式Linux工程的开发能力有极其重要意义。OpenWrt的主Makefile文件只有100行,可以简单分为三部分,1~17行为前导部分,19~31为首次执行部分,33~101为再次执行部分。前...

Linux及ArmLinux程序开发笔记(零基础入门篇)

Linux及Arm-Linux程序开发笔记(零基础入门篇)  作者:一点一滴的Beerhttp://beer.cnblogs.com/ 本文地址:http://www.cnblogs.com/beer/archive/2011/05/05/2037449.html 目录 一、Arm-Linux程序开发平台简要介绍... 3 1.1程序开发所需系统及开发...

makefile中的自动化变量 【转】

转自:http://blog.chinaunix.net/uid-28458801-id-3495215.html 自动化变量 模式规则中,规则的目标和依赖文件名代表了一类文件名;规则的命令是对所有这一类文件重建过程的描述,显然,在命令中不能出现具体的文件名,否则模式规则失去意义。那么在模式规则的命令行中该如何表示文件,将是本小节的讨论的重点。 假如你需要...