Macro cpp::cpp [−][src]
macro_rules! cpp { ({$($body:tt)*}) => { ... }; ([$($captures:tt)*] $($rest:tt)*) => { ... }; (unsafe $($tail:tt)*) => { ... }; }
This macro is used to embed arbitrary C++ code.
There are two variants of the cpp!
macro. The first variant is used for
raw text inclusion. Text is included into the generated C++
file in the
order which they were defined, inlining module declarations.
cpp! {{ #include <stdint.h> #include <stdio.h> }}
The second variant is used to embed C++ code within rust code. A list of variable names which should be captured are taken as the first argument, with their corresponding C++ type. The body is compiled as a C++ function.
This variant of the macro may only be invoked in expression context, and
requires an unsafe
block, as it is performing FFI.
let y: i32 = 10; let mut z: i32 = 20; let x: i32 = unsafe { cpp!([y as "int32_t", mut z as "int32_t"] -> i32 as "int32_t" { z++; return y + z; })};
You can also put the unsafe keyword as the first keyword of the cpp! macro, which has the same effect as putting the whole macro in an unsafe block:
let x: i32 = cpp!(unsafe [y as "int32_t", mut z as "int32_t"] -> i32 as "int32_t" { z++; return y + z; });
rust! pseudo-macro
The cpp! macro can contain, in the C++ code, a rust! sub-macro, which allows to include rust code in C++ code. This is useful to implement callback or override virtual functions. Example:
trait MyTrait { fn compute_value(&self, x : i32) -> i32; } cpp!{{ struct TraitPtr { void *a,*b; }; class MyClassImpl : public MyClass { public: TraitPtr m_trait; int computeValue(int x) const override { return rust!(MCI_computeValue [m_trait : &MyTrait as "TraitPtr", x : i32 as "int"] -> i32 as "int" { m_trait.compute_value(x) }); } } }}
The syntax for the rust! macro is:
rust!($uniq_ident:ident [$($arg_name:ident : $arg_rust_type:ty as $arg_c_type:tt),*] $(-> $ret_rust_type:ty as $rust_c_type:tt)* {$($body:tt)*})
uniq_ident is an unique identifier which will be used to name the extern function