qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 00/14] rust: allow older versions of rustc and bindgen
@ 2024-10-22 10:09 Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
                   ` (14 more replies)
  0 siblings, 15 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

This is the second of three series needed to enable Rust for all CI
jobs (the third is due to differences in the functionality between
C and Rust implementations of PL011, for which I have sent the RFC
a little earlier).

My overall patch queue can be found at branch rust-next of my git
repository https://gitlab.com/bonzini/qemu.git.

Note that this requires "meson subprojects update --reset" in order to do
an incremental build if you have already downloaded the Rust subprojects.
While I have a solution for that (modeled after scripts/git-submodule.sh),
I first need to check with the Meson folks whether my script is using only
stable interfaces.

Paolo

Based-on: <20241021163538.136941-1-pbonzini@redhat.com>

CI:
- Debian: https://gitlab.com/bonzini/qemu/-/jobs/8149518712
- Fedora: https://gitlab.com/bonzini/qemu/-/jobs/8149518714
- Fedora + nightly Rust: https://gitlab.com/bonzini/qemu/-/jobs/8149518716
- Ubuntu: https://gitlab.com/bonzini/qemu/-/jobs/8149518709


Junjie Mao (1):
  rust: introduce alternative implementation of offset_of!

Paolo Bonzini (13):
  rust: patch bilge-impl to allow compilation with 1.63.0
  rust: fix cfgs of proc-macro2 for 1.63.0
  rust: use std::os::raw instead of core::ffi
  rust: introduce a c_str macro
  rust: silence unknown warnings for the sake of old compilers
  rust: synchronize dependencies between subprojects and Cargo.lock
  rust: do not use MaybeUninit::zeroed()
  rust: clean up detection of the language
  rust: allow version 1.63.0 of rustc
  rust: do not use --generate-cstr
  rust: allow older version of bindgen
  rust: make rustfmt optional
  dockerfiles: install bindgen from cargo on Ubuntu 22.04

 docs/about/build-platforms.rst                |   8 +
 meson.build                                   | 102 +++++++----
 .gitattributes                                |   2 +
 .gitlab-ci.d/buildtest.yml                    |   2 +-
 meson_options.txt                             |   2 +
 rust/hw/char/pl011/Cargo.lock                 |   6 +-
 rust/hw/char/pl011/src/device.rs              |  28 +--
 rust/hw/char/pl011/src/device_class.rs        |   5 +-
 rust/hw/char/pl011/src/lib.rs                 |   4 +-
 rust/hw/char/pl011/src/memory_ops.rs          |  10 +-
 rust/qemu-api-macros/Cargo.lock               |  11 +-
 rust/qemu-api-macros/Cargo.toml               |   5 +-
 rust/qemu-api-macros/src/lib.rs               |  29 +++-
 rust/qemu-api/Cargo.lock                      |  56 +++++-
 rust/qemu-api/Cargo.toml                      |   7 +-
 rust/qemu-api/build.rs                        |   8 +
 rust/qemu-api/meson.build                     |  16 +-
 rust/qemu-api/src/c_str.rs                    |  53 ++++++
 rust/qemu-api/src/definitions.rs              |   2 +-
 rust/qemu-api/src/device_class.rs             |  26 ++-
 rust/qemu-api/src/lib.rs                      |  16 +-
 rust/qemu-api/src/offset_of.rs                | 161 ++++++++++++++++++
 rust/qemu-api/src/zeroable.rs                 |  91 ++++++++--
 rust/qemu-api/tests/tests.rs                  |  22 +--
 scripts/meson-buildoptions.sh                 |   4 +
 subprojects/bilge-impl-0.2-rs.wrap            |   1 +
 subprojects/packagefiles/.gitattributes       |   1 +
 .../packagefiles/bilge-impl-1.63.0.patch      |  45 +++++
 .../packagefiles/proc-macro2-1-rs/meson.build |   4 +-
 subprojects/packagefiles/syn-2-rs/meson.build |   1 +
 tests/docker/dockerfiles/ubuntu2204.docker    |   5 +
 tests/lcitool/mappings.yml                    |   4 +
 tests/lcitool/refresh                         |  11 +-
 33 files changed, 644 insertions(+), 104 deletions(-)
 create mode 100644 rust/qemu-api/src/c_str.rs
 create mode 100644 rust/qemu-api/src/offset_of.rs
 create mode 100644 subprojects/packagefiles/.gitattributes
 create mode 100644 subprojects/packagefiles/bilge-impl-1.63.0.patch

-- 
2.46.2



^ permalink raw reply	[flat|nested] 23+ messages in thread

* [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-24  2:12   ` Junjie Mao
  2024-10-24 10:43   ` Alex Bennée
  2024-10-22 10:09 ` [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0 Paolo Bonzini
                   ` (13 subsequent siblings)
  14 siblings, 2 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis, Zhao Liu

Apply a patch that removes "let ... else" constructs, replacing them with
"if let ... else" or "let ... = match ...".  "let ... else" was stabilized in
Rust 1.65.0.

Reviewed-by: Zhao Liu <zhao1.liu@intel.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 .gitattributes                                |  2 +
 subprojects/bilge-impl-0.2-rs.wrap            |  1 +
 subprojects/packagefiles/.gitattributes       |  1 +
 .../packagefiles/bilge-impl-1.63.0.patch      | 45 +++++++++++++++++++
 4 files changed, 49 insertions(+)
 create mode 100644 subprojects/packagefiles/.gitattributes
 create mode 100644 subprojects/packagefiles/bilge-impl-1.63.0.patch

diff --git a/.gitattributes b/.gitattributes
index 6dc6383d3d1..9ce7a19581a 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -5,3 +5,5 @@
 *.rs            diff=rust
 *.rs.inc        diff=rust
 Cargo.lock      diff=toml merge=binary
+
+*.patch         -text -whitespace
diff --git a/subprojects/bilge-impl-0.2-rs.wrap b/subprojects/bilge-impl-0.2-rs.wrap
index eefb10c36c2..b24c34a9043 100644
--- a/subprojects/bilge-impl-0.2-rs.wrap
+++ b/subprojects/bilge-impl-0.2-rs.wrap
@@ -5,3 +5,4 @@ source_filename = bilge-impl-0.2.0.tar.gz
 source_hash = feb11e002038ad243af39c2068c8a72bcf147acf05025dcdb916fcc000adb2d8
 #method = cargo
 patch_directory = bilge-impl-0.2-rs
+diff_files = bilge-impl-1.63.0.patch
diff --git a/subprojects/packagefiles/.gitattributes b/subprojects/packagefiles/.gitattributes
new file mode 100644
index 00000000000..bf5b766d75d
--- /dev/null
+++ b/subprojects/packagefiles/.gitattributes
@@ -0,0 +1 @@
+/*.patch     -text
diff --git a/subprojects/packagefiles/bilge-impl-1.63.0.patch b/subprojects/packagefiles/bilge-impl-1.63.0.patch
new file mode 100644
index 00000000000..987428a6d65
--- /dev/null
+++ b/subprojects/packagefiles/bilge-impl-1.63.0.patch
@@ -0,0 +1,45 @@
+--- a/src/shared/discriminant_assigner.rs
++++ b/src/shared/discriminant_assigner.rs
+@@ -26,20 +26,20 @@
+         let discriminant_expr = &discriminant.1;
+         let variant_name = &variant.ident;
+ 
+-        let Expr::Lit(ExprLit { lit: Lit::Int(int), .. }) = discriminant_expr else {
++        if let Expr::Lit(ExprLit { lit: Lit::Int(int), .. }) = discriminant_expr {
++            let discriminant_value: u128 = int.base10_parse().unwrap_or_else(unreachable);
++            if discriminant_value > self.max_value() {
++                abort!(variant, "Value of variant exceeds the given number of bits")
++            }
++
++            Some(discriminant_value)
++        } else {
+             abort!(
+                 discriminant_expr,
+                 "variant `{}` is not a number", variant_name;
+                 help = "only literal integers currently supported"
+             )
+-        };
+-
+-        let discriminant_value: u128 = int.base10_parse().unwrap_or_else(unreachable);
+-        if discriminant_value > self.max_value() {
+-            abort!(variant, "Value of variant exceeds the given number of bits")
+         }
+-
+-        Some(discriminant_value)
+     }
+ 
+     fn assign(&mut self, variant: &Variant) -> u128 {
+--- a/src/shared/fallback.rs
++++ b/src/shared/fallback.rs
+@@ -22,8 +22,9 @@
+             }
+             Unnamed(fields) => {
+                 let variant_fields = fields.unnamed.iter();
+-                let Ok(fallback_value) = variant_fields.exactly_one() else {
+-                    abort!(variant, "fallback variant must have exactly one field"; help = "use only one field or change to a unit variant")
++                let fallback_value = match variant_fields.exactly_one() {
++                    Ok(ok) => ok,
++                    _ => abort!(variant, "fallback variant must have exactly one field"; help = "use only one field or change to a unit variant")
+                 };
+ 
+                 if !is_last_variant {
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-24  2:33   ` Junjie Mao
  2024-10-22 10:09 ` [PATCH v2 03/14] rust: use std::os::raw instead of core::ffi Paolo Bonzini
                   ` (12 subsequent siblings)
  14 siblings, 1 reply; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Replay the configuration that would be computed by build.rs when compiling
on a 1.63.0 compiler.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 subprojects/packagefiles/proc-macro2-1-rs/meson.build | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/subprojects/packagefiles/proc-macro2-1-rs/meson.build b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
index 818ec59336b..8e601b50ccc 100644
--- a/subprojects/packagefiles/proc-macro2-1-rs/meson.build
+++ b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
@@ -15,7 +15,9 @@ _proc_macro2_rs = static_library(
   rust_abi: 'rust',
   rust_args: [
     '--cfg', 'feature="proc-macro"',
-    '--cfg', 'span_locations',
+    '--cfg', 'no_literal_byte_character',
+    '--cfg', 'no_literal_c_string',
+    '--cfg', 'no_source_text',
     '--cfg', 'wrap_proc_macro',
   ],
   dependencies: [
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 03/14] rust: use std::os::raw instead of core::ffi
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0 Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 04/14] rust: introduce a c_str macro Paolo Bonzini
                   ` (11 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis, Zhao Liu

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>
---
 meson.build                          |  3 +--
 rust/hw/char/pl011/src/device.rs     | 20 +++++++++++---------
 rust/hw/char/pl011/src/lib.rs        |  2 +-
 rust/hw/char/pl011/src/memory_ops.rs | 10 ++++++----
 rust/qemu-api/src/definitions.rs     |  2 +-
 rust/qemu-api/src/device_class.rs    |  8 ++++----
 rust/qemu-api/src/lib.rs             | 11 +++++++----
 rust/qemu-api/tests/tests.rs         |  9 ++++-----
 8 files changed, 35 insertions(+), 30 deletions(-)

diff --git a/meson.build b/meson.build
index 3c71d129494..94f30033f68 100644
--- a/meson.build
+++ b/meson.build
@@ -3933,14 +3933,13 @@ if have_rust and have_system
   bindgen_args = [
     '--disable-header-comment',
     '--raw-line', '// @generated',
-    '--ctypes-prefix', 'core::ffi',
+    '--ctypes-prefix', 'std::os::raw',
     '--formatter', 'rustfmt',
     '--generate-block',
     '--generate-cstr',
     '--impl-debug',
     '--merge-extern-blocks',
     '--no-doc-comments',
-    '--use-core',
     '--with-derive-default',
     '--no-layout-tests',
     '--no-prepend-enum-name',
diff --git a/rust/hw/char/pl011/src/device.rs b/rust/hw/char/pl011/src/device.rs
index b3d8bc004e0..7be21769ae4 100644
--- a/rust/hw/char/pl011/src/device.rs
+++ b/rust/hw/char/pl011/src/device.rs
@@ -2,9 +2,11 @@
 // Author(s): Manos Pitsidianakis <manos.pitsidianakis@linaro.org>
 // SPDX-License-Identifier: GPL-2.0-or-later
 
-use core::{
-    ffi::{c_int, c_uchar, c_uint, c_void, CStr},
-    ptr::{addr_of, addr_of_mut, NonNull},
+use core::ptr::{addr_of, addr_of_mut, NonNull};
+
+use std::{
+    ffi::CStr,
+    os::raw::{c_int, c_uchar, c_uint, c_void}
 };
 
 use qemu_api::{
@@ -89,10 +91,10 @@ pub struct PL011Class {
 
 impl qemu_api::definitions::Class for PL011Class {
     const CLASS_INIT: Option<
-        unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut core::ffi::c_void),
+        unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut c_void),
     > = Some(crate::device_class::pl011_class_init);
     const CLASS_BASE_INIT: Option<
-        unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut core::ffi::c_void),
+        unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut c_void),
     > = None;
 }
 
@@ -151,7 +153,7 @@ pub unsafe fn init(&mut self) {
     pub fn read(
         &mut self,
         offset: hwaddr,
-        _size: core::ffi::c_uint,
+        _size: c_uint,
     ) -> std::ops::ControlFlow<u64, u64> {
         use RegisterOffset::*;
 
@@ -530,9 +532,9 @@ pub fn update(&self) {
 ///
 /// The buffer and size arguments must also be valid.
 pub unsafe extern "C" fn pl011_receive(
-    opaque: *mut core::ffi::c_void,
+    opaque: *mut c_void,
     buf: *const u8,
-    size: core::ffi::c_int,
+    size: c_int,
 ) {
     unsafe {
         debug_assert!(!opaque.is_null());
@@ -552,7 +554,7 @@ pub fn update(&self) {
 /// We expect the FFI user of this function to pass a valid pointer, that has
 /// the same size as [`PL011State`]. We also expect the device is
 /// readable/writeable from one thread at any time.
-pub unsafe extern "C" fn pl011_event(opaque: *mut core::ffi::c_void, event: QEMUChrEvent) {
+pub unsafe extern "C" fn pl011_event(opaque: *mut c_void, event: QEMUChrEvent) {
     unsafe {
         debug_assert!(!opaque.is_null());
         let mut state = NonNull::new_unchecked(opaque.cast::<PL011State>());
diff --git a/rust/hw/char/pl011/src/lib.rs b/rust/hw/char/pl011/src/lib.rs
index 2939ee50c99..2b157868b0f 100644
--- a/rust/hw/char/pl011/src/lib.rs
+++ b/rust/hw/char/pl011/src/lib.rs
@@ -45,7 +45,7 @@
 pub mod device_class;
 pub mod memory_ops;
 
-pub const TYPE_PL011: &::core::ffi::CStr = c"pl011";
+pub const TYPE_PL011: &::std::ffi::CStr = c"pl011";
 
 /// Offset of each register from the base memory address of the device.
 ///
diff --git a/rust/hw/char/pl011/src/memory_ops.rs b/rust/hw/char/pl011/src/memory_ops.rs
index 24ac9c870c1..6d822027d51 100644
--- a/rust/hw/char/pl011/src/memory_ops.rs
+++ b/rust/hw/char/pl011/src/memory_ops.rs
@@ -4,6 +4,8 @@
 
 use core::ptr::NonNull;
 
+use std::os::raw::{c_uint, c_void};
+
 use qemu_api::{
     bindings::*,
     zeroable::Zeroable
@@ -26,9 +28,9 @@
 };
 
 unsafe extern "C" fn pl011_read(
-    opaque: *mut core::ffi::c_void,
+    opaque: *mut c_void,
     addr: hwaddr,
-    size: core::ffi::c_uint,
+    size: c_uint,
 ) -> u64 {
     assert!(!opaque.is_null());
     let mut state = unsafe { NonNull::new_unchecked(opaque.cast::<PL011State>()) };
@@ -47,10 +49,10 @@
 }
 
 unsafe extern "C" fn pl011_write(
-    opaque: *mut core::ffi::c_void,
+    opaque: *mut c_void,
     addr: hwaddr,
     data: u64,
-    _size: core::ffi::c_uint,
+    _size: c_uint,
 ) {
     unsafe {
         assert!(!opaque.is_null());
diff --git a/rust/qemu-api/src/definitions.rs b/rust/qemu-api/src/definitions.rs
index 064afe60549..26597934bbd 100644
--- a/rust/qemu-api/src/definitions.rs
+++ b/rust/qemu-api/src/definitions.rs
@@ -4,7 +4,7 @@
 
 //! Definitions required by QEMU when registering a device.
 
-use ::core::ffi::{c_void, CStr};
+use std::{ffi::CStr, os::raw::c_void};
 
 use crate::bindings::{Object, ObjectClass, TypeInfo};
 
diff --git a/rust/qemu-api/src/device_class.rs b/rust/qemu-api/src/device_class.rs
index ed2d7ce1a54..5c305d945d3 100644
--- a/rust/qemu-api/src/device_class.rs
+++ b/rust/qemu-api/src/device_class.rs
@@ -7,7 +7,7 @@ macro_rules! device_class_init {
     ($func:ident, props => $props:ident, realize_fn => $realize_fn:expr, legacy_reset_fn => $legacy_reset_fn:expr, vmsd => $vmsd:ident$(,)*) => {
         pub unsafe extern "C" fn $func(
             klass: *mut $crate::bindings::ObjectClass,
-            _: *mut ::core::ffi::c_void,
+            _: *mut ::std::os::raw::c_void,
         ) {
             let mut dc =
                 ::core::ptr::NonNull::new(klass.cast::<$crate::bindings::DeviceClass>()).unwrap();
@@ -26,7 +26,7 @@ macro_rules! define_property {
     ($name:expr, $state:ty, $field:expr, $prop:expr, $type:expr, default = $defval:expr$(,)*) => {
         $crate::bindings::Property {
             // use associated function syntax for type checking
-            name: ::core::ffi::CStr::as_ptr($name),
+            name: ::std::ffi::CStr::as_ptr($name),
             info: $prop,
             offset: ::core::mem::offset_of!($state, $field) as isize,
             set_default: true,
@@ -37,7 +37,7 @@ macro_rules! define_property {
     ($name:expr, $state:ty, $field:expr, $prop:expr, $type:expr$(,)*) => {
         $crate::bindings::Property {
             // use associated function syntax for type checking
-            name: ::core::ffi::CStr::as_ptr($name),
+            name: ::std::ffi::CStr::as_ptr($name),
             info: $prop,
             offset: ::core::mem::offset_of!($state, $field) as isize,
             set_default: false,
@@ -75,7 +75,7 @@ macro_rules! vm_state_description {
         pub static $name: $crate::bindings::VMStateDescription = $crate::bindings::VMStateDescription {
             $(name: {
                 #[used]
-                static VMSTATE_NAME: &::core::ffi::CStr = $vname;
+                static VMSTATE_NAME: &::std::ffi::CStr = $vname;
                 $vname.as_ptr()
             },)*
             unmigratable: true,
diff --git a/rust/qemu-api/src/lib.rs b/rust/qemu-api/src/lib.rs
index e94a15bb823..321c33d2c7b 100644
--- a/rust/qemu-api/src/lib.rs
+++ b/rust/qemu-api/src/lib.rs
@@ -31,7 +31,10 @@ unsafe impl Sync for bindings::VMStateDescription {}
 pub mod device_class;
 pub mod zeroable;
 
-use std::alloc::{GlobalAlloc, Layout};
+use std::{
+    alloc::{GlobalAlloc, Layout},
+    os::raw::c_void,
+};
 
 #[cfg(HAVE_GLIB_WITH_ALIGNED_ALLOC)]
 extern "C" {
@@ -45,8 +48,8 @@ fn g_aligned_alloc0(
 
 #[cfg(not(HAVE_GLIB_WITH_ALIGNED_ALLOC))]
 extern "C" {
-    fn qemu_memalign(alignment: usize, size: usize) -> *mut ::core::ffi::c_void;
-    fn qemu_vfree(ptr: *mut ::core::ffi::c_void);
+    fn qemu_memalign(alignment: usize, size: usize) -> *mut c_void;
+    fn qemu_vfree(ptr: *mut c_void);
 }
 
 extern "C" {
@@ -111,7 +114,7 @@ fn default() -> Self {
 }
 
 // Sanity check.
-const _: [(); 8] = [(); ::core::mem::size_of::<*mut ::core::ffi::c_void>()];
+const _: [(); 8] = [(); ::core::mem::size_of::<*mut c_void>()];
 
 unsafe impl GlobalAlloc for QemuAllocator {
     unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
diff --git a/rust/qemu-api/tests/tests.rs b/rust/qemu-api/tests/tests.rs
index aa1e0568c69..3396c33fe1e 100644
--- a/rust/qemu-api/tests/tests.rs
+++ b/rust/qemu-api/tests/tests.rs
@@ -2,7 +2,7 @@
 // Author(s): Manos Pitsidianakis <manos.pitsidianakis@linaro.org>
 // SPDX-License-Identifier: GPL-2.0-or-later
 
-use core::ffi::CStr;
+use std::{ffi::CStr, os::raw::c_void};
 
 use qemu_api::{
     bindings::*,
@@ -63,11 +63,10 @@ impl ObjectImpl for DummyState {
     }
 
     impl Class for DummyClass {
-        const CLASS_INIT: Option<
-            unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut core::ffi::c_void),
-        > = Some(dummy_class_init);
+        const CLASS_INIT: Option<unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut c_void)> =
+            Some(dummy_class_init);
         const CLASS_BASE_INIT: Option<
-            unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut core::ffi::c_void),
+            unsafe extern "C" fn(klass: *mut ObjectClass, data: *mut c_void),
         > = None;
     }
 
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 04/14] rust: introduce a c_str macro
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (2 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 03/14] rust: use std::os::raw instead of core::ffi Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 05/14] rust: silence unknown warnings for the sake of old compilers Paolo Bonzini
                   ` (10 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

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.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 rust/hw/char/pl011/src/device.rs       |  5 ++-
 rust/hw/char/pl011/src/device_class.rs |  5 ++-
 rust/hw/char/pl011/src/lib.rs          |  4 +-
 rust/qemu-api/meson.build              |  4 ++
 rust/qemu-api/src/c_str.rs             | 53 ++++++++++++++++++++++++++
 rust/qemu-api/src/lib.rs               |  1 +
 rust/qemu-api/tests/tests.rs           |  8 ++--
 7 files changed, 71 insertions(+), 9 deletions(-)
 create mode 100644 rust/qemu-api/src/c_str.rs

diff --git a/rust/hw/char/pl011/src/device.rs b/rust/hw/char/pl011/src/device.rs
index 7be21769ae4..5ffe1911376 100644
--- a/rust/hw/char/pl011/src/device.rs
+++ b/rust/hw/char/pl011/src/device.rs
@@ -11,6 +11,7 @@
 
 use qemu_api::{
     bindings::{self, *},
+    c_str,
     definitions::ObjectImpl,
 };
 
@@ -99,7 +100,7 @@ impl qemu_api::definitions::Class for PL011Class {
 }
 
 #[used]
-pub static CLK_NAME: &CStr = c"clk";
+pub static CLK_NAME: &CStr = c_str!("clk");
 
 impl PL011State {
     /// Initializes a pre-allocated, unitialized instance of `PL011State`.
@@ -575,7 +576,7 @@ pub fn update(&self) {
         let dev: *mut DeviceState = qdev_new(PL011State::TYPE_INFO.name);
         let sysbus: *mut SysBusDevice = dev.cast::<SysBusDevice>();
 
-        qdev_prop_set_chr(dev, c"chardev".as_ptr(), chr);
+        qdev_prop_set_chr(dev, c_str!("chardev").as_ptr(), chr);
         sysbus_realize_and_unref(sysbus, addr_of!(error_fatal) as *mut *mut Error);
         sysbus_mmio_map(sysbus, 0, addr);
         sysbus_connect_irq(sysbus, 0, irq);
diff --git a/rust/hw/char/pl011/src/device_class.rs b/rust/hw/char/pl011/src/device_class.rs
index 78fa1cdd5b6..3b9b0267b4c 100644
--- a/rust/hw/char/pl011/src/device_class.rs
+++ b/rust/hw/char/pl011/src/device_class.rs
@@ -6,6 +6,7 @@
 
 use qemu_api::{
     bindings::*,
+    c_str,
     definitions::ObjectImpl,
     zeroable::Zeroable,
 };
@@ -22,14 +23,14 @@
 qemu_api::declare_properties! {
     PL011_PROPERTIES,
     qemu_api::define_property!(
-        c"chardev",
+        c_str!("chardev"),
         PL011State,
         char_backend,
         unsafe { &qdev_prop_chr },
         CharBackend
     ),
     qemu_api::define_property!(
-        c"migrate-clk",
+        c_str!("migrate-clk"),
         PL011State,
         migrate_clock,
         unsafe { &qdev_prop_bool },
diff --git a/rust/hw/char/pl011/src/lib.rs b/rust/hw/char/pl011/src/lib.rs
index 2b157868b0f..0a598e5629d 100644
--- a/rust/hw/char/pl011/src/lib.rs
+++ b/rust/hw/char/pl011/src/lib.rs
@@ -41,11 +41,13 @@
 extern crate bilge_impl;
 extern crate qemu_api;
 
+use qemu_api::c_str;
+
 pub mod device;
 pub mod device_class;
 pub mod memory_ops;
 
-pub const TYPE_PL011: &::std::ffi::CStr = c"pl011";
+pub const TYPE_PL011: &::std::ffi::CStr = c_str!("pl011");
 
 /// Offset of each register from the base memory address of the device.
 ///
diff --git a/rust/qemu-api/meson.build b/rust/qemu-api/meson.build
index 1b0fd406378..2b3dea59fb6 100644
--- a/rust/qemu-api/meson.build
+++ b/rust/qemu-api/meson.build
@@ -3,6 +3,7 @@ _qemu_api_rs = static_library(
   structured_sources(
     [
       'src/lib.rs',
+      'src/c_str.rs',
       'src/definitions.rs',
       'src/device_class.rs',
       'src/zeroable.rs',
@@ -17,6 +18,9 @@ _qemu_api_rs = static_library(
   ],
 )
 
+rust.test('rust-qemu-api-tests', _qemu_api_rs,
+          suite: ['unit', 'rust'])
+
 qemu_api = declare_dependency(
   link_with: _qemu_api_rs,
   dependencies: qemu_api_macros,
diff --git a/rust/qemu-api/src/c_str.rs b/rust/qemu-api/src/c_str.rs
new file mode 100644
index 00000000000..5ef46d12bef
--- /dev/null
+++ b/rust/qemu-api/src/c_str.rs
@@ -0,0 +1,53 @@
+// Copyright 2024 Red Hat, Inc.
+// Author(s): Paolo Bonzini <pbonzini@redhat.com>
+// SPDX-License-Identifier: GPL-2.0-or-later
+
+#[macro_export]
+/// Given a string constant _without_ embedded or trailing NULs, return
+/// a CStr.
+///
+/// Needed for compatibility with Rust <1.77.
+macro_rules! c_str {
+    ($str:expr) => {{
+        const STRING: &str = concat!($str, "\0");
+        const BYTES: &[u8] = STRING.as_bytes();
+
+        // "for" is not allowed in const context... oh well,
+        // everybody loves some lisp.  This could be turned into
+        // a procedural macro if this is a problem; alternatively
+        // Rust 1.72 makes CStr::from_bytes_with_nul a const function.
+        const fn f(b: &[u8], i: usize) {
+            if i == BYTES.len() - 1 {
+            } else if BYTES[i] == 0 {
+                panic!("c_str argument contains NUL")
+            } else {
+                f(b, i + 1)
+            }
+        }
+        f(BYTES, 0);
+
+        // SAFETY: absence of NULs apart from the final byte was checked above
+        unsafe { std::ffi::CStr::from_bytes_with_nul_unchecked(BYTES) }
+    }};
+}
+
+#[cfg(test)]
+mod tests {
+    use std::ffi::CStr;
+
+    use crate::c_str;
+
+    #[test]
+    fn test_cstr_macro() {
+        let good = c_str!("🦀");
+        let good_bytes = b"\xf0\x9f\xa6\x80\0";
+        assert_eq!(good.to_bytes_with_nul(), good_bytes);
+    }
+
+    #[test]
+    fn test_cstr_macro_const() {
+        const GOOD: &CStr = c_str!("🦀");
+        const GOOD_BYTES: &[u8] = b"\xf0\x9f\xa6\x80\0";
+        assert_eq!(GOOD.to_bytes_with_nul(), GOOD_BYTES);
+    }
+}
diff --git a/rust/qemu-api/src/lib.rs b/rust/qemu-api/src/lib.rs
index 321c33d2c7b..9c3be4f6489 100644
--- a/rust/qemu-api/src/lib.rs
+++ b/rust/qemu-api/src/lib.rs
@@ -27,6 +27,7 @@ unsafe impl Sync for bindings::Property {}
 unsafe impl Sync for bindings::TypeInfo {}
 unsafe impl Sync for bindings::VMStateDescription {}
 
+pub mod c_str;
 pub mod definitions;
 pub mod device_class;
 pub mod zeroable;
diff --git a/rust/qemu-api/tests/tests.rs b/rust/qemu-api/tests/tests.rs
index 3396c33fe1e..605bc99ed4c 100644
--- a/rust/qemu-api/tests/tests.rs
+++ b/rust/qemu-api/tests/tests.rs
@@ -6,7 +6,7 @@
 
 use qemu_api::{
     bindings::*,
-    declare_properties, define_property,
+    c_str, declare_properties, define_property,
     definitions::{Class, ObjectImpl},
     device_class_init, vm_state_description,
 };
@@ -16,7 +16,7 @@ fn test_device_decl_macros() {
     // Test that macros can compile.
     vm_state_description! {
         VMSTATE,
-        name: c"name",
+        name: c_str!("name"),
         unmigratable: true,
     }
 
@@ -35,7 +35,7 @@ pub struct DummyClass {
     declare_properties! {
         DUMMY_PROPERTIES,
             define_property!(
-                c"migrate-clk",
+                c_str!("migrate-clk"),
                 DummyState,
                 migrate_clock,
                 unsafe { &qdev_prop_bool },
@@ -54,7 +54,7 @@ pub struct DummyClass {
     impl ObjectImpl for DummyState {
         type Class = DummyClass;
         const TYPE_INFO: qemu_api::bindings::TypeInfo = qemu_api::type_info! { Self };
-        const TYPE_NAME: &'static CStr = c"dummy";
+        const TYPE_NAME: &'static CStr = c_str!("dummy");
         const PARENT_TYPE_NAME: Option<&'static CStr> = Some(TYPE_DEVICE);
         const ABSTRACT: bool = false;
         const INSTANCE_INIT: Option<unsafe extern "C" fn(obj: *mut Object)> = None;
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 05/14] rust: silence unknown warnings for the sake of old compilers
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (3 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 04/14] rust: introduce a c_str macro Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock Paolo Bonzini
                   ` (9 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Occasionally, we may need to silence warnings and clippy lints that
were only introduced in newer Rust compiler versions.  However, this
would fail when compiling with an older rustc:

error: unknown lint: `non_local_definitions`
   --> rust/qemu-api/rust-qemu-api-tests.p/structured/offset_of.rs:79:17

So by default we need to block the unknown_lints warning.  To avoid
misspelled lints or other similar issues, re-enable it in the CI job
that uses nightly rust.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 meson.build                   | 8 ++++++++
 .gitlab-ci.d/buildtest.yml    | 2 +-
 meson_options.txt             | 2 ++
 scripts/meson-buildoptions.sh | 4 ++++
 4 files changed, 15 insertions(+), 1 deletion(-)

diff --git a/meson.build b/meson.build
index 94f30033f68..fe72f9951ca 100644
--- a/meson.build
+++ b/meson.build
@@ -3327,6 +3327,14 @@ if have_rust and have_system
   # Prohibit code that is forbidden in Rust 2024
   rustc_args += ['-D', 'unsafe_op_in_unsafe_fn']
 
+  # Occasionally, we may need to silence warnings and clippy lints that
+  # were only introduced in newer Rust compiler versions.  Do not croak
+  # in that case; a CI job with rust_strict_lints == true ensures that
+  # we do not have misspelled allow() attributes.
+  if not get_option('strict_rust_lints')
+    rustc_args += ['-A', 'unknown_lints']
+  endif
+
   # Apart from procedural macros, our Rust executables will often link
   # with C code, so include all the libraries that C code needs.  This
   # is safe; https://github.com/rust-lang/rust/pull/54675 says that
diff --git a/.gitlab-ci.d/buildtest.yml b/.gitlab-ci.d/buildtest.yml
index 7705000e3cc..4c87f8788d5 100644
--- a/.gitlab-ci.d/buildtest.yml
+++ b/.gitlab-ci.d/buildtest.yml
@@ -128,7 +128,7 @@ build-system-fedora-rust-nightly:
     job: amd64-fedora-rust-nightly-container
   variables:
     IMAGE: fedora-rust-nightly
-    CONFIGURE_ARGS: --disable-docs --enable-rust
+    CONFIGURE_ARGS: --disable-docs --enable-rust --enable-strict-rust-lints
     TARGETS: aarch64-softmmu
     MAKE_CHECK_ARGS: check-build
   allow_failure: true
diff --git a/meson_options.txt b/meson_options.txt
index 0ee4d7bb86b..e46199a3232 100644
--- a/meson_options.txt
+++ b/meson_options.txt
@@ -376,3 +376,5 @@ option('x86_version', type : 'combo', choices : ['0', '1', '2', '3', '4'], value
 
 option('rust', type: 'feature', value: 'disabled',
        description: 'Rust support')
+option('strict_rust_lints', type: 'boolean', value: false,
+       description: 'Enable stricter set of Rust warnings')
diff --git a/scripts/meson-buildoptions.sh b/scripts/meson-buildoptions.sh
index 6d08605b771..e898b20307d 100644
--- a/scripts/meson-buildoptions.sh
+++ b/scripts/meson-buildoptions.sh
@@ -47,6 +47,8 @@ meson_options_help() {
   printf "%s\n" '                           getrandom()'
   printf "%s\n" '  --enable-safe-stack      SafeStack Stack Smash Protection (requires'
   printf "%s\n" '                           clang/llvm and coroutine backend ucontext)'
+  printf "%s\n" '  --enable-strict-rust-lints'
+  printf "%s\n" '                           Enable stricter set of Rust warnings'
   printf "%s\n" '  --enable-strip           Strip targets on install'
   printf "%s\n" '  --enable-tcg-interpreter TCG with bytecode interpreter (slow)'
   printf "%s\n" '  --enable-trace-backends=CHOICES'
@@ -490,6 +492,8 @@ _meson_option_parse() {
     --disable-spice-protocol) printf "%s" -Dspice_protocol=disabled ;;
     --enable-stack-protector) printf "%s" -Dstack_protector=enabled ;;
     --disable-stack-protector) printf "%s" -Dstack_protector=disabled ;;
+    --enable-strict-rust-lints) printf "%s" -Dstrict_rust_lints=true ;;
+    --disable-strict-rust-lints) printf "%s" -Dstrict_rust_lints=false ;;
     --enable-strip) printf "%s" -Dstrip=true ;;
     --disable-strip) printf "%s" -Dstrip=false ;;
     --sysconfdir=*) quote_sh "-Dsysconfdir=$2" ;;
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (4 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 05/14] rust: silence unknown warnings for the sake of old compilers Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-24  2:53   ` Junjie Mao
  2024-10-22 10:09 ` [PATCH v2 07/14] rust: introduce alternative implementation of offset_of! Paolo Bonzini
                   ` (8 subsequent siblings)
  14 siblings, 1 reply; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

The next commit will introduce a new build dependency for rust/qemu-api,
version_check.  Before adding it, ensure that all dependencies are
synchronized between the Meson- and cargo-based build systems.

Note that it's not clear whether in the long term we'll use Cargo for
anything; it seems that the three main uses (clippy, rustfmt, rustdoc)
can all be invoked manually---either via glue code in QEMU, or by
extending Meson to gain the relevant functionality.  However, for
the time being we're stuck with Cargo so it should at least look at
the same code as the rest of the build system.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 rust/hw/char/pl011/Cargo.lock   |  5 +++-
 rust/qemu-api-macros/Cargo.lock | 11 ++++----
 rust/qemu-api/Cargo.lock        | 49 ++++++++++++++++++++++++++++++++-
 rust/qemu-api/Cargo.toml        |  1 +
 4 files changed, 59 insertions(+), 7 deletions(-)

diff --git a/rust/hw/char/pl011/Cargo.lock b/rust/hw/char/pl011/Cargo.lock
index b58cebb186e..82028ddf793 100644
--- a/rust/hw/char/pl011/Cargo.lock
+++ b/rust/hw/char/pl011/Cargo.lock
@@ -1,6 +1,6 @@
 # This file is automatically @generated by Cargo.
 # It is not intended for manual editing.
-version = 3
+version = 4
 
 [[package]]
 name = "arbitrary-int"
@@ -91,6 +91,9 @@ dependencies = [
 [[package]]
 name = "qemu_api"
 version = "0.1.0"
+dependencies = [
+ "qemu_api_macros",
+]
 
 [[package]]
 name = "qemu_api_macros"
diff --git a/rust/qemu-api-macros/Cargo.lock b/rust/qemu-api-macros/Cargo.lock
index fdc0fce116c..779b0ac6a25 100644
--- a/rust/qemu-api-macros/Cargo.lock
+++ b/rust/qemu-api-macros/Cargo.lock
@@ -1,12 +1,12 @@
 # This file is automatically @generated by Cargo.
 # It is not intended for manual editing.
-version = 3
+version = 4
 
 [[package]]
 name = "proc-macro2"
-version = "1.0.86"
+version = "1.0.84"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "5e719e8df665df0d1c8fbfd238015744736151d4445ec0836b8e628aae103b77"
+checksum = "ec96c6a92621310b51366f1e28d05ef11489516e93be030060e5fc12024a49d6"
 dependencies = [
  "unicode-ident",
 ]
@@ -18,6 +18,7 @@ dependencies = [
  "proc-macro2",
  "quote",
  "syn",
+ "unicode-ident",
 ]
 
 [[package]]
@@ -31,9 +32,9 @@ dependencies = [
 
 [[package]]
 name = "syn"
-version = "2.0.72"
+version = "2.0.66"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "dc4b9b9bf2add8093d3f2c0204471e951b2285580335de42f9d2534f3ae7a8af"
+checksum = "c42f3f41a2de00b01c0aaad383c5a45241efc8b2d1eda5661812fda5f3cdcff5"
 dependencies = [
  "proc-macro2",
  "quote",
diff --git a/rust/qemu-api/Cargo.lock b/rust/qemu-api/Cargo.lock
index e9c51a243a8..468293feedd 100644
--- a/rust/qemu-api/Cargo.lock
+++ b/rust/qemu-api/Cargo.lock
@@ -1,7 +1,54 @@
 # This file is automatically @generated by Cargo.
 # It is not intended for manual editing.
-version = 3
+version = 4
+
+[[package]]
+name = "proc-macro2"
+version = "1.0.84"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "ec96c6a92621310b51366f1e28d05ef11489516e93be030060e5fc12024a49d6"
+dependencies = [
+ "unicode-ident",
+]
 
 [[package]]
 name = "qemu_api"
 version = "0.1.0"
+dependencies = [
+ "qemu_api_macros",
+]
+
+[[package]]
+name = "qemu_api_macros"
+version = "0.1.0"
+dependencies = [
+ "proc-macro2",
+ "quote",
+ "syn",
+]
+
+[[package]]
+name = "quote"
+version = "1.0.36"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7"
+dependencies = [
+ "proc-macro2",
+]
+
+[[package]]
+name = "syn"
+version = "2.0.66"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "c42f3f41a2de00b01c0aaad383c5a45241efc8b2d1eda5661812fda5f3cdcff5"
+dependencies = [
+ "proc-macro2",
+ "quote",
+ "unicode-ident",
+]
+
+[[package]]
+name = "unicode-ident"
+version = "1.0.12"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
diff --git a/rust/qemu-api/Cargo.toml b/rust/qemu-api/Cargo.toml
index 3677def3fe2..db594c64083 100644
--- a/rust/qemu-api/Cargo.toml
+++ b/rust/qemu-api/Cargo.toml
@@ -14,6 +14,7 @@ keywords = []
 categories = []
 
 [dependencies]
+qemu_api_macros = { path = "../qemu-api-macros" }
 
 [features]
 default = []
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 07/14] rust: introduce alternative implementation of offset_of!
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (5 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 08/14] rust: do not use MaybeUninit::zeroed() Paolo Bonzini
                   ` (7 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

From: Junjie Mao <junjie.mao@hotmail.com>

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)].

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>
---
 rust/hw/char/pl011/Cargo.lock                 |   1 +
 rust/hw/char/pl011/src/device.rs              |   2 +-
 rust/qemu-api-macros/Cargo.toml               |   5 +-
 rust/qemu-api-macros/src/lib.rs               |  29 +++-
 rust/qemu-api/Cargo.lock                      |   7 +
 rust/qemu-api/Cargo.toml                      |   6 +-
 rust/qemu-api/build.rs                        |   8 +
 rust/qemu-api/meson.build                     |  12 +-
 rust/qemu-api/src/device_class.rs             |   8 +-
 rust/qemu-api/src/lib.rs                      |   4 +
 rust/qemu-api/src/offset_of.rs                | 161 ++++++++++++++++++
 rust/qemu-api/tests/tests.rs                  |   1 +
 subprojects/packagefiles/syn-2-rs/meson.build |   1 +
 13 files changed, 232 insertions(+), 13 deletions(-)
 create mode 100644 rust/qemu-api/src/offset_of.rs

diff --git a/rust/hw/char/pl011/Cargo.lock b/rust/hw/char/pl011/Cargo.lock
index 82028ddf793..087658ca72b 100644
--- a/rust/hw/char/pl011/Cargo.lock
+++ b/rust/hw/char/pl011/Cargo.lock
@@ -93,6 +93,7 @@ name = "qemu_api"
 version = "0.1.0"
 dependencies = [
  "qemu_api_macros",
+ "version_check",
 ]
 
 [[package]]
diff --git a/rust/hw/char/pl011/src/device.rs b/rust/hw/char/pl011/src/device.rs
index 5ffe1911376..c26d21e079d 100644
--- a/rust/hw/char/pl011/src/device.rs
+++ b/rust/hw/char/pl011/src/device.rs
@@ -29,7 +29,7 @@
 pub const PL011_FIFO_DEPTH: usize = 16_usize;
 
 #[repr(C)]
-#[derive(Debug, qemu_api_macros::Object)]
+#[derive(Debug, qemu_api_macros::Object, qemu_api_macros::offsets)]
 /// PL011 Device Model in QEMU
 pub struct PL011State {
     pub parent_obj: SysBusDevice,
diff --git a/rust/qemu-api-macros/Cargo.toml b/rust/qemu-api-macros/Cargo.toml
index 144cc3650fa..47fec2e4637 100644
--- a/rust/qemu-api-macros/Cargo.toml
+++ b/rust/qemu-api-macros/Cargo.toml
@@ -19,7 +19,10 @@ proc-macro = true
 [dependencies]
 proc-macro2 = "1"
 quote = "1"
-syn = "2"
+
+[dependencies.syn]
+version = "2"
+features= ["extra-traits"]
 
 # Do not include in any global workspace
 [workspace]
diff --git a/rust/qemu-api-macros/src/lib.rs b/rust/qemu-api-macros/src/lib.rs
index a4bc5d01ee8..472264159d6 100644
--- a/rust/qemu-api-macros/src/lib.rs
+++ b/rust/qemu-api-macros/src/lib.rs
@@ -3,8 +3,8 @@
 // SPDX-License-Identifier: GPL-2.0-or-later
 
 use proc_macro::TokenStream;
-use quote::quote;
-use syn::{parse_macro_input, DeriveInput};
+use quote::{quote, quote_spanned};
+use syn::{parse_macro_input, parse_quote, spanned::Spanned, Attribute, DeriveInput};
 
 #[proc_macro_derive(Object)]
 pub fn derive_object(input: TokenStream) -> TokenStream {
@@ -21,3 +21,28 @@ pub fn derive_object(input: TokenStream) -> TokenStream {
 
     TokenStream::from(expanded)
 }
+
+#[proc_macro_derive(offsets)]
+pub fn derive_offsets(input: TokenStream) -> TokenStream {
+    let input = parse_macro_input!(input as DeriveInput);
+    let repr_c: Attribute = parse_quote! { #[repr(C)] };
+
+    // All the work for expanding this macro is done in "with_offsets!",
+    // a macro in the qemu_api crate which re-parses the struct declaration;
+    // this derive macro is just a convenience.
+    //
+    // The with_offsets! macro expands to nothing if the compiler is new enough
+    // to have a stable offset_of.
+    let expanded = if !input.attrs.iter().any(|x| *x == repr_c) {
+        quote_spanned! {
+            input.span() =>
+            compile_error!("expected #[repr(C)] together with #[derive(offsets)]");
+        }
+    } else {
+        quote! {
+            ::qemu_api::with_offsets! { #input }
+        }
+    };
+
+    TokenStream::from(expanded)
+}
diff --git a/rust/qemu-api/Cargo.lock b/rust/qemu-api/Cargo.lock
index 468293feedd..371c6167918 100644
--- a/rust/qemu-api/Cargo.lock
+++ b/rust/qemu-api/Cargo.lock
@@ -16,6 +16,7 @@ name = "qemu_api"
 version = "0.1.0"
 dependencies = [
  "qemu_api_macros",
+ "version_check",
 ]
 
 [[package]]
@@ -52,3 +53,9 @@ name = "unicode-ident"
 version = "1.0.12"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
+
+[[package]]
+name = "version_check"
+version = "0.9.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
diff --git a/rust/qemu-api/Cargo.toml b/rust/qemu-api/Cargo.toml
index db594c64083..9c3a99522a9 100644
--- a/rust/qemu-api/Cargo.toml
+++ b/rust/qemu-api/Cargo.toml
@@ -16,6 +16,9 @@ categories = []
 [dependencies]
 qemu_api_macros = { path = "../qemu-api-macros" }
 
+[build-dependencies]
+version_check = "~0.9"
+
 [features]
 default = []
 allocator = []
@@ -24,4 +27,5 @@ allocator = []
 [workspace]
 
 [lints.rust]
-unexpected_cfgs = { level = "warn", check-cfg = ['cfg(MESON)', 'cfg(HAVE_GLIB_WITH_ALIGNED_ALLOC)'] }
+unexpected_cfgs = { level = "warn", check-cfg = ['cfg(MESON)', 'cfg(HAVE_GLIB_WITH_ALIGNED_ALLOC)',
+                                                 'cfg(has_offset_of)'] }
diff --git a/rust/qemu-api/build.rs b/rust/qemu-api/build.rs
index 419b154c2d2..0a68c3712f1 100644
--- a/rust/qemu-api/build.rs
+++ b/rust/qemu-api/build.rs
@@ -3,6 +3,7 @@
 // SPDX-License-Identifier: GPL-2.0-or-later
 
 use std::path::Path;
+use version_check as rustc;
 
 fn main() {
     if !Path::new("src/bindings.rs").exists() {
@@ -11,4 +12,11 @@ fn main() {
              (`ninja bindings.rs`) and copy them to src/bindings.rs, or build through meson."
         );
     }
+
+    // Check for available rustc features
+    if rustc::is_min_version("1.77.0").unwrap_or(false) {
+        println!("cargo:rustc-cfg=has_offset_of");
+    }
+
+    println!("cargo:rerun-if-changed=build.rs");
 }
diff --git a/rust/qemu-api/meson.build b/rust/qemu-api/meson.build
index 2b3dea59fb6..4ac33acced3 100644
--- a/rust/qemu-api/meson.build
+++ b/rust/qemu-api/meson.build
@@ -1,3 +1,9 @@
+_qemu_api_cfg = ['--cfg', 'MESON']
+# _qemu_api_cfg += ['--cfg', 'feature="allocator"']
+if rustc.version().version_compare('>=1.77.0')
+  _qemu_api_cfg += ['--cfg', 'has_offset_of']
+endif
+
 _qemu_api_rs = static_library(
   'qemu_api',
   structured_sources(
@@ -6,16 +12,14 @@ _qemu_api_rs = static_library(
       'src/c_str.rs',
       'src/definitions.rs',
       'src/device_class.rs',
+      'src/offset_of.rs',
       'src/zeroable.rs',
     ],
     {'.' : bindings_rs},
   ),
   override_options: ['rust_std=2021', 'build.rust_std=2021'],
   rust_abi: 'rust',
-  rust_args: [
-    '--cfg', 'MESON',
-    # '--cfg', 'feature="allocator"',
-  ],
+  rust_args: _qemu_api_cfg,
 )
 
 rust.test('rust-qemu-api-tests', _qemu_api_rs,
diff --git a/rust/qemu-api/src/device_class.rs b/rust/qemu-api/src/device_class.rs
index 5c305d945d3..ce3d5f50507 100644
--- a/rust/qemu-api/src/device_class.rs
+++ b/rust/qemu-api/src/device_class.rs
@@ -23,23 +23,23 @@ macro_rules! device_class_init {
 
 #[macro_export]
 macro_rules! define_property {
-    ($name:expr, $state:ty, $field:expr, $prop:expr, $type:expr, default = $defval:expr$(,)*) => {
+    ($name:expr, $state:ty, $field:ident, $prop:expr, $type:expr, default = $defval:expr$(,)*) => {
         $crate::bindings::Property {
             // use associated function syntax for type checking
             name: ::std::ffi::CStr::as_ptr($name),
             info: $prop,
-            offset: ::core::mem::offset_of!($state, $field) as isize,
+            offset: $crate::offset_of!($state, $field) as isize,
             set_default: true,
             defval: $crate::bindings::Property__bindgen_ty_1 { u: $defval.into() },
             ..$crate::zeroable::Zeroable::ZERO
         }
     };
-    ($name:expr, $state:ty, $field:expr, $prop:expr, $type:expr$(,)*) => {
+    ($name:expr, $state:ty, $field:ident, $prop:expr, $type:expr$(,)*) => {
         $crate::bindings::Property {
             // use associated function syntax for type checking
             name: ::std::ffi::CStr::as_ptr($name),
             info: $prop,
-            offset: ::core::mem::offset_of!($state, $field) as isize,
+            offset: $crate::offset_of!($state, $field) as isize,
             set_default: false,
             ..$crate::zeroable::Zeroable::ZERO
         }
diff --git a/rust/qemu-api/src/lib.rs b/rust/qemu-api/src/lib.rs
index 9c3be4f6489..92f1785d891 100644
--- a/rust/qemu-api/src/lib.rs
+++ b/rust/qemu-api/src/lib.rs
@@ -30,6 +30,7 @@ unsafe impl Sync for bindings::VMStateDescription {}
 pub mod c_str;
 pub mod definitions;
 pub mod device_class;
+pub mod offset_of;
 pub mod zeroable;
 
 use std::{
@@ -166,3 +167,6 @@ unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout) {
         }
     }
 }
+
+#[cfg(has_offset_of)]
+pub use std::mem::offset_of;
diff --git a/rust/qemu-api/src/offset_of.rs b/rust/qemu-api/src/offset_of.rs
new file mode 100644
index 00000000000..87db8607592
--- /dev/null
+++ b/rust/qemu-api/src/offset_of.rs
@@ -0,0 +1,161 @@
+// SPDX-License-Identifier: MIT
+
+/// This macro provides the same functionality as `core::mem::offset_of`,
+/// except that only one level of field access is supported.  The declaration
+/// of the struct must be wrapped with `with_offsets! { }`.
+///
+/// It is needed because `offset_of!` was only stabilized in Rust 1.77.
+#[cfg(not(has_offset_of))]
+#[macro_export]
+macro_rules! offset_of {
+    ($Container:ty, $field:ident) => {
+        <$Container>::OFFSET_TO__.$field
+    };
+}
+
+/// A wrapper for struct declarations, that allows using `offset_of!` in
+/// versions of Rust prior to 1.77
+#[macro_export]
+macro_rules! with_offsets {
+    // This method to generate field offset constants comes from:
+    //
+    //     https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=10a22a9b8393abd7b541d8fc844bc0df
+    //
+    // used under MIT license with permission of Yandros aka Daniel Henry-Mantilla
+    (
+        $(#[$struct_meta:meta])*
+        $struct_vis:vis
+        struct $StructName:ident {
+            $(
+                $(#[$field_meta:meta])*
+                $field_vis:vis
+                $field_name:ident : $field_ty:ty
+            ),*
+            $(,)?
+        }
+    ) => (
+        #[cfg(not(has_offset_of))]
+        const _: () = {
+            struct StructOffsetsHelper<T>(std::marker::PhantomData<T>);
+            const END_OF_PREV_FIELD: usize = 0;
+
+            // populate StructOffsetsHelper<T> with associated consts,
+            // one for each field
+            $crate::with_offsets! {
+                @struct $StructName
+                @names [ $($field_name)* ]
+                @tys [ $($field_ty ,)*]
+            }
+
+            // now turn StructOffsetsHelper<T>'s consts into a single struct,
+            // applying field visibility.  This provides better error messages
+            // than if offset_of! used StructOffsetsHelper::<T> directly.
+            pub
+            struct StructOffsets {
+                $(
+                    $field_vis
+                    $field_name: usize,
+                )*
+            }
+            impl $StructName {
+                pub
+                const OFFSET_TO__: StructOffsets = StructOffsets {
+                    $(
+                        $field_name: StructOffsetsHelper::<$StructName>::$field_name,
+                    )*
+                };
+            }
+        };
+    );
+
+    (
+        @struct $StructName:ident
+        @names []
+        @tys []
+    ) => ();
+
+    (
+        @struct $StructName:ident
+        @names [$field_name:ident $($other_names:tt)*]
+        @tys [$field_ty:ty , $($other_tys:tt)*]
+    ) => (
+        #[allow(non_local_definitions)]
+        #[allow(clippy::modulo_one)]
+        impl StructOffsetsHelper<$StructName> {
+            #[allow(nonstandard_style)]
+            const $field_name: usize = {
+                const ALIGN: usize = std::mem::align_of::<$field_ty>();
+                const TRAIL: usize = END_OF_PREV_FIELD % ALIGN;
+                END_OF_PREV_FIELD + (if TRAIL == 0 { 0usize } else { ALIGN - TRAIL })
+            };
+        }
+        const _: () = {
+            const END_OF_PREV_FIELD: usize =
+                StructOffsetsHelper::<$StructName>::$field_name +
+                std::mem::size_of::<$field_ty>()
+            ;
+            $crate::with_offsets! {
+                @struct $StructName
+                @names [$($other_names)*]
+                @tys [$($other_tys)*]
+            }
+        };
+    );
+}
+
+#[cfg(test)]
+mod tests {
+    use crate::offset_of;
+
+    #[repr(C)]
+    struct Foo {
+        a: u16,
+        b: u32,
+        c: u64,
+        d: u16,
+    }
+
+    #[repr(C)]
+    struct Bar {
+        pub a: u16,
+        pub b: u64,
+        c: Foo,
+        d: u64,
+    }
+
+    crate::with_offsets! {
+        #[repr(C)]
+        struct Bar {
+            pub a: u16,
+            pub b: u64,
+            c: Foo,
+            d: u64,
+        }
+    }
+
+    #[repr(C)]
+    pub struct Baz {
+        b: u32,
+        a: u8,
+    }
+    crate::with_offsets! {
+        #[repr(C)]
+        pub struct Baz {
+            b: u32,
+            a: u8,
+        }
+    }
+
+    #[test]
+    fn test_offset_of() {
+        const OFFSET_TO_C: usize = offset_of!(Bar, c);
+
+        assert_eq!(offset_of!(Bar, a), 0);
+        assert_eq!(offset_of!(Bar, b), 8);
+        assert_eq!(OFFSET_TO_C, 16);
+        assert_eq!(offset_of!(Bar, d), 40);
+
+        assert_eq!(offset_of!(Baz, b), 0);
+        assert_eq!(offset_of!(Baz, a), 4);
+    }
+}
diff --git a/rust/qemu-api/tests/tests.rs b/rust/qemu-api/tests/tests.rs
index 605bc99ed4c..96e413b75ee 100644
--- a/rust/qemu-api/tests/tests.rs
+++ b/rust/qemu-api/tests/tests.rs
@@ -20,6 +20,7 @@ fn test_device_decl_macros() {
         unmigratable: true,
     }
 
+    #[derive(qemu_api_macros::offsets)]
     #[repr(C)]
     #[derive(qemu_api_macros::Object)]
     pub struct DummyState {
diff --git a/subprojects/packagefiles/syn-2-rs/meson.build b/subprojects/packagefiles/syn-2-rs/meson.build
index a53335f3092..9f56ce1c24d 100644
--- a/subprojects/packagefiles/syn-2-rs/meson.build
+++ b/subprojects/packagefiles/syn-2-rs/meson.build
@@ -24,6 +24,7 @@ _syn_rs = static_library(
     '--cfg', 'feature="printing"',
     '--cfg', 'feature="clone-impls"',
     '--cfg', 'feature="proc-macro"',
+    '--cfg', 'feature="extra-traits"',
   ],
   dependencies: [
     quote_dep,
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 08/14] rust: do not use MaybeUninit::zeroed()
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (6 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 07/14] rust: introduce alternative implementation of offset_of! Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 09/14] rust: clean up detection of the language Paolo Bonzini
                   ` (6 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

MaybeUninit::zeroed() is handy is not available as a "const" function until
Rust 1.75.0.

Remove the default implemntation of Zeroable::ZERO, and write by hand
the definitions for those types that need it.  It may be possible to
add automatic implementation of the trait, via a procedural macro and/or
a trick similar to offset_of!, but do it the easy way for now.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 rust/qemu-api/src/zeroable.rs | 91 +++++++++++++++++++++++++++++------
 1 file changed, 77 insertions(+), 14 deletions(-)

diff --git a/rust/qemu-api/src/zeroable.rs b/rust/qemu-api/src/zeroable.rs
index 45ec95c9f70..13cdb2ccba5 100644
--- a/rust/qemu-api/src/zeroable.rs
+++ b/rust/qemu-api/src/zeroable.rs
@@ -1,23 +1,86 @@
 // SPDX-License-Identifier: GPL-2.0-or-later
 
+use std::ptr;
+
 /// Encapsulates the requirement that
-/// `MaybeUninit::<Self>::zeroed().assume_init()` does not cause
-/// undefined behavior.
+/// `MaybeUninit::<Self>::zeroed().assume_init()` does not cause undefined
+/// behavior.  This trait in principle could be implemented as just:
+///
+/// ```
+///     const ZERO: Self = unsafe {
+///         ::core::mem::MaybeUninit::<$crate::bindings::Property>::zeroed().assume_init()
+///     },
+/// ```
+///
+/// The need for a manual implementation is only because `zeroed()` cannot
+/// be used as a `const fn` prior to Rust 1.75.0. Once we can assume a new
+/// enough version of the compiler, we could provide a `#[derive(Zeroable)]`
+/// macro to check at compile-time that all struct fields are Zeroable, and
+/// use the above blanket implementation of the `ZERO` constant.
 ///
 /// # Safety
 ///
-/// Do not add this trait to a type unless all-zeroes is
-/// a valid value for the type.  In particular, remember that raw
-/// pointers can be zero, but references and `NonNull<T>` cannot
-/// unless wrapped with `Option<>`.
+/// Because the implementation of `ZERO` is manual, it does not make
+/// any assumption on the safety of `zeroed()`.  However, other users of the
+/// trait could use it that way.  Do not add this trait to a type unless
+/// all-zeroes is a valid value for the type.  In particular, remember that
+/// raw pointers can be zero, but references and `NonNull<T>` cannot
 pub unsafe trait Zeroable: Default {
-    /// SAFETY: If the trait was added to a type, then by definition
-    /// this is safe.
-    const ZERO: Self = unsafe { ::core::mem::MaybeUninit::<Self>::zeroed().assume_init() };
+    const ZERO: Self;
 }
 
-unsafe impl Zeroable for crate::bindings::Property__bindgen_ty_1 {}
-unsafe impl Zeroable for crate::bindings::Property {}
-unsafe impl Zeroable for crate::bindings::VMStateDescription {}
-unsafe impl Zeroable for crate::bindings::MemoryRegionOps__bindgen_ty_1 {}
-unsafe impl Zeroable for crate::bindings::MemoryRegionOps__bindgen_ty_2 {}
+unsafe impl Zeroable for crate::bindings::Property__bindgen_ty_1 {
+    const ZERO: Self = Self { i: 0 };
+}
+
+unsafe impl Zeroable for crate::bindings::Property {
+    const ZERO: Self = Self {
+        name: ptr::null(),
+        info: ptr::null(),
+        offset: 0,
+        bitnr: 0,
+        bitmask: 0,
+        set_default: false,
+        defval: Zeroable::ZERO,
+        arrayoffset: 0,
+        arrayinfo: ptr::null(),
+        arrayfieldsize: 0,
+        link_type: ptr::null(),
+    };
+}
+
+unsafe impl Zeroable for crate::bindings::VMStateDescription {
+    const ZERO: Self = Self {
+        name: ptr::null(),
+        unmigratable: false,
+        early_setup: false,
+        version_id: 0,
+        minimum_version_id: 0,
+        priority: crate::bindings::MigrationPriority::MIG_PRI_DEFAULT,
+        pre_load: None,
+        post_load: None,
+        pre_save: None,
+        post_save: None,
+        needed: None,
+        dev_unplug_pending: None,
+        fields: ptr::null(),
+        subsections: ptr::null(),
+    };
+}
+
+unsafe impl Zeroable for crate::bindings::MemoryRegionOps__bindgen_ty_1 {
+    const ZERO: Self = Self {
+        min_access_size: 0,
+        max_access_size: 0,
+        unaligned: false,
+        accepts: None,
+    };
+}
+
+unsafe impl Zeroable for crate::bindings::MemoryRegionOps__bindgen_ty_2 {
+    const ZERO: Self = Self {
+        min_access_size: 0,
+        max_access_size: 0,
+        unaligned: false,
+    };
+}
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 09/14] rust: clean up detection of the language
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (7 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 08/14] rust: do not use MaybeUninit::zeroed() Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 10/14] rust: allow version 1.63.0 of rustc Paolo Bonzini
                   ` (5 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Disable the detection code altogether if have_system == false.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 meson.build | 42 ++++++++++++++++++++++--------------------
 1 file changed, 22 insertions(+), 20 deletions(-)

diff --git a/meson.build b/meson.build
index fe72f9951ca..e411a8ae567 100644
--- a/meson.build
+++ b/meson.build
@@ -53,6 +53,17 @@ cpu = host_machine.cpu_family()
 
 target_dirs = config_host['TARGET_DIRS'].split()
 
+# type of binaries to build
+have_linux_user = false
+have_bsd_user = false
+have_system = false
+foreach target : target_dirs
+  have_linux_user = have_linux_user or target.endswith('linux-user')
+  have_bsd_user = have_bsd_user or target.endswith('bsd-user')
+  have_system = have_system or target.endswith('-softmmu')
+endforeach
+have_user = have_linux_user or have_bsd_user
+
 ############
 # Programs #
 ############
@@ -71,11 +82,13 @@ if host_os == 'darwin' and \
   all_languages += ['objc']
   objc = meson.get_compiler('objc')
 endif
-have_rust = false
-if not get_option('rust').disabled() and add_languages('rust', required: get_option('rust'), native: false) \
-    and add_languages('rust', required: get_option('rust'), native: true)
+
+have_rust = add_languages('rust', native: false,
+    required: get_option('rust').disable_auto_if(not have_system))
+have_rust = have_rust and add_languages('rust', native: true,
+    required: get_option('rust').disable_auto_if(not have_system))
+if have_rust
   rustc = meson.get_compiler('rust')
-  have_rust = true
   if rustc.version().version_compare('<1.80.0')
     if get_option('rust').enabled()
       error('rustc version ' + rustc.version() + ' is unsupported: Please upgrade to at least 1.80.0')
@@ -186,17 +199,6 @@ have_vhost_net_vdpa = have_vhost_vdpa and get_option('vhost_net').allowed()
 have_vhost_net_kernel = have_vhost_kernel and get_option('vhost_net').allowed()
 have_vhost_net = have_vhost_net_kernel or have_vhost_net_user or have_vhost_net_vdpa
 
-# type of binaries to build
-have_linux_user = false
-have_bsd_user = false
-have_system = false
-foreach target : target_dirs
-  have_linux_user = have_linux_user or target.endswith('linux-user')
-  have_bsd_user = have_bsd_user or target.endswith('bsd-user')
-  have_system = have_system or target.endswith('-softmmu')
-endforeach
-have_user = have_linux_user or have_bsd_user
-
 have_tools = get_option('tools') \
   .disable_auto_if(not have_system) \
   .allowed()
@@ -3317,7 +3319,7 @@ endif
 
 genh += configure_file(output: 'config-host.h', configuration: config_host_data)
 
-if have_rust and have_system
+if have_rust
   rustc_args = run_command(
     find_program('scripts/rust/rustc_args.py'),
     '--config-headers', meson.project_build_root() / 'config-host.h',
@@ -3937,7 +3939,7 @@ common_all = static_library('common',
                             implicit_include_directories: false,
                             dependencies: common_ss.all_dependencies())
 
-if have_rust and have_system
+if have_rust
   bindgen_args = [
     '--disable-header-comment',
     '--raw-line', '// @generated',
@@ -4091,7 +4093,7 @@ foreach target : target_dirs
   arch_srcs += target_specific.sources()
   arch_deps += target_specific.dependencies()
 
-  if have_rust and have_system
+  if have_rust and target_type == 'system'
     target_rust = rust_devices_ss.apply(config_target, strict: false)
     crates = []
     foreach dep : target_rust.dependencies()
@@ -4453,9 +4455,9 @@ else
 endif
 summary_info += {'Rust support':      have_rust}
 if have_rust
-  summary_info += {'rustc version':   rustc.version()}
-  summary_info += {'rustc':           ' '.join(rustc.cmd_array())}
   summary_info += {'Rust target':     config_host['RUST_TARGET_TRIPLE']}
+  summary_info += {'rustc':           ' '.join(rustc.cmd_array())}
+  summary_info += {'rustc version':   rustc.version()}
 endif
 option_cflags = (get_option('debug') ? ['-g'] : [])
 if get_option('optimization') != 'plain'
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 10/14] rust: allow version 1.63.0 of rustc
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (8 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 09/14] rust: clean up detection of the language Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 11/14] rust: do not use --generate-cstr Paolo Bonzini
                   ` (4 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

All constructs introduced by newer versions of Rust have been removed.

Apart from Debian 12, all other supported Linux distributions have
rustc 1.75.0 or newer.  This means that they only lack c"" literals
and stable offset_of!.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 meson.build | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/meson.build b/meson.build
index e411a8ae567..9c57d7e5c6d 100644
--- a/meson.build
+++ b/meson.build
@@ -89,11 +89,12 @@ have_rust = have_rust and add_languages('rust', native: true,
     required: get_option('rust').disable_auto_if(not have_system))
 if have_rust
   rustc = meson.get_compiler('rust')
-  if rustc.version().version_compare('<1.80.0')
+  if rustc.version().version_compare('<1.63.0')
     if get_option('rust').enabled()
-      error('rustc version ' + rustc.version() + ' is unsupported: Please upgrade to at least 1.80.0')
+      error('rustc version ' + rustc.version() + ' is unsupported. Please upgrade to at least 1.63.0')
     else
-      warning('rustc version ' + rustc.version() + ' is unsupported: Disabling Rust compilation. Please upgrade to at least 1.80.0 to use Rust.')
+      warning('rustc version ' + rustc.version() + ' is unsupported, disabling Rust compilation.')
+      message('Please upgrade to at least 1.63.0 to use Rust.')
       have_rust = false
     endif
   endif
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 11/14] rust: do not use --generate-cstr
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (9 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 10/14] rust: allow version 1.63.0 of rustc Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 12/14] rust: allow older version of bindgen Paolo Bonzini
                   ` (3 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

--generate-cstr is a good idea and generally the right thing to do,
but it is not available in Debian 12 and Ubuntu 22.04.  Work around
the absence.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 meson.build                       |  4 +++-
 rust/hw/char/pl011/src/device.rs  |  1 +
 rust/qemu-api/src/device_class.rs | 10 ++++++++++
 rust/qemu-api/tests/tests.rs      |  4 ++--
 4 files changed, 16 insertions(+), 3 deletions(-)

diff --git a/meson.build b/meson.build
index 9c57d7e5c6d..a083e3434b3 100644
--- a/meson.build
+++ b/meson.build
@@ -3941,13 +3941,15 @@ common_all = static_library('common',
                             dependencies: common_ss.all_dependencies())
 
 if have_rust
+  # We would like to use --generate-cstr, but it is only available
+  # starting with bindgen 0.66.0.  The oldest supported versions
+  # are in Ubuntu 22.04 (0.59.1) and Debian 12 (0.60.1).
   bindgen_args = [
     '--disable-header-comment',
     '--raw-line', '// @generated',
     '--ctypes-prefix', 'std::os::raw',
     '--formatter', 'rustfmt',
     '--generate-block',
-    '--generate-cstr',
     '--impl-debug',
     '--merge-extern-blocks',
     '--no-doc-comments',
diff --git a/rust/hw/char/pl011/src/device.rs b/rust/hw/char/pl011/src/device.rs
index c26d21e079d..1bcb6a0fba8 100644
--- a/rust/hw/char/pl011/src/device.rs
+++ b/rust/hw/char/pl011/src/device.rs
@@ -13,6 +13,7 @@
     bindings::{self, *},
     c_str,
     definitions::ObjectImpl,
+    device_class::TYPE_SYS_BUS_DEVICE,
 };
 
 use crate::{
diff --git a/rust/qemu-api/src/device_class.rs b/rust/qemu-api/src/device_class.rs
index ce3d5f50507..995267dd715 100644
--- a/rust/qemu-api/src/device_class.rs
+++ b/rust/qemu-api/src/device_class.rs
@@ -2,6 +2,10 @@
 // Author(s): Manos Pitsidianakis <manos.pitsidianakis@linaro.org>
 // SPDX-License-Identifier: GPL-2.0-or-later
 
+use std::ffi::CStr;
+
+use crate::bindings;
+
 #[macro_export]
 macro_rules! device_class_init {
     ($func:ident, props => $props:ident, realize_fn => $realize_fn:expr, legacy_reset_fn => $legacy_reset_fn:expr, vmsd => $vmsd:ident$(,)*) => {
@@ -83,3 +87,9 @@ macro_rules! vm_state_description {
         };
     }
 }
+
+// workaround until we can use --generate-cstr in bindgen.
+pub const TYPE_DEVICE: &CStr =
+    unsafe { CStr::from_bytes_with_nul_unchecked(bindings::TYPE_DEVICE) };
+pub const TYPE_SYS_BUS_DEVICE: &CStr =
+    unsafe { CStr::from_bytes_with_nul_unchecked(bindings::TYPE_SYS_BUS_DEVICE) };
diff --git a/rust/qemu-api/tests/tests.rs b/rust/qemu-api/tests/tests.rs
index 96e413b75ee..f932acd5c10 100644
--- a/rust/qemu-api/tests/tests.rs
+++ b/rust/qemu-api/tests/tests.rs
@@ -8,7 +8,7 @@
     bindings::*,
     c_str, declare_properties, define_property,
     definitions::{Class, ObjectImpl},
-    device_class_init, vm_state_description,
+    device_class, device_class_init, vm_state_description,
 };
 
 #[test]
@@ -56,7 +56,7 @@ impl ObjectImpl for DummyState {
         type Class = DummyClass;
         const TYPE_INFO: qemu_api::bindings::TypeInfo = qemu_api::type_info! { Self };
         const TYPE_NAME: &'static CStr = c_str!("dummy");
-        const PARENT_TYPE_NAME: Option<&'static CStr> = Some(TYPE_DEVICE);
+        const PARENT_TYPE_NAME: Option<&'static CStr> = Some(device_class::TYPE_DEVICE);
         const ABSTRACT: bool = false;
         const INSTANCE_INIT: Option<unsafe extern "C" fn(obj: *mut Object)> = None;
         const INSTANCE_POST_INIT: Option<unsafe extern "C" fn(obj: *mut Object)> = None;
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 12/14] rust: allow older version of bindgen
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (10 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 11/14] rust: do not use --generate-cstr Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 13/14] rust: make rustfmt optional Paolo Bonzini
                   ` (2 subsequent siblings)
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Cope with the old version that is provided in Debian 12.

--size_t-is-usize is needed on bindgen <0.61.0, and it was removed in
bindgen 0.65.0, so check for it in meson.build.

--merge-extern-blocks was added in 0.61.0.

--formatter rustfmt was added in 0.65.0 and is the default, so remove it.

Apart from Debian 12 and Ubuntu 22.04, all other supported distros have
version 0.66.x of bindgen or newer (or do not have bindgen at all).

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 docs/about/build-platforms.rst |  8 ++++++++
 meson.build                    | 29 +++++++++++++++++++++++++----
 2 files changed, 33 insertions(+), 4 deletions(-)

diff --git a/docs/about/build-platforms.rst b/docs/about/build-platforms.rst
index 8fd7da140a3..8173830c17a 100644
--- a/docs/about/build-platforms.rst
+++ b/docs/about/build-platforms.rst
@@ -107,6 +107,14 @@ Python build dependencies
   required, it may be necessary to fetch python modules from the Python
   Package Index (PyPI) via ``pip``, in order to build QEMU.
 
+Rust build dependencies
+  QEMU is generally conservative in adding new Rust dependencies, and all
+  of them are included in the distributed tarballs.  One exception is the
+  bindgen tool, which is too big to package and distribute.  The minimum
+  supported version of bindgen is 0.60.x.  For distributions that do not
+  include bindgen or have an older version, it is recommended to install
+  a newer version using ``cargo install bindgen-cli``.
+
 Optional build dependencies
   Build components whose absence does not affect the ability to build
   QEMU may not be available in distros, or may be too old for QEMU's
diff --git a/meson.build b/meson.build
index a083e3434b3..d78afb79d67 100644
--- a/meson.build
+++ b/meson.build
@@ -100,6 +100,21 @@ if have_rust
   endif
 endif
 
+bindgen = find_program('bindgen', required: get_option('rust').disable_auto_if(not have_rust))
+if not bindgen.found() or bindgen.version().version_compare('<0.60.0')
+  if get_option('rust').enabled()
+    error('bindgen version ' + bindgen.version() + ' is unsupported. You can install a new version with "cargo install bindgen-cli"')
+  else
+    if bindgen.found()
+      warning('bindgen version ' + bindgen.version() + ' is unsupported, disabling Rust compilation.')
+    else
+      warning('bindgen not found, disabling Rust compilation.')
+    endif
+    message('To use Rust you can install a new version with "cargo install bindgen-cli"')
+    have_rust = false
+  endif
+endif
+
 dtrace = not_found
 stap = not_found
 if 'dtrace' in get_option('trace_backends')
@@ -3943,15 +3958,13 @@ common_all = static_library('common',
 if have_rust
   # We would like to use --generate-cstr, but it is only available
   # starting with bindgen 0.66.0.  The oldest supported versions
-  # are in Ubuntu 22.04 (0.59.1) and Debian 12 (0.60.1).
+  # is 0.60.x (Debian 12 has 0.60.1) which introduces --allowlist-file.
   bindgen_args = [
     '--disable-header-comment',
     '--raw-line', '// @generated',
     '--ctypes-prefix', 'std::os::raw',
-    '--formatter', 'rustfmt',
     '--generate-block',
     '--impl-debug',
-    '--merge-extern-blocks',
     '--no-doc-comments',
     '--with-derive-default',
     '--no-layout-tests',
@@ -3960,6 +3973,12 @@ if have_rust
     '--allowlist-file', meson.project_source_root() + '/.*',
     '--allowlist-file', meson.project_build_root() + '/.*'
     ]
+  if bindgen.version().version_compare('<0.61.0')
+    # default in 0.61+
+    bindgen_args += ['--size_t-is-usize']
+  else
+    bindgen_args += ['--merge-extern-blocks']
+  endif
   c_enums = [
     'DeviceCategory',
     'GpioPolarity',
@@ -3995,7 +4014,7 @@ if have_rust
     dependencies: common_ss.all_dependencies(),
     output: 'bindings.rs',
     include_directories: include_directories('.', 'include'),
-    bindgen_version: ['>=0.69.4'],
+    bindgen_version: ['>=0.60.0'],
     args: bindgen_args,
     )
   subdir('rust')
@@ -4461,6 +4480,8 @@ if have_rust
   summary_info += {'Rust target':     config_host['RUST_TARGET_TRIPLE']}
   summary_info += {'rustc':           ' '.join(rustc.cmd_array())}
   summary_info += {'rustc version':   rustc.version()}
+  summary_info += {'bindgen':         bindgen.full_path()}
+  summary_info += {'bindgen version': bindgen.version()}
 endif
 option_cflags = (get_option('debug') ? ['-g'] : [])
 if get_option('optimization') != 'plain'
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 13/14] rust: make rustfmt optional
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (11 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 12/14] rust: allow older version of bindgen Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-22 10:09 ` [PATCH v2 14/14] dockerfiles: install bindgen from cargo on Ubuntu 22.04 Paolo Bonzini
  2024-10-24 11:28 ` [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 meson.build | 11 +++++++++++
 1 file changed, 11 insertions(+)

diff --git a/meson.build b/meson.build
index d78afb79d67..5e3501750a1 100644
--- a/meson.build
+++ b/meson.build
@@ -115,6 +115,10 @@ if not bindgen.found() or bindgen.version().version_compare('<0.60.0')
   endif
 endif
 
+if have_rust
+  rustfmt = find_program('rustfmt', required: false)
+endif
+
 dtrace = not_found
 stap = not_found
 if 'dtrace' in get_option('trace_backends')
@@ -3973,6 +3977,13 @@ if have_rust
     '--allowlist-file', meson.project_source_root() + '/.*',
     '--allowlist-file', meson.project_build_root() + '/.*'
     ]
+  if not rustfmt.found()
+    if bindgen.version().version_compare('<0.65.0')
+      bindgen_args += ['--no-rustfmt-bindings']
+    else
+      bindgen_args += ['--formatter', 'none']
+    endif
+  endif
   if bindgen.version().version_compare('<0.61.0')
     # default in 0.61+
     bindgen_args += ['--size_t-is-usize']
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* [PATCH v2 14/14] dockerfiles: install bindgen from cargo on Ubuntu 22.04
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (12 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 13/14] rust: make rustfmt optional Paolo Bonzini
@ 2024-10-22 10:09 ` Paolo Bonzini
  2024-10-24 11:28 ` [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-22 10:09 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

Because Ubuntu 22.04 has a very old version of bindgen, that
does not have the important option --allowlist-file, it will
not be able to use --enable-rust out of the box.  Instead,
install the latest version of bindgen-cli via "cargo install"
in the container, following the documentation.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 tests/docker/dockerfiles/ubuntu2204.docker |  5 +++++
 tests/lcitool/mappings.yml                 |  4 ++++
 tests/lcitool/refresh                      | 11 ++++++++++-
 3 files changed, 19 insertions(+), 1 deletion(-)

diff --git a/tests/docker/dockerfiles/ubuntu2204.docker b/tests/docker/dockerfiles/ubuntu2204.docker
index ce3aa39d4f3..245ac879622 100644
--- a/tests/docker/dockerfiles/ubuntu2204.docker
+++ b/tests/docker/dockerfiles/ubuntu2204.docker
@@ -149,6 +149,11 @@ ENV LANG "en_US.UTF-8"
 ENV MAKE "/usr/bin/make"
 ENV NINJA "/usr/bin/ninja"
 ENV PYTHON "/usr/bin/python3"
+ENV CARGO_HOME=/usr/local/cargo
+ENV PATH=$CARGO_HOME/bin:$PATH
+RUN DEBIAN_FRONTEND=noninteractive eatmydata \
+  apt install -y --no-install-recommends cargo
+RUN cargo install bindgen-cli
 # As a final step configure the user (if env is defined)
 ARG USER
 ARG UID
diff --git a/tests/lcitool/mappings.yml b/tests/lcitool/mappings.yml
index 9c5ac87c1c2..c90b23a00f1 100644
--- a/tests/lcitool/mappings.yml
+++ b/tests/lcitool/mappings.yml
@@ -1,4 +1,8 @@
 mappings:
+  # Too old on Ubuntu 22.04; we install it from cargo instead
+  bindgen:
+    Ubuntu2204:
+
   flake8:
     OpenSUSELeap15:
 
diff --git a/tests/lcitool/refresh b/tests/lcitool/refresh
index 0f16f4d525c..a46cbbdca41 100755
--- a/tests/lcitool/refresh
+++ b/tests/lcitool/refresh
@@ -137,6 +137,14 @@ fedora_rustup_nightly_extras = [
     'RUN /usr/local/cargo/bin/rustup run nightly cargo install bindgen-cli\n',
 ]
 
+ubuntu2204_bindgen_extras = [
+    "ENV CARGO_HOME=/usr/local/cargo\n",
+    'ENV PATH=$CARGO_HOME/bin:$PATH\n',
+    "RUN DEBIAN_FRONTEND=noninteractive eatmydata \\\n",
+    "  apt install -y --no-install-recommends cargo\n",
+    'RUN cargo install bindgen-cli\n',
+]
+
 def cross_build(prefix, targets):
     conf = "ENV QEMU_CONFIGURE_OPTS --cross-prefix=%s\n" % (prefix)
     targets = "ENV DEF_TARGET_LIST %s\n" % (targets)
@@ -157,7 +165,8 @@ try:
                         trailer="".join(debian12_extras))
     generate_dockerfile("fedora", "fedora-40")
     generate_dockerfile("opensuse-leap", "opensuse-leap-15")
-    generate_dockerfile("ubuntu2204", "ubuntu-2204")
+    generate_dockerfile("ubuntu2204", "ubuntu-2204",
+                        trailer="".join(ubuntu2204_bindgen_extras))
 
     #
     # Non-fatal Rust-enabled build
-- 
2.46.2



^ permalink raw reply related	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0
  2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
@ 2024-10-24  2:12   ` Junjie Mao
  2024-10-24 10:43   ` Alex Bennée
  1 sibling, 0 replies; 23+ messages in thread
From: Junjie Mao @ 2024-10-24  2:12 UTC (permalink / raw)
  To: Paolo Bonzini; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis, Zhao Liu


Paolo Bonzini <pbonzini@redhat.com> writes:

> Apply a patch that removes "let ... else" constructs, replacing them with
> "if let ... else" or "let ... = match ...".  "let ... else" was stabilized in
> Rust 1.65.0.
>
> Reviewed-by: Zhao Liu <zhao1.liu@intel.com>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>

Reviewed-by: Junjie Mao <junjie.mao@hotmail.com>

One question and one note below.

> ---
>  .gitattributes                                |  2 +
>  subprojects/bilge-impl-0.2-rs.wrap            |  1 +
>  subprojects/packagefiles/.gitattributes       |  1 +
>  .../packagefiles/bilge-impl-1.63.0.patch      | 45 +++++++++++++++++++
>  4 files changed, 49 insertions(+)
>  create mode 100644 subprojects/packagefiles/.gitattributes
>  create mode 100644 subprojects/packagefiles/bilge-impl-1.63.0.patch
>
> diff --git a/.gitattributes b/.gitattributes
> index 6dc6383d3d1..9ce7a19581a 100644
> --- a/.gitattributes
> +++ b/.gitattributes
> @@ -5,3 +5,5 @@
>  *.rs            diff=rust
>  *.rs.inc        diff=rust
>  Cargo.lock      diff=toml merge=binary
> +
> +*.patch         -text -whitespace
<snip>
> diff --git a/subprojects/packagefiles/.gitattributes b/subprojects/packagefiles/.gitattributes
> new file mode 100644
> index 00000000000..bf5b766d75d
> --- /dev/null
> +++ b/subprojects/packagefiles/.gitattributes
> @@ -0,0 +1 @@
> +/*.patch     -text

Do we really need unsetting the attrs for *.patch in both .gitattributes
and subprojects/packagefiles/.gitattributes? Is that related to the
different setting of -whitespace?

> diff --git a/subprojects/packagefiles/bilge-impl-1.63.0.patch b/subprojects/packagefiles/bilge-impl-1.63.0.patch
> new file mode 100644
> index 00000000000..987428a6d65
> --- /dev/null
> +++ b/subprojects/packagefiles/bilge-impl-1.63.0.patch
> @@ -0,0 +1,45 @@
> +--- a/src/shared/discriminant_assigner.rs
> ++++ b/src/shared/discriminant_assigner.rs

Just a note: when fetching this series using b4 am, I still get this
patch with LF line ending. Later when merging one may need to fetch this
specific commit directly from the git repository.

--
Best Regards
Junjie Mao


^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0
  2024-10-22 10:09 ` [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0 Paolo Bonzini
@ 2024-10-24  2:33   ` Junjie Mao
  2024-10-24  9:02     ` Paolo Bonzini
  0 siblings, 1 reply; 23+ messages in thread
From: Junjie Mao @ 2024-10-24  2:33 UTC (permalink / raw)
  To: Paolo Bonzini; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis


Paolo Bonzini <pbonzini@redhat.com> writes:

> Replay the configuration that would be computed by build.rs when compiling
> on a 1.63.0 compiler.
>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>

Reviewed-by: Junjie Mao <junjie.mao@hotmail.com>

One question below.

> ---
>  subprojects/packagefiles/proc-macro2-1-rs/meson.build | 4 +++-
>  1 file changed, 3 insertions(+), 1 deletion(-)
>
> diff --git a/subprojects/packagefiles/proc-macro2-1-rs/meson.build b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> index 818ec59336b..8e601b50ccc 100644
> --- a/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> +++ b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> @@ -15,7 +15,9 @@ _proc_macro2_rs = static_library(
>    rust_abi: 'rust',
>    rust_args: [
>      '--cfg', 'feature="proc-macro"',
> -    '--cfg', 'span_locations',

'span_locations' is not subject to any version check in build.rs. Is it
removed because of its performance penalty and the fact that we are not
using it anywhere?

--
Best Regards
Junjie Mao


^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock
  2024-10-22 10:09 ` [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock Paolo Bonzini
@ 2024-10-24  2:53   ` Junjie Mao
  2024-10-24  9:04     ` Paolo Bonzini
  0 siblings, 1 reply; 23+ messages in thread
From: Junjie Mao @ 2024-10-24  2:53 UTC (permalink / raw)
  To: Paolo Bonzini; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis


Paolo Bonzini <pbonzini@redhat.com> writes:

> The next commit will introduce a new build dependency for rust/qemu-api,
> version_check.  Before adding it, ensure that all dependencies are
> synchronized between the Meson- and cargo-based build systems.
>
> Note that it's not clear whether in the long term we'll use Cargo for
> anything; it seems that the three main uses (clippy, rustfmt, rustdoc)

Here's a fourth use case: "cargo expand" for debugging Rust macros.

> can all be invoked manually---either via glue code in QEMU, or by
> extending Meson to gain the relevant functionality.  However, for
> the time being we're stuck with Cargo so it should at least look at
> the same code as the rest of the build system.
>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
> ---
>  rust/hw/char/pl011/Cargo.lock   |  5 +++-
>  rust/qemu-api-macros/Cargo.lock | 11 ++++----
>  rust/qemu-api/Cargo.lock        | 49 ++++++++++++++++++++++++++++++++-
>  rust/qemu-api/Cargo.toml        |  1 +
>  4 files changed, 59 insertions(+), 7 deletions(-)
>
> diff --git a/rust/hw/char/pl011/Cargo.lock b/rust/hw/char/pl011/Cargo.lock
> index b58cebb186e..82028ddf793 100644
> --- a/rust/hw/char/pl011/Cargo.lock
> +++ b/rust/hw/char/pl011/Cargo.lock
> @@ -1,6 +1,6 @@
>  # This file is automatically @generated by Cargo.
>  # It is not intended for manual editing.
> -version = 3
> +version = 4

V4 was introduced in Rust 1.78. Should we stick to V3 as the MSRV is 1.63.0?

>
>  [[package]]
>  name = "arbitrary-int"
> @@ -91,6 +91,9 @@ dependencies = [
>  [[package]]
>  name = "qemu_api"
>  version = "0.1.0"
> +dependencies = [
> + "qemu_api_macros",
> +]

I would suggest adding those dependencies and version constraints in
Cargo.toml, not Cargo.lock. Future devices in Rust will have their
Cargo.lock derived from Cargo.toml of qemu-api and qemu-api-macro, so
missing version info there will force device writers to manually tweak
their Cargo.lock.

--
Best Regards
Junjie Mao


^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0
  2024-10-24  2:33   ` Junjie Mao
@ 2024-10-24  9:02     ` Paolo Bonzini
  2024-10-24  9:09       ` Paolo Bonzini
  0 siblings, 1 reply; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-24  9:02 UTC (permalink / raw)
  To: Junjie Mao; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis

On Thu, Oct 24, 2024 at 4:35 AM Junjie Mao <junjie.mao@hotmail.com> wrote:
>
>
> Paolo Bonzini <pbonzini@redhat.com> writes:
>
> > Replay the configuration that would be computed by build.rs when compiling
> > on a 1.63.0 compiler.
> >
> > Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
>
> Reviewed-by: Junjie Mao <junjie.mao@hotmail.com>
>
> One question below.
>
> > ---
> >  subprojects/packagefiles/proc-macro2-1-rs/meson.build | 4 +++-
> >  1 file changed, 3 insertions(+), 1 deletion(-)
> >
> > diff --git a/subprojects/packagefiles/proc-macro2-1-rs/meson.build b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> > index 818ec59336b..8e601b50ccc 100644
> > --- a/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> > +++ b/subprojects/packagefiles/proc-macro2-1-rs/meson.build
> > @@ -15,7 +15,9 @@ _proc_macro2_rs = static_library(
> >    rust_abi: 'rust',
> >    rust_args: [
> >      '--cfg', 'feature="proc-macro"',
> > -    '--cfg', 'span_locations',
>
> 'span_locations' is not subject to any version check in build.rs. Is it
> removed because of its performance penalty and the fact that we are not
> using it anywhere?

The docs say "When executing in a procedural macro context, the
returned line/column are only meaningful if compiled with a nightly
toolchain. The stable toolchain does not have this information
available. When executing outside of a procedural macro, such as
main.rs or build.rs, the line/column are always meaningful regardless
of toolchain". So for our case it seems useless.

Paolo



^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock
  2024-10-24  2:53   ` Junjie Mao
@ 2024-10-24  9:04     ` Paolo Bonzini
  0 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-24  9:04 UTC (permalink / raw)
  To: Junjie Mao; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis

On Thu, Oct 24, 2024 at 5:01 AM Junjie Mao <junjie.mao@hotmail.com> wrote:
>
>
> Paolo Bonzini <pbonzini@redhat.com> writes:
>
> > The next commit will introduce a new build dependency for rust/qemu-api,
> > version_check.  Before adding it, ensure that all dependencies are
> > synchronized between the Meson- and cargo-based build systems.
> >
> > Note that it's not clear whether in the long term we'll use Cargo for
> > anything; it seems that the three main uses (clippy, rustfmt, rustdoc)
>
> Here's a fourth use case: "cargo expand" for debugging Rust macros.
>
> > can all be invoked manually---either via glue code in QEMU, or by
> > extending Meson to gain the relevant functionality.  However, for
> > the time being we're stuck with Cargo so it should at least look at
> > the same code as the rest of the build system.
> >
> > Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
> > ---
> >  rust/hw/char/pl011/Cargo.lock   |  5 +++-
> >  rust/qemu-api-macros/Cargo.lock | 11 ++++----
> >  rust/qemu-api/Cargo.lock        | 49 ++++++++++++++++++++++++++++++++-
> >  rust/qemu-api/Cargo.toml        |  1 +
> >  4 files changed, 59 insertions(+), 7 deletions(-)
> >
> > diff --git a/rust/hw/char/pl011/Cargo.lock b/rust/hw/char/pl011/Cargo.lock
> > index b58cebb186e..82028ddf793 100644
> > --- a/rust/hw/char/pl011/Cargo.lock
> > +++ b/rust/hw/char/pl011/Cargo.lock
> > @@ -1,6 +1,6 @@
> >  # This file is automatically @generated by Cargo.
> >  # It is not intended for manual editing.
> > -version = 3
> > +version = 4
>
> V4 was introduced in Rust 1.78. Should we stick to V3 as the MSRV is 1.63.0?

Good point.

> I would suggest adding those dependencies and version constraints in
> Cargo.toml, not Cargo.lock. Future devices in Rust will have their
> Cargo.lock derived from Cargo.toml of qemu-api and qemu-api-macro, so
> missing version info there will force device writers to manually tweak
> their Cargo.lock.

Ok, will do.

Paolo



^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0
  2024-10-24  9:02     ` Paolo Bonzini
@ 2024-10-24  9:09       ` Paolo Bonzini
  0 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-24  9:09 UTC (permalink / raw)
  To: Junjie Mao; +Cc: qemu-devel, berrange, kwolf, manos.pitsidianakis

On Thu, Oct 24, 2024 at 11:02 AM Paolo Bonzini <pbonzini@redhat.com> wrote:
> > 'span_locations' is not subject to any version check in build.rs. Is it
> > removed because of its performance penalty and the fact that we are not
> > using it anywhere?
>
> The docs say "When executing in a procedural macro context, the
> returned line/column are only meaningful if compiled with a nightly
> toolchain. The stable toolchain does not have this information
> available. When executing outside of a procedural macro, such as
> main.rs or build.rs, the line/column are always meaningful regardless
> of toolchain". So for our case it seems useless.

Ah, it's also removed because we don't specify it the feature in
qemu-api-macros/Cargo.toml, and therefore the build script does not
emit the corresponding cargo:rustc-cfg line.

$ OUT_DIR=$PWD/proc-macro2-0b9b0b4e3b86e043 \
   RUSTC=$(rustup +1.63.0 which  rustc) \
   proc-macro2-0b9b0b4e3b86e043/build-script-build
cargo:rustc-cfg=no_source_text
cargo:rustc-cfg=no_literal_byte_character
cargo:rustc-cfg=no_literal_c_string
cargo:rerun-if-changed=build/probe.rs
cargo:rustc-cfg=wrap_proc_macro
cargo:rerun-if-env-changed=RUSTC_BOOTSTRAP

Paolo



^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0
  2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
  2024-10-24  2:12   ` Junjie Mao
@ 2024-10-24 10:43   ` Alex Bennée
  1 sibling, 0 replies; 23+ messages in thread
From: Alex Bennée @ 2024-10-24 10:43 UTC (permalink / raw)
  To: Paolo Bonzini
  Cc: qemu-devel, berrange, kwolf, junjie.mao, manos.pitsidianakis,
	Zhao Liu

Paolo Bonzini <pbonzini@redhat.com> writes:

> Apply a patch that removes "let ... else" constructs, replacing them with
> "if let ... else" or "let ... = match ...".  "let ... else" was stabilized in
> Rust 1.65.0.
>
> Reviewed-by: Zhao Liu <zhao1.liu@intel.com>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>

My configure on a clean build dir blows up with:

  bilge-0.2-rs| Downloading bilge-impl-0.2-rs source from https://crates.io/api/v1/crates/bilge-impl/0.2.0/download
  Downloading: 100%|███████████████████████████████████████████████████████████████████████████████████████████████████████████████████████████| 23.9k/23.9k 5.30MB/s eta 00:00
  bilge-0.2-rs| Applying diff file "bilge-impl-1.63.0.patch"
  bilge-0.2-rs| patching file src/shared/discriminant_assigner.rs
  bilge-0.2-rs| Hunk #1 FAILED at 26 (different line endings).
  bilge-0.2-rs| 1 out of 1 hunk FAILED -- saving rejects to file src/shared/discriminant_assigner.rs.rej
  bilge-0.2-rs| patching file src/shared/fallback.rs
  bilge-0.2-rs| Hunk #1 FAILED at 22 (different line endings).
  bilge-0.2-rs| 1 out of 1 hunk FAILED -- saving rejects to file src/shared/fallback.rs.rej

  ../../subprojects/bilge-0.2.0/meson.build:9:0: ERROR: Failed to apply diff file "bilge-impl-1.63.0.patch"

  A full log can be found at /home/alex/lsrc/qemu.git/builds/rust/meson-logs/meson-log.txt

  ERROR: meson setup failed

So do I have some hidden state somewhere?

-- 
Alex Bennée
Virtualisation Tech Lead @ Linaro

^ permalink raw reply	[flat|nested] 23+ messages in thread

* Re: [PATCH v2 00/14] rust: allow older versions of rustc and bindgen
  2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
                   ` (13 preceding siblings ...)
  2024-10-22 10:09 ` [PATCH v2 14/14] dockerfiles: install bindgen from cargo on Ubuntu 22.04 Paolo Bonzini
@ 2024-10-24 11:28 ` Paolo Bonzini
  14 siblings, 0 replies; 23+ messages in thread
From: Paolo Bonzini @ 2024-10-24 11:28 UTC (permalink / raw)
  To: qemu-devel; +Cc: berrange, kwolf, junjie.mao, manos.pitsidianakis

On 10/22/24 12:09, Paolo Bonzini wrote:
> This is the second of three series needed to enable Rust for all CI
> jobs (the third is due to differences in the functionality between
> C and Rust implementations of PL011, for which I have sent the RFC
> a little earlier).
> 
> My overall patch queue can be found at branch rust-next of my git
> repository https://gitlab.com/bonzini/qemu.git.
> 
> Note that this requires "meson subprojects update --reset" in order to do
> an incremental build if you have already downloaded the Rust subprojects.
> While I have a solution for that (modeled after scripts/git-submodule.sh),
> I first need to check with the Meson folks whether my script is using only
> stable interfaces.

This is the contents of subprojects/packagefiles/bilge-impl-1.63.0.patch 
in base64 encoding.  You can replace it in your tree by executing the 
command:

base64 -d <<\EOF > subprojects/packagefiles/bilge-impl-1.63.0.patch

LS0tIGEvc3JjL3NoYXJlZC9kaXNjcmltaW5hbnRfYXNzaWduZXIucnMKKysrIGIvc3JjL3NoYXJl
ZC9kaXNjcmltaW5hbnRfYXNzaWduZXIucnMKQEAgLTI2LDIwICsyNiwyMCBAQAogICAgICAgICBs
ZXQgZGlzY3JpbWluYW50X2V4cHIgPSAmZGlzY3JpbWluYW50LjE7DQogICAgICAgICBsZXQgdmFy
aWFudF9uYW1lID0gJnZhcmlhbnQuaWRlbnQ7DQogDQotICAgICAgICBsZXQgRXhwcjo6TGl0KEV4
cHJMaXQgeyBsaXQ6IExpdDo6SW50KGludCksIC4uIH0pID0gZGlzY3JpbWluYW50X2V4cHIgZWxz
ZSB7DQorICAgICAgICBpZiBsZXQgRXhwcjo6TGl0KEV4cHJMaXQgeyBsaXQ6IExpdDo6SW50KGlu
dCksIC4uIH0pID0gZGlzY3JpbWluYW50X2V4cHIgew0KKyAgICAgICAgICAgIGxldCBkaXNjcmlt
aW5hbnRfdmFsdWU6IHUxMjggPSBpbnQuYmFzZTEwX3BhcnNlKCkudW53cmFwX29yX2Vsc2UodW5y
ZWFjaGFibGUpOw0KKyAgICAgICAgICAgIGlmIGRpc2NyaW1pbmFudF92YWx1ZSA+IHNlbGYubWF4
X3ZhbHVlKCkgew0KKyAgICAgICAgICAgICAgICBhYm9ydCEodmFyaWFudCwgIlZhbHVlIG9mIHZh
cmlhbnQgZXhjZWVkcyB0aGUgZ2l2ZW4gbnVtYmVyIG9mIGJpdHMiKQ0KKyAgICAgICAgICAgIH0N
CisNCisgICAgICAgICAgICBTb21lKGRpc2NyaW1pbmFudF92YWx1ZSkNCisgICAgICAgIH0gZWxz
ZSB7DQogICAgICAgICAgICAgYWJvcnQhKA0KICAgICAgICAgICAgICAgICBkaXNjcmltaW5hbnRf
ZXhwciwNCiAgICAgICAgICAgICAgICAgInZhcmlhbnQgYHt9YCBpcyBub3QgYSBudW1iZXIiLCB2
YXJpYW50X25hbWU7DQogICAgICAgICAgICAgICAgIGhlbHAgPSAib25seSBsaXRlcmFsIGludGVn
ZXJzIGN1cnJlbnRseSBzdXBwb3J0ZWQiDQogICAgICAgICAgICAgKQ0KLSAgICAgICAgfTsNCi0N
Ci0gICAgICAgIGxldCBkaXNjcmltaW5hbnRfdmFsdWU6IHUxMjggPSBpbnQuYmFzZTEwX3BhcnNl
KCkudW53cmFwX29yX2Vsc2UodW5yZWFjaGFibGUpOw0KLSAgICAgICAgaWYgZGlzY3JpbWluYW50
X3ZhbHVlID4gc2VsZi5tYXhfdmFsdWUoKSB7DQotICAgICAgICAgICAgYWJvcnQhKHZhcmlhbnQs
ICJWYWx1ZSBvZiB2YXJpYW50IGV4Y2VlZHMgdGhlIGdpdmVuIG51bWJlciBvZiBiaXRzIikNCiAg
ICAgICAgIH0NCi0NCi0gICAgICAgIFNvbWUoZGlzY3JpbWluYW50X3ZhbHVlKQ0KICAgICB9DQog
DQogICAgIGZuIGFzc2lnbigmbXV0IHNlbGYsIHZhcmlhbnQ6ICZWYXJpYW50KSAtPiB1MTI4IHsN
Ci0tLSBhL3NyYy9zaGFyZWQvZmFsbGJhY2sucnMKKysrIGIvc3JjL3NoYXJlZC9mYWxsYmFjay5y
cwpAQCAtMjIsOCArMjIsOSBAQAogICAgICAgICAgICAgfQ0KICAgICAgICAgICAgIFVubmFtZWQo
ZmllbGRzKSA9PiB7DQogICAgICAgICAgICAgICAgIGxldCB2YXJpYW50X2ZpZWxkcyA9IGZpZWxk
cy51bm5hbWVkLml0ZXIoKTsNCi0gICAgICAgICAgICAgICAgbGV0IE9rKGZhbGxiYWNrX3ZhbHVl
KSA9IHZhcmlhbnRfZmllbGRzLmV4YWN0bHlfb25lKCkgZWxzZSB7DQotICAgICAgICAgICAgICAg
ICAgICBhYm9ydCEodmFyaWFudCwgImZhbGxiYWNrIHZhcmlhbnQgbXVzdCBoYXZlIGV4YWN0bHkg
b25lIGZpZWxkIjsgaGVscCA9ICJ1c2Ugb25seSBvbmUgZmllbGQgb3IgY2hhbmdlIHRvIGEgdW5p
dCB2YXJpYW50IikNCisgICAgICAgICAgICAgICAgbGV0IGZhbGxiYWNrX3ZhbHVlID0gbWF0Y2gg
dmFyaWFudF9maWVsZHMuZXhhY3RseV9vbmUoKSB7DQorICAgICAgICAgICAgICAgICAgICBPayhv
aykgPT4gb2ssDQorICAgICAgICAgICAgICAgICAgICBfID0+IGFib3J0ISh2YXJpYW50LCAiZmFs
bGJhY2sgdmFyaWFudCBtdXN0IGhhdmUgZXhhY3RseSBvbmUgZmllbGQiOyBoZWxwID0gInVzZSBv
bmx5IG9uZSBmaWVsZCBvciBjaGFuZ2UgdG8gYSB1bml0IHZhcmlhbnQiKQ0KICAgICAgICAgICAg
ICAgICB9Ow0KIA0KICAgICAgICAgICAgICAgICBpZiAhaXNfbGFzdF92YXJpYW50IHsNCg==

Paolo



^ permalink raw reply	[flat|nested] 23+ messages in thread

end of thread, other threads:[~2024-10-24 11:29 UTC | newest]

Thread overview: 23+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2024-10-22 10:09 [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 01/14] rust: patch bilge-impl to allow compilation with 1.63.0 Paolo Bonzini
2024-10-24  2:12   ` Junjie Mao
2024-10-24 10:43   ` Alex Bennée
2024-10-22 10:09 ` [PATCH v2 02/14] rust: fix cfgs of proc-macro2 for 1.63.0 Paolo Bonzini
2024-10-24  2:33   ` Junjie Mao
2024-10-24  9:02     ` Paolo Bonzini
2024-10-24  9:09       ` Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 03/14] rust: use std::os::raw instead of core::ffi Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 04/14] rust: introduce a c_str macro Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 05/14] rust: silence unknown warnings for the sake of old compilers Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 06/14] rust: synchronize dependencies between subprojects and Cargo.lock Paolo Bonzini
2024-10-24  2:53   ` Junjie Mao
2024-10-24  9:04     ` Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 07/14] rust: introduce alternative implementation of offset_of! Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 08/14] rust: do not use MaybeUninit::zeroed() Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 09/14] rust: clean up detection of the language Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 10/14] rust: allow version 1.63.0 of rustc Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 11/14] rust: do not use --generate-cstr Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 12/14] rust: allow older version of bindgen Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 13/14] rust: make rustfmt optional Paolo Bonzini
2024-10-22 10:09 ` [PATCH v2 14/14] dockerfiles: install bindgen from cargo on Ubuntu 22.04 Paolo Bonzini
2024-10-24 11:28 ` [PATCH v2 00/14] rust: allow older versions of rustc and bindgen Paolo Bonzini

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).