You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何限制bindgen仅为自定义C库生成绑定,排除标准库函数?

问题

我正尝试使用bindgen为某C库生成Rust绑定。已编写wrapper.h文件,仅引入该库的必要头文件(#include <mylib/mylib.h>),build.rs中的bindgen使用代码如下:

let bindings = bindgen::Builder::default()
    .clang_arg("-I/opt/mylib/usr/local/include") 
    .header("wrapper.h")
    .wrap_static_fns(true)
    .generate()
    .expect("Unable to generate bindings");

但该C库调用了strcpy等标准函数,导致bindgen同时生成了自定义库和标准库(如strcpy、malloc)的绑定。我希望仅生成自定义库mylib的函数与类型绑定,该如何实现?

我尝试的方案:在mylib的sys crate中生成绑定,通过lib.rs仅暴露所需函数:

mod bindings {
    include!(concat!(env!("OUT_DIR"), "/bindings.rs"));
}

pub use bindings::my_external_function;

此方法可实现所需暴露效果,但不确定是否为最优解。

解决方案

方法1:用bindgen白名单精准控制生成内容(推荐)

bindgen自带白名单配置API,能直接在生成阶段只保留目标库的符号,从根源上避免生成标准库或无关绑定。

修改build.rs如下:

let bindings = bindgen::Builder::default()
    .clang_arg("-I/opt/mylib/usr/local/include") 
    .header("wrapper.h")
    .wrap_static_fns(true)
    // 匹配mylib的函数,按实际命名前缀调整正则
    .allowlist_function("my_.*")
    // 匹配mylib的类型/结构体/枚举
    .allowlist_type("My.*")
    // 若有全局常量,可添加此规则
    .allowlist_var("MY_.*")
    .generate()
    .expect("Unable to generate bindings");

根据mylib的符号命名规则调整正则表达式即可,比如所有函数以mylib_开头就用"mylib_.*"。这种方式生成的bindings.rs会非常简洁,后续也不用手动筛选暴露的符号,是最优解。

方法2:手动筛选暴露符号(你的现有方案)

你现在用的在sys crate里通过pub use手动暴露所需符号的方法是可行的,也是Rust生态中sys crate的常规做法——先生成完整绑定,再向上层暴露必要API。但缺点是生成的bindings.rs会包含大量无关内容,略微增加编译时间和二进制体积;如果mylib API较多,手动维护pub use会比较麻烦。

内容的提问来源于stack exchange,提问作者Martin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.14 11:52:42