aboutsummaryrefslogtreecommitdiff
path: root/rust/qemu-api/src/lib.rs
AgeCommit message (Collapse)AuthorFilesLines
2025-02-10rust: restrict missing_const_for_fn to qemu_api cratePaolo Bonzini1-0/+1
missing_const_for_fn is not necessarily useful or good. For example in a private API you can always add const later, and in a public API it can be unnecessarily restrictive to annotate everything with const (blocking further improvements to the API). Nevertheless, QEMU turns it on because qemu_api uses const quite aggressively and therefore it can be handy to have as much as possible annotated with const. Outside qemu_api though, not so much: devices are self contained consumers and if there is nothing that could use their functions in const contexts that were not anticipated. Since missing_const_for_fn can be a bit noisy and trigger on trivial functions that no one would ever call in const context, do not turn it on everywhere and only keep it in qemu_api as a special case. Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2025-01-10rust: add a utility module for compile-time type checksPaolo Bonzini1-0/+1
It is relatively common in the low-level qemu_api code to assert that a field of a struct has a specific type; for example, it can be used to ensure that the fields match what the qemu_api and C code expects for safety. Reviewed-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-19rust: qemu-api: add a module to wrap functions and zero-sized closuresPaolo Bonzini1-0/+1
One recurring issue when writing Rust bindings is how to convert a Rust function ("fn" or "impl Fn") to a C function, and how to pass around "self" to a C function that only takes a void*. An easy solution would be to store on the heap a pair consisting of a pointer to the Rust function and the pointer to "self", but it is possible to do better. If an "Fn" has zero size (that is, if it is a zero-capture closures or a function pointer---which in turn includes all methods), it is possible to build a generic Rust function that calls it even if you only have the type; you don't need either the pointer to the function itself (because the address of the code is part of the type) or any closure data (because it has size zero). Introduce a wrapper that provides the functionality of calling the function given only its type. Reviewed-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-19rust: rename qemu-api modules to follow C code a bit morePaolo Bonzini1-2/+3
A full match would mean calling them qom::object and hw::core::qdev. For now, keep the names shorter but still a bit easier to find. Reviewed-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-10rust: add a bit operation modulePaolo Bonzini1-0/+1
The bindgen supports `static inline` function binding since v0.64.0 as an experimental feature (`--wrap-static-fns`), and stabilizes it after v0.70.0. But the oldest version of bindgen supported by QEMU is v0.60.1, so there's no way to generate the binding for deposit64() which is `static inline` (in include/qemu/bitops.h). Instead, implement it by hand in Rust and make it available for all unsigned types through an IntegerExt trait. Since it only involves bit operations, the Rust version of the code is almost identical to the original C version, but it applies to more types than just u64. Signed-off-by: Zhao Liu <zhao1.liu@intel.com> Co-authored-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-10rust: add bindings for interrupt sourcesPaolo Bonzini1-0/+2
The InterruptSource bindings let us call qemu_set_irq() and sysbus_init_irq() as safe code. Interrupt sources, qemu_irq in C code, are pointers to IRQState objects. They are QOM link properties and can be written to outside the control of the device (i.e. from a shared reference); therefore they must be interior-mutable in Rust. Since thread-safety is provided by the BQL, what we want here is the newly-introduced BqlCell. A pointer to the contents of the BqlCell (an IRQState**, or equivalently qemu_irq*) is then passed to the C sysbus_init_irq function. Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-10rust: define preludePaolo Bonzini1-0/+5
Add a module that will contain frequently used traits and occasionally structs. They can be included quickly with "use qemu_api::prelude::*". Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-10rust: cell: add BQL-enforcing Cell variantPaolo Bonzini1-0/+1
QEMU objects usually have their pointer shared with the "outside world" very early in their lifetime, for example when they create their MemoryRegions. Because at this point it is not valid anymore to create a &mut reference to the device, individual parts of the device struct must be made mutable in a controlled manner. QEMU's Big Lock (BQL) effectively turns multi-threaded code into single-threaded code while device code runs, as long as the BQL is not released while the device is borrowed (because C code could sneak in and mutate the device). We can then introduce custom interior mutability primitives that are semantically similar to the standard library's (single-threaded) Cell and RefCell, but account for QEMU's threading model. Accessing the "BqlCell" or borrowing the "BqlRefCell" requires proving that the BQL is held, and attempting to access without the BQL is a runtime panic, similar to RefCell's already-borrowed panic. With respect to naming I also considered omitting the "Bql" prefix or moving it to the module, e.g. qemu_api::bql::{Cell, RefCell}. However, this could easily lead to mistakes and confusion; for example rustc could suggest the wrong import, leading to subtle bugs. As a start introduce the an equivalent of Cell. Almost all of the code was taken from Rust's standard library, while removing unstable features and probably-unnecessary functionality that constitute a large of the original code. A lot of what's left is documentation, as well as unit tests in the form of doctests. These are not yet integrated in "make check" but can be run with "cargo test --doc". Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-12-10rust: allow using build-root bindings.rs from cargoPaolo Bonzini1-22/+0
Right now, using cargo with QEMU requires copying by hand the bindings.rs to the source tree. Instead, we can use an include file to escape the cage of cargo's mandated source directory structure. By running cargo within meson's "devenv" and adding a MESON_BUILD_ROOT environment variable, it is easy for build.rs to find the file. However, the file must be symlinked into cargo's output directory for rust-analyzer to find it. Suggested-by: Junjie Mao <junjie.mao@hotmail.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: introduce alternative implementation of offset_of!Junjie Mao1-0/+4
offset_of! was stabilized in Rust 1.77.0. Use an alternative implemenation that was found on the Rust forums, and whose author agreed to license as MIT for use in QEMU. The alternative allows only one level of field access, but apart from this can be used just by replacing core::mem::offset_of! with qemu_api::offset_of!. The actual implementation of offset_of! is done in a declarative macro, but for simplicity and to avoid introducing an extra level of indentation, the trigger is a procedural macro #[derive(offsets)]. The procedural macro is perhaps a bit overengineered, but it helps introducing some idioms that will be useful in the future as well. Signed-off-by: Junjie Mao <junjie.mao@hotmail.com> Co-developed-by: Paolo Bonzini <pbonzini@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: introduce a c_str macroPaolo Bonzini1-0/+1
This allows CStr constants to be defined easily on Rust 1.63.0, while checking that there are no embedded NULs. c"" literals were only stabilized in Rust 1.77.0. Reviewed-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: use std::os::raw instead of core::ffiPaolo Bonzini1-4/+7
core::ffi::c_* types were introduced in Rust 1.64.0. Use the older types in std::os::raw, which are now aliases of the types in core::ffi. There is no need to compile QEMU as no_std, so this is acceptable as long as we support a version of Debian with Rust 1.63.0. Reviewed-by: Zhao Liu <zhao1.liu@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: add definitions for vmstateManos Pitsidianakis1-0/+3
Add a new qemu_api module, `vmstate`. Declare a bunch of Rust macros declared that are equivalent in spirit to the C macros in include/migration/vmstate.h. For example the Rust of equivalent of the C macro: VMSTATE_UINT32(field_name, struct_name) is: vmstate_uint32!(field_name, StructName) This breathtaking development will allow us to reach feature parity between the Rust and C pl011 implementations. Extracted from a patch by Manos Pitsidianakis (https://lore.kernel.org/qemu-devel/20241024-rust-round-2-v1-4-051e7a25b978@linaro.org/). Signed-off-by: Manos Pitsidianakis <manos.pitsidianakis@linaro.org> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: provide safe wrapper for MaybeUninit::zeroed()Paolo Bonzini1-0/+1
MaybeUninit::zeroed() is handy, but it introduces unsafe (and has a pretty heavy syntax in general). Introduce a trait that provides the same functionality while staying within safe Rust. In addition, MaybeUninit::zeroed() is not available as a "const" function until Rust 1.75.0, so this also prepares for having handwritten implementations of the trait until we can assume that version. Reviewed-by: Junjie Mao <junjie.mao@hotmail.com> Reviewed-by: Kevin Wolf <kwolf@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-11-05rust: build integration test for the qemu_api cratePaolo Bonzini1-3/+0
Adjust the integration test to compile with a subset of QEMU object files, and make it actually create an object of the class it defines. Follow the Rust filesystem conventions, where tests go in tests/ if they use the library in the same way any other code would. Reviewed-by: Junjie Mao <junjie.mao@hotmail.com> Reviewed-by: Kevin Wolf <kwolf@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
2024-10-11rust: add crate to expose bindings and interfacesManos Pitsidianakis1-0/+166
Add rust/qemu-api, which exposes rust-bindgen generated FFI bindings and provides some declaration macros for symbols visible to the rest of QEMU. Co-authored-by: Junjie Mao <junjie.mao@intel.com> Co-authored-by: Paolo Bonzini <pbonzini@redhat.com> Signed-off-by: Junjie Mao <junjie.mao@intel.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Signed-off-by: Manos Pitsidianakis <manos.pitsidianakis@linaro.org> Link: https://lore.kernel.org/r/0fb23fbe211761b263aacec03deaf85c0cc39995.1727961605.git.manos.pitsidianakis@linaro.org Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>