marcandre.lur...@redhat.com writes:

> From: Marc-André Lureau <marcandre.lur...@redhat.com>
>
> Hi,
>
> Among the QEMU developers, there is a desire to use Rust. (see previous
> thread from Stefan "Why QEMU should move from C to Rust", the rust-vmm
> related projects and other experiments).
>
> Thanks to our QAPI type system and the associate code generator, it is
> relatively straightforward to create Rust bindings for the generated C
> types (also called sys/ffi binding) and functions. (rust-bindgen could
> probably do a similar job, but it would probably bring other issues).
> This provides an important internal API already.
>
> Slightly more complicated is to expose a Rust API for those, and provide
> convenient conversions C<->Rust. Taking inspiration from glib-rs
> binding, I implemented a simplified version of the FromGlib/ToGlib
> traits, with simpler ownership model, sufficient for QAPI needs.
>
> The usage is relatively simple:
>
> - from_qemu_none(ptr: *const sys::P) -> T
>   Return a Rust type T for a const ffi pointer P.
>
> - from_qemu_full(ptr: *mut sys::P) -> T
>   Return a Rust type T for a ffi pointer P, taking ownership.
>
> - T::to_qemu_none() -> Stash<P>
>   Returns a borrowed ffi pointer P (using a Stash to destroy "glue"
>   storage data, if any).
>
> - T::to_qemu_full() -> P
>   Returns a ffi pointer P. (P resources are leaked/passed to C/ffi)
>
> With those traits, it's relatively easy to implement the QMP callbacks.
> With enough interest, we could eventually start rewriting QGA in
> Rust, as it is a simple service. See qga/qmp.rs for some examples.
> We could also try to tackle qemu itself.

Up to here, you're talking about *internal* interfaces.  Correct?

Your motivation is enabling use of Rust in QEMU.  Correct?

> Finally, given that the QAPI types are easy to serialize, it was simple
> to use "serde" on them, and provide a D-Bus interface for QMP with zbus.
> (a similar approach could probably be taken for other protocols, that
> could be dynamically loaded... anyone like protobuf better?)

QMP is an *external* interface.

It supports compatible evolution: we can make certain kinds of changes
without affecting clients.  These include:

* Adding optional arguments

* Adding results

* Adding values to an enumeration type, branches to a union or
  alternate

* Reordering members of enumerations, structs, unions

* Turning an argument type into an alternate with the old type as branch

We've made use of this extensively.  See also
docs/devel/qapi-code-gen.txt section "Compatibility considerations."

How do such changes affect clients of the proposed D-Bus interface?

> This PoC modifies qemu-ga to provide the interface on the session bus:
> $ qga/qemu-ga -m unix-listen -p /tmp/qga.sock -t /tmp -v
> $ busctl --user introspect org.qemu.qga /org/qemu/qga org.qemu.QgaQapi
> ...
> $ busctl --user call org.qemu.qga /org/qemu/qga org.qemu.QgaQapi
> GuestSetVcpus aa\{sv\} 1 2 logical-id x 0 online b 1
> ...
>
> Note: the generated code doesn't work with the qemu schema, there is a
> couple of fixme/todo left.
>
> Shameful pain point: meson & cargo don't play nicely together.
>
> Signed-off-by: Marc-André Lureau <marcandre.lur...@redhat.com>


Reply via email to