Rust调用C动态库

Rust调用C动态库

环境

复制代码
rust: 1.83.0(2024-11-26)
bindgen: 0.71.1
cmake: 3.26.4

1. rust bindgen

bindgen 是一个能自动为 C(或 C++)库生成 Rust 绑定的辅助库和命令行工具。C++ (目前)的支持并不完整。

也就是说,bindgen 可以作为一个 crate,与 Cargo 的 build.rs 机制配合,根据 C/C++ 的头文件(.h, .hpp),在构建阶段,编译主体 Rust 代码之前,自动生成 Rust 绑定文件。

2. 安装bindgen

复制代码
cargo install bindgen-cli

3. 编写及编译C静态库

  • example.h

    #ifndef EXAMPLE_H
    #define EXAMPLE_H

    #ifdef _WIN32
    #define DLL_EXPORT __declspec(dllexport)
    #else
    #define DLL_EXPORT
    #endif

    DLL_EXPORT int add(int a, int b);

    #endif

  • example.c

    #include "example.h"

    int add(int a, int b)
    {
    return a + b;
    }

  • CMakeLists.txt

    cmake_minimum_required(VERSION 3.8.2)

    project(example)

    add_library(${PROJECT_NAME} SHARED example.c)

    add_library(${PROJECT_NAME} STATIC example.c)

生成c动态库

复制代码
$ cmake -B bin
$ cmake --build bin --config Release

4. bindgen生成rust绑定文件

bindgen需要用到libcang,设置环境变量LIBCLANG_PATH

复制代码
set LIBCLANG_PATH=D:/Program Files/LLVM/bin

生成rust绑定文件bindings.rs

复制代码
bindgen example.h -o bindings.rs

5. rust调用绑定文件

目录结构

复制代码
$ tree
.
+--- bin
|   +--- Release
|   |   +--- example.dll
|   |   +--- example.lib
+--- bindings.rs
+--- CMakeLists.txt
+--- example
|   +--- Cargo.toml
|   +--- example.lib
|   +--- src
|   |   +--- main.rs
|   +--- target
|   |   +--- release
|   |   |   +--- example.dll
|   |   |   +--- example.exe
+--- example.c
+--- example.h
  • 新建example项目

    cargo new example

  • 复制example.lib到example目录

    cmake -E copy bin/Release/example.lib example

  • 修改example/src/main.rs

    mod bindings {
    include!("../../bindings.rs");
    }

    use bindings::*;

    #[link(name = "example")]
    extern "C" {}

    fn main() {
    unsafe {
    let sum = add(1, 2);
    println!("1 + 2 = {}", sum);
    }
    }

编译

复制代码
cd example
cargo build -r

运行

拷贝example.dll到程序运行目录

复制代码
cmake -E copy bin/Release/example.dll example/target/release

执行

复制代码
$ cargo run -r
    Finished `release` profile [optimized] target(s) in 0.03s
     Running `target\release\example.exe`
1 + 2 = 3
相关推荐
程序员zgh3 小时前
Linux系统常用命令集合
linux·运维·服务器·c语言·开发语言·c++
Bigan(安)3 小时前
【奶茶Beta专项】【LVGL9.4源码分析】09-core-obj_class对象类系统
linux·c语言·mcu·arm·unix
受之以蒙4 小时前
Rust 与 dora-rs:吃透核心概念,手把手打造跨语言的机器人实时数据流应用
人工智能·笔记·rust
程序员zgh4 小时前
常用通信协议介绍(CAN、RS232、RS485、IIC、SPI、TCP/IP)
c语言·网络·c++
Bigan(安)5 小时前
【奶茶Beta专项】【LVGL9.4源码分析】08-theme主题管理
linux·c语言·mcu·arm·unix
了一梨5 小时前
外设与接口:按键输入 (libgpiod)
linux·c语言
昔时扬尘处5 小时前
【Files Content Replace】文件夹文件内容批量替换自动化测试脚本
c语言·python·pytest·adi
芯联智造6 小时前
【stm32简单外设篇】- 28BYJ-48 步进电机(配 ULN2003 驱动板)
c语言·stm32·单片机·嵌入式硬件
橘子真甜~7 小时前
C/C++ Linux网络编程13 - 传输层TCP协议详解(面向字节流和有连接)
linux·运维·服务器·c语言·网络·c++·tcp/ip
历程里程碑7 小时前
C++ 7vector:动态数组的终极指南
java·c语言·开发语言·数据结构·c++·算法