【问题标题】:jom/nmake rule that creats tow files创建两个文件的 jom/nmake 规则
【发布时间】:2020-07-20 15:28:15
【问题描述】:

我正在将 Makefile 从 omake.exe(来自 ClearCase)迁移到 jom.exe/nmake.exe。

一个简化的 Makefile 示例:

all: bin1 bin2

rule1 rule2: rule3
    @echo creating rule1 and rule2
    @touch rule1 rule2

rule3:
    @echo creating rule3
    @touch rule3

bin1: rule1
    @echo creating bin1
    @touch bin1

bin2: rule2
    @echo creating bin2
    @touch bin2

touch 只是创建一个文件,或者如果它已经存在,它会更新时间戳。

jom/namke 的输出是:

creating rule3
creating rule1 and rule2
creating rule1 and rule2
creating bin1
creating bin2

创建规则1和规则2执行两次。

使用 omake,规则只执行一次,意思是在一个命令中创建文件 rule1 和 rule2(此处为 touch)。

同时创建 rule1 和 rule2 的命令只被调用一次,我有什么需要改变的?

谢谢 泰迪熊

【问题讨论】:

    标签: makefile nmake


    【解决方案1】:

    我对 omake 或 nmake 一无所知。但我可以为您提供有关标准 (POSIX) make 的信息,并且在这些 make 实例符合标准的范围内,它可能会有用。

    在标准制作中,这条规则:

    rule1 rule2: rule3
             @echo creating rule1 and rule2
             @touch rule1 rule2
    

    从不表示“一次调用配方会构建两个目标”。它被解释为与您编写的完全相同:

    rule1: rule3
             @echo creating rule1 and rule2
             @touch rule1 rule2
    rule2: rule3
             @echo creating rule1 and rule2
             @touch rule1 rule2
    

    因此,从某种意义上说,您从nmake 看到的行为是可以预料的。除了,它在 POSIX make 中永远不会像那样工作,因为 POSIX make 总是一次运行一个规则。所以,首先它会尝试构建rule1,然后实际上同时构建rule1rule2。那么当 make 调查它是否需要构建 rule2 时,它发现它已经是最新的并且没有做任何事情。

    因此,尽管 make 将此规则解释为两个不同的目标,但它与只运行一个规则具有相同的效果:运行一次配方会更新两个目标,并且 make 只运行一次配方。

    如果您使用 GNU make 或其他支持并行构建的 make,则此行为不再有效,因为 make 可能会在 rule1 的配方有机会更新之前检测到 rule2 已过期.但是,那不是 POSIX。

    我无法解释为什么 nmake 不能像这样工作......这是一个非常奇怪且有限的 make 实现。

    在 POSIX 中处理此问题的传统方法是引入一个“哨兵文件”,将这些多个目标收集到一个文件中,如下所示:

    rule1 rule2 : sentinel ;
    
    sentinel: rule3
             @echo creating rule1 and rule2
             @touch rule1 rule2
             @touch $@
    

    我不知道类似的东西是否适用于nmake

    如果您使用 GNU make,它会起作用,或者如果您使用当前版本 (4.3),您可以显式声明分组目标,如下所示:

    rule1 rule2 &: rule3
             @echo creating rule1 and rule2
             @touch rule1 rule2
    

    【讨论】:

      猜你喜欢
      • 2012-09-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-05-20
      • 1970-01-01
      • 2011-07-01
      • 1970-01-01
      相关资源
      最近更新 更多