如何在链接时始终包含 Rust 依赖项?
How do I always include a Rust dependency when linking?
我正在尝试使用 Fortanix SGX 框架 运行 飞地中的 libdvdcss,但是 linker 有问题。
我围绕 libdvdcss 创建了一个简单的 FFI 包装器,它在 Linux 上正常执行时工作正常(没有 SGX 并且全局安装了 libdvdcss)。当我 运行 它与 Getting started 页面上指定的目标 x86_64-fortanix-unknown-sgx
时它不起作用,因为 linker 抱怨许多丢失的符号,尤其是 malloc
等
据我了解,问题是 SGX 中没有 libc,因此我需要手动包含 rs-libc
,这基本上是在 SGX 中使用的 libc。 rs-libc
crate 包含 C、ASM 和一些 Rust 代码(主要用于 malloc
)。因此我的 Cargo.toml:
[dependencies]
rs-libc = "0.2.3"
我发现这还不够,我必须提供以下 build.rs 来手动告诉 linker link libc.a
来自 rs-libc
箱子也是。
pub fn main() {
println!("cargo:rustc-link-search=/home/me/dev/libdvdcss/.libs"); // Will be changed later
println!("cargo:rustc-link-lib=static=dvdcss");
println!("cargo:rustc-link-lib=static=c");
}
这修复了一些 strlen
等错误,但未找到 malloc
和 free
。我认为问题在于它们不是从 C 源文件编译的,而是在 alloc.rs 中编译的。我还看到这个源文件被编译成 target/x86_64-fortanix-unknown-sgx/debug/deps/librs_libc-04111db022dd517f.rlib
中的 Rust 库并包含符号:
rs_libc-04111db022dd517f.rs_libc.53f0fd72-cgu.5.rcgu.o:
0000000000000000 T calloc
0000000000000000 T free
0000000000000000 W __llvm_lvi_thunk_r11
0000000000000000 T malloc
0000000000000000 T realloc
0000000000000000 V __rustc_debug_gdb_scripts_section__
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTalloc_zeroed17ha722ea369ab2dac9E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTalloc17h561d825df0f2dfa8E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTdealloc17hbbda0b3d0a1f9d67E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTrealloc17hf76d62802e46847bE
U _ZN4core3ptr4read17hc3470c4a404ff082E
U _ZN4core3ptr5write17ha0bb4d6cbfed535eE
U _ZN4core5alloc6layout6Layout25from_size_align_unchecked17h074422ae6f6459f7E
U _ZN4core9panicking5panic17hde9db97a7382bd28E
不幸的是,这个文件似乎没有包含在最后的 linker 命令中。我认为这是因为在我的 Rust 应用程序中没有找到这个库的用法,因此它被优化了。
有没有办法包含它?
添加一个 extern crate rs_libc;
到你 crate 的根应该可以解决问题。必须将使用 extern crate
声明的依赖项提供给链接器是强制性的。在 rust 2018 及更高版本中,当且仅当您使用该 crate 的一个或多个符号时,编译器才会将适当的声明隐式添加到您的 crate(rust 2015 要求明确添加 extern crate
)。有关详细信息,请参阅 rust reference 中的部分。
我正在尝试使用 Fortanix SGX 框架 运行 飞地中的 libdvdcss,但是 linker 有问题。
我围绕 libdvdcss 创建了一个简单的 FFI 包装器,它在 Linux 上正常执行时工作正常(没有 SGX 并且全局安装了 libdvdcss)。当我 运行 它与 Getting started 页面上指定的目标 x86_64-fortanix-unknown-sgx
时它不起作用,因为 linker 抱怨许多丢失的符号,尤其是 malloc
等
据我了解,问题是 SGX 中没有 libc,因此我需要手动包含 rs-libc
,这基本上是在 SGX 中使用的 libc。 rs-libc
crate 包含 C、ASM 和一些 Rust 代码(主要用于 malloc
)。因此我的 Cargo.toml:
[dependencies]
rs-libc = "0.2.3"
我发现这还不够,我必须提供以下 build.rs 来手动告诉 linker link libc.a
来自 rs-libc
箱子也是。
pub fn main() {
println!("cargo:rustc-link-search=/home/me/dev/libdvdcss/.libs"); // Will be changed later
println!("cargo:rustc-link-lib=static=dvdcss");
println!("cargo:rustc-link-lib=static=c");
}
这修复了一些 strlen
等错误,但未找到 malloc
和 free
。我认为问题在于它们不是从 C 源文件编译的,而是在 alloc.rs 中编译的。我还看到这个源文件被编译成 target/x86_64-fortanix-unknown-sgx/debug/deps/librs_libc-04111db022dd517f.rlib
中的 Rust 库并包含符号:
rs_libc-04111db022dd517f.rs_libc.53f0fd72-cgu.5.rcgu.o:
0000000000000000 T calloc
0000000000000000 T free
0000000000000000 W __llvm_lvi_thunk_r11
0000000000000000 T malloc
0000000000000000 T realloc
0000000000000000 V __rustc_debug_gdb_scripts_section__
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTalloc_zeroed17ha722ea369ab2dac9E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTalloc17h561d825df0f2dfa8E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTdealloc17hbbda0b3d0a1f9d67E
U _ZN3std3sys3sgx5alloc81_$LT$impl$u20$core..alloc..global..GlobalAlloc$u20$for$u20$std..alloc..System$GTrealloc17hf76d62802e46847bE
U _ZN4core3ptr4read17hc3470c4a404ff082E
U _ZN4core3ptr5write17ha0bb4d6cbfed535eE
U _ZN4core5alloc6layout6Layout25from_size_align_unchecked17h074422ae6f6459f7E
U _ZN4core9panicking5panic17hde9db97a7382bd28E
不幸的是,这个文件似乎没有包含在最后的 linker 命令中。我认为这是因为在我的 Rust 应用程序中没有找到这个库的用法,因此它被优化了。
有没有办法包含它?
添加一个 extern crate rs_libc;
到你 crate 的根应该可以解决问题。必须将使用 extern crate
声明的依赖项提供给链接器是强制性的。在 rust 2018 及更高版本中,当且仅当您使用该 crate 的一个或多个符号时,编译器才会将适当的声明隐式添加到您的 crate(rust 2015 要求明确添加 extern crate
)。有关详细信息,请参阅 rust reference 中的部分。