首页 > 其他分享 >cbindgen rust 代码生成c binding 的工具

cbindgen rust 代码生成c binding 的工具

时间:2023-12-13 17:14:02浏览次数:28  
标签:代码生成 rs cbindgen app binding build main rust

rust 与c 以及c 与rust 的互调用还是比较常见的需求,很多时候自己写可能比较费事,但是使用一些工具就比较方便了
cbindgen 是一个对于rust 代码生成c binding 的工具

参考使用

基于cbindgen 将rust 的代码生成对应的c 头文件,之后基于cmake 构建项目

  • 项目结构
 
├── CMakeLists.txt
├── Cargo.lock
├── Cargo.toml
├── README.md
├── build.rs
├── main.c
└── src
    ├── app.rs
    └── lib.rs
  • 代码简单说明
    app.rs 以及lib.rs 主要是关于rust 的,build.rs 是使用cbindgen 生成bindings,main.c 是使用生成的库文件,CMakeLists.txt 是基于
    cmake 的c 应用构建
    app.rs
 
#[repr(C)]
pub struct  Foo {
    a:i32,
    b:i32,
    c: *mut std::os::raw::c_char
}
 
#[no_mangle]
pub extern  "C" fn  addv2(a:i32,b:i32) -> i32 {
    a + b
}
 
#[no_mangle]
pub extern  "C" fn init_app(foo: Foo) -> bool {
    if foo.c.is_null() {
        return false
    } else{
        return true
    }
}

lib.rs

pub mod app;

build.rs 标准的cargo 构建扩展

use cbindgen;
 
fn main() {
    cbindgen::Builder::new()
    .with_language(cbindgen::Language::C)
      .with_crate(".")
      .generate()
      .expect("Unable to generate bindings")
      .write_to_file("bindings.h");
}

main.c

#include <stdio.h>
#include "bindings.h"
int main(){
   int result =  addv2(13,33);
   printf("Result: %d\n", result);
   Foo foo = {
      .a = 1,
      .b = 2,
   };
   bool init_result = init_app(foo);
   printf("init_result: %d\n", init_result);
}

CMakeLists.txt

cmake_minimum_required(VERSION 3.15)
project(mydemoapp)
add_executable(myapp main.c)
include_directories(${CMAKE_SOURCE_DIR})
target_link_libraries(myapp PRIVATE ${CMAKE_SOURCE_DIR}/target/release/libmylib.dylib)

构建

  • 构建rust
cargo build --release
  • 构建c应用
mkdir -p build
cd build
cmake ..
make 
  • 效果

运行

说明

cbindgen 是一个很不错的工具,可以方便c 与rust 的调用,同时对于生成的文件也方便其他语言进行互调用,比如python 的cffi 也可以方便调用

参考资料

https://github.com/mozilla/cbindgen
https://github.com/rongfengliang/cbindgen_cmake_learning

标签:代码生成,rs,cbindgen,app,binding,build,main,rust
From: https://www.cnblogs.com/rongfengliang/p/17899464.html

相关文章

  • Amazon CodeWhisperer 免费的 AI 代码生成助手!最新体验反馈~
    文章作者:段小草自这一波生成式AI浪潮以来,大家尝鲜之余最关心的问题还是如何提高生产力。我们在测试大语言模型能力的时候,往往会将代码能力作为一项重要的评价指标,也说明程序员还是希望能在AI的加持下更快捷安全地编写代码。亚马逊云科技开发者社区为开发者们提供全球的开发......
  • wpf data binding
     publicpartialclassWindow2:Window{publicPersonvmPerosn=newPerson();publicWindow2(){InitializeComponent();vmPerosn.Name="JackZhao";vmPerosn.Phone=&qu......
  • Go 模板:用代码生成代码
    用代码生成代码。不用Go写代码,就不知道Java程序员被“惯”得有多厉害。Java奉行“拿来主义”,什么东西都有现成的库。而Go就没有那么丰富的库了。本文用生成器模式作为例子,来演示如何用代码生成代码。生成器模式熟悉Java开发的同学都知道,lombok有一个著名的注解......
  • WPF 绑定binding都有哪些事件
    在WPF中,源属性(SourceProperty)指的是提供数据的属性,通常是数据模型或者其他控件的属性,而目标属性(TargetProperty)则是数据绑定的目标,通常是绑定到控件的属性,例如TextBlock的Text属性。数据绑定将源属性的值自动更新到目标属性中。 主要包含以下几个事件:1. UpdateSourceTrigg......
  • mybatis-plus 新版代码生成器模板
    publicclassCodeGenerator{publicstaticvoidmain(String[]args){//数据源配置FastAutoGenerator.create("jdbc:mysql://127.0.0.1:3306/xdclass?useUnicode=true&characterEncoding=utf-8&useSSL=false","root",&qu......
  • Binding failed for port xxxxxx
    nova-compute.log2040-13-3220:02:33.4517ERRORnova.compute.manager[Nonereq-b844f0bb-e907-4c17-807f-3f418be83679207fdd48eb414c78bdbc9b6a55362dc59252305d9c2f46bc882c15d412d25911--defaultdefault]Instancefailednetworksetupafter1attempt(s):n......
  • Tekton Trigger TriggerBindings 基础
    TriggerBindings概述TriggerBinding的功能主要用于将Event中特定属性的值传递给TriggerTemplate上的参数从而完成其resourcetemplates中模板资源的实例化。注意:Trigger使用参数名称将TriggerBinding参数与TriggerTemplate参数匹配。为了传递信息,绑定中使用的参数名称必须与......
  • 如何开发代码生成器平台?分享下思路
    大家好,我是鱼皮,我的新项目《鱼籽-定制化代码生成项目》系列教程正式开始!本次项目依然是从0到1带大家开发,会遵循企业项目开发的标准流程:需求分析=>技术选型=>项目设计=>项目初始化=>Demo编写=>前后端开发实现=>测试验证=>部署上线,带大家一步步完成整个项目。......
  • 从HumanEval到CoderEval: 你的代码生成模型真的work吗?
    本文分享自华为云社区《从HumanEval到CoderEval:你的代码生成模型真的work吗?》,作者:华为云PaaS服务小智。本文主要介绍了一个名为CoderEval的代码生成大模型评估基准,并对三个代码生成模型(CodeGen、PanGu-Coder和ChatGPT)在该基准上的表现进行了评估和比较。研究人员从真实的开源......
  • 新建模块&新建用户表&修改代码生成器文件&新建菜单
    1.新建模块打开IDEA在项目结构中新建rome-hotel的一个springboot项目,什么依赖都不需要 在pom.xml文件中修改坐标,引用父坐标 在父级pom文件中将模块加入 在rome-admin中的pom文件中加入admin-hotel,这样就能带动这个模块启动 将包名修改成和rome-admin一样 再创建其......