我正在尝试设置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
即使规则已定义,也不符合先决条件......
答案 0 :(得分:2)
只要替换变量,就会扩展递归扩展的make变量(赋值为=
的变量)。这意味着,您之前需要定义其他变量。在您的情况下,您需要向上移动TO_LIB
几行的定义(至少高于exe规则,因为LIBS
的扩展需要TO_LIB
在那里可用)