public inbox for git-commits@fedoraproject.org
help / color / mirror / Atom feed
* [rpms/rust-pyo3] rawhide: Include pending upstream fix for py315 on 32-bit / big-endian
@ 2026-06-27 12:23 Fabio Valentini
0 siblings, 0 replies; only message in thread
From: Fabio Valentini @ 2026-06-27 12:23 UTC (permalink / raw)
To: git-commits
A new commit has been pushed.
Repo : rpms/rust-pyo3
Branch : rawhide
Commit : 68152293df196ab383e40d5b4f0bd5eecb68a9c5
Author : Fabio Valentini <decathorpe@gmail.com>
Date : 2026-06-27T14:22:52+02:00
Stats : +244/-0 in 2 file(s)
URL : https://src.fedoraproject.org/rpms/rust-pyo3/c/68152293df196ab383e40d5b4f0bd5eecb68a9c5?branch=rawhide
Log:
Include pending upstream fix for py315 on 32-bit / big-endian
---
diff --git a/6150.patch b/6150.patch
new file mode 100644
index 0000000..a302712
--- /dev/null
+++ b/6150.patch
@@ -0,0 +1,242 @@
+From fe9022ff24f65b120a662199074048f031935732 Mon Sep 17 00:00:00 2001
+From: David Hewitt <mail@davidhewitt.dev>
+Date: Sun, 21 Jun 2026 21:31:16 +0100
+Subject: [PATCH 1/4] fix 3.15+ `append_to_inittab` on platforms which aren't
+ 64-bit little-endian
+
+---
+ src/impl_/pymodule.rs | 51 +++++++++++++++++++++++++++++-------------
+ src/internal_tricks.rs | 7 ++++++
+ 2 files changed, 42 insertions(+), 16 deletions(-)
+
+diff --git a/src/impl_/pymodule.rs b/src/impl_/pymodule.rs
+index 25e7415fa61..47f5ef31993 100644
+--- a/src/impl_/pymodule.rs
++++ b/src/impl_/pymodule.rs
+@@ -30,6 +30,8 @@ use portable_atomic::AtomicI64;
+
+ #[cfg(not(any(PyPy, GraalPy)))]
+ use crate::exceptions::PyImportError;
++#[cfg(not(all(Py_LIMITED_API, Py_GIL_DISABLED)))]
++use crate::internal_tricks::array_ptr_as_mut;
+ use crate::prelude::PyTypeMethods;
+ use crate::{
+ ffi,
+@@ -94,9 +96,7 @@ impl ModuleDef {
+ let ffi_def = UnsafeCell::new(ffi::PyModuleDef {
+ m_name: name.as_ptr(),
+ m_doc: doc.as_ptr(),
+- // TODO: would be slightly nicer to use `[T]::as_mut_ptr()` here,
+- // but that requires mut ptr deref on MSRV.
+- m_slots: slots.0.get() as _,
++ m_slots: array_ptr_as_mut(slots.pep_489_slots.get()),
+ ..INIT
+ });
+
+@@ -235,9 +235,10 @@ impl ModuleDef {
+ .map(|py_module| py_module.clone_ref(py))
+ }
+ }
++
+ #[cfg(Py_3_15)]
+ pub fn get_slots(&'static self) -> *mut ffi::PySlot {
+- self.slots.0.get() as *mut ffi::PySlot
++ array_ptr_as_mut(self.slots.pep_820_slots.get())
+ }
+ }
+
+@@ -307,10 +308,7 @@ const MAX_SLOTS_WITH_TRAILING_NULL: usize = MAX_SLOTS + 1;
+ /// actual slots pushed due to the need to have a zeroed element on the end.
+ pub struct PyModuleSlotsBuilder {
+ // values (initially all zeroed)
+- #[cfg(not(Py_3_15))]
+- values: [ffi::PyModuleDef_Slot; MAX_SLOTS_WITH_TRAILING_NULL],
+- #[cfg(Py_3_15)]
+- values: [ffi::PySlot; MAX_SLOTS_WITH_TRAILING_NULL],
++ slots: PyModuleSlots,
+ // current length
+ len: usize,
+ }
+@@ -325,7 +323,15 @@ impl PyModuleSlotsBuilder {
+ #[allow(clippy::new_without_default)]
+ pub const fn new() -> Self {
+ Self {
+- values: [unsafe { core::mem::zeroed() }; MAX_SLOTS_WITH_TRAILING_NULL],
++ slots: PyModuleSlots {
++ #[cfg(Py_3_15)]
++ pep_820_slots: UnsafeCell::new(
++ [unsafe { core::mem::zeroed() }; MAX_SLOTS_WITH_TRAILING_NULL],
++ ),
++ pep_489_slots: UnsafeCell::new(
++ [unsafe { core::mem::zeroed() }; MAX_SLOTS_WITH_TRAILING_NULL],
++ ),
++ },
+ len: 0,
+ }
+ }
+@@ -426,7 +432,7 @@ impl PyModuleSlotsBuilder {
+ }
+
+ pub const fn build(self) -> PyModuleSlots {
+- PyModuleSlots(UnsafeCell::new(self.values))
++ self.slots
+ }
+
+ #[cfg(not(Py_3_15))]
+@@ -437,7 +443,7 @@ impl PyModuleSlotsBuilder {
+ self.len < MAX_SLOTS,
+ "Cannot add more than MAX_SLOTS slots to a PyModuleSlots",
+ );
+- self.values[self.len] = ffi::PyModuleDef_Slot { slot, value };
++ self.slots.pep_489_slots.get_mut()[self.len] = ffi::PyModuleDef_Slot { slot, value };
+ self.len += 1;
+ self
+ }
+@@ -448,17 +454,30 @@ impl PyModuleSlotsBuilder {
+ self.len < MAX_SLOTS,
+ "Cannot add more than MAX_SLOTS slots to a PyModuleSlots",
+ );
+- self.values[self.len] = value;
++ self.slots.pep_820_slots.get_mut()[self.len] = value;
++ self.slots.pep_489_slots.get_mut()[self.len] = ffi::PyModuleDef_Slot {
++ slot: value.sl_id as c_int,
++ // SAFETY: interpreting the `PySlot` value as a void* for the slot
++ //
++ // This will need removing if any future `PySlot` values can't be
++ // represented in legacy slots.
++ value: unsafe { value.anon2.sl_ptr },
++ };
+ self.len += 1;
+ self
+ }
+ }
+
+ /// Wrapper to safely store module slots, to be used in a `ModuleDef`.
+-#[cfg(not(Py_3_15))]
+-pub struct PyModuleSlots(UnsafeCell<[ffi::PyModuleDef_Slot; MAX_SLOTS_WITH_TRAILING_NULL]>);
+-#[cfg(Py_3_15)]
+-pub struct PyModuleSlots(UnsafeCell<[ffi::PySlot; MAX_SLOTS_WITH_TRAILING_NULL]>);
++pub struct PyModuleSlots {
++ #[cfg(Py_3_15)]
++ pep_820_slots: UnsafeCell<[ffi::PySlot; MAX_SLOTS_WITH_TRAILING_NULL]>,
++ /// PEP 489 slots
++ ///
++ /// These are still needed on 3.15+ for `append_to_inittab` and for as long as
++ /// we continue to emit `PyInit_<name>` entry points on 3.15+.
++ pep_489_slots: UnsafeCell<[ffi::PyModuleDef_Slot; MAX_SLOTS_WITH_TRAILING_NULL]>,
++}
+
+ // It might be possible to avoid this with SyncUnsafeCell in the future
+ //
+diff --git a/src/internal_tricks.rs b/src/internal_tricks.rs
+index 0d21c69dcc7..04d6a8f56d7 100644
+--- a/src/internal_tricks.rs
++++ b/src/internal_tricks.rs
+@@ -55,3 +55,10 @@ pub(crate) fn box_into_non_null<T>(b: Box<T>) -> NonNull<T> {
+ // SAFETY: `Box::into_raw` guarantees an non-null pointer
+ unsafe { NonNull::new_unchecked(Box::into_raw(b)) }
+ }
++
++/// Replacement for the unstable `<*mut [T; N]>::as_mut_ptr` method, which avoids
++/// possibility of type getting lost from using e.g. `.cast()` to change array
++/// type to point to the data.
++pub(crate) const fn array_ptr_as_mut<T, const N: usize>(ptr: *mut [T; N]) -> *mut T {
++ ptr.cast()
++}
+
+From 272d8f12e57076b8bc052cb8a4cc7c45307b89e3 Mon Sep 17 00:00:00 2001
+From: David Hewitt <mail@davidhewitt.dev>
+Date: Fri, 26 Jun 2026 08:06:31 +0100
+Subject: [PATCH 2/4] fix test conditional code
+
+---
+ src/impl_/pymodule.rs | 13 +++++++++----
+ 1 file changed, 9 insertions(+), 4 deletions(-)
+
+diff --git a/src/impl_/pymodule.rs b/src/impl_/pymodule.rs
+index 47f5ef31993..a207e48b01d 100644
+--- a/src/impl_/pymodule.rs
++++ b/src/impl_/pymodule.rs
+@@ -627,7 +627,10 @@ mod tests {
+
+ #[cfg(not(all(Py_LIMITED_API, Py_GIL_DISABLED)))]
+ unsafe {
+- assert_eq!((*module_def.ffi_def.get()).m_slots, SLOTS.0.get().cast());
++ assert_eq!(
++ (*module_def.ffi_def.get()).m_slots,
++ SLOTS.pep_489_slots.get().cast()
++ );
+ }
+ #[cfg(Py_3_15)]
+ {
+@@ -639,17 +642,17 @@ mod tests {
+ #[test]
+ #[cfg(panic = "unwind")]
+ fn test_build_maximal_slots() {
+- let builder = PyModuleSlotsBuilder::new()
++ let mut builder = PyModuleSlotsBuilder::new()
+ .with_mod_exec(module_exec)
+ .with_name(c"test_module")
+ .with_doc(c"some doc")
+ .with_gil_used(false)
+ .with_abi_info();
+- let second_last = builder.values[builder.len - 1];
+- let last = builder.values[builder.len];
+
+ #[cfg(Py_3_15)]
+ {
++ let second_last = builder.slots.pep_820_slots.get_mut()[builder.len - 1];
++ let last = builder.slots.pep_820_slots.get_mut()[builder.len];
+ let zeroed = unsafe { core::mem::zeroed() };
+ fn raw_bytes(inst: &ffi::PySlot) -> &[u8] {
+ unsafe {
+@@ -665,6 +668,8 @@ mod tests {
+ }
+ #[cfg(not(Py_3_15))]
+ {
++ let second_last = builder.slots.pep_489_slots.get_mut()[builder.len - 1];
++ let last = builder.slots.pep_489_slots.get_mut()[builder.len];
+ let zeroed = ffi::PyModuleDef_Slot::default();
+ assert!(last == zeroed);
+ assert!(second_last != zeroed);
+
+From a8a989e7875498187bc9a15942ddca301f6e24e4 Mon Sep 17 00:00:00 2001
+From: David Hewitt <mail@davidhewitt.dev>
+Date: Fri, 26 Jun 2026 08:53:54 +0100
+Subject: [PATCH 3/4] fix missing import
+
+---
+ src/impl_/pymodule.rs | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/src/impl_/pymodule.rs b/src/impl_/pymodule.rs
+index a207e48b01d..9161d487cd6 100644
+--- a/src/impl_/pymodule.rs
++++ b/src/impl_/pymodule.rs
+@@ -30,7 +30,7 @@ use portable_atomic::AtomicI64;
+
+ #[cfg(not(any(PyPy, GraalPy)))]
+ use crate::exceptions::PyImportError;
+-#[cfg(not(all(Py_LIMITED_API, Py_GIL_DISABLED)))]
++#[cfg(any(not(all(Py_LIMITED_API, Py_GIL_DISABLED)), Py_3_15))]
+ use crate::internal_tricks::array_ptr_as_mut;
+ use crate::prelude::PyTypeMethods;
+ use crate::{
+
+From b41e08b3c260793473d8147aee8379245c9a00b5 Mon Sep 17 00:00:00 2001
+From: David Hewitt <mail@davidhewitt.dev>
+Date: Fri, 26 Jun 2026 11:46:30 +0100
+Subject: [PATCH 4/4] newsfragment
+
+---
+ newsfragments/6150.fixed.md | 1 +
+ 1 file changed, 1 insertion(+)
+ create mode 100644 newsfragments/6150.fixed.md
+
+diff --git a/newsfragments/6150.fixed.md b/newsfragments/6150.fixed.md
+new file mode 100644
+index 00000000000..9587b91d6dd
+--- /dev/null
++++ b/newsfragments/6150.fixed.md
+@@ -0,0 +1 @@
++Fix `append_to_inittab` and `PyInit_<module>` internal module definition corruption on 32-bit and big-endian platforms.
diff --git a/rust-pyo3.spec b/rust-pyo3.spec
index 1523486..4570151 100644
--- a/rust-pyo3.spec
+++ b/rust-pyo3.spec
@@ -21,6 +21,8 @@ Patch: pyo3-fix-metadata.diff
# * make unsafe subinterpreter support available via cfg flag:
# https://bugzilla.redhat.com/show_bug.cgi?id=2298403
Patch2: 0001-Make-unsafe-subinterpreter-support-available-via-cfg.patch
+# * pending upstream fix for Python 3.15 on 32-bit / big-endian architectures
+Patch3: https://github.com/PyO3/pyo3/pull/6150.patch
BuildRequires: cargo-rpm-macros >= 24
BuildRequires: dos2unix
^ permalink raw reply related [flat|nested] only message in thread
only message in thread, other threads:[~2026-06-27 12:23 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-06-27 12:23 [rpms/rust-pyo3] rawhide: Include pending upstream fix for py315 on 32-bit / big-endian Fabio Valentini
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox