创建一个 CMake 项目, 配置 CMakeLists.txt 如下:
cmake_minimum_required(VERSION 3.25.0)
project(test VERSION 0.1.0 LANGUAGES C CXX)
# 自动导出函数
set(CMAKE_WINDOWS_EXPORT_ALL_SYMBOLS on)
# 创建动态链接库 DLL
add_library(test SHARED test.cpp) 代码文件 test.cpp 如下:
extern "C" double plus2(double x) { return x + 2; } 上述代码中定义了一个函数 plus2. 注意函数签名前的 extern "C", 这个表示采用 C 语言规范导出符号, 不加的话导出的函数符号就是乱七八糟的样子.
编译之后会生成一个 test.dll 的动态链接库文件.
创建一个 Rust 测试项目:
cargo new loaddll 在项目配置文件 Cargo.toml 中添加 libloading 依赖:
[dependencies]
libloading="0.8" Rust 源代码 main.rs 文件编辑如下:
fn call_dll() -> Result<f64, Box<dyn std::error::Error>> {
unsafe {
let lib = libloading::Library::new("test.dll")?;
let plus2: libloading::Symbol<unsafe extern "C" fn(f64) -> f64> = lib.get(b"plus2")?;
Ok(plus2(3.0))
}
}
fn main() {
println!("plus2(3) = {}", call_dll().unwrap());
}
函数 call_dll 就是调用动态链接库的函数, lib 是要调用的动态链接库, plus2 是动态链接库中导出的函数.
将 test.dll 复制到 target/Debug 文件夹中, 然后编译运行 rust 项目会输出如下结果:
......
plus2(3) = 5 这说明 Rust 成功调用了动态链接库中导出的函数 plus2.
Rust 中的 libloading 库是跨平台的, 类似的代码也可以在 Linux 或者 Mac 操作系统中调用对应平台的动态链接库 (.so/.dylib), 非常方便.