【问题标题】:Variables in makefile prerequisitesmakefile 先决条件中的变量
【发布时间】:2013-04-22 10:54:01
【问题描述】:

是否可以在先决条件中使用 makefile 变量?我下面的例子有点落后,但应该展示我想要实现的目标:

objects_subsystem1 := $(patsubst %.c,%.o,$(wildcard ../src/ss1/*.c))
objects_subsystem2 := $(patsubst %.c,%.o,$(wildcard ../src/ss2/*.c))

all : subsystem1.elf subsystem2.elf

%.elf : $(objects_%)
    $(LD) $< -o $@

编辑: 我使用的是 GNU Make 3.80,所以很遗憾 SECONDEPANSION 不可用!

【问题讨论】:

    标签: makefile prerequisites


    【解决方案1】:

    是的,如果您使用的是 GNUMake:

    .SECONDEXPANSION:
    %.elf : $$(objects_%)
        $(LD) $< -o $@
    

    编辑:

    正如@bobbogo 指出的那样,有一个不需要.SECONDEXPANSION 的解决方案。首先,我们阐明规则:

    objects_subsystem1 := $(patsubst %.c,%.o,$(wildcard ../src/ss1/*.c))
    objects_subsystem2 := $(patsubst %.c,%.o,$(wildcard ../src/ss2/*.c))
    objects_subsystem3 := $(patsubst %.c,%.o,$(wildcard ../src/ss3/*.c))
    
    all : subsystem1.elf subsystem2.elf subsystem3.elf
    
    subsystem1.elf : $(objects_subsystem1)
        $(LD) $< -o $@
    subsystem2.elf : $(objects_subsystem2)
        $(LD) $< -o $@
    subsystem3.elf : $(objects_subsystem3)
        $(LD) $< -o $@
    

    然后我们重新整理一下:

    objects_subsystem1 := $(patsubst %.c,%.o,$(wildcard ../src/ss1/*.c))
    all : subsystem1.elf
    subsystem1.elf : $(objects_subsystem1)
    objects_subsystem2 := $(patsubst %.c,%.o,$(wildcard ../src/ss2/*.c))
    all : subsystem2.elf
    subsystem2.elf : $(objects_subsystem2)
    objects_subsystem3 := $(patsubst %.c,%.o,$(wildcard ../src/ss3/*.c))
    all : subsystem3.elf
    subsystem3.elf : $(objects_subsystem3)
    
    %.elf :
        $(LD) $< -o $@
    

    然后我们使用eval函数:

    define RULE_TEMPLATE
    objects_subsystem$(1) := $(patsubst %.c,%.o,$(wildcard ../src/ss$(1)/*.c))
    all : subsystem$(1).elf
    subsystem$(1).elf : $$(objects_subsystem$(1))
    endef
    
    $(eval $(call RULE_TEMPLATE,1))
    $(eval $(call RULE_TEMPLATE,2))
    $(eval $(call RULE_TEMPLATE,3))
    
    %.elf :
        $(LD) $< -o $@
    

    然后以一个循环结束(如果值得的话):

    define RULE_TEMPLATE
    objects_subsystem$(1) := $(patsubst %.c,%.o,$(wildcard ../src/ss$(1)/*.c))
    all : subsystem$(1).elf
    subsystem$(1).elf : $$(objects_subsystem$(1))
    endef
    
    SUBSYSTEMS := 1 2 3 # this can be made automatic...
    
    $(foreach sys,$(SUBSYSTEMS),$(eval $(call RULE_TEMPLATE,$(sys))))
    
    %.elf :
        $(LD) $< -o $@
    

    【讨论】:

    • 只是我正在寻找的指针。感谢您提供答案。
    • 虽然这个答案很好,但它在我的旧版本 GNU Make 3.80 中不起作用。似乎从 3.81 开始可用:cmcrossroads.com/article/whats-new-gnu-make-381 不幸的是,我的 make 程序是供应商工具链的一部分,我无法更新 :(
    • 那么一个简单的subsystem1.elf: ${objects_subsystem1} 单独一行就足够了。如果你需要一堆这样的东西,那就用$(eval...)把它放在一个循环中。
    • 能否请您详细说明 bobbogo。每个“一个班轮”是否也需要 LD 命令?是的,我确实有越来越多的这些,所以希望尽可能地自动化。
    • 太棒了 Beta。感谢您提供如此详细的回复:)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-05-05
    • 2012-06-05
    • 1970-01-01
    • 2023-03-23
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多