GNU的问题制作动态规则

时间:2014-04-30 10:23:12

标签: makefile gnu-make rust

我正在尝试设置Makefile来编译我的Rust项目。为了加快速度,我不想一次性重新编译整个项目。 Rust允许您创建可以链接到主可执行文件的库。给定两个文件src/iomrascalai.rs(主程序)和src/board/mod.rs(库)来手动编译它会像这样工作:

$ rustc --out-dir lib src/board/mod.rs
$ ls lib/
libboard-d085aa56-0.0.rlib
$ rustc --out-dir bin -L lib src/iomrascalai.rs
$ ls bin/
iomrascalai

我在Makefile中尝试做的是定义动态规则来编译库。我试图这样做,因为从源文件(src/board/mod.rs)到库名称(lib/libboard-d085aa56-0.0.rlib)的映射是非常重要的。但是,我似乎无法使其发挥作用:

MAIN   = src/iomrascalai.rs
CRATES = src/board/mod.rs

LIBS   = $(foreach crate, $(CRATES), $(call TO_LIB, $(crate)))

all: exe

exe: $(MAIN) $(LIBS)
    rustc --out-dir bin -L lib $(MAIN)

TO_LIB = $(addprefix lib/, $(shell rustc --crate-file-name $(1)))

define COMPILE_CRATE
$(call TO_LIB, $(1)): $(1)
    rustc --out-dir lib $(1)
endef

$(foreach crate, $(CRATES), $(eval $(call COMPILE_CRATE, $(crate))))

运行make会导致以下错误:

$ make
rustc --out-dir bin -L lib src/iomrascalai.rs
src/iomrascalai.rs:22:1: 22:20 error: can't find crate for `board`
src/iomrascalai.rs:22 extern crate board;
                  ^~~~~~~~~~~~~~~~~~~
error: aborting due to previous error
make: *** [exe] Error 101

因此库未编译,这意味着无法编译主程序。当我尝试运行make来编译lib目标时,它可以工作:

$ rustc --crate-file-name src/board/mod.rs
libboard-d085aa56-0.0.rlib
$ make lib/libboard-d085aa56-0.0.rlib
rustc --out-dir lib  src/board/mod.rs

因此,出于某种原因,exe即使规则已定义,也不符合先决条件......

1 个答案:

答案 0 :(得分:2)

只要替换变量,就会扩展递归扩展的make变量(赋值为=的变量)。这意味着,您之前需要定义其他变量。在您的情况下,您需要向上移动TO_LIB几行的定义(至少高于exe规则,因为LIBS的扩展需要TO_LIB在那里可用)