Macro ocaml_interop::ocaml_export
source · macro_rules! ocaml_export { {} => { ... }; { fn $name:ident$(|$byte_name:ident)?( $cr:ident, $($args:tt)*) -> f64 $body:block $($t:tt)* } => { ... }; { fn $name:ident$(|$byte_name:ident)?( $cr:ident, $($args:tt)*) $(-> $rtyp:ty)? $body:block $($t:tt)* } => { ... }; { fn $name:ident$(|$byte_name:ident)?( $($invalid_args:tt)* ) $(-> $rtyp:ty)? $body:block $($t:tt)* } => { ... }; }
Expand description
Defines Rust functions callable from OCaml.
The first argument in these functions declarations is a name to bind a &mut
OCamlRuntime
.
Arguments and return values must be of type OCamlRef
<T>
, or f64
in the case of unboxed floats.
The return type defaults to OCaml
<()>
when omitted.
To generate a bytecode-callable version of the function (needed when the function has 6 or more arguments),
add a second name to the function separated by |
(see last example).
§Examples
ocaml_export! {
fn rust_twice(cr, num: OCamlRef<OCamlInt>) -> OCaml<OCamlInt> {
let num: i64 = num.to_rust(cr);
unsafe { OCaml::of_i64_unchecked(num * 2) }
}
fn rust_twice_boxed_i32(cr, num: OCamlRef<OCamlInt32>) -> OCaml<OCamlInt32> {
let num: i32 = num.to_rust(cr);
let result = num * 2;
result.to_ocaml(cr)
}
fn rust_add_unboxed_floats_noalloc(_cr, num: f64, num2: f64) -> f64 {
num * num2
}
fn rust_twice_boxed_float(cr, num: OCamlRef<OCamlFloat>) -> OCaml<OCamlFloat> {
let num: f64 = num.to_rust(cr);
let result = num * 2.0;
result.to_ocaml(cr)
}
fn rust_increment_ints_list(cr, ints: OCamlRef<OCamlList<OCamlInt>>) -> OCaml<OCamlList<OCamlInt>> {
let mut vec: Vec<i64> = ints.to_rust(cr);
for i in 0..vec.len() {
vec[i] += 1;
}
vec.to_ocaml(cr)
}
fn rust_make_tuple(cr, fst: OCamlRef<String>, snd: OCamlRef<OCamlInt>) -> OCaml<(String, OCamlInt)> {
let fst: String = fst.to_rust(cr);
let snd: i64 = snd.to_rust(cr);
let tuple = (fst, snd);
tuple.to_ocaml(cr)
}
fn rust_rust_add_7ints|rust_rust_add_7ints_byte(
cr,
int1: OCamlRef<OCamlInt>,
int2: OCamlRef<OCamlInt>,
int3: OCamlRef<OCamlInt>,
int4: OCamlRef<OCamlInt>,
int5: OCamlRef<OCamlInt>,
int6: OCamlRef<OCamlInt>,
int7: OCamlRef<OCamlInt>,
) -> OCaml<OCamlInt> {
let int1: i64 = int1.to_rust(cr);
let int2: i64 = int2.to_rust(cr);
let int3: i64 = int3.to_rust(cr);
let int4: i64 = int4.to_rust(cr);
let int5: i64 = int5.to_rust(cr);
let int6: i64 = int6.to_rust(cr);
let int7: i64 = int7.to_rust(cr);
unsafe { OCaml::of_i64_unchecked(int1 + int2 + int3 + int4 + int5 + int6 + int7) }
}
}