Convert Figma logo to code with AI

mozilla logocbindgen

A project for generating C bindings from Rust code

2,342
302
2,342
207

Top Related Projects

Automatically generates Rust FFI bindings to C (and some C++) libraries.

5,795

Safe interop between Rust and C++

A project for generating C bindings from Rust code

1,234

Use C++ libraries from Rust

Quick Overview

cbindgen is a tool that generates C bindings from Rust code. It is used to create C-compatible header files and source files from Rust code, allowing Rust libraries to be used in C and C++ projects.

Pros

  • Automated Bindings Generation: cbindgen simplifies the process of creating C bindings for Rust code, reducing the manual effort required.
  • Cross-Language Interoperability: It enables Rust libraries to be used in C and C++ projects, improving the integration between these languages.
  • Customizable Output: cbindgen provides various configuration options to customize the generated bindings, such as controlling the naming conventions and including/excluding specific types.
  • Rust-Friendly: The tool is developed and maintained by the Mozilla team, ensuring it aligns with Rust's best practices and evolves alongside the language.

Cons

  • Limited Rust Feature Support: While cbindgen supports a wide range of Rust features, some more advanced or niche features may not be fully supported or may require additional configuration.
  • Potential for Complexity: Generating bindings for large or complex Rust codebases can result in complex C header files, which may require additional manual adjustments or understanding.
  • Dependency Management: Using cbindgen-generated bindings in a C/C++ project may introduce additional dependency management challenges, as the Rust library and its dependencies need to be properly integrated.
  • Learning Curve: Developers new to the Rust ecosystem may need to invest time in understanding the tool's usage and configuration options to effectively integrate it into their projects.

Code Examples

Here are a few examples of how to use cbindgen to generate C bindings from Rust code:

  1. Basic Usage:
// lib.rs
pub fn add(a: i32, b: i32) -> i32 {
    a + b
}
cbindgen --config cbindgen.toml --crate lib --output include/lib.h

This command generates a C header file lib.h containing the bindings for the add function.

  1. Customizing Output:
# cbindgen.toml
language = "C"
include_guard = "LIB_H"
cbindgen --config cbindgen.toml --crate lib --output include/lib.h

The configuration file cbindgen.toml specifies the output language as C and sets an include guard for the generated header file.

  1. Handling Enums:
// lib.rs
pub enum Color {
    Red,
    Green,
    Blue,
}

pub fn get_color_name(color: Color) -> &'static str {
    match color {
        Color::Red => "Red",
        Color::Green => "Green",
        Color::Blue => "Blue",
    }
}
cbindgen --config cbindgen.toml --crate lib --output include/lib.h

The generated header file will include the Color enum and the get_color_name function that operates on it.

Getting Started

To use cbindgen, follow these steps:

  1. Install cbindgen using Cargo:
cargo install cbindgen
  1. Create a Rust library project and add the necessary code:
cargo new --lib my-lib
  1. Configure cbindgen by creating a cbindgen.toml file in the project's root directory. Customize the settings as needed.

  2. Generate the C bindings:

cbindgen --config cbindgen.toml --crate my-lib --output include/my-lib.h
  1. Include the generated header file in your C/C++ project and link against the Rust library.

Refer to the cbindgen documentation for more detailed information on configuration options and advanced usage.

Competitor Comparisons

Automatically generates Rust FFI bindings to C (and some C++) libraries.

Pros of rust-bindgen

  • Supports generating bindings for multiple languages (C, C++, Rust)
  • More mature project with a larger community and more frequent updates
  • Offers more advanced features like custom derives and blacklisting

Cons of rust-bindgen

  • Can be more complex to set up and configure
  • May generate less idiomatic Rust code in some cases
  • Slower compilation times due to its more comprehensive approach

Code Comparison

rust-bindgen:

let bindings = bindgen::Builder::default()
    .header("wrapper.h")
    .parse_callbacks(Box::new(bindgen::CargoCallbacks))
    .generate()
    .expect("Unable to generate bindings");

cbindgen:

cbindgen::Builder::new()
    .with_crate(crate_dir)
    .generate()
    .expect("Unable to generate bindings")
    .write_to_file("bindings.h");

Both tools aim to generate bindings between Rust and C/C++, but they approach the task differently. rust-bindgen focuses on generating Rust bindings from C/C++ headers, while cbindgen generates C/C++ headers from Rust code. rust-bindgen offers more flexibility and features, making it suitable for complex projects with diverse requirements. However, cbindgen excels in simplicity and generating idiomatic C/C++ headers from Rust code, making it a good choice for Rust-centric projects that need to expose APIs to C/C++.

5,795

Safe interop between Rust and C++

Pros of cxx

  • Provides a more seamless integration between Rust and C++ with bidirectional FFI
  • Offers automatic generation of safe bindings for both Rust and C++
  • Includes runtime support for sharing common data types between languages

Cons of cxx

  • Requires more setup and configuration compared to cbindgen
  • Limited to C++11 and newer, potentially excluding older codebases
  • May have a steeper learning curve for developers new to FFI

Code Comparison

cxx:

#[cxx::bridge]
mod ffi {
    extern "Rust" {
        fn process_data(input: &str) -> String;
    }
    extern "C++" {
        include!("example.h");
        fn call_cpp_function(arg: i32) -> i32;
    }
}

cbindgen:

#[no_mangle]
pub extern "C" fn process_data(input: *const c_char) -> *mut c_char {
    // Implementation
}

Summary

cxx offers a more comprehensive and bidirectional FFI solution, while cbindgen focuses on generating C bindings for Rust code. cxx provides better type safety and seamless integration but may be more complex to set up. cbindgen is simpler and more flexible but requires manual implementation of FFI functions on the C++ side.

A project for generating C bindings from Rust code

Pros of cbindgen

  • Well-established and actively maintained project
  • Extensive documentation and community support
  • Widely used in Mozilla projects and other large-scale applications

Cons of cbindgen

  • May have more features than necessary for smaller projects
  • Learning curve can be steeper due to its comprehensive nature
  • Potential performance overhead for very simple bindings

Code Comparison

This comparison is not applicable as both repositories refer to the same project. cbindgen is a single repository, and there isn't a separate mozilla/cbindgen> repository to compare it against.

Additional Notes

cbindgen is a tool for generating C bindings for Rust code. It's primarily used by Mozilla in projects like Firefox but has found adoption in various other projects requiring Rust-to-C interoperability. The tool automatically generates C/C++ header files from Rust source code, making it easier to use Rust libraries in C/C++ projects.

Key features include:

  • Support for complex Rust types
  • Customizable output through a configuration file
  • Integration with Cargo build scripts

While cbindgen is powerful and feature-rich, smaller projects might find it overly complex for their needs. However, its widespread use and active development make it a reliable choice for many scenarios requiring Rust-to-C bindings.

1,234

Use C++ libraries from Rust

Pros of ritual

  • Supports generating Rust bindings for C++ libraries, not just C
  • Provides a more comprehensive binding generation solution, including build system integration
  • Offers more customization options for generated bindings

Cons of ritual

  • More complex setup and configuration required
  • Less mature and less widely used compared to cbindgen
  • May have more overhead for simpler binding generation tasks

Code comparison

cbindgen example:

#[no_mangle]
pub extern "C" fn add(a: i32, b: i32) -> i32 {
    a + b
}

ritual example:

#[cxx::bridge]
mod ffi {
    extern "Rust" {
        fn add(a: i32, b: i32) -> i32;
    }
}

fn add(a: i32, b: i32) -> i32 {
    a + b
}

Summary

ritual offers more comprehensive C++ binding generation capabilities and customization options, but comes with increased complexity. cbindgen is simpler and more widely used for C bindings, making it a better choice for straightforward projects. The code examples demonstrate the different approaches: cbindgen uses a simple #[no_mangle] attribute, while ritual employs a more structured cxx::bridge module for defining the FFI boundary.

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

cbindgenBuild Status Latest Version Api Rustdoc Rust

Read the full user docs here!

cbindgen creates C/C++11 headers for Rust libraries which expose a public C API.

While you could do this by hand, it's not a particularly good use of your time. It's also much more likely to be error-prone than machine-generated headers that are based on your actual Rust code. The cbindgen developers have also worked closely with the developers of Rust to ensure that the headers we generate reflect actual guarantees about Rust's type layout and ABI.

C++ headers are nice because we can use operator overloads, constructors, enum classes, and templates to make the API more ergonomic and Rust-like. C headers are nice because you can be more confident that whoever you're interoperating with can handle them. With cbindgen you don't need to choose! You can just tell it to emit both from the same Rust library.

There are two ways to use cbindgen: as a standalone program, or as a library (presumably in your build.rs). There isn't really much practical difference, because cbindgen is a simple rust library with no interesting dependencies.

Using it as a program means people building your software will need it installed. Using it in your library means people may have to build cbindgen more frequently (e.g. every time they update their rust compiler).

It's worth noting that the development of cbindgen has been largely adhoc, as features have been added to support the usecases of the maintainers. This means cbindgen may randomly fail to support some particular situation simply because no one has put in the effort to handle it yet. Please file an issue if you run into such a situation. Although since we all have other jobs, you might need to do the implementation work too :)

Quick Start

To install cbindgen, you just need to run

cargo install --force cbindgen

(--force just makes it update to the latest cbindgen if it's already installed)

Or with Homebrew, run

brew install cbindgen

To use cbindgen you need two things:

  • A configuration (cbindgen.toml, which can be empty to start)
  • A Rust crate with a public C API

Then all you need to do is run it:

cbindgen --config cbindgen.toml --crate my_rust_library --output my_header.h

This produces a header file for C++. For C, add the --lang c switch.

See cbindgen --help for more options.

Read the full user docs here!

Get a template cbindgen.toml here.

Examples

We don't currently have a nice tailored example application, but the tests contain plenty of interesting examples of our features.

You may also find it interesting to browse the projects that are using cbindgen in production:

If you're using cbindgen and would like to be added to this list, please open a pull request!

Releases

cbindgen doesn't have a fixed release calendar, please file an issue requesting a release if there's something fixed in trunk that you need released. Ping @emilio for increased effect.