cbindgen: Auto-generate C/C++ Headers for Rust
cbindgen automatically generates C/C++ headers for your Rust code, saving you from writing tedious FFI boilerplate. Use it when exposing a Rust library to other languages. Its feature set is ad-hoc, so it may not support your specific edge case out of the box.
Why it exists
Rust's safety and performance make it ideal for core libraries, but you often need to call that code from other languages like C, C++, or Python. Manually writing the C header files (.h) to define the interface is tedious, repetitive, and a common source of bugs when the Rust code and the header drift out of sync.
The mental model
Think of cbindgen as a "translator" for your Rust library's public API. It reads your Rust source code, specifically the parts you've marked for export (like #[no_mangle] pub extern "C" fn), and writes the corresponding C or C++ header file that other languages can understand and use to call your functions.
How it works
cbindgen parses your Rust code, looking for functions, structs, and enums intended for a Foreign Function Interface (FFI). Based on this, it generates header file text that correctly represents Rust's types and function signatures in C/C++ syntax. It understands how Rust lays out data in memory and ensures the generated header reflects the stable C ABI. You can run it as a command-line tool or integrate it into your build process via a build.rs script.
When to use it
Use cbindgen whenever you are writing a Rust library that needs to be consumed by a non-Rust project. This is common for building high-performance components in Rust to be used in existing C/C++ codebases, or for creating native modules for languages like Python, Ruby, or Node.js. It ensures your C API remains consistent with your Rust implementation.
When not to use it
If your Rust project is a standalone application or a library only meant to be used by other Rust crates, you don't need cbindgen. It is specifically for creating C-compatible interfaces. For extremely simple APIs (one or two functions), manual creation is possible, but automation via cbindgen is better for long-term maintenance.
One canonical example
Mozilla, the original author, uses cbindgen to integrate Rust components into Firefox's large C++ codebase. A Rust component for parsing URLs or rendering part of a web page can be written, and cbindgen will create the .h file that the C++ code includes to call the new, safe Rust functions.
Interview question
What is the primary purpose of using cbindgen in a Rust development workflow?
- a.To compile Rust code into a more optimized binary format for deployment on embedded systems.
- b.To generate C/C++ header files that allow non-Rust languages to call functions from a Rust library.Correct
- c.To automatically translate existing C/C++ source code into equivalent Rust modules.
- d.To enforce strict memory safety guarantees when Rust code interacts with other Rust components.
Why? this is the answer
cbindgen's core function is to generate C/C++ header files from Rust code, enabling other languages to call Rust functions via a stable C ABI. It does not translate C/C++ to Rust, nor does it primarily enforce Rust's internal safety or optimize compilation.
Just read this? Test yourself on what you have been reading.
Read the original → github.com
Put your scrolling time to good use
Learn one idea, try a quiz and save useful cards for revision. Tezvyn makes it easy to learn and stay current in your tech field, a few minutes at a time.
The iPhone app is on the way
We are building it. Until it lands, nothing here is held back from you: every interview card, your saved cards, streaks and the job board all work in Safari, plus hundreds of free practice quizzes of thirty questions each. Sign in and it all carries over to the app the day it arrives.
Want it as an icon? Tap Share at the bottom of Safari, then Add to Home Screen. It opens full screen and the cards you have read stay available offline.
We are hiring for this. Open roles that interview on rust — each one lists the topics its interview covers.
See open roles