From 20e7861a97b0dde43bf5d26454710ccb9681b3ac Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Sun, 6 Sep 2026 13:16:17 +0100 Subject: [PATCH 01/14] ci: update ffi-check for PyPy symbol mangling change --- noxfile.py | 8 +- pyo3-ffi-check/macro/src/lib.rs | 10 +- pyo3-ffi-check/src/main.rs | 25 ++- pyo3-ffi/src/abstract_.rs | 196 ++++++++++++---------- pyo3-ffi/src/boolobject.rs | 2 +- pyo3-ffi/src/bytearrayobject.rs | 12 +- pyo3-ffi/src/bytesobject.rs | 16 +- pyo3-ffi/src/ceval.rs | 50 +++--- pyo3-ffi/src/codecs.rs | 4 +- pyo3-ffi/src/complexobject.rs | 6 +- pyo3-ffi/src/cpython/abstract_.rs | 16 +- pyo3-ffi/src/cpython/code.rs | 1 + pyo3-ffi/src/cpython/context.rs | 5 + pyo3-ffi/src/cpython/dictobject.rs | 1 + pyo3-ffi/src/cpython/floatobject.rs | 6 + pyo3-ffi/src/cpython/funcobject.rs | 6 + pyo3-ffi/src/cpython/marshal.rs | 4 +- pyo3-ffi/src/cpython/pyframe.rs | 7 + pyo3-ffi/src/cpython/pystate.rs | 4 +- pyo3-ffi/src/cpython/pythonrun.rs | 2 +- pyo3-ffi/src/descrobject.rs | 8 +- pyo3-ffi/src/dictobject.rs | 36 ++-- pyo3-ffi/src/fileobject.rs | 8 +- pyo3-ffi/src/floatobject.rs | 6 +- pyo3-ffi/src/genericaliasobject.rs | 2 +- pyo3-ffi/src/import.rs | 22 +-- pyo3-ffi/src/intrcheck.rs | 4 +- pyo3-ffi/src/iterobject.rs | 4 +- pyo3-ffi/src/listobject.rs | 22 +-- pyo3-ffi/src/longobject.rs | 42 ++--- pyo3-ffi/src/memoryobject.rs | 8 +- pyo3-ffi/src/methodobject.rs | 4 +- pyo3-ffi/src/modsupport.rs | 26 +-- pyo3-ffi/src/moduleobject.rs | 14 +- pyo3-ffi/src/object.rs | 96 +++++------ pyo3-ffi/src/objimpl.rs | 26 +-- pyo3-ffi/src/osmodule.rs | 2 +- pyo3-ffi/src/pybuffer.rs | 16 +- pyo3-ffi/src/pycapsule.rs | 22 +-- pyo3-ffi/src/pyerrors.rs | 76 ++++----- pyo3-ffi/src/pylifecycle.rs | 8 +- pyo3-ffi/src/pymem.rs | 8 +- pyo3-ffi/src/pystate.rs | 24 +-- pyo3-ffi/src/pystrtod.rs | 4 +- pyo3-ffi/src/pythonrun.rs | 8 +- pyo3-ffi/src/pythread.rs | 2 +- pyo3-ffi/src/refcount.rs | 32 +++- pyo3-ffi/src/setobject.rs | 16 +- pyo3-ffi/src/sliceobject.rs | 8 +- pyo3-ffi/src/structseq.rs | 2 +- pyo3-ffi/src/sysmodule.rs | 8 +- pyo3-ffi/src/traceback.rs | 4 +- pyo3-ffi/src/tupleobject.rs | 12 +- pyo3-ffi/src/unicodeobject.rs | 92 +++++----- pyo3-ffi/src/warnings.rs | 6 +- pyo3-ffi/src/weakrefobject.rs | 6 +- pytests/noxfile.py | 6 +- pytests/pyproject.toml | 1 - pytests/tests/test_datetime.py | 131 --------------- pytests/tests/test_datetime_hypothesis.py | 133 +++++++++++++++ pytests/tests/test_othermod.py | 24 --- pytests/tests/test_othermod_hypothesis.py | 27 +++ 62 files changed, 735 insertions(+), 652 deletions(-) create mode 100644 pytests/tests/test_datetime_hypothesis.py create mode 100644 pytests/tests/test_othermod_hypothesis.py diff --git a/noxfile.py b/noxfile.py index a02f101beb8..9d51b469d81 100644 --- a/noxfile.py +++ b/noxfile.py @@ -1334,13 +1334,7 @@ def load_pkg_versions(): @nox.session(name="ffi-check") def ffi_check(session: nox.Session): - extra_args = [] - # This flag can be useful for debugging ffi-check errors, but overall the - # short message format is easier to read - if "--long-message-format" not in session.posargs: - extra_args.append("--message-format=short") - - _run_cargo(session, "run", _FFI_CHECK, *extra_args) + _run_cargo(session, "run", _FFI_CHECK) _check_raw_dylib_macro(session) diff --git a/pyo3-ffi-check/macro/src/lib.rs b/pyo3-ffi-check/macro/src/lib.rs index 6676a755c25..5426e04146a 100644 --- a/pyo3-ffi-check/macro/src/lib.rs +++ b/pyo3-ffi-check/macro/src/lib.rs @@ -6,7 +6,7 @@ use std::{ }; use proc_macro2::{Ident, Span, TokenStream, TokenTree}; -use pyo3_build_config::PythonVersion; +use pyo3_build_config::{PythonImplementation, PythonVersion}; use quote::quote; const PY_3_15: PythonVersion = PythonVersion { @@ -195,6 +195,7 @@ pub fn for_all_fields(input: proc_macro::TokenStream) -> proc_macro::TokenStream let bindgen_field_ident = if (pyo3_build_config::get().target_abi().version() >= PY_3_12) && struct_name == "PyObject" && field_name == "ob_refcnt" + && pyo3_build_config::get().target_abi().implementation() != PythonImplementation::PyPy { // PyObject since 3.12 implements ob_refcnt as a union; bindgen creates // an anonymous name for the field @@ -495,6 +496,13 @@ const EXCLUDED_SYMBOLS: &[&str] = &[ "PyOS_BeforeFork", "PyOS_AfterFork_Parent", "PyOS_AfterFork_Child", + // TODO: PyPy 3.12 declares these symbols in its headers but does not export them. + "PyMapping_Length", + "PyObject_IS_GC", + "PyObject_Length", + "PySequence_In", + "PySequence_Length", + "PyType_ClearCache", ]; // Assert at compile time that `MACRO_EXCLUSIONS` and `EXCLUDED_SYMBOLS` are disjoint diff --git a/pyo3-ffi-check/src/main.rs b/pyo3-ffi-check/src/main.rs index 444613db1a4..818f0e973ed 100644 --- a/pyo3-ffi-check/src/main.rs +++ b/pyo3-ffi-check/src/main.rs @@ -2,6 +2,12 @@ use std::{ffi::CStr, process::exit}; use pyo3_ffi_check_definitions::{bindgen as bindings, pyo3_ffi}; +/// Functions which don't have equivalent addresses between pyo3-ffi and bindgen. +static SPECIAL_CASE_FUNCTIONS: &[&str] = &[ + "PyEval_RestoreThread", // PyO3 adds special handling for pthread_exit + "PyGILState_Ensure", // Similar to PyEval_RestoreThread +]; + fn main() { println!( "comparing pyo3-ffi against headers generated for {}", @@ -142,8 +148,23 @@ fn main() { ($name:ident, [$($modifiers:tt)*] ($($arg_types:tt)*)) => {{ // Check functions have the same number of arguments #[allow(deprecated)] - { pyo3_ffi::$name as $($modifiers)* fn($($arg_types)*) -> _ }; - bindings::$name as $($modifiers)* fn($($arg_types)*) -> _; + let pyo3_ffi_fn = { pyo3_ffi::$name as $($modifiers)* fn($($arg_types)*) -> _ }; + let bindgen_fn = bindings::$name as $($modifiers)* fn($($arg_types)*) -> _; + + // Check function addresses are the same (i.e. link is configured as expected). + // This will also trigger build errors if linker fails to find the symbol pyo3-ffi + // is expecting. + if !std::ptr::fn_addr_eq(pyo3_ffi_fn, bindgen_fn) + && !SPECIAL_CASE_FUNCTIONS.contains(&stringify!($name)) + { + failed = true; + println!( + "error: function address of {} differs between pyo3_ffi ({:p}) and bindgen ({:p})", + stringify!($name), + pyo3_ffi_fn, + bindgen_fn + ); + } // TODO: can probably sniff arg types by binding sniffers for each argument position and then passing // those inside `todo_args!` to use type inference for each argument. diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index ecd80cfcde3..bb60ad00d96 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -29,24 +29,24 @@ extern_libpython! { ))] #[cfg_attr(PyPy, link_name = "PyPyObject_CallNoArgs")] pub fn PyObject_CallNoArgs(func: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_Call")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Call")] pub fn PyObject_Call( callable_object: *mut PyObject, args: *mut PyObject, kw: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_CallObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_CallObject")] pub fn PyObject_CallObject( callable_object: *mut PyObject, args: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_CallFunction")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_CallFunction")] pub fn PyObject_CallFunction( callable_object: *mut PyObject, format: *const c_char, ... ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_CallMethod")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_CallMethod")] pub fn PyObject_CallMethod( o: *mut PyObject, method: *const c_char, @@ -62,9 +62,9 @@ extern_libpython! { ... ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_CallFunctionObjArgs")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_CallFunctionObjArgs")] pub fn PyObject_CallFunctionObjArgs(callable: *mut PyObject, ...) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_CallMethodObjArgs")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_CallMethodObjArgs")] pub fn PyObject_CallMethodObjArgs( o: *mut PyObject, method: *mut PyObject, @@ -76,7 +76,7 @@ extern_libpython! { pub fn PyVectorcall_NARGS(nargsf: size_t) -> Py_ssize_t; #[cfg_attr(not(any(Py_3_12, PyPy)), link_name = "_PyVectorcall_Call")] // symbol made public in 3.12 - #[cfg_attr(PyPy, link_name = "PyPyVectorcall_Call")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyVectorcall_Call")] pub fn PyVectorcall_Call( callable: *mut PyObject, tuple: *mut PyObject, @@ -106,43 +106,46 @@ extern_libpython! { nargsf: size_t, kwnames: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_Type")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Type")] pub fn PyObject_Type(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Size")] pub fn PyObject_Size(o: *mut PyObject) -> Py_ssize_t; // PyObject_Length is a direct alias for PyObject_Size - #[cfg_attr(not(PyPy), link_name = "PyObject_Size")] - #[cfg_attr(PyPy, link_name = "PyPyObject_Size")] + #[cfg_attr( + any(not(PyPy), all(PyPy, Py_3_12)), + link_name = "PyObject_Size" + )] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Size")] pub fn PyObject_Length(o: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyObject_GetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetItem")] pub fn PyObject_GetItem(o: *mut PyObject, key: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_SetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_SetItem")] pub fn PyObject_SetItem(o: *mut PyObject, key: *mut PyObject, v: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_DelItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_DelItemString")] pub fn PyObject_DelItemString(o: *mut PyObject, key: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_DelItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_DelItem")] pub fn PyObject_DelItem(o: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_Format")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Format")] pub fn PyObject_Format(obj: *mut PyObject, format_spec: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_GetIter")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetIter")] pub fn PyObject_GetIter(arg1: *mut PyObject) -> *mut PyObject; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyObject_GetAIter")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetAIter")] pub fn PyObject_GetAIter(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyIter_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyIter_Check")] pub fn PyIter_Check(obj: *mut PyObject) -> c_int; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyAIter_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyAIter_Check")] pub fn PyAIter_Check(obj: *mut PyObject) -> c_int; #[cfg(Py_3_14)] #[cfg_attr(PyPy, link_name = "PyPyIter_NextItem")] pub fn PyIter_NextItem(iter: *mut PyObject, item: *mut *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyIter_Next")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyIter_Next")] pub fn PyIter_Next(arg1: *mut PyObject) -> *mut PyObject; #[cfg(all(not(PyPy), Py_3_10))] #[cfg_attr(PyPy, link_name = "PyPyIter_Send")] @@ -152,149 +155,158 @@ extern_libpython! { presult: *mut *mut PyObject, ) -> PySendResult; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Check")] pub fn PyNumber_Check(o: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Add")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Add")] pub fn PyNumber_Add(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Subtract")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Subtract")] pub fn PyNumber_Subtract(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Multiply")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Multiply")] pub fn PyNumber_Multiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_MatrixMultiply")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_MatrixMultiply")] pub fn PyNumber_MatrixMultiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_FloorDivide")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_FloorDivide")] pub fn PyNumber_FloorDivide(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_TrueDivide")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_TrueDivide")] pub fn PyNumber_TrueDivide(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Remainder")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Remainder")] pub fn PyNumber_Remainder(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Divmod")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Divmod")] pub fn PyNumber_Divmod(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Power")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Power")] pub fn PyNumber_Power(o1: *mut PyObject, o2: *mut PyObject, o3: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Negative")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Negative")] pub fn PyNumber_Negative(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Positive")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Positive")] pub fn PyNumber_Positive(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Absolute")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Absolute")] pub fn PyNumber_Absolute(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Invert")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Invert")] pub fn PyNumber_Invert(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Lshift")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Lshift")] pub fn PyNumber_Lshift(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Rshift")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Rshift")] pub fn PyNumber_Rshift(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_And")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_And")] pub fn PyNumber_And(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Xor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Xor")] pub fn PyNumber_Xor(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Or")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Or")] pub fn PyNumber_Or(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyIndex_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyIndex_Check")] pub fn PyIndex_Check(o: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Index")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Index")] pub fn PyNumber_Index(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_AsSsize_t")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_AsSsize_t")] pub fn PyNumber_AsSsize_t(o: *mut PyObject, exc: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Long")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Long")] pub fn PyNumber_Long(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_Float")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_Float")] pub fn PyNumber_Float(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceAdd")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceAdd")] pub fn PyNumber_InPlaceAdd(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceSubtract")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceSubtract")] pub fn PyNumber_InPlaceSubtract(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceMultiply")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceMultiply")] pub fn PyNumber_InPlaceMultiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceMatrixMultiply")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceMatrixMultiply")] pub fn PyNumber_InPlaceMatrixMultiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceFloorDivide")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceFloorDivide")] pub fn PyNumber_InPlaceFloorDivide(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceTrueDivide")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceTrueDivide")] pub fn PyNumber_InPlaceTrueDivide(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceRemainder")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceRemainder")] pub fn PyNumber_InPlaceRemainder(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlacePower")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlacePower")] pub fn PyNumber_InPlacePower( o1: *mut PyObject, o2: *mut PyObject, o3: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceLshift")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceLshift")] pub fn PyNumber_InPlaceLshift(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceRshift")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceRshift")] pub fn PyNumber_InPlaceRshift(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceAnd")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceAnd")] pub fn PyNumber_InPlaceAnd(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceXor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceXor")] pub fn PyNumber_InPlaceXor(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyNumber_InPlaceOr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceOr")] pub fn PyNumber_InPlaceOr(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; pub fn PyNumber_ToBase(n: *mut PyObject, base: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Check")] pub fn PySequence_Check(o: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Size")] pub fn PySequence_Size(o: *mut PyObject) -> Py_ssize_t; // PySequence_Length is a direct alias for PySequence_Size - #[cfg_attr(not(PyPy), link_name = "PySequence_Size")] - #[cfg_attr(PyPy, link_name = "PyPySequence_Size")] + #[cfg_attr( + any(not(PyPy), all(PyPy, Py_3_12)), + link_name = "PySequence_Size" + )] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Size")] pub fn PySequence_Length(o: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPySequence_Concat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Concat")] pub fn PySequence_Concat(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_Repeat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Repeat")] pub fn PySequence_Repeat(o: *mut PyObject, count: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_GetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_GetItem")] pub fn PySequence_GetItem(o: *mut PyObject, i: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_GetSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_GetSlice")] pub fn PySequence_GetSlice(o: *mut PyObject, i1: Py_ssize_t, i2: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_SetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_SetItem")] pub fn PySequence_SetItem(o: *mut PyObject, i: Py_ssize_t, v: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_DelItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_DelItem")] pub fn PySequence_DelItem(o: *mut PyObject, i: Py_ssize_t) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_SetSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_SetSlice")] pub fn PySequence_SetSlice( o: *mut PyObject, i1: Py_ssize_t, i2: Py_ssize_t, v: *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_DelSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_DelSlice")] pub fn PySequence_DelSlice(o: *mut PyObject, i1: Py_ssize_t, i2: Py_ssize_t) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_Tuple")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Tuple")] pub fn PySequence_Tuple(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_List")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_List")] pub fn PySequence_List(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_Fast")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Fast")] pub fn PySequence_Fast(o: *mut PyObject, m: *const c_char) -> *mut PyObject; pub fn PySequence_Count(o: *mut PyObject, value: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPySequence_Contains")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Contains")] pub fn PySequence_Contains(seq: *mut PyObject, ob: *mut PyObject) -> c_int; // PySequence_In is a direct alias for PySequence_Contains - #[cfg_attr(not(PyPy), link_name = "PySequence_Contains")] - #[cfg_attr(PyPy, link_name = "PyPySequence_Contains")] + #[cfg_attr( + any(not(PyPy), all(PyPy, Py_3_12)), + link_name = "PySequence_Contains" + )] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Contains")] pub fn PySequence_In(o: *mut PyObject, value: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySequence_Index")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Index")] pub fn PySequence_Index(o: *mut PyObject, value: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPySequence_InPlaceConcat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_InPlaceConcat")] pub fn PySequence_InPlaceConcat(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySequence_InPlaceRepeat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_InPlaceRepeat")] pub fn PySequence_InPlaceRepeat(o: *mut PyObject, count: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMapping_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Check")] pub fn PyMapping_Check(o: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyMapping_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Size")] pub fn PyMapping_Size(o: *mut PyObject) -> Py_ssize_t; // PyMapping_Length is a direct alias for PyMapping_Size - #[cfg_attr(not(PyPy), link_name = "PyMapping_Size")] - #[cfg_attr(PyPy, link_name = "PyPyMapping_Size")] + #[cfg_attr( + any(not(PyPy), all(PyPy, Py_3_12)), + link_name = "PyMapping_Size" + )] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Size")] pub fn PyMapping_Length(o: *mut PyObject) -> Py_ssize_t; } @@ -309,9 +321,9 @@ pub unsafe fn PyMapping_DelItem(o: *mut PyObject, key: *mut PyObject) -> c_int { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyMapping_HasKeyString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_HasKeyString")] pub fn PyMapping_HasKeyString(o: *mut PyObject, key: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyMapping_HasKey")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_HasKey")] pub fn PyMapping_HasKey(o: *mut PyObject, key: *mut PyObject) -> c_int; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyMapping_HasKeyWithError")] @@ -319,13 +331,13 @@ extern_libpython! { #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyMapping_HasKeyStringWithError")] pub fn PyMapping_HasKeyStringWithError(o: *mut PyObject, key: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyMapping_Keys")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Keys")] pub fn PyMapping_Keys(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMapping_Values")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Values")] pub fn PyMapping_Values(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMapping_Items")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Items")] pub fn PyMapping_Items(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMapping_GetItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_GetItemString")] pub fn PyMapping_GetItemString(o: *mut PyObject, key: *const c_char) -> *mut PyObject; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyMapping_GetOptionalItem")] @@ -341,14 +353,14 @@ extern_libpython! { key: *const c_char, result: *mut *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyMapping_SetItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_SetItemString")] pub fn PyMapping_SetItemString( o: *mut PyObject, key: *const c_char, value: *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_IsInstance")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_IsInstance")] pub fn PyObject_IsInstance(object: *mut PyObject, typeorclass: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_IsSubclass")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_IsSubclass")] pub fn PyObject_IsSubclass(object: *mut PyObject, typeorclass: *mut PyObject) -> c_int; } diff --git a/pyo3-ffi/src/boolobject.rs b/pyo3-ffi/src/boolobject.rs index bf55c1dedc6..ccdf1cf188d 100644 --- a/pyo3-ffi/src/boolobject.rs +++ b/pyo3-ffi/src/boolobject.rs @@ -64,6 +64,6 @@ pub unsafe fn Py_IsFalse(x: *mut PyObject) -> c_int { // skipped Py_RETURN_FALSE extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyBool_FromLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBool_FromLong")] pub fn PyBool_FromLong(arg1: c_long) -> *mut PyObject; } diff --git a/pyo3-ffi/src/bytearrayobject.rs b/pyo3-ffi/src/bytearrayobject.rs index 713a352c530..9304d3ac4b4 100644 --- a/pyo3-ffi/src/bytearrayobject.rs +++ b/pyo3-ffi/src/bytearrayobject.rs @@ -28,16 +28,16 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyByteArray_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_FromObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_FromObject")] pub fn PyByteArray_FromObject(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_Concat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_Concat")] pub fn PyByteArray_Concat(a: *mut PyObject, b: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_FromStringAndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_FromStringAndSize")] pub fn PyByteArray_FromStringAndSize(string: *const c_char, len: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_Size")] pub fn PyByteArray_Size(bytearray: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_AsString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_AsString")] pub fn PyByteArray_AsString(bytearray: *mut PyObject) -> *mut c_char; - #[cfg_attr(PyPy, link_name = "PyPyByteArray_Resize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyByteArray_Resize")] pub fn PyByteArray_Resize(bytearray: *mut PyObject, len: Py_ssize_t) -> c_int; } diff --git a/pyo3-ffi/src/bytesobject.rs b/pyo3-ffi/src/bytesobject.rs index c99e0dabefa..4417e635735 100644 --- a/pyo3-ffi/src/bytesobject.rs +++ b/pyo3-ffi/src/bytesobject.rs @@ -27,25 +27,25 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyBytes_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBytes_FromStringAndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromStringAndSize")] pub fn PyBytes_FromStringAndSize(arg1: *const c_char, arg2: Py_ssize_t) -> *mut PyObject; pub fn PyBytes_FromString(arg1: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyBytes_FromObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromObject")] pub fn PyBytes_FromObject(arg1: *mut PyObject) -> *mut PyObject; // skipped PyBytes_FromFormatV //#[cfg_attr(PyPy, link_name = "PyPyBytes_FromFormatV")] //pub fn PyBytes_FromFormatV(arg1: *const c_char, arg2: va_list) // -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyBytes_FromFormat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromFormat")] pub fn PyBytes_FromFormat(arg1: *const c_char, ...) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyBytes_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_Size")] pub fn PyBytes_Size(arg1: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyBytes_AsString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_AsString")] pub fn PyBytes_AsString(arg1: *mut PyObject) -> *mut c_char; pub fn PyBytes_Repr(arg1: *mut PyObject, arg2: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyBytes_Concat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_Concat")] pub fn PyBytes_Concat(arg1: *mut *mut PyObject, arg2: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyBytes_ConcatAndDel")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_ConcatAndDel")] pub fn PyBytes_ConcatAndDel(arg1: *mut *mut PyObject, arg2: *mut PyObject); pub fn PyBytes_DecodeEscape( arg1: *const c_char, @@ -54,7 +54,7 @@ extern_libpython! { arg4: Py_ssize_t, arg5: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyBytes_AsStringAndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_AsStringAndSize")] pub fn PyBytes_AsStringAndSize( obj: *mut PyObject, s: *mut *mut c_char, diff --git a/pyo3-ffi/src/ceval.rs b/pyo3-ffi/src/ceval.rs index c07f53c4e40..e73e9a3a5b0 100644 --- a/pyo3-ffi/src/ceval.rs +++ b/pyo3-ffi/src/ceval.rs @@ -3,7 +3,7 @@ use crate::pytypedefs::PyThreadState; use core::ffi::{c_char, c_int, c_void}; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyEval_EvalCode")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_EvalCode")] pub fn PyEval_EvalCode( arg1: *mut PyObject, arg2: *mut PyObject, @@ -26,7 +26,7 @@ extern_libpython! { #[cfg(not(Py_3_13))] #[deprecated(note = "Python 3.9")] - #[cfg_attr(PyPy, link_name = "PyPyEval_CallObjectWithKeywords")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_CallObjectWithKeywords")] pub fn PyEval_CallObjectWithKeywords( func: *mut PyObject, obj: *mut PyObject, @@ -45,24 +45,24 @@ pub unsafe fn PyEval_CallObject(func: *mut PyObject, arg: *mut PyObject) -> *mut extern_libpython! { #[cfg(not(Py_3_13))] #[deprecated(note = "Python 3.9")] - #[cfg_attr(PyPy, link_name = "PyPyEval_CallFunction")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_CallFunction")] pub fn PyEval_CallFunction(obj: *mut PyObject, format: *const c_char, ...) -> *mut PyObject; #[cfg(not(Py_3_13))] #[deprecated(note = "Python 3.9")] - #[cfg_attr(PyPy, link_name = "PyPyEval_CallMethod")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_CallMethod")] pub fn PyEval_CallMethod( obj: *mut PyObject, methodname: *const c_char, format: *const c_char, ... ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_GetBuiltins")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetBuiltins")] pub fn PyEval_GetBuiltins() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_GetGlobals")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetGlobals")] pub fn PyEval_GetGlobals() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_GetLocals")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetLocals")] pub fn PyEval_GetLocals() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_GetFrame")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetFrame")] pub fn PyEval_GetFrame() -> *mut crate::PyFrameObject; #[cfg(Py_3_13)] @@ -75,44 +75,44 @@ extern_libpython! { #[cfg_attr(PyPy, link_name = "PyPyEval_GetFrameLocals")] pub fn PyEval_GetFrameLocals() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPy_AddPendingCall")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_AddPendingCall")] pub fn Py_AddPendingCall( func: Option c_int>, arg: *mut c_void, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_MakePendingCalls")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_MakePendingCalls")] pub fn Py_MakePendingCalls() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_SetRecursionLimit")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_SetRecursionLimit")] pub fn Py_SetRecursionLimit(arg1: c_int); - #[cfg_attr(PyPy, link_name = "PyPy_GetRecursionLimit")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_GetRecursionLimit")] pub fn Py_GetRecursionLimit() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_EnterRecursiveCall")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_EnterRecursiveCall")] pub fn Py_EnterRecursiveCall(arg1: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_LeaveRecursiveCall")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_LeaveRecursiveCall")] pub fn Py_LeaveRecursiveCall(); - #[cfg_attr(PyPy, link_name = "PyPyEval_GetFuncName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetFuncName")] pub fn PyEval_GetFuncName(arg1: *mut PyObject) -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyEval_GetFuncDesc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_GetFuncDesc")] pub fn PyEval_GetFuncDesc(arg1: *mut PyObject) -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyEval_EvalFrame")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_EvalFrame")] pub fn PyEval_EvalFrame(arg1: *mut crate::PyFrameObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_EvalFrameEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_EvalFrameEx")] pub fn PyEval_EvalFrameEx(f: *mut crate::PyFrameObject, exc: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyEval_SaveThread")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_SaveThread")] pub fn PyEval_SaveThread() -> *mut PyThreadState; #[cfg(not(Py_3_13))] - #[cfg_attr(PyPy, link_name = "PyPyEval_ThreadsInitialized")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_ThreadsInitialized")] #[deprecated( note = "Deprecated in Python 3.9, this function always returns true in Python 3.7 or newer." )] pub fn PyEval_ThreadsInitialized() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyEval_InitThreads")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_InitThreads")] #[deprecated( note = "Deprecated in Python 3.9, this function does nothing in Python 3.7 or newer." )] @@ -123,9 +123,9 @@ extern_libpython! { #[cfg(not(Py_3_13))] #[deprecated(note = "Deprecated in Python 3.2")] pub fn PyEval_ReleaseLock(); - #[cfg_attr(PyPy, link_name = "PyPyEval_AcquireThread")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_AcquireThread")] pub fn PyEval_AcquireThread(tstate: *mut PyThreadState); - #[cfg_attr(PyPy, link_name = "PyPyEval_ReleaseThread")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_ReleaseThread")] pub fn PyEval_ReleaseThread(tstate: *mut PyThreadState); } @@ -139,14 +139,14 @@ extern_libpython! { mod raw { use crate::pytypedefs::PyThreadState; extern_libpython! { "C-unwind" { - #[cfg_attr(PyPy, link_name = "PyPyEval_RestoreThread")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_RestoreThread")] pub fn PyEval_RestoreThread(tstate: *mut PyThreadState); }} } #[cfg(any(Py_3_14, target_arch = "wasm32"))] extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyEval_RestoreThread")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyEval_RestoreThread")] pub fn PyEval_RestoreThread(tstate: *mut PyThreadState); } diff --git a/pyo3-ffi/src/codecs.rs b/pyo3-ffi/src/codecs.rs index 4d53f4e354f..e76afc9ca82 100644 --- a/pyo3-ffi/src/codecs.rs +++ b/pyo3-ffi/src/codecs.rs @@ -26,12 +26,12 @@ extern_libpython! { // skipped non-limited _PyCodecInfo_GetIncrementalEncoder from Include/codecs.h pub fn PyCodec_Encoder(encoding: *const c_char) -> *mut PyObject; pub fn PyCodec_Decoder(encoding: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyCodec_IncrementalEncoder")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_IncrementalEncoder")] pub fn PyCodec_IncrementalEncoder( encoding: *const c_char, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyCodec_IncrementalDecoder")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_IncrementalDecoder")] pub fn PyCodec_IncrementalDecoder( encoding: *const c_char, errors: *const c_char, diff --git a/pyo3-ffi/src/complexobject.rs b/pyo3-ffi/src/complexobject.rs index 7e4b08ac075..88f0cfcddfc 100644 --- a/pyo3-ffi/src/complexobject.rs +++ b/pyo3-ffi/src/complexobject.rs @@ -26,11 +26,11 @@ extern_libpython! { pub fn PyComplex_CheckExact(op: *mut PyObject) -> c_int; // skipped non-limited PyComplex_FromCComplex - #[cfg_attr(PyPy, link_name = "PyPyComplex_FromDoubles")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyComplex_FromDoubles")] pub fn PyComplex_FromDoubles(real: c_double, imag: c_double) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyComplex_RealAsDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyComplex_RealAsDouble")] pub fn PyComplex_RealAsDouble(op: *mut PyObject) -> c_double; - #[cfg_attr(PyPy, link_name = "PyPyComplex_ImagAsDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyComplex_ImagAsDouble")] pub fn PyComplex_ImagAsDouble(op: *mut PyObject) -> c_double; } diff --git a/pyo3-ffi/src/cpython/abstract_.rs b/pyo3-ffi/src/cpython/abstract_.rs index c95b20ebb6a..d6ee90151ce 100644 --- a/pyo3-ffi/src/cpython/abstract_.rs +++ b/pyo3-ffi/src/cpython/abstract_.rs @@ -182,23 +182,23 @@ extern_libpython! { #[cfg(not(Py_3_11))] // moved to src/buffer.rs from 3.11 extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyObject_GetBuffer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetBuffer")] pub fn PyObject_GetBuffer(obj: *mut PyObject, view: *mut Py_buffer, flags: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_GetPointer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_GetPointer")] pub fn PyBuffer_GetPointer( view: *mut Py_buffer, indices: *mut Py_ssize_t, ) -> *mut core::ffi::c_void; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_SizeFromFormat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_SizeFromFormat")] pub fn PyBuffer_SizeFromFormat(format: *const c_char) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_ToContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_ToContiguous")] pub fn PyBuffer_ToContiguous( buf: *mut core::ffi::c_void, view: *mut Py_buffer, len: Py_ssize_t, order: c_char, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_FromContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_FromContiguous")] pub fn PyBuffer_FromContiguous( view: *mut Py_buffer, buf: *mut core::ffi::c_void, @@ -206,7 +206,7 @@ extern_libpython! { order: c_char, ) -> c_int; pub fn PyObject_CopyData(dest: *mut PyObject, src: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_IsContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_IsContiguous")] pub fn PyBuffer_IsContiguous(view: *const Py_buffer, fort: c_char) -> c_int; pub fn PyBuffer_FillContiguousStrides( ndims: c_int, @@ -215,7 +215,7 @@ extern_libpython! { itemsize: c_int, fort: c_char, ); - #[cfg_attr(PyPy, link_name = "PyPyBuffer_FillInfo")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_FillInfo")] pub fn PyBuffer_FillInfo( view: *mut Py_buffer, o: *mut PyObject, @@ -224,7 +224,7 @@ extern_libpython! { readonly: c_int, flags: c_int, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_Release")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_Release")] pub fn PyBuffer_Release(view: *mut Py_buffer); } diff --git a/pyo3-ffi/src/cpython/code.rs b/pyo3-ffi/src/cpython/code.rs index 10c25cad9cd..1206656829e 100644 --- a/pyo3-ffi/src/cpython/code.rs +++ b/pyo3-ffi/src/cpython/code.rs @@ -130,6 +130,7 @@ extern_libpython! { firstlineno: c_int, ) -> *mut PyCodeObject; #[cfg(not(GraalPy))] + #[cfg_attr(PyPy, link_name = "PyPyCode_Addr2Line")] pub fn PyCode_Addr2Line(arg1: *mut PyCodeObject, arg2: c_int) -> c_int; // skipped PyCodeAddressRange "for internal use only" // skipped _PyCode_CheckLineNumber diff --git a/pyo3-ffi/src/cpython/context.rs b/pyo3-ffi/src/cpython/context.rs index ef22c4395a5..7e7d1170b9a 100644 --- a/pyo3-ffi/src/cpython/context.rs +++ b/pyo3-ffi/src/cpython/context.rs @@ -55,13 +55,18 @@ extern_libpython! { #[cfg(all(Py_3_14, not(any(PyPy, GraalPy))))] pub fn PyContext_ClearWatcher(watcher_id: c_int) -> c_int; + #[cfg_attr(PyPy, link_name = "PyPyContextVar_New")] + pub fn PyContextVar_New(name: *const c_char, def: *mut PyObject) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyContextVar_Get")] pub fn PyContextVar_Get( var: *mut PyObject, default_value: *mut PyObject, value: *mut *mut PyObject, ) -> c_int; + #[cfg_attr(PyPy, link_name = "PyPyContextVar_Set")] pub fn PyContextVar_Set(var: *mut PyObject, value: *mut PyObject) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyContextVar_Reset")] pub fn PyContextVar_Reset(var: *mut PyObject, token: *mut PyObject) -> c_int; // skipped non-limited _PyContext_NewHamtForTests } diff --git a/pyo3-ffi/src/cpython/dictobject.rs b/pyo3-ffi/src/cpython/dictobject.rs index 0420525db37..d1b014b43b7 100644 --- a/pyo3-ffi/src/cpython/dictobject.rs +++ b/pyo3-ffi/src/cpython/dictobject.rs @@ -83,6 +83,7 @@ pub unsafe fn PyAnyDict_CheckExact(op: *mut PyObject) -> c_int { extern_libpython! { #[cfg(not(GraalPy))] + #[cfg_attr(PyPy, link_name = "PyPyDict_SetDefault")] pub fn PyDict_SetDefault( mp: *mut PyObject, key: *mut PyObject, diff --git a/pyo3-ffi/src/cpython/floatobject.rs b/pyo3-ffi/src/cpython/floatobject.rs index 7a4fc165956..32781252fb1 100644 --- a/pyo3-ffi/src/cpython/floatobject.rs +++ b/pyo3-ffi/src/cpython/floatobject.rs @@ -30,16 +30,22 @@ pub unsafe fn PyFloat_AS_DOUBLE(op: *mut PyObject) -> c_double { extern_libpython! { #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Pack2")] pub fn PyFloat_Pack2(x: c_double, p: *mut c_char, le: c_int) -> c_int; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Pack4")] pub fn PyFloat_Pack4(x: c_double, p: *mut c_char, le: c_int) -> c_int; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Pack8")] pub fn PyFloat_Pack8(x: c_double, p: *mut c_char, le: c_int) -> c_int; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Unpack2")] pub fn PyFloat_Unpack2(p: *const c_char, le: c_int) -> c_double; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Unpack4")] pub fn PyFloat_Unpack4(p: *const c_char, le: c_int) -> c_double; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFloat_Unpack8")] pub fn PyFloat_Unpack8(p: *const c_char, le: c_int) -> c_double; } diff --git a/pyo3-ffi/src/cpython/funcobject.rs b/pyo3-ffi/src/cpython/funcobject.rs index 63d7299e5d8..6d5575022c8 100644 --- a/pyo3-ffi/src/cpython/funcobject.rs +++ b/pyo3-ffi/src/cpython/funcobject.rs @@ -75,8 +75,11 @@ extern_libpython! { globals: *mut PyObject, qualname: *mut PyObject, ) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyFunction_GetCode")] pub fn PyFunction_GetCode(op: *mut PyObject) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyFunction_GetGlobals")] pub fn PyFunction_GetGlobals(op: *mut PyObject) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyFunction_GetModule")] pub fn PyFunction_GetModule(op: *mut PyObject) -> *mut PyObject; pub fn PyFunction_GetDefaults(op: *mut PyObject) -> *mut PyObject; pub fn PyFunction_SetDefaults(op: *mut PyObject, defaults: *mut PyObject) -> c_int; @@ -143,6 +146,9 @@ extern_libpython! { pub static mut PyClassMethod_Type: crate::PyTypeObject; pub static mut PyStaticMethod_Type: crate::PyTypeObject; + #[cfg_attr(PyPy, link_name = "PyPyClassMethod_New")] + pub fn PyClassMethod_New(ob: *mut PyObject) -> *mut PyObject; + #[cfg_attr(PyPy, link_name = "PyPyStaticMethod_New")] pub fn PyStaticMethod_New(ob: *mut PyObject) -> *mut PyObject; } diff --git a/pyo3-ffi/src/cpython/marshal.rs b/pyo3-ffi/src/cpython/marshal.rs index bd09e37baf2..bdba8db4b19 100644 --- a/pyo3-ffi/src/cpython/marshal.rs +++ b/pyo3-ffi/src/cpython/marshal.rs @@ -9,10 +9,10 @@ pub const Py_MARSHAL_VERSION: c_int = 6; pub const Py_MARSHAL_VERSION: c_int = 5; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyMarshal_WriteObjectToString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMarshal_WriteObjectToString")] pub fn PyMarshal_WriteObjectToString(object: *mut PyObject, version: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMarshal_ReadObjectFromString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMarshal_ReadObjectFromString")] pub fn PyMarshal_ReadObjectFromString(data: *const c_char, len: Py_ssize_t) -> *mut PyObject; pub fn PyMarshal_WriteLongToFile(value: c_long, file: *mut FILE, version: c_int); diff --git a/pyo3-ffi/src/cpython/pyframe.rs b/pyo3-ffi/src/cpython/pyframe.rs index d1d259cbbd3..09c64fd8d0f 100644 --- a/pyo3-ffi/src/cpython/pyframe.rs +++ b/pyo3-ffi/src/cpython/pyframe.rs @@ -45,24 +45,31 @@ extern_libpython! { pub fn PyFrame_GetBack(frame: *mut PyFrameObject) -> *mut PyFrameObject; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetLocals")] pub fn PyFrame_GetLocals(frame: *mut PyFrameObject) -> *mut PyObject; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetGlobals")] pub fn PyFrame_GetGlobals(frame: *mut PyFrameObject) -> *mut PyObject; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetBuiltins")] pub fn PyFrame_GetBuiltins(frame: *mut PyFrameObject) -> *mut PyObject; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetGenerator")] pub fn PyFrame_GetGenerator(frame: *mut PyFrameObject) -> *mut PyObject; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetLasti")] pub fn PyFrame_GetLasti(frame: *mut PyFrameObject) -> c_int; #[cfg(Py_3_12)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetVar")] pub fn PyFrame_GetVar(frame: *mut PyFrameObject, name: *mut PyObject) -> *mut PyObject; #[cfg(Py_3_12)] + #[cfg_attr(PyPy, link_name = "PyPyFrame_GetVarString")] pub fn PyFrame_GetVarString(frame: *mut PyFrameObject, name: *mut c_char) -> *mut PyObject; #[cfg(Py_3_12)] diff --git a/pyo3-ffi/src/cpython/pystate.rs b/pyo3-ffi/src/cpython/pystate.rs index e7d728d934a..727c4a479be 100644 --- a/pyo3-ffi/src/cpython/pystate.rs +++ b/pyo3-ffi/src/cpython/pystate.rs @@ -69,8 +69,10 @@ extern_libpython! { pub(crate) fn _PyThreadState_UncheckedGet() -> *mut PyThreadState; #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyThreadState_EnterTracing")] pub fn PyThreadState_EnterTracing(state: *mut PyThreadState); #[cfg(Py_3_11)] + #[cfg_attr(PyPy, link_name = "PyPyThreadState_LeaveTracing")] pub fn PyThreadState_LeaveTracing(state: *mut PyThreadState); #[cfg_attr(PyPy, link_name = "PyPyGILState_Check")] @@ -92,7 +94,7 @@ extern_libpython! { #[cfg(not(PyPy))] pub fn PyThreadState_Next(tstate: *mut PyThreadState) -> *mut PyThreadState; - #[cfg_attr(PyPy, link_name = "PyPyThreadState_DeleteCurrent")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_DeleteCurrent")] pub fn PyThreadState_DeleteCurrent(); #[cfg(all(not(Py_3_11), not(PyPy)))] diff --git a/pyo3-ffi/src/cpython/pythonrun.rs b/pyo3-ffi/src/cpython/pythonrun.rs index 0818a97082b..30798c0bcc5 100644 --- a/pyo3-ffi/src/cpython/pythonrun.rs +++ b/pyo3-ffi/src/cpython/pythonrun.rs @@ -153,7 +153,7 @@ extern_libpython! { arg2: *const c_char, arg3: *mut PyCompilerFlags, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyRun_SimpleString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyRun_SimpleString")] pub fn PyRun_SimpleString(s: *const c_char) -> c_int; #[cfg(not(any(PyPy, GraalPy)))] pub fn PyRun_SimpleFile(f: *mut FILE, p: *const c_char) -> c_int; diff --git a/pyo3-ffi/src/descrobject.rs b/pyo3-ffi/src/descrobject.rs index cd65e7b6a92..2c5fec5ca7c 100644 --- a/pyo3-ffi/src/descrobject.rs +++ b/pyo3-ffi/src/descrobject.rs @@ -55,15 +55,15 @@ extern_libpython! { extern_libpython! { pub fn PyDescr_NewMethod(arg1: *mut PyTypeObject, arg2: *mut PyMethodDef) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDescr_NewClassMethod")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDescr_NewClassMethod")] pub fn PyDescr_NewClassMethod(arg1: *mut PyTypeObject, arg2: *mut PyMethodDef) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDescr_NewMember")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDescr_NewMember")] pub fn PyDescr_NewMember(arg1: *mut PyTypeObject, arg2: *mut PyMemberDef) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDescr_NewGetSet")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDescr_NewGetSet")] pub fn PyDescr_NewGetSet(arg1: *mut PyTypeObject, arg2: *mut PyGetSetDef) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDictProxy_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDictProxy_New")] pub fn PyDictProxy_New(arg1: *mut PyObject) -> *mut PyObject; pub fn PyWrapper_New(arg1: *mut PyObject, arg2: *mut PyObject) -> *mut PyObject; } diff --git a/pyo3-ffi/src/dictobject.rs b/pyo3-ffi/src/dictobject.rs index a8edf2fdcfa..34ce94518d2 100644 --- a/pyo3-ffi/src/dictobject.rs +++ b/pyo3-ffi/src/dictobject.rs @@ -25,51 +25,51 @@ extern_libpython! { pub fn PyDict_Check(op: *mut PyObject) -> c_int; #[cfg(RustPython)] pub fn PyDict_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_New")] pub fn PyDict_New() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_GetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_GetItem")] pub fn PyDict_GetItem(mp: *mut PyObject, key: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_GetItemWithError")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_GetItemWithError")] pub fn PyDict_GetItemWithError(mp: *mut PyObject, key: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_SetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_SetItem")] pub fn PyDict_SetItem(mp: *mut PyObject, key: *mut PyObject, item: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_DelItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_DelItem")] pub fn PyDict_DelItem(mp: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_Clear")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Clear")] pub fn PyDict_Clear(mp: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyDict_Next")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Next")] pub fn PyDict_Next( mp: *mut PyObject, pos: *mut Py_ssize_t, key: *mut *mut PyObject, value: *mut *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_Keys")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Keys")] pub fn PyDict_Keys(mp: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_Values")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Values")] pub fn PyDict_Values(mp: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_Items")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Items")] pub fn PyDict_Items(mp: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Size")] pub fn PyDict_Size(mp: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyDict_Copy")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Copy")] pub fn PyDict_Copy(mp: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_Contains")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Contains")] pub fn PyDict_Contains(mp: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_Update")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Update")] pub fn PyDict_Update(mp: *mut PyObject, other: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_Merge")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_Merge")] pub fn PyDict_Merge(mp: *mut PyObject, other: *mut PyObject, _override: c_int) -> c_int; pub fn PyDict_MergeFromSeq2(d: *mut PyObject, seq2: *mut PyObject, _override: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_GetItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_GetItemString")] pub fn PyDict_GetItemString(dp: *mut PyObject, key: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyDict_SetItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_SetItemString")] pub fn PyDict_SetItemString( dp: *mut PyObject, key: *const c_char, item: *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyDict_DelItemString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDict_DelItemString")] pub fn PyDict_DelItemString(dp: *mut PyObject, key: *const c_char) -> c_int; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyDict_GetItemRef")] diff --git a/pyo3-ffi/src/fileobject.rs b/pyo3-ffi/src/fileobject.rs index 537e998bafa..04f5a7f3dd2 100644 --- a/pyo3-ffi/src/fileobject.rs +++ b/pyo3-ffi/src/fileobject.rs @@ -14,13 +14,13 @@ extern_libpython! { arg7: *const c_char, arg8: c_int, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFile_GetLine")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_GetLine")] pub fn PyFile_GetLine(arg1: *mut PyObject, arg2: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFile_WriteObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_WriteObject")] pub fn PyFile_WriteObject(arg1: *mut PyObject, arg2: *mut PyObject, arg3: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyFile_WriteString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_WriteString")] pub fn PyFile_WriteString(arg1: *const c_char, arg2: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyFile_AsFileDescriptor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_AsFileDescriptor")] pub fn PyObject_AsFileDescriptor(arg1: *mut PyObject) -> c_int; } diff --git a/pyo3-ffi/src/floatobject.rs b/pyo3-ffi/src/floatobject.rs index 5597d6d2922..59c43985690 100644 --- a/pyo3-ffi/src/floatobject.rs +++ b/pyo3-ffi/src/floatobject.rs @@ -35,11 +35,11 @@ extern_libpython! { pub fn PyFloat_GetMax() -> c_double; pub fn PyFloat_GetMin() -> c_double; pub fn PyFloat_GetInfo() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFloat_FromString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFloat_FromString")] pub fn PyFloat_FromString(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFloat_FromDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFloat_FromDouble")] pub fn PyFloat_FromDouble(arg1: c_double) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFloat_AsDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFloat_AsDouble")] pub fn PyFloat_AsDouble(arg1: *mut PyObject) -> c_double; } diff --git a/pyo3-ffi/src/genericaliasobject.rs b/pyo3-ffi/src/genericaliasobject.rs index 78013094cca..deab56be608 100644 --- a/pyo3-ffi/src/genericaliasobject.rs +++ b/pyo3-ffi/src/genericaliasobject.rs @@ -3,7 +3,7 @@ use crate::PyObject; use crate::PyTypeObject; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPy_GenericAlias")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_GenericAlias")] pub fn Py_GenericAlias(origin: *mut PyObject, args: *mut PyObject) -> *mut PyObject; #[cfg(not(RustPython))] diff --git a/pyo3-ffi/src/import.rs b/pyo3-ffi/src/import.rs index 6aee0b7df1a..371653afeb0 100644 --- a/pyo3-ffi/src/import.rs +++ b/pyo3-ffi/src/import.rs @@ -4,9 +4,9 @@ use core::ffi::{c_char, c_int, c_long}; extern_libpython! { pub fn PyImport_GetMagicNumber() -> c_long; pub fn PyImport_GetMagicTag() -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyImport_ExecCodeModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ExecCodeModule")] pub fn PyImport_ExecCodeModule(name: *const c_char, co: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_ExecCodeModuleEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ExecCodeModuleEx")] pub fn PyImport_ExecCodeModuleEx( name: *const c_char, co: *mut PyObject, @@ -24,23 +24,23 @@ extern_libpython! { pathname: *mut PyObject, cpathname: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_GetModuleDict")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_GetModuleDict")] pub fn PyImport_GetModuleDict() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_GetModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_GetModule")] pub fn PyImport_GetModule(name: *mut PyObject) -> *mut PyObject; pub fn PyImport_AddModuleObject(name: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_AddModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_AddModule")] pub fn PyImport_AddModule(name: *const c_char) -> *mut PyObject; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyImport_AddModuleRef")] pub fn PyImport_AddModuleRef(name: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_ImportModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ImportModule")] pub fn PyImport_ImportModule(name: *const c_char) -> *mut PyObject; #[cfg(not(Py_3_15))] #[deprecated(note = "Python 3.13")] - #[cfg_attr(PyPy, link_name = "PyPyImport_ImportModuleNoBlock")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ImportModuleNoBlock")] pub fn PyImport_ImportModuleNoBlock(name: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_ImportModuleLevel")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ImportModuleLevel")] pub fn PyImport_ImportModuleLevel( name: *const c_char, globals: *mut PyObject, @@ -48,7 +48,7 @@ extern_libpython! { fromlist: *mut PyObject, level: c_int, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_ImportModuleLevelObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ImportModuleLevelObject")] pub fn PyImport_ImportModuleLevelObject( name: *mut PyObject, globals: *mut PyObject, @@ -70,9 +70,9 @@ pub unsafe fn PyImport_ImportModuleEx( extern_libpython! { pub fn PyImport_GetImporter(path: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_Import")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_Import")] pub fn PyImport_Import(name: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyImport_ReloadModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ReloadModule")] pub fn PyImport_ReloadModule(m: *mut PyObject) -> *mut PyObject; pub fn PyImport_ImportFrozenModuleObject(name: *mut PyObject) -> c_int; pub fn PyImport_ImportFrozenModule(name: *const c_char) -> c_int; diff --git a/pyo3-ffi/src/intrcheck.rs b/pyo3-ffi/src/intrcheck.rs index 32702d171a8..fbc01fb9cd5 100644 --- a/pyo3-ffi/src/intrcheck.rs +++ b/pyo3-ffi/src/intrcheck.rs @@ -1,7 +1,7 @@ use core::ffi::c_int; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyOS_InterruptOccurred")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_InterruptOccurred")] pub fn PyOS_InterruptOccurred() -> c_int; #[cfg(not(Py_3_10))] #[deprecated(note = "Not documented in Python API; see Python 3.10 release notes")] @@ -11,7 +11,7 @@ extern_libpython! { pub fn PyOS_AfterFork_Parent(); pub fn PyOS_AfterFork_Child(); #[deprecated(note = "use PyOS_AfterFork_Child instead")] - #[cfg_attr(PyPy, link_name = "PyPyOS_AfterFork")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_AfterFork")] pub fn PyOS_AfterFork(); // skipped non-limited _PyOS_IsMainThread diff --git a/pyo3-ffi/src/iterobject.rs b/pyo3-ffi/src/iterobject.rs index 4236a6be48f..82c715db2a7 100644 --- a/pyo3-ffi/src/iterobject.rs +++ b/pyo3-ffi/src/iterobject.rs @@ -17,7 +17,7 @@ extern_libpython! { #[cfg(RustPython)] pub fn PySeqIter_Check(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySeqIter_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySeqIter_New")] pub fn PySeqIter_New(arg1: *mut PyObject) -> *mut PyObject; } @@ -31,6 +31,6 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyCallIter_Check(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCallIter_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCallIter_New")] pub fn PyCallIter_New(arg1: *mut PyObject, arg2: *mut PyObject) -> *mut PyObject; } diff --git a/pyo3-ffi/src/listobject.rs b/pyo3-ffi/src/listobject.rs index ed5f1cd5f7c..4a6526d0193 100644 --- a/pyo3-ffi/src/listobject.rs +++ b/pyo3-ffi/src/listobject.rs @@ -28,28 +28,28 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyList_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_New")] pub fn PyList_New(size: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyList_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_Size")] pub fn PyList_Size(arg1: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyList_GetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_GetItem")] pub fn PyList_GetItem(arg1: *mut PyObject, arg2: Py_ssize_t) -> *mut PyObject; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyList_GetItemRef")] pub fn PyList_GetItemRef(arg1: *mut PyObject, arg2: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyList_SetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_SetItem")] pub fn PyList_SetItem(arg1: *mut PyObject, arg2: Py_ssize_t, arg3: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_Insert")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_Insert")] pub fn PyList_Insert(arg1: *mut PyObject, arg2: Py_ssize_t, arg3: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_Append")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_Append")] pub fn PyList_Append(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_GetSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_GetSlice")] pub fn PyList_GetSlice( arg1: *mut PyObject, arg2: Py_ssize_t, arg3: Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyList_SetSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_SetSlice")] pub fn PyList_SetSlice( arg1: *mut PyObject, arg2: Py_ssize_t, @@ -60,11 +60,11 @@ extern_libpython! { pub fn PyList_Extend(list: *mut PyObject, iterable: *mut PyObject) -> c_int; #[cfg(Py_3_13)] pub fn PyList_Clear(list: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_Sort")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_Sort")] pub fn PyList_Sort(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_Reverse")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_Reverse")] pub fn PyList_Reverse(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyList_AsTuple")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyList_AsTuple")] pub fn PyList_AsTuple(arg1: *mut PyObject) -> *mut PyObject; // CPython macros exported as functions on PyPy or GraalPy diff --git a/pyo3-ffi/src/longobject.rs b/pyo3-ffi/src/longobject.rs index 5c72771a7f2..c9bfd9650e5 100644 --- a/pyo3-ffi/src/longobject.rs +++ b/pyo3-ffi/src/longobject.rs @@ -25,27 +25,27 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyLong_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromLong")] pub fn PyLong_FromLong(arg1: c_long) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromUnsignedLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromUnsignedLong")] pub fn PyLong_FromUnsignedLong(arg1: c_ulong) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromSize_t")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromSize_t")] pub fn PyLong_FromSize_t(arg1: size_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromSsize_t")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromSsize_t")] pub fn PyLong_FromSsize_t(arg1: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromDouble")] pub fn PyLong_FromDouble(arg1: c_double) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsLong")] pub fn PyLong_AsLong(arg1: *mut PyObject) -> c_long; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsLongAndOverflow")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsLongAndOverflow")] pub fn PyLong_AsLongAndOverflow(arg1: *mut PyObject, arg2: *mut c_int) -> c_long; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsSsize_t")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsSsize_t")] pub fn PyLong_AsSsize_t(arg1: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsSize_t")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsSize_t")] pub fn PyLong_AsSize_t(arg1: *mut PyObject) -> size_t; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsUnsignedLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsUnsignedLong")] pub fn PyLong_AsUnsignedLong(arg1: *mut PyObject) -> c_ulong; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsUnsignedLongMask")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsUnsignedLongMask")] pub fn PyLong_AsUnsignedLongMask(arg1: *mut PyObject) -> c_ulong; // skipped non-limited PyLong_AsInt @@ -115,25 +115,25 @@ extern_libpython! { // skipped _Py_PARSE_INTPTR // skipped _Py_PARSE_UINTPTR - #[cfg_attr(PyPy, link_name = "PyPyLong_AsDouble")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsDouble")] pub fn PyLong_AsDouble(arg1: *mut PyObject) -> c_double; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromVoidPtr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromVoidPtr")] pub fn PyLong_FromVoidPtr(arg1: *mut c_void) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsVoidPtr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsVoidPtr")] pub fn PyLong_AsVoidPtr(arg1: *mut PyObject) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromLongLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromLongLong")] pub fn PyLong_FromLongLong(arg1: c_longlong) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromUnsignedLongLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromUnsignedLongLong")] pub fn PyLong_FromUnsignedLongLong(arg1: c_ulonglong) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsLongLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsLongLong")] pub fn PyLong_AsLongLong(arg1: *mut PyObject) -> c_longlong; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsUnsignedLongLong")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsUnsignedLongLong")] pub fn PyLong_AsUnsignedLongLong(arg1: *mut PyObject) -> c_ulonglong; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsUnsignedLongLongMask")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsUnsignedLongLongMask")] pub fn PyLong_AsUnsignedLongLongMask(arg1: *mut PyObject) -> c_ulonglong; - #[cfg_attr(PyPy, link_name = "PyPyLong_AsLongLongAndOverflow")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_AsLongLongAndOverflow")] pub fn PyLong_AsLongLongAndOverflow(arg1: *mut PyObject, arg2: *mut c_int) -> c_longlong; - #[cfg_attr(PyPy, link_name = "PyPyLong_FromString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyLong_FromString")] pub fn PyLong_FromString( arg1: *const c_char, arg2: *mut *mut c_char, diff --git a/pyo3-ffi/src/memoryobject.rs b/pyo3-ffi/src/memoryobject.rs index 7ebc2a211d7..a78f45c58d3 100644 --- a/pyo3-ffi/src/memoryobject.rs +++ b/pyo3-ffi/src/memoryobject.rs @@ -23,18 +23,18 @@ pub unsafe fn PyMemoryView_Check(op: *mut PyObject) -> c_int { // skipped non-limited PyMemoryView_GET_BASE extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyMemoryView_FromObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMemoryView_FromObject")] pub fn PyMemoryView_FromObject(base: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMemoryView_FromMemory")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMemoryView_FromMemory")] pub fn PyMemoryView_FromMemory( mem: *mut c_char, size: Py_ssize_t, flags: c_int, ) -> *mut PyObject; #[cfg(any(Py_3_11, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyMemoryView_FromBuffer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMemoryView_FromBuffer")] pub fn PyMemoryView_FromBuffer(view: *const crate::Py_buffer) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyMemoryView_GetContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMemoryView_GetContiguous")] pub fn PyMemoryView_GetContiguous( base: *mut PyObject, buffertype: c_int, diff --git a/pyo3-ffi/src/methodobject.rs b/pyo3-ffi/src/methodobject.rs index 18e7cb75c54..758d4e18002 100644 --- a/pyo3-ffi/src/methodobject.rs +++ b/pyo3-ffi/src/methodobject.rs @@ -82,7 +82,7 @@ pub type PyCMethod = unsafe extern "C" fn( ) -> *mut PyObject; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyCFunction_GetFunction")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCFunction_GetFunction")] pub fn PyCFunction_GetFunction(f: *mut PyObject) -> Option; pub fn PyCFunction_GetSelf(f: *mut PyObject) -> *mut PyObject; pub fn PyCFunction_GetFlags(f: *mut PyObject) -> c_int; @@ -225,7 +225,7 @@ pub unsafe fn PyCFunction_NewEx( } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyCMethod_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCMethod_New")] pub fn PyCMethod_New( ml: *mut PyMethodDef, slf: *mut PyObject, diff --git a/pyo3-ffi/src/modsupport.rs b/pyo3-ffi/src/modsupport.rs index 90d091fbff1..953bcb67f48 100644 --- a/pyo3-ffi/src/modsupport.rs +++ b/pyo3-ffi/src/modsupport.rs @@ -5,11 +5,11 @@ use crate::pyport::Py_ssize_t; use core::ffi::{c_char, c_int, c_long}; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyArg_Parse")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyArg_Parse")] pub fn PyArg_Parse(arg1: *mut PyObject, arg2: *const c_char, ...) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyArg_ParseTuple")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyArg_ParseTuple")] pub fn PyArg_ParseTuple(arg1: *mut PyObject, arg2: *const c_char, ...) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyArg_ParseTupleAndKeywords")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyArg_ParseTupleAndKeywords")] pub fn PyArg_ParseTupleAndKeywords( arg1: *mut PyObject, arg2: *mut PyObject, @@ -23,7 +23,7 @@ extern_libpython! { // skipped PyArg_VaParseTupleAndKeywords pub fn PyArg_ValidateKeywordArguments(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyArg_UnpackTuple")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyArg_UnpackTuple")] pub fn PyArg_UnpackTuple( arg1: *mut PyObject, arg2: *const c_char, @@ -32,39 +32,39 @@ extern_libpython! { ... ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_BuildValue")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_BuildValue")] pub fn Py_BuildValue(arg1: *const c_char, ...) -> *mut PyObject; // skipped Py_VaBuildValue #[cfg(Py_3_13)] pub fn PyModule_Add(module: *mut PyObject, name: *const c_char, value: *mut PyObject) -> c_int; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyModule_AddObjectRef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddObjectRef")] pub fn PyModule_AddObjectRef( module: *mut PyObject, name: *const c_char, value: *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyModule_AddObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddObject")] pub fn PyModule_AddObject( module: *mut PyObject, name: *const c_char, value: *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyModule_AddIntConstant")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddIntConstant")] pub fn PyModule_AddIntConstant( module: *mut PyObject, name: *const c_char, value: c_long, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyModule_AddStringConstant")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddStringConstant")] pub fn PyModule_AddStringConstant( module: *mut PyObject, name: *const c_char, value: *const c_char, ) -> c_int; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyModule_AddType")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddType")] pub fn PyModule_AddType( module: *mut PyObject, type_: *mut crate::object::PyTypeObject, @@ -73,7 +73,7 @@ extern_libpython! { // skipped PyModule_AddStringMacro pub fn PyModule_SetDocString(arg1: *mut PyObject, arg2: *const c_char) -> c_int; pub fn PyModule_AddFunctions(arg1: *mut PyObject, arg2: *mut PyMethodDef) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyModule_ExecDef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_ExecDef")] pub fn PyModule_ExecDef(module: *mut PyObject, def: *mut PyModuleDef) -> c_int; } @@ -84,7 +84,7 @@ pub const PYTHON_ABI_VERSION: i32 = 3; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyModule_Create2")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_Create2")] pub fn PyModule_Create2(module: *mut PyModuleDef, apiver: c_int) -> *mut PyObject; } @@ -102,7 +102,7 @@ pub unsafe fn PyModule_Create(module: *mut PyModuleDef) -> *mut PyObject { extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyModule_FromDefAndSpec2")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_FromDefAndSpec2")] pub fn PyModule_FromDefAndSpec2( def: *mut PyModuleDef, spec: *mut PyObject, diff --git a/pyo3-ffi/src/moduleobject.rs b/pyo3-ffi/src/moduleobject.rs index f4ff551474a..1246e2f3c9d 100644 --- a/pyo3-ffi/src/moduleobject.rs +++ b/pyo3-ffi/src/moduleobject.rs @@ -33,15 +33,15 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyModule_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyModule_NewObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_NewObject")] pub fn PyModule_NewObject(name: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyModule_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_New")] pub fn PyModule_New(name: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyModule_GetDict")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_GetDict")] pub fn PyModule_GetDict(arg1: *mut PyObject) -> *mut PyObject; #[cfg(not(PyPy))] pub fn PyModule_GetNameObject(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyModule_GetName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_GetName")] pub fn PyModule_GetName(arg1: *mut PyObject) -> *const c_char; #[cfg(not(all(windows, PyPy)))] #[deprecated(note = "Python 3.2")] @@ -51,11 +51,11 @@ extern_libpython! { // skipped non-limited _PyModule_Clear // skipped non-limited _PyModule_ClearDict // skipped non-limited _PyModuleSpec_IsInitializing - #[cfg_attr(PyPy, link_name = "PyPyModule_GetDef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_GetDef")] pub fn PyModule_GetDef(arg1: *mut PyObject) -> *mut PyModuleDef; - #[cfg_attr(PyPy, link_name = "PyPyModule_GetState")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_GetState")] pub fn PyModule_GetState(arg1: *mut PyObject) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyModuleDef_Init")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModuleDef_Init")] pub fn PyModuleDef_Init(arg1: *mut PyModuleDef) -> *mut PyObject; #[cfg(not(RustPython))] diff --git a/pyo3-ffi/src/object.rs b/pyo3-ffi/src/object.rs index ee1508e97fb..c6dbd2df693 100644 --- a/pyo3-ffi/src/object.rs +++ b/pyo3-ffi/src/object.rs @@ -61,7 +61,7 @@ struct Aligner(c_char); #[repr(C)] #[derive(Copy, Clone)] -#[cfg(all(Py_3_12, not(Py_GIL_DISABLED)))] +#[cfg(all(all(Py_3_12, not(PyPy)), not(Py_GIL_DISABLED)))] /// This union is anonymous in CPython, so the name was given by PyO3 because /// Rust union need a name. pub union PyObjectObRefcnt { @@ -76,7 +76,7 @@ pub union PyObjectObRefcnt { _aligner: Aligner, } -#[cfg(all(Py_3_12, not(Py_GIL_DISABLED)))] +#[cfg(all(all(Py_3_12, not(PyPy)), not(Py_GIL_DISABLED)))] impl core::fmt::Debug for PyObjectObRefcnt { fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result { // SAFETY: always valid to print `ob_refcnt` as a number @@ -84,7 +84,7 @@ impl core::fmt::Debug for PyObjectObRefcnt { } } -#[cfg(all(not(Py_3_12), not(Py_GIL_DISABLED)))] +#[cfg(all(not(all(Py_3_12, not(PyPy))), not(Py_GIL_DISABLED)))] pub type PyObjectObRefcnt = Py_ssize_t; const _PyObject_MIN_ALIGNMENT: usize = 4; @@ -117,7 +117,7 @@ pub struct PyObject { pub ob_ref_shared: AtomicIsize, // shared reference count #[cfg(not(Py_GIL_DISABLED))] pub ob_refcnt: PyObjectObRefcnt, - #[cfg(PyPy)] + #[cfg(all(PyPy, not(Py_3_12)))] pub ob_pypy_link: Py_ssize_t, pub ob_type: *mut PyTypeObject, } @@ -147,11 +147,11 @@ pub const PyObject_HEAD_INIT: PyObject = PyObject { ob_ref_local: AtomicU32::new(refcount::_Py_IMMORTAL_REFCNT_LOCAL), #[cfg(Py_GIL_DISABLED)] ob_ref_shared: AtomicIsize::new(0), - #[cfg(all(not(Py_GIL_DISABLED), Py_3_12))] + #[cfg(all(not(Py_GIL_DISABLED), not(PyPy), Py_3_12))] ob_refcnt: PyObjectObRefcnt { ob_refcnt: 1 }, - #[cfg(not(Py_3_12))] + #[cfg(any(not(Py_3_12), PyPy))] ob_refcnt: 1, - #[cfg(PyPy)] + #[cfg(all(PyPy, not(Py_3_12)))] ob_pypy_link: 0, ob_type: core::ptr::null_mut(), }; @@ -187,7 +187,7 @@ pub unsafe fn Py_Is(x: *mut PyObject, y: *mut PyObject) -> c_int { #[cfg(any(GraalPy, PyPy, RustPython))] #[cfg_attr(docsrs, doc(cfg(all())))] extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPy_Is")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_Is")] pub fn Py_Is(x: *mut PyObject, y: *mut PyObject) -> c_int; } @@ -339,17 +339,17 @@ pub struct PyType_Spec { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyType_FromSpec")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_FromSpec")] pub fn PyType_FromSpec(arg1: *mut PyType_Spec) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyType_FromSpecWithBases")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_FromSpecWithBases")] pub fn PyType_FromSpecWithBases(arg1: *mut PyType_Spec, arg2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyType_GetSlot")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetSlot")] pub fn PyType_GetSlot(arg1: *mut PyTypeObject, arg2: c_int) -> *mut c_void; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyType_FromModuleAndSpec")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_FromModuleAndSpec")] pub fn PyType_FromModuleAndSpec( module: *mut PyObject, spec: *mut PyType_Spec, @@ -357,19 +357,19 @@ extern_libpython! { ) -> *mut PyObject; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyType_GetModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetModule")] pub fn PyType_GetModule(arg1: *mut PyTypeObject) -> *mut PyObject; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyType_GetModuleState")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetModuleState")] pub fn PyType_GetModuleState(arg1: *mut PyTypeObject) -> *mut c_void; #[cfg(Py_3_11)] - #[cfg_attr(PyPy, link_name = "PyPyType_GetName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetName")] pub fn PyType_GetName(arg1: *mut PyTypeObject) -> *mut PyObject; #[cfg(Py_3_11)] - #[cfg_attr(PyPy, link_name = "PyPyType_GetQualName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetQualName")] pub fn PyType_GetQualName(arg1: *mut PyTypeObject) -> *mut PyObject; #[cfg(Py_3_13)] @@ -381,7 +381,7 @@ extern_libpython! { pub fn PyType_GetModuleName(arg1: *mut PyTypeObject) -> *mut PyObject; #[cfg(Py_3_12)] - #[cfg_attr(PyPy, link_name = "PyPyType_FromMetaclass")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_FromMetaclass")] pub fn PyType_FromMetaclass( metaclass: *mut PyTypeObject, module: *mut PyObject, @@ -393,7 +393,7 @@ extern_libpython! { pub fn PyObject_GetTypeData(obj: *mut PyObject, cls: *mut PyTypeObject) -> *mut c_void; #[cfg(Py_3_12)] - #[cfg_attr(PyPy, link_name = "PyPyType_GetTypeDataSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GetTypeDataSize")] pub fn PyType_GetTypeDataSize(cls: *mut PyTypeObject) -> Py_ssize_t; #[cfg(Py_3_14)] @@ -408,7 +408,7 @@ extern_libpython! { #[cfg_attr(PyPy, link_name = "PyPyType_FromSlot")] pub fn PyType_FromSlots(slots: *mut PySlot) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyType_IsSubtype")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_IsSubtype")] pub fn PyType_IsSubtype(a: *mut PyTypeObject, b: *mut PyTypeObject) -> c_int; } @@ -424,7 +424,7 @@ extern_libpython! { pub static mut PyType_Type: PyTypeObject; /// built-in 'object' #[cfg(not(RustPython))] - #[cfg_attr(PyPy, link_name = "PyPyBaseObject_Type")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBaseObject_Type")] pub static mut PyBaseObject_Type: PyTypeObject; /// built-in 'super' #[cfg(not(RustPython))] @@ -432,40 +432,40 @@ extern_libpython! { pub fn PyType_GetFlags(arg1: *mut PyTypeObject) -> c_ulong; - #[cfg_attr(PyPy, link_name = "PyPyType_Ready")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_Ready")] pub fn PyType_Ready(t: *mut PyTypeObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyType_GenericAlloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GenericAlloc")] pub fn PyType_GenericAlloc(t: *mut PyTypeObject, nitems: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyType_GenericNew")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_GenericNew")] pub fn PyType_GenericNew( t: *mut PyTypeObject, args: *mut PyObject, kwds: *mut PyObject, ) -> *mut PyObject; pub fn PyType_ClearCache() -> c_uint; - #[cfg_attr(PyPy, link_name = "PyPyType_Modified")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyType_Modified")] pub fn PyType_Modified(t: *mut PyTypeObject); - #[cfg_attr(PyPy, link_name = "PyPyObject_Repr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Repr")] pub fn PyObject_Repr(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_Str")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Str")] pub fn PyObject_Str(o: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_ASCII")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_ASCII")] pub fn PyObject_ASCII(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_Bytes")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Bytes")] pub fn PyObject_Bytes(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_RichCompare")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_RichCompare")] pub fn PyObject_RichCompare( arg1: *mut PyObject, arg2: *mut PyObject, arg3: c_int, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_RichCompareBool")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_RichCompareBool")] pub fn PyObject_RichCompareBool(arg1: *mut PyObject, arg2: *mut PyObject, arg3: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_GetAttrString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetAttrString")] pub fn PyObject_GetAttrString(arg1: *mut PyObject, arg2: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_SetAttrString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_SetAttrString")] pub fn PyObject_SetAttrString( arg1: *mut PyObject, arg2: *const c_char, @@ -474,9 +474,9 @@ extern_libpython! { #[cfg(any(Py_3_13, all(PyPy, not(Py_3_11))))] // CPython defined in 3.12 as an inline function in abstract.h #[cfg_attr(PyPy, link_name = "PyPyObject_DelAttrString")] pub fn PyObject_DelAttrString(arg1: *mut PyObject, arg2: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_HasAttrString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_HasAttrString")] pub fn PyObject_HasAttrString(arg1: *mut PyObject, arg2: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_GetAttr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetAttr")] pub fn PyObject_GetAttr(arg1: *mut PyObject, arg2: *mut PyObject) -> *mut PyObject; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyObject_GetOptionalAttr")] @@ -492,13 +492,13 @@ extern_libpython! { arg2: *const c_char, arg3: *mut *mut PyObject, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_SetAttr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_SetAttr")] pub fn PyObject_SetAttr(arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject) -> c_int; #[cfg(any(Py_3_13, all(PyPy, not(Py_3_11))))] // CPython defined in 3.12 as an inline function in abstract.h #[cfg_attr(PyPy, link_name = "PyPyObject_DelAttr")] pub fn PyObject_DelAttr(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_HasAttr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_HasAttr")] pub fn PyObject_HasAttr(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyObject_HasAttrWithError")] @@ -506,39 +506,39 @@ extern_libpython! { #[cfg(Py_3_13)] #[cfg_attr(PyPy, link_name = "PyPyObject_HasAttrStringWithError")] pub fn PyObject_HasAttrStringWithError(arg1: *mut PyObject, arg2: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_SelfIter")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_SelfIter")] pub fn PyObject_SelfIter(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_GenericGetAttr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GenericGetAttr")] pub fn PyObject_GenericGetAttr(arg1: *mut PyObject, arg2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_GenericSetAttr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GenericSetAttr")] pub fn PyObject_GenericSetAttr( arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject, ) -> c_int; #[cfg(not(all(Py_LIMITED_API, not(Py_3_10))))] - #[cfg_attr(PyPy, link_name = "PyPyObject_GenericGetDict")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GenericGetDict")] pub fn PyObject_GenericGetDict(arg1: *mut PyObject, arg2: *mut c_void) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_GenericSetDict")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GenericSetDict")] pub fn PyObject_GenericSetDict( arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut c_void, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_Hash")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Hash")] pub fn PyObject_Hash(arg1: *mut PyObject) -> Py_hash_t; - #[cfg_attr(PyPy, link_name = "PyPyObject_HashNotImplemented")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_HashNotImplemented")] pub fn PyObject_HashNotImplemented(arg1: *mut PyObject) -> Py_hash_t; - #[cfg_attr(PyPy, link_name = "PyPyObject_IsTrue")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_IsTrue")] pub fn PyObject_IsTrue(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_Not")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Not")] pub fn PyObject_Not(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCallable_Check")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCallable_Check")] pub fn PyCallable_Check(arg1: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_ClearWeakRefs")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_ClearWeakRefs")] pub fn PyObject_ClearWeakRefs(arg1: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyObject_Dir")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Dir")] pub fn PyObject_Dir(arg1: *mut PyObject) -> *mut PyObject; pub fn Py_ReprEnter(arg1: *mut PyObject) -> c_int; pub fn Py_ReprLeave(arg1: *mut PyObject); diff --git a/pyo3-ffi/src/objimpl.rs b/pyo3-ffi/src/objimpl.rs index b4de5b5a572..6e2baf0fc88 100644 --- a/pyo3-ffi/src/objimpl.rs +++ b/pyo3-ffi/src/objimpl.rs @@ -5,13 +5,13 @@ use crate::object::*; use crate::pyport::Py_ssize_t; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyObject_Malloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Malloc")] pub fn PyObject_Malloc(size: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyObject_Calloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Calloc")] pub fn PyObject_Calloc(nelem: size_t, elsize: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyObject_Realloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Realloc")] pub fn PyObject_Realloc(ptr: *mut c_void, new_size: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyObject_Free")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Free")] pub fn PyObject_Free(ptr: *mut c_void); // skipped PyObject_MALLOC @@ -20,9 +20,9 @@ extern_libpython! { // skipped PyObject_Del // skipped PyObject_DEL - #[cfg_attr(PyPy, link_name = "PyPyObject_Init")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Init")] pub fn PyObject_Init(arg1: *mut PyObject, arg2: *mut PyTypeObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyObject_InitVar")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_InitVar")] pub fn PyObject_InitVar( arg1: *mut PyVarObject, arg2: *mut PyTypeObject, @@ -53,19 +53,19 @@ pub unsafe fn PyObject_NewVar(typeobj: *mut PyTypeObject, n: Py_ssize_t) -> * // skipped PyObject_NEW_VAR extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyGC_Collect")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_Collect")] pub fn PyGC_Collect() -> Py_ssize_t; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyGC_Enable")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_Enable")] pub fn PyGC_Enable() -> c_int; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyGC_Disable")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_Disable")] pub fn PyGC_Disable() -> c_int; #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyGC_IsEnabled")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_IsEnabled")] pub fn PyGC_IsEnabled() -> c_int; } @@ -108,7 +108,7 @@ pub unsafe fn PyObject_GC_Track(_: *mut c_void) {} pub unsafe fn PyObject_GC_UnTrack(_: *mut c_void) {} extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyObject_GC_Del")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GC_Del")] pub fn PyObject_GC_Del(arg1: *mut c_void); } @@ -124,10 +124,10 @@ pub unsafe fn PyObject_GC_NewVar(typeobj: *mut PyTypeObject, n: Py_ssize_t) - extern_libpython! { #[cfg(any(not(PyPy), Py_3_10))] // added in 3.9, or 3.10 on PyPy - #[cfg_attr(PyPy, link_name = "PyPyObject_GC_IsTracked")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GC_IsTracked")] pub fn PyObject_GC_IsTracked(arg1: *mut PyObject) -> c_int; #[cfg(any(not(PyPy), Py_3_10))] // added in 3.9, or 3.10 on PyPy - #[cfg_attr(PyPy, link_name = "PyPyObject_GC_IsFinalized")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GC_IsFinalized")] pub fn PyObject_GC_IsFinalized(arg1: *mut PyObject) -> c_int; } diff --git a/pyo3-ffi/src/osmodule.rs b/pyo3-ffi/src/osmodule.rs index 84ce095ac2f..1e7c53dcc80 100644 --- a/pyo3-ffi/src/osmodule.rs +++ b/pyo3-ffi/src/osmodule.rs @@ -1,6 +1,6 @@ use crate::object::PyObject; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyOS_FSPath")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_FSPath")] pub fn PyOS_FSPath(path: *mut PyObject) -> *mut PyObject; } diff --git a/pyo3-ffi/src/pybuffer.rs b/pyo3-ffi/src/pybuffer.rs index 83975c744e1..bed166cb5f2 100644 --- a/pyo3-ffi/src/pybuffer.rs +++ b/pyo3-ffi/src/pybuffer.rs @@ -59,20 +59,20 @@ extern_libpython! { #[cfg(not(PyPy))] pub fn PyObject_CheckBuffer(obj: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyObject_GetBuffer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_GetBuffer")] pub fn PyObject_GetBuffer(obj: *mut PyObject, view: *mut Py_buffer, flags: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_GetPointer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_GetPointer")] pub fn PyBuffer_GetPointer(view: *const Py_buffer, indices: *const Py_ssize_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_SizeFromFormat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_SizeFromFormat")] pub fn PyBuffer_SizeFromFormat(format: *const c_char) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_ToContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_ToContiguous")] pub fn PyBuffer_ToContiguous( buf: *mut c_void, view: *const Py_buffer, len: Py_ssize_t, order: c_char, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_FromContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_FromContiguous")] pub fn PyBuffer_FromContiguous( view: *const Py_buffer, buf: *const c_void, @@ -80,7 +80,7 @@ extern_libpython! { order: c_char, ) -> c_int; pub fn PyObject_CopyData(dest: *mut PyObject, src: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_IsContiguous")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_IsContiguous")] pub fn PyBuffer_IsContiguous(view: *const Py_buffer, fort: c_char) -> c_int; pub fn PyBuffer_FillContiguousStrides( ndims: c_int, @@ -89,7 +89,7 @@ extern_libpython! { itemsize: c_int, fort: c_char, ); - #[cfg_attr(PyPy, link_name = "PyPyBuffer_FillInfo")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_FillInfo")] pub fn PyBuffer_FillInfo( view: *mut Py_buffer, o: *mut PyObject, @@ -98,7 +98,7 @@ extern_libpython! { readonly: c_int, flags: c_int, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyBuffer_Release")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBuffer_Release")] pub fn PyBuffer_Release(view: *mut Py_buffer); } diff --git a/pyo3-ffi/src/pycapsule.rs b/pyo3-ffi/src/pycapsule.rs index a5a3df91057..2cc464cbc47 100644 --- a/pyo3-ffi/src/pycapsule.rs +++ b/pyo3-ffi/src/pycapsule.rs @@ -19,33 +19,33 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyCapsule_CheckExact(ob: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_New")] pub fn PyCapsule_New( pointer: *mut c_void, name: *const c_char, destructor: Option, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_GetPointer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_GetPointer")] pub fn PyCapsule_GetPointer(capsule: *mut PyObject, name: *const c_char) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_GetDestructor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_GetDestructor")] pub fn PyCapsule_GetDestructor(capsule: *mut PyObject) -> Option; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_GetName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_GetName")] pub fn PyCapsule_GetName(capsule: *mut PyObject) -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_GetContext")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_GetContext")] pub fn PyCapsule_GetContext(capsule: *mut PyObject) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_IsValid")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_IsValid")] pub fn PyCapsule_IsValid(capsule: *mut PyObject, name: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_SetPointer")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_SetPointer")] pub fn PyCapsule_SetPointer(capsule: *mut PyObject, pointer: *mut c_void) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_SetDestructor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_SetDestructor")] pub fn PyCapsule_SetDestructor( capsule: *mut PyObject, destructor: Option, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_SetName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_SetName")] pub fn PyCapsule_SetName(capsule: *mut PyObject, name: *const c_char) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_SetContext")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_SetContext")] pub fn PyCapsule_SetContext(capsule: *mut PyObject, context: *mut c_void) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyCapsule_Import")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCapsule_Import")] pub fn PyCapsule_Import(name: *const c_char, no_block: c_int) -> *mut c_void; } diff --git a/pyo3-ffi/src/pyerrors.rs b/pyo3-ffi/src/pyerrors.rs index 25d4e2db717..0f76f72ece3 100644 --- a/pyo3-ffi/src/pyerrors.rs +++ b/pyo3-ffi/src/pyerrors.rs @@ -3,39 +3,39 @@ use crate::pyport::Py_ssize_t; use core::ffi::{c_char, c_int}; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyErr_SetNone")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetNone")] pub fn PyErr_SetNone(arg1: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyErr_SetObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetObject")] pub fn PyErr_SetObject(arg1: *mut PyObject, arg2: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyErr_SetString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetString")] pub fn PyErr_SetString(exception: *mut PyObject, string: *const c_char); - #[cfg_attr(PyPy, link_name = "PyPyErr_Occurred")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Occurred")] pub fn PyErr_Occurred() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_Clear")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Clear")] pub fn PyErr_Clear(); #[cfg_attr(Py_3_12, deprecated(note = "Use PyErr_GetRaisedException() instead."))] - #[cfg_attr(PyPy, link_name = "PyPyErr_Fetch")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Fetch")] pub fn PyErr_Fetch( arg1: *mut *mut PyObject, arg2: *mut *mut PyObject, arg3: *mut *mut PyObject, ); #[cfg_attr(Py_3_12, deprecated(note = "Use PyErr_SetRaisedException() instead."))] - #[cfg_attr(PyPy, link_name = "PyPyErr_Restore")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Restore")] pub fn PyErr_Restore(arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyErr_GetExcInfo")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_GetExcInfo")] pub fn PyErr_GetExcInfo( arg1: *mut *mut PyObject, arg2: *mut *mut PyObject, arg3: *mut *mut PyObject, ); - #[cfg_attr(PyPy, link_name = "PyPyErr_SetExcInfo")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetExcInfo")] pub fn PyErr_SetExcInfo(arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPy_FatalError")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_FatalError")] pub fn Py_FatalError(message: *const c_char) -> !; - #[cfg_attr(PyPy, link_name = "PyPyErr_GivenExceptionMatches")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_GivenExceptionMatches")] pub fn PyErr_GivenExceptionMatches(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_ExceptionMatches")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_ExceptionMatches")] pub fn PyErr_ExceptionMatches(arg1: *mut PyObject) -> c_int; #[cfg_attr( Py_3_12, @@ -43,35 +43,35 @@ extern_libpython! { note = "Use PyErr_GetRaisedException() instead, to avoid any possible de-normalization." ) )] - #[cfg_attr(PyPy, link_name = "PyPyErr_NormalizeException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_NormalizeException")] pub fn PyErr_NormalizeException( arg1: *mut *mut PyObject, arg2: *mut *mut PyObject, arg3: *mut *mut PyObject, ); #[cfg(Py_3_12)] - #[cfg_attr(PyPy, link_name = "PyPyErr_GetRaisedException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_GetRaisedException")] pub fn PyErr_GetRaisedException() -> *mut PyObject; #[cfg(Py_3_12)] - #[cfg_attr(PyPy, link_name = "PyPyErr_SetRaisedException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetRaisedException")] pub fn PyErr_SetRaisedException(exc: *mut PyObject); #[cfg(Py_3_11)] - #[cfg_attr(PyPy, link_name = "PyPyErr_GetHandledException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_GetHandledException")] pub fn PyErr_GetHandledException() -> *mut PyObject; #[cfg(Py_3_11)] - #[cfg_attr(PyPy, link_name = "PyPyErr_SetHandledException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetHandledException")] pub fn PyErr_SetHandledException(exc: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyException_SetTraceback")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_SetTraceback")] pub fn PyException_SetTraceback(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyException_GetTraceback")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_GetTraceback")] pub fn PyException_GetTraceback(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyException_GetCause")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_GetCause")] pub fn PyException_GetCause(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyException_SetCause")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_SetCause")] pub fn PyException_SetCause(arg1: *mut PyObject, arg2: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyException_GetContext")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_GetContext")] pub fn PyException_GetContext(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyException_SetContext")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyException_SetContext")] pub fn PyException_SetContext(arg1: *mut PyObject, arg2: *mut PyObject); #[cfg(RustPython)] @@ -279,13 +279,13 @@ extern_libpython! { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyErr_BadArgument")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_BadArgument")] pub fn PyErr_BadArgument() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_NoMemory")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_NoMemory")] pub fn PyErr_NoMemory() -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_SetFromErrno")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrno")] pub fn PyErr_SetFromErrno(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_SetFromErrnoWithFilenameObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilenameObject")] pub fn PyErr_SetFromErrnoWithFilenameObject( arg1: *mut PyObject, arg2: *mut PyObject, @@ -299,7 +299,7 @@ extern_libpython! { exc: *mut PyObject, filename: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_Format")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Format")] pub fn PyErr_Format(exception: *mut PyObject, format: *const c_char, ...) -> *mut PyObject; pub fn PyErr_SetImportErrorSubclass( arg1: *mut PyObject, @@ -313,7 +313,7 @@ extern_libpython! { arg3: *mut PyObject, ) -> *mut PyObject; #[cfg(PyPy)] - #[cfg_attr(PyPy, link_name = "PyPyErr_BadInternalCall")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_BadInternalCall")] pub fn PyErr_BadInternalCall(); #[cfg(not(PyPy))] @@ -336,33 +336,33 @@ pub unsafe fn PyErr_BadInternalCall() { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyErr_NewException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_NewException")] pub fn PyErr_NewException( name: *const c_char, base: *mut PyObject, dict: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_NewExceptionWithDoc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_NewExceptionWithDoc")] pub fn PyErr_NewExceptionWithDoc( name: *const c_char, doc: *const c_char, base: *mut PyObject, dict: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_WriteUnraisable")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_WriteUnraisable")] pub fn PyErr_WriteUnraisable(arg1: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyErr_CheckSignals")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_CheckSignals")] pub fn PyErr_CheckSignals() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_SetInterrupt")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetInterrupt")] pub fn PyErr_SetInterrupt(); #[cfg(Py_3_10)] - #[cfg_attr(PyPy, link_name = "PyPyErr_SetInterruptEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetInterruptEx")] pub fn PyErr_SetInterruptEx(signum: c_int) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_SyntaxLocation")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SyntaxLocation")] pub fn PyErr_SyntaxLocation(filename: *const c_char, lineno: c_int); - #[cfg_attr(PyPy, link_name = "PyPyErr_SyntaxLocationEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SyntaxLocationEx")] pub fn PyErr_SyntaxLocationEx(filename: *const c_char, lineno: c_int, col_offset: c_int); - #[cfg_attr(PyPy, link_name = "PyPyErr_ProgramText")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_ProgramText")] pub fn PyErr_ProgramText(filename: *const c_char, lineno: c_int) -> *mut PyObject; #[cfg(not(PyPy))] pub fn PyUnicodeDecodeError_Create( diff --git a/pyo3-ffi/src/pylifecycle.rs b/pyo3-ffi/src/pylifecycle.rs index 758f5228f61..e95b652c686 100644 --- a/pyo3-ffi/src/pylifecycle.rs +++ b/pyo3-ffi/src/pylifecycle.rs @@ -9,13 +9,13 @@ extern_libpython! { pub fn Py_Finalize(); pub fn Py_FinalizeEx() -> c_int; - #[cfg_attr(PyPy, link_name = "PyPy_IsInitialized")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_IsInitialized")] pub fn Py_IsInitialized() -> c_int; pub fn Py_NewInterpreter() -> *mut PyThreadState; pub fn Py_EndInterpreter(arg1: *mut PyThreadState); - #[cfg_attr(PyPy, link_name = "PyPy_AtExit")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_AtExit")] pub fn Py_AtExit(func: Option) -> c_int; pub fn Py_Exit(arg1: c_int) -> !; @@ -29,7 +29,7 @@ extern_libpython! { )] pub fn Py_SetProgramName(arg1: *const wchar_t); #[cfg(not(Py_3_15))] - #[cfg_attr(PyPy, link_name = "PyPy_GetProgramName")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_GetProgramName")] #[cfg_attr( Py_3_13, deprecated(note = "Deprecated since Python 3.13. Use `sys.executable` instead.") @@ -82,7 +82,7 @@ extern_libpython! { // skipped _Py_CheckPython3 - #[cfg_attr(PyPy, link_name = "PyPy_GetVersion")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_GetVersion")] pub fn Py_GetVersion() -> *const c_char; pub fn Py_GetPlatform() -> *const c_char; pub fn Py_GetCopyright() -> *const c_char; diff --git a/pyo3-ffi/src/pymem.rs b/pyo3-ffi/src/pymem.rs index 45e57ef1db6..7ddf864f43c 100644 --- a/pyo3-ffi/src/pymem.rs +++ b/pyo3-ffi/src/pymem.rs @@ -2,12 +2,12 @@ use core::ffi::c_void; use libc::size_t; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyMem_Malloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMem_Malloc")] pub fn PyMem_Malloc(size: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyMem_Calloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMem_Calloc")] pub fn PyMem_Calloc(nelem: size_t, elsize: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyMem_Realloc")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMem_Realloc")] pub fn PyMem_Realloc(ptr: *mut c_void, new_size: size_t) -> *mut c_void; - #[cfg_attr(PyPy, link_name = "PyPyMem_Free")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMem_Free")] pub fn PyMem_Free(ptr: *mut c_void); } diff --git a/pyo3-ffi/src/pystate.rs b/pyo3-ffi/src/pystate.rs index 7058684a2a1..87bff364fe5 100644 --- a/pyo3-ffi/src/pystate.rs +++ b/pyo3-ffi/src/pystate.rs @@ -29,22 +29,22 @@ extern_libpython! { #[cfg(not(PyPy))] pub fn PyInterpreterState_GetID(arg1: *mut PyInterpreterState) -> i64; - #[cfg_attr(PyPy, link_name = "PyPyState_AddModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyState_AddModule")] pub fn PyState_AddModule(arg1: *mut PyObject, arg2: *mut PyModuleDef) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyState_RemoveModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyState_RemoveModule")] pub fn PyState_RemoveModule(arg1: *mut PyModuleDef) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyState_FindModule")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyState_FindModule")] pub fn PyState_FindModule(arg1: *mut PyModuleDef) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyThreadState_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_New")] pub fn PyThreadState_New(arg1: *mut PyInterpreterState) -> *mut PyThreadState; - #[cfg_attr(PyPy, link_name = "PyPyThreadState_Clear")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_Clear")] pub fn PyThreadState_Clear(arg1: *mut PyThreadState); - #[cfg_attr(PyPy, link_name = "PyPyThreadState_Delete")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_Delete")] pub fn PyThreadState_Delete(arg1: *mut PyThreadState); - #[cfg_attr(PyPy, link_name = "PyPyThreadState_Get")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_Get")] pub fn PyThreadState_Get() -> *mut PyThreadState; } @@ -54,9 +54,9 @@ pub unsafe fn PyThreadState_GET() -> *mut PyThreadState { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyThreadState_Swap")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_Swap")] pub fn PyThreadState_Swap(arg1: *mut PyThreadState) -> *mut PyThreadState; - #[cfg_attr(PyPy, link_name = "PyPyThreadState_GetDict")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThreadState_GetDict")] pub fn PyThreadState_GetDict() -> *mut PyObject; #[cfg(not(PyPy))] pub fn PyThreadState_SetAsyncExc(arg1: c_long, arg2: *mut PyObject) -> c_int; @@ -90,13 +90,13 @@ pub enum PyGILState_STATE { mod raw { #[cfg(not(any(Py_3_14, target_arch = "wasm32")))] extern_libpython! { "C-unwind" { - #[cfg_attr(PyPy, link_name = "PyPyGILState_Ensure")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGILState_Ensure")] pub fn PyGILState_Ensure() -> super::PyGILState_STATE; }} #[cfg(any(Py_3_14, target_arch = "wasm32"))] extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyGILState_Ensure")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGILState_Ensure")] pub fn PyGILState_Ensure() -> super::PyGILState_STATE; } } @@ -131,7 +131,7 @@ pub unsafe extern "C" fn PyGILState_Ensure() -> PyGILState_STATE { pub use self::raw::PyGILState_Ensure; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyGILState_Release")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGILState_Release")] pub fn PyGILState_Release(arg1: PyGILState_STATE); #[cfg(not(PyPy))] pub fn PyGILState_GetThisThreadState() -> *mut PyThreadState; diff --git a/pyo3-ffi/src/pystrtod.rs b/pyo3-ffi/src/pystrtod.rs index 43ac27b26cd..9f851adadf2 100644 --- a/pyo3-ffi/src/pystrtod.rs +++ b/pyo3-ffi/src/pystrtod.rs @@ -2,13 +2,13 @@ use crate::object::PyObject; use core::ffi::{c_char, c_double, c_int}; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyOS_string_to_double")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_string_to_double")] pub fn PyOS_string_to_double( str: *const c_char, endptr: *mut *mut c_char, overflow_exception: *mut PyObject, ) -> c_double; - #[cfg_attr(PyPy, link_name = "PyPyOS_double_to_string")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_double_to_string")] pub fn PyOS_double_to_string( val: c_double, format_code: c_char, diff --git a/pyo3-ffi/src/pythonrun.rs b/pyo3-ffi/src/pythonrun.rs index daf1bae6562..891e55a2b20 100644 --- a/pyo3-ffi/src/pythonrun.rs +++ b/pyo3-ffi/src/pythonrun.rs @@ -9,15 +9,15 @@ extern_libpython! { #[cfg(any(all(Py_LIMITED_API, not(PyPy)), GraalPy))] pub fn Py_CompileString(string: *const c_char, p: *const c_char, s: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyErr_Print")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Print")] pub fn PyErr_Print(); - #[cfg_attr(PyPy, link_name = "PyPyErr_PrintEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_PrintEx")] pub fn PyErr_PrintEx(arg1: c_int); - #[cfg_attr(PyPy, link_name = "PyPyErr_Display")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_Display")] pub fn PyErr_Display(arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject); #[cfg(Py_3_12)] - #[cfg_attr(PyPy, link_name = "PyPyErr_DisplayException")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_DisplayException")] pub fn PyErr_DisplayException(exc: *mut PyObject); } diff --git a/pyo3-ffi/src/pythread.rs b/pyo3-ffi/src/pythread.rs index 1124a130646..edb8b4d0b70 100644 --- a/pyo3-ffi/src/pythread.rs +++ b/pyo3-ffi/src/pythread.rs @@ -7,7 +7,7 @@ use core::ffi::{c_int, c_ulong, c_void}; // skipped PyThread_exit_thread extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyThread_get_thread_ident")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyThread_get_thread_ident")] pub fn PyThread_get_thread_ident() -> c_ulong; } diff --git a/pyo3-ffi/src/refcount.rs b/pyo3-ffi/src/refcount.rs index 4da10969b4a..e349aaa2f89 100644 --- a/pyo3-ffi/src/refcount.rs +++ b/pyo3-ffi/src/refcount.rs @@ -2,7 +2,10 @@ use crate::pyport::Py_ssize_t; use crate::PyObject; #[cfg(all(not(Py_LIMITED_API), py_sys_config = "Py_REF_DEBUG"))] use core::ffi::c_char; -#[cfg(any(Py_3_12, all(py_sys_config = "Py_REF_DEBUG", not(Py_LIMITED_API))))] +#[cfg(any( + all(Py_3_12, not(PyPy)), + all(py_sys_config = "Py_REF_DEBUG", not(Py_LIMITED_API)) +))] use core::ffi::c_int; #[cfg(all(Py_3_14, any(not(Py_GIL_DISABLED), target_pointer_width = "32")))] use core::ffi::c_long; @@ -102,7 +105,15 @@ pub unsafe fn Py_REFCNT(ob: *mut PyObject) -> Py_ssize_t { #[cfg(all(not(Py_GIL_DISABLED), not(all(Py_LIMITED_API, Py_3_14)), Py_3_12))] { - (*ob).ob_refcnt.ob_refcnt + #[cfg(not(PyPy))] + { + (*ob).ob_refcnt.ob_refcnt + } + + #[cfg(PyPy)] + { + (*ob).ob_refcnt + } } #[cfg(all(not(Py_GIL_DISABLED), not(Py_3_12), not(GraalPy)))] @@ -118,6 +129,7 @@ pub unsafe fn Py_REFCNT(ob: *mut PyObject) -> Py_ssize_t { #[cfg(not(all(Py_LIMITED_API, Py_GIL_DISABLED)))] #[cfg(Py_3_12)] +#[cfg(not(PyPy))] #[inline(always)] unsafe fn _Py_IsImmortal(op: *mut PyObject) -> c_int { #[cfg(all(target_pointer_width = "64", not(Py_GIL_DISABLED)))] @@ -159,10 +171,10 @@ extern_libpython! { #[cfg_attr(PyPy, link_name = "_PyPy_Dealloc")] fn _Py_Dealloc(arg1: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPy_IncRef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_IncRef")] #[cfg_attr(GraalPy, link_name = "_Py_IncRef")] pub fn Py_IncRef(o: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPy_DecRef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_DecRef")] #[cfg_attr(GraalPy, link_name = "_Py_DecRef")] pub fn Py_DecRef(o: *mut PyObject); @@ -183,7 +195,8 @@ pub unsafe fn Py_INCREF(op: *mut PyObject) { Py_GIL_DISABLED, Py_LIMITED_API, py_sys_config = "Py_REF_DEBUG", - GraalPy + GraalPy, + PyPy ))] { // _Py_IncRef was added to the ABI in 3.10; skips null checks @@ -203,7 +216,8 @@ pub unsafe fn Py_INCREF(op: *mut PyObject) { Py_GIL_DISABLED, Py_LIMITED_API, py_sys_config = "Py_REF_DEBUG", - GraalPy + GraalPy, + PyPy )))] { #[cfg(all(Py_3_14, target_pointer_width = "64"))] @@ -260,7 +274,8 @@ pub unsafe fn Py_DECREF(op: *mut PyObject) { Py_GIL_DISABLED, Py_LIMITED_API, all(py_sys_config = "Py_REF_DEBUG", not(Py_3_12)), - GraalPy + GraalPy, + PyPy ))] { // _Py_DecRef was added to the ABI in 3.10; skips null checks @@ -279,7 +294,8 @@ pub unsafe fn Py_DECREF(op: *mut PyObject) { Py_GIL_DISABLED, Py_LIMITED_API, all(py_sys_config = "Py_REF_DEBUG", not(Py_3_12)), - GraalPy + GraalPy, + PyPy )))] { #[cfg(Py_3_12)] diff --git a/pyo3-ffi/src/setobject.rs b/pyo3-ffi/src/setobject.rs index 505b50d6bed..8b1efbb1e0a 100644 --- a/pyo3-ffi/src/setobject.rs +++ b/pyo3-ffi/src/setobject.rs @@ -12,22 +12,22 @@ extern_libpython! { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPySet_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_New")] pub fn PySet_New(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyFrozenSet_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFrozenSet_New")] pub fn PyFrozenSet_New(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySet_Add")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Add")] pub fn PySet_Add(set: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySet_Clear")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Clear")] pub fn PySet_Clear(set: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySet_Contains")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Contains")] pub fn PySet_Contains(anyset: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySet_Discard")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Discard")] pub fn PySet_Discard(set: *mut PyObject, key: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySet_Pop")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Pop")] pub fn PySet_Pop(set: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySet_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySet_Size")] pub fn PySet_Size(anyset: *mut PyObject) -> Py_ssize_t; #[cfg(any(PyPy, RustPython))] diff --git a/pyo3-ffi/src/sliceobject.rs b/pyo3-ffi/src/sliceobject.rs index 175a65f0622..4321b689f11 100644 --- a/pyo3-ffi/src/sliceobject.rs +++ b/pyo3-ffi/src/sliceobject.rs @@ -52,7 +52,7 @@ extern_libpython! { #[cfg(RustPython)] pub fn PySlice_Check(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySlice_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySlice_New")] pub fn PySlice_New( start: *mut PyObject, stop: *mut PyObject, @@ -62,7 +62,7 @@ extern_libpython! { // skipped non-limited _PySlice_FromIndices // skipped non-limited _PySlice_GetLongIndices - #[cfg_attr(PyPy, link_name = "PyPySlice_GetIndices")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySlice_GetIndices")] pub fn PySlice_GetIndices( r: *mut PyObject, length: Py_ssize_t, @@ -91,7 +91,7 @@ pub unsafe fn PySlice_GetIndicesEx( } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPySlice_Unpack")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySlice_Unpack")] pub fn PySlice_Unpack( slice: *mut PyObject, start: *mut Py_ssize_t, @@ -99,7 +99,7 @@ extern_libpython! { step: *mut Py_ssize_t, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPySlice_AdjustIndices")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySlice_AdjustIndices")] pub fn PySlice_AdjustIndices( length: Py_ssize_t, start: *mut Py_ssize_t, diff --git a/pyo3-ffi/src/structseq.rs b/pyo3-ffi/src/structseq.rs index f25bb4379b2..b6ff0a6cf11 100644 --- a/pyo3-ffi/src/structseq.rs +++ b/pyo3-ffi/src/structseq.rs @@ -38,7 +38,7 @@ extern_libpython! { #[cfg(not(PyPy))] pub fn PyStructSequence_NewType(desc: *mut PyStructSequence_Desc) -> *mut PyTypeObject; - #[cfg_attr(PyPy, link_name = "PyPyStructSequence_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyStructSequence_New")] pub fn PyStructSequence_New(_type: *mut PyTypeObject) -> *mut PyObject; } diff --git a/pyo3-ffi/src/sysmodule.rs b/pyo3-ffi/src/sysmodule.rs index d5c2bebdf8c..aaa61d66fb0 100644 --- a/pyo3-ffi/src/sysmodule.rs +++ b/pyo3-ffi/src/sysmodule.rs @@ -3,9 +3,9 @@ use core::ffi::{c_char, c_int}; use libc::wchar_t; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPySys_GetObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySys_GetObject")] pub fn PySys_GetObject(arg1: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPySys_SetObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySys_SetObject")] pub fn PySys_SetObject(arg1: *const c_char, arg2: *mut PyObject) -> c_int; #[cfg_attr( @@ -24,9 +24,9 @@ extern_libpython! { pub fn PySys_SetArgvEx(arg1: c_int, arg2: *mut *mut wchar_t, arg3: c_int); pub fn PySys_SetPath(arg1: *const wchar_t); - #[cfg_attr(PyPy, link_name = "PyPySys_WriteStdout")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySys_WriteStdout")] pub fn PySys_WriteStdout(format: *const c_char, ...); - #[cfg_attr(PyPy, link_name = "PyPySys_WriteStderr")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySys_WriteStderr")] pub fn PySys_WriteStderr(format: *const c_char, ...); pub fn PySys_FormatStdout(format: *const c_char, ...); pub fn PySys_FormatStderr(format: *const c_char, ...); diff --git a/pyo3-ffi/src/traceback.rs b/pyo3-ffi/src/traceback.rs index 9cfb11dcb9d..e5868f00217 100644 --- a/pyo3-ffi/src/traceback.rs +++ b/pyo3-ffi/src/traceback.rs @@ -2,9 +2,9 @@ use crate::object::*; use core::ffi::c_int; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyTraceBack_Here")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTraceBack_Here")] pub fn PyTraceBack_Here(arg1: *mut crate::PyFrameObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyTraceBack_Print")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTraceBack_Print")] pub fn PyTraceBack_Print(arg1: *mut PyObject, arg2: *mut PyObject) -> c_int; #[cfg(not(RustPython))] diff --git a/pyo3-ffi/src/tupleobject.rs b/pyo3-ffi/src/tupleobject.rs index caa0ccc955d..8a3c678243c 100644 --- a/pyo3-ffi/src/tupleobject.rs +++ b/pyo3-ffi/src/tupleobject.rs @@ -27,21 +27,21 @@ extern_libpython! { #[cfg(RustPython)] pub fn PyTuple_CheckExact(op: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyTuple_New")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_New")] pub fn PyTuple_New(size: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyTuple_Size")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_Size")] pub fn PyTuple_Size(arg1: *mut PyObject) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyTuple_GetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_GetItem")] pub fn PyTuple_GetItem(arg1: *mut PyObject, arg2: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyTuple_SetItem")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_SetItem")] pub fn PyTuple_SetItem(arg1: *mut PyObject, arg2: Py_ssize_t, arg3: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyTuple_GetSlice")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_GetSlice")] pub fn PyTuple_GetSlice( arg1: *mut PyObject, arg2: Py_ssize_t, arg3: Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyTuple_Pack")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyTuple_Pack")] pub fn PyTuple_Pack(arg1: Py_ssize_t, ...) -> *mut PyObject; #[cfg(any(all(Py_3_15, not(Py_LIMITED_API)), RustPython))] pub fn PyTuple_FromArray(array: *const *mut PyObject, size: Py_ssize_t) -> *mut PyObject; diff --git a/pyo3-ffi/src/unicodeobject.rs b/pyo3-ffi/src/unicodeobject.rs index b3d3efea4f9..ec51d9d443e 100644 --- a/pyo3-ffi/src/unicodeobject.rs +++ b/pyo3-ffi/src/unicodeobject.rs @@ -39,7 +39,7 @@ pub const Py_UNICODE_REPLACEMENT_CHARACTER: Py_UCS4 = 0xFFFD; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromStringAndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromStringAndSize")] pub fn PyUnicode_FromStringAndSize(u: *const c_char, size: Py_ssize_t) -> *mut PyObject; pub fn PyUnicode_FromString(u: *const c_char) -> *mut PyObject; @@ -55,7 +55,7 @@ extern_libpython! { copy_null: c_int, ) -> *mut Py_UCS4; pub fn PyUnicode_AsUCS4Copy(unicode: *mut PyObject) -> *mut Py_UCS4; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_GetLength")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_GetLength")] pub fn PyUnicode_GetLength(unicode: *mut PyObject) -> Py_ssize_t; #[cfg(not(Py_3_12))] #[deprecated(note = "Removed in Python 3.12")] @@ -67,45 +67,45 @@ extern_libpython! { index: Py_ssize_t, character: Py_UCS4, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Resize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Resize")] pub fn PyUnicode_Resize(unicode: *mut *mut PyObject, length: Py_ssize_t) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromEncodedObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromEncodedObject")] pub fn PyUnicode_FromEncodedObject( obj: *mut PyObject, encoding: *const c_char, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromObject")] pub fn PyUnicode_FromObject(obj: *mut PyObject) -> *mut PyObject; // #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromFormatV")] // pub fn PyUnicode_FromFormatV(format: *const c_char, vargs: va_list) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromFormat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromFormat")] pub fn PyUnicode_FromFormat(format: *const c_char, ...) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_InternInPlace")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_InternInPlace")] pub fn PyUnicode_InternInPlace(arg1: *mut *mut PyObject); #[cfg(not(Py_3_12))] #[cfg_attr(Py_3_10, deprecated(note = "Python 3.10"))] pub fn PyUnicode_InternImmortal(arg1: *mut *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyUnicode_InternFromString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_InternFromString")] pub fn PyUnicode_InternFromString(u: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromWideChar")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromWideChar")] pub fn PyUnicode_FromWideChar(w: *const wchar_t, size: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsWideChar")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsWideChar")] pub fn PyUnicode_AsWideChar( unicode: *mut PyObject, w: *mut wchar_t, size: Py_ssize_t, ) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsWideCharString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsWideCharString")] pub fn PyUnicode_AsWideCharString( unicode: *mut PyObject, size: *mut Py_ssize_t, ) -> *mut wchar_t; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FromOrdinal")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromOrdinal")] pub fn PyUnicode_FromOrdinal(ordinal: c_int) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_GetDefaultEncoding")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_GetDefaultEncoding")] pub fn PyUnicode_GetDefaultEncoding() -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Decode")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Decode")] pub fn PyUnicode_Decode( s: *const c_char, size: Py_ssize_t, @@ -128,13 +128,13 @@ extern_libpython! { ) -> *mut PyObject; #[cfg(not(Py_3_15))] #[deprecated(note = "use PyCodec_Encode() instead")] - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsEncodedObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsEncodedObject")] pub fn PyUnicode_AsEncodedObject( unicode: *mut PyObject, encoding: *const c_char, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsEncodedString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsEncodedString")] pub fn PyUnicode_AsEncodedString( unicode: *mut PyObject, encoding: *const c_char, @@ -159,7 +159,7 @@ extern_libpython! { errors: *const c_char, consumed: *mut Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeUTF8")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeUTF8")] pub fn PyUnicode_DecodeUTF8( string: *const c_char, length: Py_ssize_t, @@ -171,12 +171,12 @@ extern_libpython! { errors: *const c_char, consumed: *mut Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsUTF8String")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUTF8String")] pub fn PyUnicode_AsUTF8String(unicode: *mut PyObject) -> *mut PyObject; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsUTF8AndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUTF8AndSize")] pub fn PyUnicode_AsUTF8AndSize(unicode: *mut PyObject, size: *mut Py_ssize_t) -> *const c_char; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeUTF32")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeUTF32")] pub fn PyUnicode_DecodeUTF32( string: *const c_char, length: Py_ssize_t, @@ -190,9 +190,9 @@ extern_libpython! { byteorder: *mut c_int, consumed: *mut Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsUTF32String")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUTF32String")] pub fn PyUnicode_AsUTF32String(unicode: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeUTF16")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeUTF16")] pub fn PyUnicode_DecodeUTF16( string: *const c_char, length: Py_ssize_t, @@ -206,14 +206,14 @@ extern_libpython! { byteorder: *mut c_int, consumed: *mut Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsUTF16String")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUTF16String")] pub fn PyUnicode_AsUTF16String(unicode: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_DecodeUnicodeEscape( string: *const c_char, length: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsUnicodeEscapeString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUnicodeEscapeString")] pub fn PyUnicode_AsUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_DecodeRawUnicodeEscape( string: *const c_char, @@ -221,21 +221,21 @@ extern_libpython! { errors: *const c_char, ) -> *mut PyObject; pub fn PyUnicode_AsRawUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeLatin1")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeLatin1")] pub fn PyUnicode_DecodeLatin1( string: *const c_char, length: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsLatin1String")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsLatin1String")] pub fn PyUnicode_AsLatin1String(unicode: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeASCII")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeASCII")] pub fn PyUnicode_DecodeASCII( string: *const c_char, length: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_AsASCIIString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsASCIIString")] pub fn PyUnicode_AsASCIIString(unicode: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_DecodeCharmap( string: *const c_char, @@ -283,27 +283,27 @@ extern_libpython! { ) -> *mut PyObject; pub fn PyUnicode_DecodeLocale(str: *const c_char, errors: *const c_char) -> *mut PyObject; pub fn PyUnicode_EncodeLocale(unicode: *mut PyObject, errors: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FSConverter")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FSConverter")] pub fn PyUnicode_FSConverter(arg1: *mut PyObject, arg2: *mut c_void) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_FSDecoder")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FSDecoder")] pub fn PyUnicode_FSDecoder(arg1: *mut PyObject, arg2: *mut c_void) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeFSDefault")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeFSDefault")] pub fn PyUnicode_DecodeFSDefault(s: *const c_char) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_DecodeFSDefaultAndSize")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeFSDefaultAndSize")] pub fn PyUnicode_DecodeFSDefaultAndSize(s: *const c_char, size: Py_ssize_t) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_EncodeFSDefault")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_EncodeFSDefault")] pub fn PyUnicode_EncodeFSDefault(unicode: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Concat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Concat")] pub fn PyUnicode_Concat(left: *mut PyObject, right: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_Append(pleft: *mut *mut PyObject, right: *mut PyObject); pub fn PyUnicode_AppendAndDel(pleft: *mut *mut PyObject, right: *mut PyObject); - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Split")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Split")] pub fn PyUnicode_Split( s: *mut PyObject, sep: *mut PyObject, maxsplit: Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Splitlines")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Splitlines")] pub fn PyUnicode_Splitlines(s: *mut PyObject, keepends: c_int) -> *mut PyObject; pub fn PyUnicode_Partition(s: *mut PyObject, sep: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_RPartition(s: *mut PyObject, sep: *mut PyObject) -> *mut PyObject; @@ -317,18 +317,18 @@ extern_libpython! { table: *mut PyObject, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Join")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Join")] pub fn PyUnicode_Join(separator: *mut PyObject, seq: *mut PyObject) -> *mut PyObject; } -#[cfg(PyPy)] +#[cfg(all(PyPy, not(Py_3_12)))] type TailmatchResult = c_int; -#[cfg(not(PyPy))] +#[cfg(not(all(PyPy, not(Py_3_12))))] type TailmatchResult = Py_ssize_t; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Tailmatch")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Tailmatch")] pub fn PyUnicode_Tailmatch( str: *mut PyObject, substr: *mut PyObject, @@ -336,7 +336,7 @@ extern_libpython! { end: Py_ssize_t, direction: c_int, ) -> TailmatchResult; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Find")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Find")] pub fn PyUnicode_Find( str: *mut PyObject, substr: *mut PyObject, @@ -351,23 +351,23 @@ extern_libpython! { end: Py_ssize_t, direction: c_int, ) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Count")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Count")] pub fn PyUnicode_Count( str: *mut PyObject, substr: *mut PyObject, start: Py_ssize_t, end: Py_ssize_t, ) -> Py_ssize_t; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Replace")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Replace")] pub fn PyUnicode_Replace( str: *mut PyObject, substr: *mut PyObject, replstr: *mut PyObject, maxcount: Py_ssize_t, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Compare")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Compare")] pub fn PyUnicode_Compare(left: *mut PyObject, right: *mut PyObject) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_CompareWithASCIIString")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_CompareWithASCIIString")] pub fn PyUnicode_CompareWithASCIIString(left: *mut PyObject, right: *const c_char) -> c_int; #[cfg(Py_3_13)] pub fn PyUnicode_EqualToUTF8(unicode: *mut PyObject, string: *const c_char) -> c_int; @@ -384,7 +384,7 @@ extern_libpython! { right: *mut PyObject, op: c_int, ) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyUnicode_Format")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Format")] pub fn PyUnicode_Format(format: *mut PyObject, args: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_Contains(container: *mut PyObject, element: *mut PyObject) -> c_int; pub fn PyUnicode_IsIdentifier(s: *mut PyObject) -> c_int; diff --git a/pyo3-ffi/src/warnings.rs b/pyo3-ffi/src/warnings.rs index 4277c4daf84..47577d3e59a 100644 --- a/pyo3-ffi/src/warnings.rs +++ b/pyo3-ffi/src/warnings.rs @@ -3,13 +3,13 @@ use crate::pyport::Py_ssize_t; use core::ffi::{c_char, c_int}; extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyErr_WarnEx")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_WarnEx")] pub fn PyErr_WarnEx( category: *mut PyObject, message: *const c_char, stack_level: Py_ssize_t, ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_WarnFormat")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_WarnFormat")] pub fn PyErr_WarnFormat( category: *mut PyObject, stack_level: Py_ssize_t, @@ -22,7 +22,7 @@ extern_libpython! { format: *const c_char, ... ) -> c_int; - #[cfg_attr(PyPy, link_name = "PyPyErr_WarnExplicit")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_WarnExplicit")] pub fn PyErr_WarnExplicit( category: *mut PyObject, message: *const c_char, diff --git a/pyo3-ffi/src/weakrefobject.rs b/pyo3-ffi/src/weakrefobject.rs index 84b94125ca7..98161a740fa 100644 --- a/pyo3-ffi/src/weakrefobject.rs +++ b/pyo3-ffi/src/weakrefobject.rs @@ -56,12 +56,12 @@ pub unsafe fn PyWeakref_Check(op: *mut PyObject) -> c_int { } extern_libpython! { - #[cfg_attr(PyPy, link_name = "PyPyWeakref_NewRef")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyWeakref_NewRef")] pub fn PyWeakref_NewRef(ob: *mut PyObject, callback: *mut PyObject) -> *mut PyObject; - #[cfg_attr(PyPy, link_name = "PyPyWeakref_NewProxy")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyWeakref_NewProxy")] pub fn PyWeakref_NewProxy(ob: *mut PyObject, callback: *mut PyObject) -> *mut PyObject; #[cfg(not(Py_3_15))] - #[cfg_attr(PyPy, link_name = "PyPyWeakref_GetObject")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyWeakref_GetObject")] #[cfg_attr( Py_3_13, deprecated(note = "deprecated since Python 3.13. Use `PyWeakref_GetRef` instead.") diff --git a/pytests/noxfile.py b/pytests/noxfile.py index 8cfa4109cfb..73c0aa097bb 100644 --- a/pytests/noxfile.py +++ b/pytests/noxfile.py @@ -29,10 +29,10 @@ def try_install_binary(package: str, constraint: str): pass try_install_binary("numpy", ">=1.16") - # https://github.com/zopefoundation/zope.interface/issues/316 - # - is a dependency of gevent - try_install_binary("zope.interface", "<7") try_install_binary("gevent", ">=22.10.2") + # hypothesis itself depends on PyO3 so newer Python versions may fail + # to build + try_install_binary("hypothesis", ">=6.171.1") ignored_paths = [] if sys.version_info < (3, 10): # Match syntax is only available in Python >= 3.10 diff --git a/pytests/pyproject.toml b/pytests/pyproject.toml index d42b6bb9dde..1413c0826c6 100644 --- a/pytests/pyproject.toml +++ b/pytests/pyproject.toml @@ -34,7 +34,6 @@ requires-python = ">=3.9" [project.optional-dependencies] dev = [ - "hypothesis>=3.55", # mypy doesn't build on GraalPy when installed via uv "mypy~=1.0; platform_python_implementation != 'GraalVM'", "pyrefly~=0.57.0", diff --git a/pytests/tests/test_datetime.py b/pytests/tests/test_datetime.py index 134dbdea071..45772522318 100644 --- a/pytests/tests/test_datetime.py +++ b/pytests/tests/test_datetime.py @@ -1,13 +1,8 @@ import datetime as pdt -import platform import re -import struct -import sys import pyo3_pytests.datetime as rdt import pytest -from hypothesis import example, given -from hypothesis import strategies as st # Constants @@ -41,75 +36,17 @@ def tzname(self, dt): MAX_MICROSECONDS = int(pdt.timedelta.max.total_seconds() * 1e6) MIN_MICROSECONDS = int(pdt.timedelta.min.total_seconds() * 1e6) -# The reason we don't use platform.architecture() here is that it's not -# reliable on macOS. See https://stackoverflow.com/a/1405971/823869. Similarly, -# sys.maxsize is not reliable on Windows. See -# https://stackoverflow.com/questions/1405913/how-do-i-determine-if-my-python-shell-is-executing-in-32bit-or-64bit-mode-on-os/1405971#comment6209952_1405971 -# and https://stackoverflow.com/a/3411134/823869. -_pointer_size = struct.calcsize("P") -if _pointer_size == 8: - IS_32_BIT = False -elif _pointer_size == 4: - IS_32_BIT = True -else: - raise RuntimeError("unexpected pointer size: " + repr(_pointer_size)) -IS_WINDOWS = sys.platform == "win32" - -if IS_WINDOWS: - MIN_DATETIME = pdt.datetime(1970, 1, 1, 0, 0, 0) # noqa: DTZ001 - if IS_32_BIT: - MAX_DATETIME = pdt.datetime(2038, 1, 18, 23, 59, 59) # noqa: DTZ001 - else: - MAX_DATETIME = pdt.datetime(3000, 12, 31, 23, 59, 59) # noqa: DTZ001 -else: - if IS_32_BIT: - # TS ±2147483648 (2**31) - MIN_DATETIME = pdt.datetime(1901, 12, 13, 20, 45, 52) # noqa: DTZ001 - MAX_DATETIME = pdt.datetime(2038, 1, 19, 3, 14, 8) # noqa: DTZ001 - else: - MIN_DATETIME = pdt.datetime(1, 1, 2, 0, 0) # noqa: DTZ001 - MAX_DATETIME = pdt.datetime(9999, 12, 31, 18, 59, 59) # noqa: DTZ001 - -PYPY = platform.python_implementation() == "PyPy" - # Tests def test_date(): assert rdt.make_date(2017, 9, 1) == pdt.date(2017, 9, 1) -@given(d=st.dates()) -def test_date_accessors(d): - act = rdt.get_date_tuple(d) - exp = (d.year, d.month, d.day) - - assert act == exp - - def test_invalid_date_fails(): with pytest.raises(ValueError): rdt.make_date(2017, 2, 30) -@given(dt=st.datetimes(MIN_DATETIME, MAX_DATETIME)) -def test_date_from_timestamp(dt): - try: - ts = pdt.datetime.timestamp(dt) - except OverflowError: - # out of range for timestamp - return - - try: - expected = pdt.date.fromtimestamp(ts) # noqa: DTZ012 - except OverflowError as pdt_fail: - # date from timestamp failed; expect the same from Rust binding - with pytest.raises(type(pdt_fail)) as exc_info: - rdt.date_from_timestamp(ts) - assert str(exc_info.value) == str(pdt_fail) - else: - assert rdt.date_from_timestamp(ts) == expected - - @pytest.mark.parametrize( "args, kwargs", [ @@ -127,26 +64,6 @@ def test_time(args, kwargs): assert rdt.get_time_tzinfo(act) == exp.tzinfo -@given(t=st.times()) -def test_time_hypothesis(t): - act = rdt.get_time_tuple(t) - exp = (t.hour, t.minute, t.second, t.microsecond) - - assert act == exp - - -@given(t=st.times()) -def test_time_tuple_fold(t): - t_nofold = t.replace(fold=0) - t_fold = t.replace(fold=1) - - for t in (t_nofold, t_fold): # noqa: PLR1704 - act = rdt.get_time_tuple_fold(t) - exp = (t.hour, t.minute, t.second, t.microsecond, t.fold) - - assert act == exp - - @pytest.mark.parametrize("fold", [False, True]) def test_time_with_fold(fold): t = rdt.time_with_fold(0, 0, 0, 0, None, fold) @@ -206,26 +123,6 @@ def test_datetime(args, kwargs): assert rdt.get_datetime_tzinfo(act) == exp.tzinfo -@given(dt=st.datetimes()) -def test_datetime_tuple(dt): - act = rdt.get_datetime_tuple(dt) - exp = dt.timetuple()[0:6] + (dt.microsecond,) - - assert act == exp - - -@given(dt=st.datetimes()) -def test_datetime_tuple_fold(dt): - dt_fold = dt.replace(fold=1) - dt_nofold = dt.replace(fold=0) - - for dt in (dt_fold, dt_nofold): # noqa: PLR1704 - act = rdt.get_datetime_tuple_fold(dt) - exp = dt.timetuple()[0:6] + (dt.microsecond, dt.fold) - - assert act == exp - - def test_invalid_datetime_fails(): with pytest.raises(ValueError): rdt.make_datetime(2011, 1, 42, 0, 0, 0, 0) @@ -236,26 +133,6 @@ def test_datetime_typeerror(): rdt.make_datetime("2011", 1, 1, 0, 0, 0, 0) # type: ignore[bad-argument-type] -@given(dt=st.datetimes(MIN_DATETIME, MAX_DATETIME)) -@example(dt=pdt.datetime(1971, 1, 2, 0, 0)) # noqa: DTZ001 -def test_datetime_from_timestamp(dt): - try: - ts = pdt.datetime.timestamp(dt) - except OverflowError: - # out of range for timestamp - return - - try: - expected = pdt.datetime.fromtimestamp(ts) # noqa: DTZ006 - except OverflowError as pdt_fail: - # datetime from timestamp failed; expect the same from Rust binding - with pytest.raises(type(pdt_fail)) as exc_info: - rdt.datetime_from_timestamp(ts) - assert str(exc_info.value) == str(pdt_fail) - else: - assert rdt.datetime_from_timestamp(ts) == expected - - def test_datetime_from_timestamp_tzinfo(): d1 = rdt.datetime_from_timestamp(0, tz=UTC) d2 = rdt.datetime_from_timestamp(0, tz=UTC) @@ -285,14 +162,6 @@ def test_delta(args): assert act == exp -@given(td=st.timedeltas()) -def test_delta_accessors(td): - act = rdt.get_delta_tuple(td) - exp = (td.days, td.seconds, td.microseconds) - - assert act == exp - - @pytest.mark.parametrize( "args,err_type", [ diff --git a/pytests/tests/test_datetime_hypothesis.py b/pytests/tests/test_datetime_hypothesis.py new file mode 100644 index 00000000000..606f2441df4 --- /dev/null +++ b/pytests/tests/test_datetime_hypothesis.py @@ -0,0 +1,133 @@ +import datetime as pdt +import struct +import sys + +import pyo3_pytests.datetime as rdt +import pytest + +hypothesis = pytest.importorskip("hypothesis") +st = pytest.importorskip("hypothesis.strategies") + +# The reason we don't use platform.architecture() here is that it's not +# reliable on macOS. See https://stackoverflow.com/a/1405971/823869. Similarly, +# sys.maxsize is not reliable on Windows. See +# https://stackoverflow.com/questions/1405913/how-do-i-determine-if-my-python-shell-is-executing-in-32bit-or-64bit-mode-on-os/1405971#comment6209952_1405971 +# and https://stackoverflow.com/a/3411134/823869. +_pointer_size = struct.calcsize("P") +if _pointer_size == 8: + IS_32_BIT = False +elif _pointer_size == 4: + IS_32_BIT = True +else: + raise RuntimeError("unexpected pointer size: " + repr(_pointer_size)) +IS_WINDOWS = sys.platform == "win32" + +if IS_WINDOWS: + MIN_DATETIME = pdt.datetime(1970, 1, 1, 0, 0, 0) # noqa: DTZ001 + if IS_32_BIT: + MAX_DATETIME = pdt.datetime(2038, 1, 18, 23, 59, 59) # noqa: DTZ001 + else: + MAX_DATETIME = pdt.datetime(3000, 12, 31, 23, 59, 59) # noqa: DTZ001 +else: + if IS_32_BIT: + # TS ±2147483648 (2**31) + MIN_DATETIME = pdt.datetime(1901, 12, 13, 20, 45, 52) # noqa: DTZ001 + MAX_DATETIME = pdt.datetime(2038, 1, 19, 3, 14, 8) # noqa: DTZ001 + else: + MIN_DATETIME = pdt.datetime(1, 1, 2, 0, 0) # noqa: DTZ001 + MAX_DATETIME = pdt.datetime(9999, 12, 31, 18, 59, 59) # noqa: DTZ001 + + +@hypothesis.given(d=st.dates()) +def test_date_accessors(d): + act = rdt.get_date_tuple(d) + exp = (d.year, d.month, d.day) + + assert act == exp + + +@hypothesis.given(dt=st.datetimes(MIN_DATETIME, MAX_DATETIME)) +def test_date_from_timestamp(dt): + try: + ts = pdt.datetime.timestamp(dt) + except OverflowError: + # out of range for timestamp + return + + try: + expected = pdt.date.fromtimestamp(ts) # noqa: DTZ012 + except OverflowError as pdt_fail: + # date from timestamp failed; expect the same from Rust binding + with pytest.raises(type(pdt_fail)) as exc_info: + rdt.date_from_timestamp(ts) + assert str(exc_info.value) == str(pdt_fail) + else: + assert rdt.date_from_timestamp(ts) == expected + + +@hypothesis.given(t=st.times()) +def test_time_hypothesis(t): + act = rdt.get_time_tuple(t) + exp = (t.hour, t.minute, t.second, t.microsecond) + + assert act == exp + + +@hypothesis.given(t=st.times()) +def test_time_tuple_fold(t): + t_nofold = t.replace(fold=0) + t_fold = t.replace(fold=1) + + for t in (t_nofold, t_fold): # noqa: PLR1704 + act = rdt.get_time_tuple_fold(t) + exp = (t.hour, t.minute, t.second, t.microsecond, t.fold) + + assert act == exp + + +@hypothesis.given(dt=st.datetimes()) +def test_datetime_tuple(dt): + act = rdt.get_datetime_tuple(dt) + exp = dt.timetuple()[0:6] + (dt.microsecond,) + + assert act == exp + + +@hypothesis.given(dt=st.datetimes()) +def test_datetime_tuple_fold(dt): + dt_fold = dt.replace(fold=1) + dt_nofold = dt.replace(fold=0) + + for dt in (dt_fold, dt_nofold): # noqa: PLR1704 + act = rdt.get_datetime_tuple_fold(dt) + exp = dt.timetuple()[0:6] + (dt.microsecond, dt.fold) + + assert act == exp + + +@hypothesis.given(dt=st.datetimes(MIN_DATETIME, MAX_DATETIME)) +@hypothesis.example(dt=pdt.datetime(1971, 1, 2, 0, 0)) # noqa: DTZ001 +def test_datetime_from_timestamp(dt): + try: + ts = pdt.datetime.timestamp(dt) + except OverflowError: + # out of range for timestamp + return + + try: + expected = pdt.datetime.fromtimestamp(ts) # noqa: DTZ006 + except OverflowError as pdt_fail: + # datetime from timestamp failed; expect the same from Rust binding + with pytest.raises(type(pdt_fail)) as exc_info: + rdt.datetime_from_timestamp(ts) + assert str(exc_info.value) == str(pdt_fail) + else: + assert rdt.datetime_from_timestamp(ts) == expected + + +@hypothesis.given(td=st.timedeltas()) +def test_delta_accessors(td): + act = rdt.get_delta_tuple(td) + exp = (td.days, td.seconds, td.microseconds) + + assert act == exp diff --git a/pytests/tests/test_othermod.py b/pytests/tests/test_othermod.py index 36aaa7bc8f9..4de4f946e8a 100644 --- a/pytests/tests/test_othermod.py +++ b/pytests/tests/test_othermod.py @@ -1,22 +1,5 @@ -from hypothesis import assume, given -from hypothesis import strategies as st from pyo3_pytests import othermod -INTEGER31_ST = st.integers(min_value=(-(2**30)), max_value=(2**30 - 1)) -USIZE_ST = st.integers(min_value=othermod.USIZE_MIN, max_value=othermod.USIZE_MAX) - - -# If the full 32 bits are used here, then you can get failures that look like this: -# hypothesis.errors.FailedHealthCheck: It looks like your strategy is filtering out a lot of data. -# Health check found 50 filtered examples but only 7 good ones. -# -# Limit the range to 31 bits to avoid this problem. -@given(x=INTEGER31_ST) -def test_double(x): - expected = x * 2 - assume(-(2**31) <= expected <= (2**31 - 1)) - assert othermod.double(x) == expected - def test_modclass(): # Test that the repr of the class itself doesn't crash anything @@ -33,10 +16,3 @@ def test_modclass_instance(): assert isinstance(mi, othermod.ModClass) assert isinstance(mi, object) - - -@given(x=USIZE_ST) -def test_modclas_noop(x): - mi = othermod.ModClass() - - assert mi.noop(x) == x diff --git a/pytests/tests/test_othermod_hypothesis.py b/pytests/tests/test_othermod_hypothesis.py new file mode 100644 index 00000000000..594f61e5a4e --- /dev/null +++ b/pytests/tests/test_othermod_hypothesis.py @@ -0,0 +1,27 @@ +import pytest +from pyo3_pytests import othermod + +hypothesis = pytest.importorskip("hypothesis") +st = pytest.importorskip("hypothesis.strategies") + +INTEGER31_ST = st.integers(min_value=(-(2**30)), max_value=(2**30 - 1)) +USIZE_ST = st.integers(min_value=othermod.USIZE_MIN, max_value=othermod.USIZE_MAX) + + +# If the full 32 bits are used here, then you can get failures that look like this: +# hypothesis.errors.FailedHealthCheck: It looks like your strategy is filtering out a lot of data. +# Health check found 50 filtered examples but only 7 good ones. +# +# Limit the range to 31 bits to avoid this problem. +@hypothesis.given(x=INTEGER31_ST) +def test_double(x): + expected = x * 2 + hypothesis.assume(-(2**31) <= expected <= (2**31 - 1)) + assert othermod.double(x) == expected + + +@hypothesis.given(x=USIZE_ST) +def test_modclas_noop(x): + mi = othermod.ModClass() + + assert mi.noop(x) == x From de6f5d7354adabcee932d9d080660f95f49d3469 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Sun, 6 Sep 2026 14:39:59 +0100 Subject: [PATCH 02/14] fix formatting --- pyo3-ffi/src/abstract_.rs | 25 ++++++++----------------- pyo3-ffi/src/cpython/context.rs | 1 - pyo3-ffi/src/cpython/funcobject.rs | 1 - pyo3-ffi/src/cpython/marshal.rs | 5 ++++- pyo3-ffi/src/import.rs | 5 ++++- pyo3-ffi/src/pyerrors.rs | 5 ++++- pyo3-ffi/src/unicodeobject.rs | 15 ++++++++++++--- 7 files changed, 32 insertions(+), 25 deletions(-) diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index bb60ad00d96..a8df976c0cf 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -112,10 +112,7 @@ extern_libpython! { pub fn PyObject_Size(o: *mut PyObject) -> Py_ssize_t; // PyObject_Length is a direct alias for PyObject_Size - #[cfg_attr( - any(not(PyPy), all(PyPy, Py_3_12)), - link_name = "PyObject_Size" - )] + #[cfg_attr(any(not(PyPy), all(PyPy, Py_3_12)), link_name = "PyObject_Size")] #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Size")] pub fn PyObject_Length(o: *mut PyObject) -> Py_ssize_t; @@ -212,7 +209,10 @@ extern_libpython! { pub fn PyNumber_InPlaceSubtract(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceMultiply")] pub fn PyNumber_InPlaceMultiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceMatrixMultiply")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyNumber_InPlaceMatrixMultiply" + )] pub fn PyNumber_InPlaceMatrixMultiply(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceFloorDivide")] pub fn PyNumber_InPlaceFloorDivide(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; @@ -244,10 +244,7 @@ extern_libpython! { pub fn PySequence_Size(o: *mut PyObject) -> Py_ssize_t; // PySequence_Length is a direct alias for PySequence_Size - #[cfg_attr( - any(not(PyPy), all(PyPy, Py_3_12)), - link_name = "PySequence_Size" - )] + #[cfg_attr(any(not(PyPy), all(PyPy, Py_3_12)), link_name = "PySequence_Size")] #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Size")] pub fn PySequence_Length(o: *mut PyObject) -> Py_ssize_t; @@ -283,10 +280,7 @@ extern_libpython! { pub fn PySequence_Contains(seq: *mut PyObject, ob: *mut PyObject) -> c_int; // PySequence_In is a direct alias for PySequence_Contains - #[cfg_attr( - any(not(PyPy), all(PyPy, Py_3_12)), - link_name = "PySequence_Contains" - )] + #[cfg_attr(any(not(PyPy), all(PyPy, Py_3_12)), link_name = "PySequence_Contains")] #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Contains")] pub fn PySequence_In(o: *mut PyObject, value: *mut PyObject) -> c_int; @@ -302,10 +296,7 @@ extern_libpython! { pub fn PyMapping_Size(o: *mut PyObject) -> Py_ssize_t; // PyMapping_Length is a direct alias for PyMapping_Size - #[cfg_attr( - any(not(PyPy), all(PyPy, Py_3_12)), - link_name = "PyMapping_Size" - )] + #[cfg_attr(any(not(PyPy), all(PyPy, Py_3_12)), link_name = "PyMapping_Size")] #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMapping_Size")] pub fn PyMapping_Length(o: *mut PyObject) -> Py_ssize_t; } diff --git a/pyo3-ffi/src/cpython/context.rs b/pyo3-ffi/src/cpython/context.rs index 7e7d1170b9a..a61d85839bb 100644 --- a/pyo3-ffi/src/cpython/context.rs +++ b/pyo3-ffi/src/cpython/context.rs @@ -56,7 +56,6 @@ extern_libpython! { pub fn PyContext_ClearWatcher(watcher_id: c_int) -> c_int; #[cfg_attr(PyPy, link_name = "PyPyContextVar_New")] - pub fn PyContextVar_New(name: *const c_char, def: *mut PyObject) -> *mut PyObject; #[cfg_attr(PyPy, link_name = "PyPyContextVar_Get")] pub fn PyContextVar_Get( diff --git a/pyo3-ffi/src/cpython/funcobject.rs b/pyo3-ffi/src/cpython/funcobject.rs index 6d5575022c8..683a03dfc7c 100644 --- a/pyo3-ffi/src/cpython/funcobject.rs +++ b/pyo3-ffi/src/cpython/funcobject.rs @@ -147,7 +147,6 @@ extern_libpython! { pub static mut PyStaticMethod_Type: crate::PyTypeObject; #[cfg_attr(PyPy, link_name = "PyPyClassMethod_New")] - pub fn PyClassMethod_New(ob: *mut PyObject) -> *mut PyObject; #[cfg_attr(PyPy, link_name = "PyPyStaticMethod_New")] pub fn PyStaticMethod_New(ob: *mut PyObject) -> *mut PyObject; diff --git a/pyo3-ffi/src/cpython/marshal.rs b/pyo3-ffi/src/cpython/marshal.rs index bdba8db4b19..bcdbcaa5386 100644 --- a/pyo3-ffi/src/cpython/marshal.rs +++ b/pyo3-ffi/src/cpython/marshal.rs @@ -12,7 +12,10 @@ extern_libpython! { #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMarshal_WriteObjectToString")] pub fn PyMarshal_WriteObjectToString(object: *mut PyObject, version: c_int) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMarshal_ReadObjectFromString")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyMarshal_ReadObjectFromString" + )] pub fn PyMarshal_ReadObjectFromString(data: *const c_char, len: Py_ssize_t) -> *mut PyObject; pub fn PyMarshal_WriteLongToFile(value: c_long, file: *mut FILE, version: c_int); diff --git a/pyo3-ffi/src/import.rs b/pyo3-ffi/src/import.rs index 371653afeb0..05f9287c1cc 100644 --- a/pyo3-ffi/src/import.rs +++ b/pyo3-ffi/src/import.rs @@ -48,7 +48,10 @@ extern_libpython! { fromlist: *mut PyObject, level: c_int, ) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyImport_ImportModuleLevelObject")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyImport_ImportModuleLevelObject" + )] pub fn PyImport_ImportModuleLevelObject( name: *mut PyObject, globals: *mut PyObject, diff --git a/pyo3-ffi/src/pyerrors.rs b/pyo3-ffi/src/pyerrors.rs index 0f76f72ece3..26d27d4b04d 100644 --- a/pyo3-ffi/src/pyerrors.rs +++ b/pyo3-ffi/src/pyerrors.rs @@ -285,7 +285,10 @@ extern_libpython! { pub fn PyErr_NoMemory() -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrno")] pub fn PyErr_SetFromErrno(arg1: *mut PyObject) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilenameObject")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyErr_SetFromErrnoWithFilenameObject" + )] pub fn PyErr_SetFromErrnoWithFilenameObject( arg1: *mut PyObject, arg2: *mut PyObject, diff --git a/pyo3-ffi/src/unicodeobject.rs b/pyo3-ffi/src/unicodeobject.rs index ec51d9d443e..9c88e8b5618 100644 --- a/pyo3-ffi/src/unicodeobject.rs +++ b/pyo3-ffi/src/unicodeobject.rs @@ -213,7 +213,10 @@ extern_libpython! { length: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUnicodeEscapeString")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyUnicode_AsUnicodeEscapeString" + )] pub fn PyUnicode_AsUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; pub fn PyUnicode_DecodeRawUnicodeEscape( string: *const c_char, @@ -289,7 +292,10 @@ extern_libpython! { pub fn PyUnicode_FSDecoder(arg1: *mut PyObject, arg2: *mut c_void) -> c_int; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeFSDefault")] pub fn PyUnicode_DecodeFSDefault(s: *const c_char) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeFSDefaultAndSize")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyUnicode_DecodeFSDefaultAndSize" + )] pub fn PyUnicode_DecodeFSDefaultAndSize(s: *const c_char, size: Py_ssize_t) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_EncodeFSDefault")] pub fn PyUnicode_EncodeFSDefault(unicode: *mut PyObject) -> *mut PyObject; @@ -367,7 +373,10 @@ extern_libpython! { ) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Compare")] pub fn PyUnicode_Compare(left: *mut PyObject, right: *mut PyObject) -> c_int; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_CompareWithASCIIString")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyUnicode_CompareWithASCIIString" + )] pub fn PyUnicode_CompareWithASCIIString(left: *mut PyObject, right: *const c_char) -> c_int; #[cfg(Py_3_13)] pub fn PyUnicode_EqualToUTF8(unicode: *mut PyObject, string: *const c_char) -> c_int; From 90317dd38488b4d01563737c329c17308906f926 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Fri, 11 Sep 2026 10:11:08 +0100 Subject: [PATCH 03/14] fix ffi check failures on older versions --- pyo3-ffi-check/macro/src/lib.rs | 9 +++++---- pyo3-ffi/src/abstract_.rs | 3 +-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/pyo3-ffi-check/macro/src/lib.rs b/pyo3-ffi-check/macro/src/lib.rs index 5426e04146a..de549213dfe 100644 --- a/pyo3-ffi-check/macro/src/lib.rs +++ b/pyo3-ffi-check/macro/src/lib.rs @@ -453,9 +453,6 @@ const MACRO_EXCLUSIONS: &[(&str, &str)] = &[ ("Py_UNICODE_TODECIMAL", ""), ("Py_XDECREF", ""), ("Py_XINCREF", ""), - ("_PyCode_GetExtra", "Py_3_12"), - ("_PyCode_SetExtra", "Py_3_12"), - ("_PyEval_RequestCodeExtraIndex", "Py_3_12"), // These functions were only added in 3.10, but pyo3-ffi defines them for // all versions. Technically not macros but the machinery happens to work // the same way. @@ -496,13 +493,17 @@ const EXCLUDED_SYMBOLS: &[&str] = &[ "PyOS_BeforeFork", "PyOS_AfterFork_Parent", "PyOS_AfterFork_Child", - // TODO: PyPy 3.12 declares these symbols in its headers but does not export them. + // TODO: PyPy 3.12 declares these symbols in its headers but does not implement them? "PyMapping_Length", "PyObject_IS_GC", "PyObject_Length", "PySequence_In", "PySequence_Length", "PyType_ClearCache", + // TODO: deprecated backwards compatibility aliases to be removed in PyO3 0.31 + "_PyCode_GetExtra", + "_PyCode_SetExtra", + "_PyEval_RequestCodeExtraIndex", ]; // Assert at compile time that `MACRO_EXCLUSIONS` and `EXCLUDED_SYMBOLS` are disjoint diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index a8df976c0cf..8df288798e9 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -75,8 +75,7 @@ extern_libpython! { #[cfg_attr(PyPy, link_name = "PyPyVectorcall_NARGS")] pub fn PyVectorcall_NARGS(nargsf: size_t) -> Py_ssize_t; - #[cfg_attr(not(any(Py_3_12, PyPy)), link_name = "_PyVectorcall_Call")] // symbol made public in 3.12 - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyVectorcall_Call")] + #[cfg(Py_3_12)] pub fn PyVectorcall_Call( callable: *mut PyObject, tuple: *mut PyObject, From cab9b622d98ad049c253438211d253dd5fddd2a1 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Fri, 11 Sep 2026 12:51:56 +0100 Subject: [PATCH 04/14] fix pypy 3.11 link aliases --- newsfragments/6389.fixed.md | 1 + pyo3-ffi-check/definitions/build.rs | 22 +--------------------- pyo3-ffi-check/macro/src/lib.rs | 22 +++++++++++++++------- pyo3-ffi-check/src/main.rs | 15 +++++++++------ pyo3-ffi/src/abstract_.rs | 1 + pyo3-ffi/src/bytesobject.rs | 1 + pyo3-ffi/src/codecs.rs | 4 ++++ pyo3-ffi/src/descrobject.rs | 3 +++ pyo3-ffi/src/fileobject.rs | 3 ++- pyo3-ffi/src/methodobject.rs | 1 + pyo3-ffi/src/modsupport.rs | 2 +- pyo3-ffi/src/object.rs | 2 ++ pyo3-ffi/src/objimpl.rs | 9 ++++++++- pyo3-ffi/src/pyerrors.rs | 2 ++ pyo3-ffi/src/pyframe.rs | 1 + pyo3-ffi/src/pylifecycle.rs | 2 ++ pyo3-ffi/src/unicodeobject.rs | 20 ++++++++++++++++++++ 17 files changed, 74 insertions(+), 37 deletions(-) create mode 100644 newsfragments/6389.fixed.md diff --git a/newsfragments/6389.fixed.md b/newsfragments/6389.fixed.md new file mode 100644 index 00000000000..eeb3b5af576 --- /dev/null +++ b/newsfragments/6389.fixed.md @@ -0,0 +1 @@ +Fix many unresolved symbols when linking for PyPy due to incorrect link names in `pyo3-ffi`. diff --git a/pyo3-ffi-check/definitions/build.rs b/pyo3-ffi-check/definitions/build.rs index 02e765d77ed..5899215c62e 100644 --- a/pyo3-ffi-check/definitions/build.rs +++ b/pyo3-ffi-check/definitions/build.rs @@ -19,19 +19,6 @@ impl bindgen::callbacks::ParseCallbacks for ParseCallbacks { } } -#[derive(Debug)] -struct PyPyReplaceCallbacks; - -impl bindgen::callbacks::ParseCallbacks for PyPyReplaceCallbacks { - fn item_name(&self, item_info: ItemInfo<'_>) -> Option { - if item_info.name.starts_with("PyPy") || item_info.name.starts_with("_PyPy") { - Some(item_info.name.replacen("PyPy", "Py", 1)) - } else { - None - } - } -} - fn main() { let config = pyo3_build_config::get(); @@ -57,7 +44,7 @@ fn main() { println!("cargo:rerun-if-changed=wrapper.h"); - let mut builder = bindgen::Builder::default() + let builder = bindgen::Builder::default() .header("wrapper.h") .clang_args(clang_args) .parse_callbacks(Box::new(bindgen::CargoCallbacks::new())) @@ -69,13 +56,6 @@ fn main() { .blocklist_item("strlen") .blocklist_item("bcmp"); - if matches!( - config.implementation(), - pyo3_build_config::PythonImplementation::PyPy - ) { - builder = builder.parse_callbacks(Box::new(PyPyReplaceCallbacks)); - } - let bindings = builder // blocklist some values which apparently have conflicting definitions on unix .blocklist_item("FP_NORMAL") diff --git a/pyo3-ffi-check/macro/src/lib.rs b/pyo3-ffi-check/macro/src/lib.rs index de549213dfe..6a786daa1b1 100644 --- a/pyo3-ffi-check/macro/src/lib.rs +++ b/pyo3-ffi-check/macro/src/lib.rs @@ -557,13 +557,20 @@ pub fn for_all_functions(_input: proc_macro::TokenStream) -> proc_macro::TokenSt continue; } - if pyo3_build_config::get().implementation() - == pyo3_build_config::PythonImplementation::PyPy - { + let mut bindgen_name = function_name.to_owned(); + if pyo3_build_config::get().implementation() == PythonImplementation::PyPy { + // For PyPy, some functions are prefixed with "PyPy", we check whether the + // bindgen name contains the prefixed name and use that if it does. + if function_name.starts_with("Py") || function_name.starts_with("_Py") { + let prefixed_name = function_name.replacen("Py", "PyPy", 1); + if BINDGEN_FUNCTION_NAMES.contains(&prefixed_name) { + bindgen_name = prefixed_name; + } + } // If the function doesn't exist in PyPy, for now we don't care: // - For PyO3 inline functions it's probably fine to include anyway // - For extern symbols - PyPy may add them in a future release - if !BINDGEN_FUNCTION_NAMES.contains(function_name) { + if !BINDGEN_FUNCTION_NAMES.contains(&bindgen_name) { continue; } } @@ -623,6 +630,7 @@ pub fn for_all_functions(_input: proc_macro::TokenStream) -> proc_macro::TokenSt }; let function_ident = Ident::new(function_name, Span::call_site()); + let bindgen_ident = Ident::new(&bindgen_name, Span::call_site()); let arg_types = std::iter::repeat_n(quote!(_), arg_count); @@ -649,7 +657,7 @@ pub fn for_all_functions(_input: proc_macro::TokenStream) -> proc_macro::TokenSt .map(|(_, cfg)| if cfg.is_empty() { "all()" } else { *cfg }) .map(|cfg| cfg.parse().expect("failed to parse macro exclusion cfg")); - let has_symbol = BINDGEN_FUNCTION_NAMES.contains(function_name); + let has_symbol = BINDGEN_FUNCTION_NAMES.contains(&bindgen_name); match (macro_exclusion_cfg, has_symbol) { (Some(cfg), true) => { // emit an error if checking within the cfgs where a macro is expected @@ -659,7 +667,7 @@ pub fn for_all_functions(_input: proc_macro::TokenStream) -> proc_macro::TokenSt output.extend(quote!(#[cfg(#cfg)] compile_error!(#error_message);)); // if not within the macro range, we found a symbol, this should be good output.extend( - quote!(#[cfg(not(#cfg))] #macro_name!(#inline #function_ident, #modifiers (#(#arg_types),* #vararg));), + quote!(#[cfg(not(#cfg))] #macro_name!(#inline #function_ident, #bindgen_ident, #modifiers (#(#arg_types),* #vararg));), ); } (Some(cfg), false) => { @@ -673,7 +681,7 @@ pub fn for_all_functions(_input: proc_macro::TokenStream) -> proc_macro::TokenSt (None, true) => { // emit the comparison macro to check that the argument count matches output.extend( - quote!(#macro_name!(#inline #function_ident, #modifiers (#(#arg_types),* #vararg));), + quote!(#macro_name!(#inline #function_ident, #bindgen_ident, #modifiers (#(#arg_types),* #vararg));), ); } (None, false) => { diff --git a/pyo3-ffi-check/src/main.rs b/pyo3-ffi-check/src/main.rs index 818f0e973ed..9e42045ec28 100644 --- a/pyo3-ffi-check/src/main.rs +++ b/pyo3-ffi-check/src/main.rs @@ -144,12 +144,15 @@ fn main() { }; } + // Check that the function signatures are compatible between pyo3-ffi and bindgen. + // + // Typically `name` == `bindgen_name`, but e.g. for PyPy this is not the case. macro_rules! check_function { - ($name:ident, [$($modifiers:tt)*] ($($arg_types:tt)*)) => {{ + ($name:ident, $bindgen_name:ident, [$($modifiers:tt)*] ($($arg_types:tt)*)) => {{ // Check functions have the same number of arguments #[allow(deprecated)] let pyo3_ffi_fn = { pyo3_ffi::$name as $($modifiers)* fn($($arg_types)*) -> _ }; - let bindgen_fn = bindings::$name as $($modifiers)* fn($($arg_types)*) -> _; + let bindgen_fn = bindings::$bindgen_name as $($modifiers)* fn($($arg_types)*) -> _; // Check function addresses are the same (i.e. link is configured as expected). // This will also trigger build errors if linker fails to find the symbol pyo3-ffi @@ -172,17 +175,17 @@ fn main() { // Check return types are compatible #[allow(deprecated)] let pyo3_ffi_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((pyo3_ffi::$name)($($arg_types)*)) }); - let bindgen_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((bindings::$name)($($arg_types)*)) }); + let bindgen_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((bindings::$bindgen_name)($($arg_types)*)) }); failed |= !ReturnTypeSniffer::check_compatible(stringify!($name), &pyo3_ffi_return_type, &bindgen_return_type); }}; // case when the function is an inline function in the headers, in which case pyo3-ffi will use the // Rust abi and the extern symbol uses the C abi - (@inline $name:ident, ($($arg_types:tt)*)) => {{ + (@inline $name:ident, $bindgen_name:ident, ($($arg_types:tt)*)) => {{ // Check functions have the same number of arguments #[allow(deprecated)] { pyo3_ffi::$name as unsafe fn($($arg_types)*) -> _ }; - bindings::$name as unsafe extern "C" fn($($arg_types)*) -> _; + bindings::$bindgen_name as unsafe extern "C" fn($($arg_types)*) -> _; // TODO: can probably sniff arg types by binding sniffers for each argument position and then passing // those inside `todo_args!` to use type inference for each argument. @@ -190,7 +193,7 @@ fn main() { // Check return types are compatible #[allow(deprecated)] let pyo3_ffi_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((pyo3_ffi::$name)($($arg_types)*)) }); - let bindgen_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((bindings::$name)($($arg_types)*)) }); + let bindgen_return_type = ReturnTypeSniffer::new(|| unsafe { todo_args!((bindings::$bindgen_name)($($arg_types)*)) }); failed |= !ReturnTypeSniffer::check_compatible(stringify!($name), &pyo3_ffi_return_type, &bindgen_return_type); }}; diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index 8df288798e9..877f3c0c6a1 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -235,6 +235,7 @@ extern_libpython! { pub fn PyNumber_InPlaceXor(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_InPlaceOr")] pub fn PyNumber_InPlaceOr(o1: *mut PyObject, o2: *mut PyObject) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyNumber_ToBase")] pub fn PyNumber_ToBase(n: *mut PyObject, base: c_int) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPySequence_Check")] diff --git a/pyo3-ffi/src/bytesobject.rs b/pyo3-ffi/src/bytesobject.rs index 4417e635735..12348c540f2 100644 --- a/pyo3-ffi/src/bytesobject.rs +++ b/pyo3-ffi/src/bytesobject.rs @@ -29,6 +29,7 @@ extern_libpython! { #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromStringAndSize")] pub fn PyBytes_FromStringAndSize(arg1: *const c_char, arg2: Py_ssize_t) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromString")] pub fn PyBytes_FromString(arg1: *const c_char) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyBytes_FromObject")] pub fn PyBytes_FromObject(arg1: *mut PyObject) -> *mut PyObject; diff --git a/pyo3-ffi/src/codecs.rs b/pyo3-ffi/src/codecs.rs index e76afc9ca82..fb146a43ddf 100644 --- a/pyo3-ffi/src/codecs.rs +++ b/pyo3-ffi/src/codecs.rs @@ -9,11 +9,13 @@ extern_libpython! { // skipped non-limited _PyCodec_Lookup from Include/codecs.h // skipped non-limited _PyCodec_Forget from Include/codecs.h pub fn PyCodec_KnownEncoding(encoding: *const c_char) -> c_int; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_Encode")] pub fn PyCodec_Encode( object: *mut PyObject, encoding: *const c_char, errors: *const c_char, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_Decode")] pub fn PyCodec_Decode( object: *mut PyObject, encoding: *const c_char, @@ -24,7 +26,9 @@ extern_libpython! { // skipped non-limited _PyCodec_DecodeText from Include/codecs.h // skipped non-limited _PyCodecInfo_GetIncrementalDecoder from Include/codecs.h // skipped non-limited _PyCodecInfo_GetIncrementalEncoder from Include/codecs.h + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_Encoder")] pub fn PyCodec_Encoder(encoding: *const c_char) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_Decoder")] pub fn PyCodec_Decoder(encoding: *const c_char) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCodec_IncrementalEncoder")] pub fn PyCodec_IncrementalEncoder( diff --git a/pyo3-ffi/src/descrobject.rs b/pyo3-ffi/src/descrobject.rs index 2c5fec5ca7c..23f8cbc272a 100644 --- a/pyo3-ffi/src/descrobject.rs +++ b/pyo3-ffi/src/descrobject.rs @@ -54,6 +54,7 @@ extern_libpython! { } extern_libpython! { + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDescr_NewMethod")] pub fn PyDescr_NewMethod(arg1: *mut PyTypeObject, arg2: *mut PyMethodDef) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyDescr_NewClassMethod")] pub fn PyDescr_NewClassMethod(arg1: *mut PyTypeObject, arg2: *mut PyMethodDef) @@ -128,6 +129,8 @@ pub const _Py_WRITE_RESTRICTED: c_int = 4; // Deprecated, no-op. Do not reuse th pub const Py_RELATIVE_OFFSET: c_int = 8; extern_libpython! { + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMember_GetOne")] pub fn PyMember_GetOne(addr: *const c_char, l: *mut PyMemberDef) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyMember_SetOne")] pub fn PyMember_SetOne(addr: *mut c_char, l: *mut PyMemberDef, value: *mut PyObject) -> c_int; } diff --git a/pyo3-ffi/src/fileobject.rs b/pyo3-ffi/src/fileobject.rs index 04f5a7f3dd2..3c8873f92f0 100644 --- a/pyo3-ffi/src/fileobject.rs +++ b/pyo3-ffi/src/fileobject.rs @@ -4,6 +4,7 @@ use core::ffi::{c_char, c_int}; pub const PY_STDIOTEXTMODE: &str = "b"; extern_libpython! { + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_FromFd")] pub fn PyFile_FromFd( arg1: c_int, arg2: *const c_char, @@ -20,7 +21,7 @@ extern_libpython! { pub fn PyFile_WriteObject(arg1: *mut PyObject, arg2: *mut PyObject, arg3: c_int) -> c_int; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_WriteString")] pub fn PyFile_WriteString(arg1: *const c_char, arg2: *mut PyObject) -> c_int; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFile_AsFileDescriptor")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_AsFileDescriptor")] pub fn PyObject_AsFileDescriptor(arg1: *mut PyObject) -> c_int; } diff --git a/pyo3-ffi/src/methodobject.rs b/pyo3-ffi/src/methodobject.rs index 758d4e18002..8fe4942bda8 100644 --- a/pyo3-ffi/src/methodobject.rs +++ b/pyo3-ffi/src/methodobject.rs @@ -88,6 +88,7 @@ extern_libpython! { pub fn PyCFunction_GetFlags(f: *mut PyObject) -> c_int; #[cfg(not(Py_3_13))] #[deprecated(note = "Python 3.9")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyCFunction_Call")] pub fn PyCFunction_Call( f: *mut PyObject, args: *mut PyObject, diff --git a/pyo3-ffi/src/modsupport.rs b/pyo3-ffi/src/modsupport.rs index 953bcb67f48..87270ca0a18 100644 --- a/pyo3-ffi/src/modsupport.rs +++ b/pyo3-ffi/src/modsupport.rs @@ -64,7 +64,6 @@ extern_libpython! { value: *const c_char, ) -> c_int; #[cfg(any(Py_3_10, not(Py_LIMITED_API)))] - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddType")] pub fn PyModule_AddType( module: *mut PyObject, type_: *mut crate::object::PyTypeObject, @@ -72,6 +71,7 @@ extern_libpython! { // skipped PyModule_AddIntMacro // skipped PyModule_AddStringMacro pub fn PyModule_SetDocString(arg1: *mut PyObject, arg2: *const c_char) -> c_int; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_AddFunctions")] pub fn PyModule_AddFunctions(arg1: *mut PyObject, arg2: *mut PyMethodDef) -> c_int; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyModule_ExecDef")] pub fn PyModule_ExecDef(module: *mut PyObject, def: *mut PyModuleDef) -> c_int; diff --git a/pyo3-ffi/src/object.rs b/pyo3-ffi/src/object.rs index c6dbd2df693..08f705f7bf6 100644 --- a/pyo3-ffi/src/object.rs +++ b/pyo3-ffi/src/object.rs @@ -540,7 +540,9 @@ extern_libpython! { #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyObject_Dir")] pub fn PyObject_Dir(arg1: *mut PyObject) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_ReprEnter")] pub fn Py_ReprEnter(arg1: *mut PyObject) -> c_int; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPy_ReprLeave")] pub fn Py_ReprLeave(arg1: *mut PyObject); } diff --git a/pyo3-ffi/src/objimpl.rs b/pyo3-ffi/src/objimpl.rs index 6e2baf0fc88..1f62f2ef94a 100644 --- a/pyo3-ffi/src/objimpl.rs +++ b/pyo3-ffi/src/objimpl.rs @@ -52,9 +52,16 @@ pub unsafe fn PyObject_NewVar(typeobj: *mut PyTypeObject, n: Py_ssize_t) -> * // skipped PyObject_NEW_VAR +#[cfg(not(all(PyPy, not(Py_3_12))))] +type PyGCCollectReturn = Py_ssize_t; + +// PyPy before 3.12 seems to use `int` for return type +#[cfg(all(PyPy, not(Py_3_12)))] +type PyGCCollectReturn = c_int; + extern_libpython! { #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_Collect")] - pub fn PyGC_Collect() -> Py_ssize_t; + pub fn PyGC_Collect() -> PyGCCollectReturn; #[cfg(Py_3_10)] #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyGC_Enable")] diff --git a/pyo3-ffi/src/pyerrors.rs b/pyo3-ffi/src/pyerrors.rs index 26d27d4b04d..b21297c0e7f 100644 --- a/pyo3-ffi/src/pyerrors.rs +++ b/pyo3-ffi/src/pyerrors.rs @@ -293,11 +293,13 @@ extern_libpython! { arg1: *mut PyObject, arg2: *mut PyObject, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilenameObjects")] pub fn PyErr_SetFromErrnoWithFilenameObjects( arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilename")] pub fn PyErr_SetFromErrnoWithFilename( exc: *mut PyObject, filename: *const c_char, diff --git a/pyo3-ffi/src/pyframe.rs b/pyo3-ffi/src/pyframe.rs index b8aebaf070c..6f2bec0db1e 100644 --- a/pyo3-ffi/src/pyframe.rs +++ b/pyo3-ffi/src/pyframe.rs @@ -5,6 +5,7 @@ use crate::PyFrameObject; use core::ffi::c_int; extern_libpython! { + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyFrame_GetLineNumber")] pub fn PyFrame_GetLineNumber(frame: *mut PyFrameObject) -> c_int; #[cfg(not(GraalPy))] diff --git a/pyo3-ffi/src/pylifecycle.rs b/pyo3-ffi/src/pylifecycle.rs index e95b652c686..b3bbdffab7a 100644 --- a/pyo3-ffi/src/pylifecycle.rs +++ b/pyo3-ffi/src/pylifecycle.rs @@ -93,7 +93,9 @@ extern_libpython! { type PyOS_sighandler_t = unsafe extern "C" fn(arg1: c_int); extern_libpython! { + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_getsig")] pub fn PyOS_getsig(arg1: c_int) -> PyOS_sighandler_t; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyOS_setsig")] pub fn PyOS_setsig(arg1: c_int, arg2: PyOS_sighandler_t) -> PyOS_sighandler_t; #[cfg(Py_3_11)] diff --git a/pyo3-ffi/src/unicodeobject.rs b/pyo3-ffi/src/unicodeobject.rs index 9c88e8b5618..1aece46c51a 100644 --- a/pyo3-ffi/src/unicodeobject.rs +++ b/pyo3-ffi/src/unicodeobject.rs @@ -41,19 +41,23 @@ extern_libpython! { #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromStringAndSize")] pub fn PyUnicode_FromStringAndSize(u: *const c_char, size: Py_ssize_t) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FromString")] pub fn PyUnicode_FromString(u: *const c_char) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Substring")] pub fn PyUnicode_Substring( str: *mut PyObject, start: Py_ssize_t, end: Py_ssize_t, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUCS4")] pub fn PyUnicode_AsUCS4( unicode: *mut PyObject, buffer: *mut Py_UCS4, buflen: Py_ssize_t, copy_null: c_int, ) -> *mut Py_UCS4; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsUCS4Copy")] pub fn PyUnicode_AsUCS4Copy(unicode: *mut PyObject) -> *mut Py_UCS4; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_GetLength")] pub fn PyUnicode_GetLength(unicode: *mut PyObject) -> Py_ssize_t; @@ -61,7 +65,9 @@ extern_libpython! { #[deprecated(note = "Removed in Python 3.12")] #[cfg_attr(PyPy, link_name = "PyPyUnicode_GetSize")] pub fn PyUnicode_GetSize(unicode: *mut PyObject) -> Py_ssize_t; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_ReadChar")] pub fn PyUnicode_ReadChar(unicode: *mut PyObject, index: Py_ssize_t) -> Py_UCS4; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_WriteChar")] pub fn PyUnicode_WriteChar( unicode: *mut PyObject, index: Py_ssize_t, @@ -218,11 +224,16 @@ extern_libpython! { link_name = "PyPyUnicode_AsUnicodeEscapeString" )] pub fn PyUnicode_AsUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeRawUnicodeEscape")] pub fn PyUnicode_DecodeRawUnicodeEscape( string: *const c_char, length: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyUnicode_AsRawUnicodeEscapeString" + )] pub fn PyUnicode_AsRawUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeLatin1")] pub fn PyUnicode_DecodeLatin1( @@ -279,12 +290,15 @@ extern_libpython! { unicode: *mut PyObject, errors: *const c_char, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeLocaleAndSize")] pub fn PyUnicode_DecodeLocaleAndSize( str: *const c_char, len: Py_ssize_t, errors: *const c_char, ) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeLocale")] pub fn PyUnicode_DecodeLocale(str: *const c_char, errors: *const c_char) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_EncodeLocale")] pub fn PyUnicode_EncodeLocale(unicode: *mut PyObject, errors: *const c_char) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FSConverter")] pub fn PyUnicode_FSConverter(arg1: *mut PyObject, arg2: *mut c_void) -> c_int; @@ -301,7 +315,9 @@ extern_libpython! { pub fn PyUnicode_EncodeFSDefault(unicode: *mut PyObject) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Concat")] pub fn PyUnicode_Concat(left: *mut PyObject, right: *mut PyObject) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Append")] pub fn PyUnicode_Append(pleft: *mut *mut PyObject, right: *mut PyObject); + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AppendAndDel")] pub fn PyUnicode_AppendAndDel(pleft: *mut *mut PyObject, right: *mut PyObject); #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Split")] pub fn PyUnicode_Split( @@ -350,6 +366,7 @@ extern_libpython! { end: Py_ssize_t, direction: c_int, ) -> Py_ssize_t; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_FindChar")] pub fn PyUnicode_FindChar( str: *mut PyObject, ch: Py_UCS4, @@ -388,6 +405,7 @@ extern_libpython! { ) -> c_int; #[cfg(Py_3_14)] pub fn PyUnicode_Equal(str1: *mut PyObject, str2: *mut PyObject) -> c_int; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_RichCompare")] pub fn PyUnicode_RichCompare( left: *mut PyObject, right: *mut PyObject, @@ -395,6 +413,8 @@ extern_libpython! { ) -> *mut PyObject; #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Format")] pub fn PyUnicode_Format(format: *mut PyObject, args: *mut PyObject) -> *mut PyObject; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_Contains")] pub fn PyUnicode_Contains(container: *mut PyObject, element: *mut PyObject) -> c_int; + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_IsIdentifier")] pub fn PyUnicode_IsIdentifier(s: *mut PyObject) -> c_int; } From 2a937258f4d29c15cfab3dd3c42465753e76d2f5 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Fri, 11 Sep 2026 12:52:45 +0100 Subject: [PATCH 05/14] fmt --- pyo3-ffi/src/pyerrors.rs | 10 ++++++++-- pyo3-ffi/src/unicodeobject.rs | 5 ++++- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/pyo3-ffi/src/pyerrors.rs b/pyo3-ffi/src/pyerrors.rs index b21297c0e7f..edc51310d68 100644 --- a/pyo3-ffi/src/pyerrors.rs +++ b/pyo3-ffi/src/pyerrors.rs @@ -293,13 +293,19 @@ extern_libpython! { arg1: *mut PyObject, arg2: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilenameObjects")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyErr_SetFromErrnoWithFilenameObjects" + )] pub fn PyErr_SetFromErrnoWithFilenameObjects( arg1: *mut PyObject, arg2: *mut PyObject, arg3: *mut PyObject, ) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyErr_SetFromErrnoWithFilename")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyErr_SetFromErrnoWithFilename" + )] pub fn PyErr_SetFromErrnoWithFilename( exc: *mut PyObject, filename: *const c_char, diff --git a/pyo3-ffi/src/unicodeobject.rs b/pyo3-ffi/src/unicodeobject.rs index 1aece46c51a..0ad3a598ac1 100644 --- a/pyo3-ffi/src/unicodeobject.rs +++ b/pyo3-ffi/src/unicodeobject.rs @@ -224,7 +224,10 @@ extern_libpython! { link_name = "PyPyUnicode_AsUnicodeEscapeString" )] pub fn PyUnicode_AsUnicodeEscapeString(unicode: *mut PyObject) -> *mut PyObject; - #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeRawUnicodeEscape")] + #[cfg_attr( + all(PyPy, not(Py_3_12)), + link_name = "PyPyUnicode_DecodeRawUnicodeEscape" + )] pub fn PyUnicode_DecodeRawUnicodeEscape( string: *const c_char, length: Py_ssize_t, From 53471c4cd88b8fa32d192cb904cee0567d4cb636 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Fri, 11 Sep 2026 14:40:02 +0100 Subject: [PATCH 06/14] try fix windows build --- pyo3-ffi-check/definitions/build.rs | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/pyo3-ffi-check/definitions/build.rs b/pyo3-ffi-check/definitions/build.rs index 5899215c62e..a57dbd52921 100644 --- a/pyo3-ffi-check/definitions/build.rs +++ b/pyo3-ffi-check/definitions/build.rs @@ -42,6 +42,17 @@ fn main() { vec![format!("-I{python_include_dir}")] }; + // Windows requires a link library to resolve symbols for the function address checks + if env::var("TARGET").is_ok_and(|t| t.contains("windows")) { + if let Some(python_lib_dir) = config.lib_dir() { + println!("cargo:rustc-link-search=native={python_lib_dir}"); + } + + if let Some(python_lib_name) = config.lib_name() { + println!("cargo:rustc-link-lib={python_lib_name}"); + } + } + println!("cargo:rerun-if-changed=wrapper.h"); let builder = bindgen::Builder::default() From 6afd8e88aa0dc6fbd940e04effa4836a861758b2 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Fri, 11 Sep 2026 15:31:04 +0100 Subject: [PATCH 07/14] try to fix windows --- pyo3-ffi-check/definitions/Cargo.toml | 3 +- pyo3-ffi-check/definitions/build.rs | 59 +++++++++++++++++++++------ 2 files changed, 48 insertions(+), 14 deletions(-) diff --git a/pyo3-ffi-check/definitions/Cargo.toml b/pyo3-ffi-check/definitions/Cargo.toml index 2cd1b7f6854..729969338bb 100644 --- a/pyo3-ffi-check/definitions/Cargo.toml +++ b/pyo3-ffi-check/definitions/Cargo.toml @@ -8,5 +8,6 @@ publish = false pyo3-ffi = { path = "../../pyo3-ffi" } [build-dependencies] -bindgen = "0.72" +bindgen = "0.73" +target-lexicon = "0.13" pyo3-build-config = { path = "../../pyo3-build-config" } diff --git a/pyo3-ffi-check/definitions/build.rs b/pyo3-ffi-check/definitions/build.rs index a57dbd52921..394858d8336 100644 --- a/pyo3-ffi-check/definitions/build.rs +++ b/pyo3-ffi-check/definitions/build.rs @@ -1,7 +1,8 @@ use std::env; use std::path::PathBuf; -use bindgen::callbacks::ItemInfo; +use bindgen::callbacks::{ItemInfo, ItemKind}; +use target_lexicon::{Architecture, OperatingSystem, Triple}; #[derive(Debug)] struct ParseCallbacks; @@ -19,8 +20,24 @@ impl bindgen::callbacks::ParseCallbacks for ParseCallbacks { } } +#[derive(Debug)] +struct WindowsX86RawDylibCallbacks; + +// Matches the adjustment in `pyo3-ffi` to force the link name for functions starting +// with `_Py` (see `pyo3-ffi/src/impl_/macros.rs`) +impl bindgen::callbacks::ParseCallbacks for WindowsX86RawDylibCallbacks { + fn generated_link_name_override(&self, item: ItemInfo<'_>) -> Option { + if item.kind == ItemKind::Function && item.name.starts_with("_Py") { + Some(format!("_{}", item.name)) + } else { + None + } + } +} + fn main() { let config = pyo3_build_config::get(); + let target: Triple = env::var("TARGET").unwrap().parse().unwrap(); let python_include_dir = config .run_python_script( @@ -42,20 +59,9 @@ fn main() { vec![format!("-I{python_include_dir}")] }; - // Windows requires a link library to resolve symbols for the function address checks - if env::var("TARGET").is_ok_and(|t| t.contains("windows")) { - if let Some(python_lib_dir) = config.lib_dir() { - println!("cargo:rustc-link-search=native={python_lib_dir}"); - } - - if let Some(python_lib_name) = config.lib_name() { - println!("cargo:rustc-link-lib={python_lib_name}"); - } - } - println!("cargo:rerun-if-changed=wrapper.h"); - let builder = bindgen::Builder::default() + let mut builder = bindgen::Builder::default() .header("wrapper.h") .clang_args(clang_args) .parse_callbacks(Box::new(bindgen::CargoCallbacks::new())) @@ -67,6 +73,33 @@ fn main() { .blocklist_item("strlen") .blocklist_item("bcmp"); + // Match PyO3's choice to use raw-dylib linking on Windows for the bindgen symbols + // so that link resolution is done identically + if target.operating_system == OperatingSystem::Windows { + println!("cargo:rerun-if-env-changed=PYO3_USE_RAW_DYLIB"); + let lib_name = config.lib_name().expect("missing Python library name"); + if env::var("PYO3_USE_RAW_DYLIB").map_or(true, |value| value == "1") { + // Make sure that only `Py` symbols have raw-dylib bindings generated + // rather than any CRT standard library stuff + builder = builder + .allowlist_type(".*") + .allowlist_function("_?Py.*") + .allowlist_var("_?Py.*|PY.*"); + + // Matches the adjustment in `pyo3-ffi` to force the link name for functions starting + // with `_Py` (see `pyo3-ffi/src/impl_/macros.rs`) + let import_name_type = if matches!(target.architecture, Architecture::X86_32(_)) { + builder = builder.parse_callbacks(Box::new(WindowsX86RawDylibCallbacks)); + ", import_name_type = \"undecorated\"" + } else { + "" + }; + builder = builder.extern_block_attrs(format!( + "#[link(name = \"{lib_name}\", kind = \"raw-dylib\"{import_name_type})]" + )); + } + } + let bindings = builder // blocklist some values which apparently have conflicting definitions on unix .blocklist_item("FP_NORMAL") From 1efc64fa153c3a72e35322b0c7e6f6a738534db8 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Mon, 14 Sep 2026 09:10:48 +0100 Subject: [PATCH 08/14] try switch to allowlist for bindgen --- pyo3-ffi-check/definitions/build.rs | 43 +++++------------------------ 1 file changed, 7 insertions(+), 36 deletions(-) diff --git a/pyo3-ffi-check/definitions/build.rs b/pyo3-ffi-check/definitions/build.rs index 394858d8336..aca869f6ae7 100644 --- a/pyo3-ffi-check/definitions/build.rs +++ b/pyo3-ffi-check/definitions/build.rs @@ -43,7 +43,7 @@ fn main() { .run_python_script( "import sysconfig; print(sysconfig.get_config_var('INCLUDEPY'), end='');", ) - .expect("failed to get lib dir"); + .expect("failed to get include dir"); let gil_disabled_on_windows = config .run_python_script( "import sysconfig; import platform; print(sysconfig.get_config_var('Py_GIL_DISABLED') == 1 and platform.system() == 'Windows');", @@ -66,12 +66,11 @@ fn main() { .clang_args(clang_args) .parse_callbacks(Box::new(bindgen::CargoCallbacks::new())) .parse_callbacks(Box::new(ParseCallbacks)) - .blocklist_item("memcpy") - .blocklist_item("memmove") - .blocklist_item("memset") - .blocklist_item("memcmp") - .blocklist_item("strlen") - .blocklist_item("bcmp"); + // Minimising bindgen output to `Py` symbols and their dependencies, avoiding + // system declarations etc which are not relevant to `pyo3-ffi-check`. + .allowlist_type("_?Py.*") + .allowlist_function("_?Py.*") + .allowlist_var("_?Py.*|PY.*"); // Match PyO3's choice to use raw-dylib linking on Windows for the bindgen symbols // so that link resolution is done identically @@ -79,15 +78,6 @@ fn main() { println!("cargo:rerun-if-env-changed=PYO3_USE_RAW_DYLIB"); let lib_name = config.lib_name().expect("missing Python library name"); if env::var("PYO3_USE_RAW_DYLIB").map_or(true, |value| value == "1") { - // Make sure that only `Py` symbols have raw-dylib bindings generated - // rather than any CRT standard library stuff - builder = builder - .allowlist_type(".*") - .allowlist_function("_?Py.*") - .allowlist_var("_?Py.*|PY.*"); - - // Matches the adjustment in `pyo3-ffi` to force the link name for functions starting - // with `_Py` (see `pyo3-ffi/src/impl_/macros.rs`) let import_name_type = if matches!(target.architecture, Architecture::X86_32(_)) { builder = builder.parse_callbacks(Box::new(WindowsX86RawDylibCallbacks)); ", import_name_type = \"undecorated\"" @@ -100,26 +90,7 @@ fn main() { } } - let bindings = builder - // blocklist some values which apparently have conflicting definitions on unix - .blocklist_item("FP_NORMAL") - .blocklist_item("FP_SUBNORMAL") - .blocklist_item("FP_NAN") - .blocklist_item("FP_INFINITE") - .blocklist_item("FP_INT_UPWARD") - .blocklist_item("FP_INT_DOWNWARD") - .blocklist_item("FP_INT_TOWARDZERO") - .blocklist_item("FP_INT_TONEARESTFROMZERO") - .blocklist_item("FP_INT_TONEAREST") - .blocklist_item("FP_ZERO") - // blocklist mingw specific types - .blocklist_type("__mingw_ldbl_type_t") - // ARM neon intrinsics cause issue on GitHub actions windows CI, also not relevant to - // what we're trying to check anyway. - .blocklist_file(r".*(\\|/)arm(64)?_neon\.h") - .blocklist_file(r".*(\\|/)arm_vector_types\.h") - .generate() - .expect("Unable to generate bindings"); + let bindings = builder.generate().expect("Unable to generate bindings"); let out_path = PathBuf::from(env::var("OUT_DIR").unwrap()); bindings From 0425d70d370673468ef05633869858b17f3af626 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Mon, 14 Sep 2026 09:55:38 +0100 Subject: [PATCH 09/14] try to make link failures on windows easier to diagnose --- noxfile.py | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/noxfile.py b/noxfile.py index 3344bd0bb71..ca70d05c47d 100644 --- a/noxfile.py +++ b/noxfile.py @@ -1334,7 +1334,16 @@ def load_pkg_versions(): @nox.session(name="ffi-check") def ffi_check(session: nox.Session): - _run_cargo(session, "run", _FFI_CHECK) + # on windows, missing symbols are reported best at link time against a + # proper import library, so running with raw dylib disabled gets the best + # feedback. Exercise both paths. + no_raw_dylib_env = {**os.environ, "PYO3_USE_RAW_DYLIB": "0"} + raw_dylib_env = {**os.environ, "PYO3_USE_RAW_DYLIB": "1"} + if sys.platform == "win32": + # only relevant to run this on windows; the env var is ignored on + # other platforms + _run_cargo(session, "run", _FFI_CHECK, env=no_raw_dylib_env) + _run_cargo(session, "run", _FFI_CHECK, env=raw_dylib_env) _check_raw_dylib_macro(session) From 756151dd89600e420d6b068178c123cd39ab6f80 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Mon, 14 Sep 2026 11:30:09 +0100 Subject: [PATCH 10/14] fix link name for pypy without raw-dylib --- pyo3-ffi/build.rs | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/pyo3-ffi/build.rs b/pyo3-ffi/build.rs index df985dbe0b6..70e193d2cae 100644 --- a/pyo3-ffi/build.rs +++ b/pyo3-ffi/build.rs @@ -276,6 +276,30 @@ fn emit_link_config(build_config: &BuildConfig) -> Result<()> { return Ok(()); } + // Not using raw-dylib linking: PyPy dll needs to be the import library not the DLL name + let lib_name = if interpreter_config.target_abi().implementation() == PythonImplementation::PyPy + && target_os == "windows" + { + // FIXME: this should probably be done with better configuration in pyo3-build-config + // for `raw-dylib` in general, rather than as a patch here. + // + // Assert expected raw pypy dll name as a sanity check for now + assert_eq!( + lib_name, + format!( + "libpypy3.{}-c", + interpreter_config.target_abi().version().minor + ) + ); + format!( + "python{}{}", + interpreter_config.target_abi().version().major, + interpreter_config.target_abi().version().minor + ) + } else { + lib_name.to_string() + }; + println!( "cargo:rustc-link-lib={link_model}{alias}{lib_name}", link_model = if interpreter_config.shared() { From 584bfdba697b8d0382f1cc3de1a3ad091d0b14f7 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Mon, 14 Sep 2026 13:05:05 +0100 Subject: [PATCH 11/14] fix missing PyPy link name attributes --- pyo3-ffi/src/unicodeobject.rs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/pyo3-ffi/src/unicodeobject.rs b/pyo3-ffi/src/unicodeobject.rs index 0ad3a598ac1..08c550a3a14 100644 --- a/pyo3-ffi/src/unicodeobject.rs +++ b/pyo3-ffi/src/unicodeobject.rs @@ -265,6 +265,7 @@ extern_libpython! { mapping: *mut PyObject, ) -> *mut PyObject; #[cfg(target_os = "windows")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_DecodeMBCS")] pub fn PyUnicode_DecodeMBCS( string: *const c_char, length: Py_ssize_t, @@ -286,8 +287,10 @@ extern_libpython! { consumed: *mut Py_ssize_t, ) -> *mut PyObject; #[cfg(target_os = "windows")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_AsMBCSString")] pub fn PyUnicode_AsMBCSString(unicode: *mut PyObject) -> *mut PyObject; #[cfg(target_os = "windows")] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyUnicode_EncodeCodePage")] pub fn PyUnicode_EncodeCodePage( code_page: c_int, unicode: *mut PyObject, From 55a3e5f5eb1df973a6906e454512a44f3777213b Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Mon, 14 Sep 2026 13:45:35 +0100 Subject: [PATCH 12/14] only decorate x86 symbols on `raw-dylib` builds --- pyo3-ffi/src/impl_/macros.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyo3-ffi/src/impl_/macros.rs b/pyo3-ffi/src/impl_/macros.rs index ad70330ae4e..7a0c0b1b2c7 100644 --- a/pyo3-ffi/src/impl_/macros.rs +++ b/pyo3-ffi/src/impl_/macros.rs @@ -15,7 +15,7 @@ macro_rules! extern_libpython_cpython_private_fn { ($(#[$attrs:meta])* $vis:vis $name:ident($($args:tt)*) $(-> $ret:ty)?) => { #[cfg_attr( - all(windows, target_arch = "x86", not(any(PyPy, GraalPy))), + all(windows, pyo3_use_raw_dylib, target_arch = "x86"), link_name = concat!("_", stringify!($name)) )] $(#[$attrs])* From d153d628ab4feb4e1f4df74016379e9d73d9d45a Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Wed, 16 Sep 2026 08:35:33 +0100 Subject: [PATCH 13/14] Update link name for PyVectorcall_Call in abstract_.rs --- pyo3-ffi/src/abstract_.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index d335cc487a5..01df2cd0b95 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -72,10 +72,10 @@ extern_libpython! { ) -> *mut PyObject; #[cfg(all(Py_3_12, Py_LIMITED_API))] // is an inline function in cpython/abstract.rs on version-specific ABI - #[cfg_attr(PyPy, link_name = "PyPyVectorcall_NARGS")] pub fn PyVectorcall_NARGS(nargsf: size_t) -> Py_ssize_t; #[cfg(any(Py_3_12, not(Py_LIMITED_API)))] + #[cfg_attr(all(PyPy, not(Py_3_12)), link_name = "PyPyVectorcall_Call")] pub fn PyVectorcall_Call( callable: *mut PyObject, tuple: *mut PyObject, From 7e50cbc056eb0777cbc646fbf71afc407c08fcb9 Mon Sep 17 00:00:00 2001 From: David Hewitt Date: Wed, 16 Sep 2026 08:57:35 +0100 Subject: [PATCH 14/14] fmt --- pyo3-ffi/src/abstract_.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pyo3-ffi/src/abstract_.rs b/pyo3-ffi/src/abstract_.rs index 01df2cd0b95..c99c2cba1cf 100644 --- a/pyo3-ffi/src/abstract_.rs +++ b/pyo3-ffi/src/abstract_.rs @@ -71,7 +71,8 @@ extern_libpython! { ... ) -> *mut PyObject; - #[cfg(all(Py_3_12, Py_LIMITED_API))] // is an inline function in cpython/abstract.rs on version-specific ABI + #[cfg(all(Py_3_12, Py_LIMITED_API))] + // is an inline function in cpython/abstract.rs on version-specific ABI pub fn PyVectorcall_NARGS(nargsf: size_t) -> Py_ssize_t; #[cfg(any(Py_3_12, not(Py_LIMITED_API)))]