|
| 1 | +.. _rust_bindings: |
| 2 | + |
| 3 | +Bindings to Zephyr for Rust |
| 4 | +########################### |
| 5 | + |
| 6 | +Zephyr is written in C, and it's primary API is also made available to C. It is written as a |
| 7 | +mixture of types, function prototypes, inline functions, and macros. |
| 8 | + |
| 9 | +Although Rust interfaces fairly easily with C at an ABI level, the compiler does not have any |
| 10 | +support for generating the code necessary for these bindings. In order to call C code, the types |
| 11 | +must be reproduced in Rust, function prototypes written in Rust, and often wrappers made for inline |
| 12 | +functions and macros (or this functionality replicated in Rust). |
| 13 | + |
| 14 | +This is a tedious, and error-prone process, and the end result would quickly get out of date with |
| 15 | +the development of Zephyr. |
| 16 | + |
| 17 | +The `bindgen`_ project seeks to address much of this issue by automatically generating bindings to C |
| 18 | +code for Rust. It makes use of ``libclang`` to parse and interpret a given set of headers, and |
| 19 | +generate the Rust code needed to call this code. |
| 20 | + |
| 21 | +.. _bindgen: https://github.com/rust-lang/rust-bindgen |
| 22 | + |
| 23 | +Because the Zephyr headers use numerous conditional compilation macros, the bindings needed will be |
| 24 | +very specialized to a given board, and even a given configuration. To do this, the file |
| 25 | +:file:`lib/rust/zephyr-sys/build.rs`, which ``cargo`` knows to run at build time will |
| 26 | +generate the bindings for the particular build of Zephyr being used by the current Rust application. |
| 27 | + |
| 28 | +These bindings will be made available in the ``zephyr-sys`` crate, as well as under ``zephyr::raw``. |
| 29 | + |
| 30 | +Using the Bindings |
| 31 | +****************** |
| 32 | + |
| 33 | +In general, using direct bindings to C function from Rust is a bit more difficult than calling them |
| 34 | +from C. Although all of these calls are considered "unsafe", and must be placed in an ``unsafe`` |
| 35 | +block, the rust language has stricter constraints on what is allowed, even by unsafe code. Although |
| 36 | +the intent of the Rust on Zephyr project is to allow full use of Zephyr, without needing to resort |
| 37 | +to unsafe code, it is understandable that this implementation will be incomplete, and some |
| 38 | +applications may require resorting to, what is sometimes referred to as "The Dark Arts". The |
| 39 | +`Rustinomicon`_ is a good resource for those wishing to delve into this area. |
| 40 | + |
| 41 | +.. _Rustinomicon: https://doc.rust-lang.org/nomicon/ |
| 42 | + |
| 43 | +In addition, the code in :file:`zephyr/lib/rust/zephyr` that provides the higher level abstractions |
| 44 | +will primarily be implemented using these auto-generated bindings. |
| 45 | + |
| 46 | +Generation |
| 47 | +********** |
| 48 | + |
| 49 | +The generation of the bindings is controlled by the ``build.rs`` program. This attempts to capture |
| 50 | +the symbols that are needed for successful bindings, but there may be things missing. Additional |
| 51 | +bindings can be included by adding their patterns to the list of patterns in ``build.rs``, and |
| 52 | +possibly adding additional ``#include`` directives to :file:`lib/rust/zephyr-sys/wrapper.h`. |
0 commit comments