Lines Matching +full:rust +full:- +full:src
1 CXX — safe FFI between Rust and C++
4 [<img alt="github" src="https://img.shields.io/badge/github-dtolnay/cxx-8da0cb?style=for-the-badge&…
5 [<img alt="crates.io" src="https://img.shields.io/crates/v/cxx.svg?style=for-the-badge&color=fc8d62…
6 [<img alt="docs.rs" src="https://img.shields.io/badge/docs.rs-cxx-66c2a5?style=for-the-badge&labelC…
7 [<img alt="build status" src="https://img.shields.io/github/workflow/status/dtolnay/cxx/CI/master?s…
9 This library provides a **safe** mechanism for calling C++ code from Rust and
10 Rust code from C++, not subject to the many ways that things can go wrong when
11 using bindgen or cbindgen to generate unsafe C-style bindings.
14 project, you would be on the hook for auditing all the unsafe Rust code and
16 just the C++ side would be sufficient to catch all problems, i.e. the Rust side
23 [build-dependencies]
24 cxx-build = "1.0"
42 embedded together in one Rust module (the next section shows an example). From
44 against the types and function signatures to uphold both Rust's and C++'s
50 correctness. On the Rust side this code generator is simply an attribute
60 such as Rust's `String` or C++'s `std::string`, Rust's `Box` or C++'s
61 `std::unique_ptr`, Rust's `Vec` or C++'s `std::vector`, etc in any combination.
62 CXX guarantees an ABI-compatible signature that both sides understand, based on
65 from Rust, its `len()` method becomes a call of the `size()` member function
66 defined by C++; when manipulating a Rust string from C++, its `size()` member
67 function calls Rust's `len()`.
73 In this example we are writing a Rust application that wishes to take advantage
74 of an existing C++ client for a large-file blobstore service. The blobstore
82 ```rust
91 extern "Rust" {
93 // only Rust can see the fields.
96 // Functions implemented in Rust.
97 fn next_chunk(buf: &mut MultiBuf) -> &[u8];
111 fn new_blobstore_client() -> UniquePtr<BlobstoreClient>;
112 fn put(&self, parts: &mut MultiBuf) -> u64;
114 fn metadata(&self, blobid: u64) -> BlobMetadata;
119 Now we simply provide Rust definitions of all the things in the `extern "Rust"`
125 - [demo/src/main.rs](demo/src/main.rs)
126 - [demo/build.rs](demo/build.rs)
127 - [demo/include/blobstore.h](demo/include/blobstore.h)
128 - [demo/src/blobstore.cc](demo/src/blobstore.cc)
134 # run Rust code generator and print to stdout
135 # (requires https://github.com/dtolnay/cargo-expand)
136 $ cargo expand --manifest-path demo/Cargo.toml
139 $ cargo run --manifest-path gen/cmd/Cargo.toml -- demo/src/main.rs
149 - **Shared structs** — their fields are made visible to both languages.
152 - **Opaque types** — their fields are secret from the other language.
154 such as a reference `&`, a Rust `Box`, or a `UniquePtr`. Can be a type alias
155 for an arbitrarily complicated generic language-specific type depending on
158 - **Functions** — implemented in either language, callable from the other
161 Within the `extern "Rust"` part of the CXX bridge we list the types and
162 functions for which Rust is the source of truth. These all implicitly refer to
165 `use super::next_chunk` except re-exported to C++. The parent module will either
171 it's possible that this section could be generated bindgen-style from the
175 Your function implementations themselves, whether in C++ or Rust, *do not* need
184 are typed out once where the implementation is defined (in C++ or Rust) and
185 again inside the cxx::bridge module, though compile-time assertions guarantee
190 [bindgen]: https://github.com/rust-lang/rust-bindgen
197 bindgen-like tool on top of CXX which consumes a C++ header and/or Rust module
204 with an idiomatic C++ API we would end up manually wrapping that API in C-style
205 raw pointer functions, applying bindgen to get unsafe raw pointer Rust
206 functions, and replicating the API again to expose those idiomatically in Rust.
210 than `extern "C"` C-style signatures as the shared understanding, common FFI use
222 ## Cargo-based setup
237 [build-dependencies]
238 cxx-build = "1.0"
241 ```rust
245 cxx_build::bridge("src/main.rs") // returns a cc::Build
246 .file("src/demo.cc")
247 .flag_if_supported("-std=c++11")
248 .compile("cxxbridge-demo");
250 println!("cargo:rerun-if-changed=src/main.rs");
251 println!("cargo:rerun-if-changed=src/demo.cc");
252 println!("cargo:rerun-if-changed=include/demo.h");
258 ## Non-Cargo setup
260 For use in non-Cargo builds like Bazel or Buck, CXX provides an alternate way of
262 packaged as the `cxxbridge-cmd` crate on crates.io or can be built from the
266 $ cargo install cxxbridge-cmd
268 $ cxxbridge src/main.rs --header > path/to/mybridge.h
269 $ cxxbridge src/main.rs > path/to/mybridge.cc
286 - By design, our paired code generators work together to control both sides of
287 the FFI boundary. Ordinarily in Rust writing your own `extern "C"` blocks is
288 unsafe because the Rust compiler has no way to know whether the signatures
293 - Our static analysis detects and prevents passing types by value that shouldn't
294 be passed by value from C++ to Rust, for example because they may contain
295 internal pointers that would be screwed up by Rust's move behavior.
297 - To many people's surprise, it is possible to have a struct in Rust and a
300 bindgen bug that leads to segfaults in absolutely correct-looking code
301 ([rust-lang/rust-bindgen#778]). CXX knows about this and can insert the
302 necessary zero-cost workaround transparently where needed, so go ahead and
306 - Template instantiations: for example in order to expose a UniquePtr\<T\> type
307 in Rust backed by a real C++ unique\_ptr, we have a way of using a Rust trait
311 [rust-lang/rust-bindgen#778]: https://github.com/rust-lang/rust-bindgen/issues/778
322 <tr><th>name in Rust</th><th>name in C++</th><th>restrictions</th></tr>
323 <tr><td>String</td><td>rust::String</td><td></td></tr>
324 <tr><td>&str</td><td>rust::Str</td><td></td></tr>
325 <tr><td>&[T]</td><td>rust::Slice<const T></td><td><sup><i>cannot hold opaque C++ type</i>…
326 <tr><td>&mut [T]</td><td>rust::Slice<T></td><td><sup><i>cannot hold opaque C++ type</i></…
328 <tr><td>Box<T></td><td>rust::Box<T></td><td><sup><i>cannot hold opaque C++ type</i></su…
329 …;</a></td><td>std::unique_ptr<T></td><td><sup><i>cannot hold opaque Rust type</i></sup></td>…
330 …;</a></td><td>std::shared_ptr<T></td><td><sup><i>cannot hold opaque Rust type</i></sup></td>…
332 <tr><td>Vec<T></td><td>rust::Vec<T></td><td><sup><i>cannot hold opaque C++ type</i></su…
333 …or<T></td><td><sup><i>cannot be passed by value, cannot hold opaque Rust type</i></sup></td>…
335 <tr><td>fn(T, U) -> V</td><td>rust::Fn<V(T, U)></td><td><sup><i>only passing from Rust to …
339 The C++ API of the `rust` namespace is defined by the *include/cxx.h* file in
345 matter of designing a nice API for each in its non-native language.
348 <tr><th>name in Rust</th><th>name in C++</th></tr>
369 Finally, I know more about Rust library design than C++ library design so I
378 Licensed under either of <a href="LICENSE-APACHE">Apache License, Version
379 2.0</a> or <a href="LICENSE-MIT">MIT license</a> at your option.
386 for inclusion in this project by you, as defined in the Apache-2.0 license,