From 60a1ffeb8fbbb217cbf3a444f1653c3fd8bb71ac Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Mon, 23 Mar 2026 22:52:18 +0200 Subject: [PATCH 01/13] try to fix sanitizers; first step --- Modules/cpython-sys/build.rs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index a97c1413914a02..609fa21c8af4c9 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -63,6 +63,10 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // Suppress all clang warnings (deprecation warnings, etc.) builder = builder.clang_arg("-w"); + // Use C11 with GNU extensions so that is available, + // required by the mimalloc headers. + builder = builder.clang_arg("-std=gnu11"); + // Tell clang the correct target triple for cross-compilation when we have // an LLVM-specific triple. Otherwise let bindgen translate Cargo's TARGET // itself (e.g. aarch64-apple-ios-sim -> arm64-apple-ios-simulator). From 5e10f6a9e3a15073ea654a57ce1cbe2cb0f7ce6c Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Mon, 23 Mar 2026 23:06:54 +0200 Subject: [PATCH 02/13] stop forwarding this thing --- Modules/cpython-sys/build.rs | 1 - 1 file changed, 1 deletion(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 609fa21c8af4c9..47503da4c7d166 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -101,7 +101,6 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat } } else if flag.starts_with("-I") || flag.starts_with("-D") - || flag.starts_with("-std=") || flag.starts_with("-isystem") { builder = builder.clang_arg(flag); From 09f41e8b7d114860d78dd9137ac59dc1291b6b1c Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Mon, 23 Mar 2026 23:39:45 +0200 Subject: [PATCH 03/13] what if... --- Modules/cpython-sys/build.rs | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 47503da4c7d166..5d9cc2e918ac90 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -63,10 +63,6 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // Suppress all clang warnings (deprecation warnings, etc.) builder = builder.clang_arg("-w"); - // Use C11 with GNU extensions so that is available, - // required by the mimalloc headers. - builder = builder.clang_arg("-std=gnu11"); - // Tell clang the correct target triple for cross-compilation when we have // an LLVM-specific triple. Otherwise let bindgen translate Cargo's TARGET // itself (e.g. aarch64-apple-ios-sim -> arm64-apple-ios-simulator). @@ -155,6 +151,11 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat } builder = add_target_clang_args(builder, builddir); + // Use C11 with GNU extensions so that is available, + // required by the mimalloc headers. This must be the last clang arg + // to ensure it is not overridden by any earlier -std= flag. + builder = builder.clang_arg("-std=gnu11"); + let bindings = builder .allowlist_function("_?Py.*") .allowlist_type("_?Py.*") From 7f2a04a6ac181ef436c1a471b3b41f1574962d9d Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Mon, 23 Mar 2026 23:51:57 +0200 Subject: [PATCH 04/13] Okay. --- Modules/cpython-sys/build.rs | 6 +----- Modules/cpython-sys/wrapper.h | 5 +++++ 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 5d9cc2e918ac90..a97c1413914a02 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -97,6 +97,7 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat } } else if flag.starts_with("-I") || flag.starts_with("-D") + || flag.starts_with("-std=") || flag.starts_with("-isystem") { builder = builder.clang_arg(flag); @@ -151,11 +152,6 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat } builder = add_target_clang_args(builder, builddir); - // Use C11 with GNU extensions so that is available, - // required by the mimalloc headers. This must be the last clang arg - // to ensure it is not overridden by any earlier -std= flag. - builder = builder.clang_arg("-std=gnu11"); - let bindings = builder .allowlist_function("_?Py.*") .allowlist_type("_?Py.*") diff --git a/Modules/cpython-sys/wrapper.h b/Modules/cpython-sys/wrapper.h index f79a44f0580633..fab678da50d928 100644 --- a/Modules/cpython-sys/wrapper.h +++ b/Modules/cpython-sys/wrapper.h @@ -32,6 +32,11 @@ #define Py_BUILD_CORE // Internal +// Ensure C11 atomics are available for mimalloc headers. +// Clang supports in all C modes via __has_extension(c_atomic). +#if !defined(__cplusplus) +#include +#endif #include "internal/pycore_parser.h" #include "internal/pycore_mimalloc.h" #include "internal/mimalloc/mimalloc.h" From bb7b9bb2a6cf256ed52be0b189a8d09df2636b5b Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 01:05:30 +0200 Subject: [PATCH 05/13] hm --- .github/workflows/reusable-san.yml | 2 ++ Modules/cpython-sys/wrapper.h | 5 ----- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/.github/workflows/reusable-san.yml b/.github/workflows/reusable-san.yml index 7fe96d1b238b04..d8e837f81591a2 100644 --- a/.github/workflows/reusable-san.yml +++ b/.github/workflows/reusable-san.yml @@ -52,6 +52,8 @@ jobs: else sudo ./llvm.sh 20 fi + env: + SANITIZER: ${{ inputs.sanitizer }} - name: Sanitizer option setup run: | diff --git a/Modules/cpython-sys/wrapper.h b/Modules/cpython-sys/wrapper.h index fab678da50d928..f79a44f0580633 100644 --- a/Modules/cpython-sys/wrapper.h +++ b/Modules/cpython-sys/wrapper.h @@ -32,11 +32,6 @@ #define Py_BUILD_CORE // Internal -// Ensure C11 atomics are available for mimalloc headers. -// Clang supports in all C modes via __has_extension(c_atomic). -#if !defined(__cplusplus) -#include -#endif #include "internal/pycore_parser.h" #include "internal/pycore_mimalloc.h" #include "internal/mimalloc/mimalloc.h" From ebf7866a59d23bdaa32ec9a8831e11abe3dc49bd Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 17:41:42 +0200 Subject: [PATCH 06/13] Okay. --- .github/workflows/reusable-san.yml | 2 - .../cpython-sys/bindgen-fallback/stdatomic.h | 44 +++++++++++++++++++ Modules/cpython-sys/build.rs | 8 ++++ 3 files changed, 52 insertions(+), 2 deletions(-) create mode 100644 Modules/cpython-sys/bindgen-fallback/stdatomic.h diff --git a/.github/workflows/reusable-san.yml b/.github/workflows/reusable-san.yml index d8e837f81591a2..7fe96d1b238b04 100644 --- a/.github/workflows/reusable-san.yml +++ b/.github/workflows/reusable-san.yml @@ -52,8 +52,6 @@ jobs: else sudo ./llvm.sh 20 fi - env: - SANITIZER: ${{ inputs.sanitizer }} - name: Sanitizer option setup run: | diff --git a/Modules/cpython-sys/bindgen-fallback/stdatomic.h b/Modules/cpython-sys/bindgen-fallback/stdatomic.h new file mode 100644 index 00000000000000..8e14df84aae997 --- /dev/null +++ b/Modules/cpython-sys/bindgen-fallback/stdatomic.h @@ -0,0 +1,44 @@ +/* + * Fallback for bindgen. + * + * Some libclang builds ship a that silently provides no + * declarations. This makes any header that relies on C11 atomics + * (e.g. mimalloc) unparseable by bindgen. + * + * This file provides the standard C11 atomics API with non-atomic stubs. + * Bindgen only needs correct type layouts -- it never executes atomic + * operations -- so plain loads/stores are sufficient. + * + * The build script adds this directory via -isystem so it shadows a + * broken system header while remaining invisible when the real header + * works (libclang picks whichever it finds first on the include path). + */ +#ifndef _STDATOMIC_BINDGEN_FALLBACK_H +#define _STDATOMIC_BINDGEN_FALLBACK_H + +/* Strip _Atomic qualifier -- bindgen cares about layout, not atomicity. */ +#define _Atomic(tp) tp + +typedef enum { + memory_order_relaxed, + memory_order_consume, + memory_order_acquire, + memory_order_release, + memory_order_acq_rel, + memory_order_seq_cst +} memory_order; + +#define ATOMIC_VAR_INIT(value) (value) + +#define atomic_load_explicit(p, mo) (*(p)) +#define atomic_store_explicit(p, v, mo) ((void)(*(p) = (v))) +#define atomic_fetch_add_explicit(p, v, mo) (*(p)) +#define atomic_fetch_sub_explicit(p, v, mo) (*(p)) +#define atomic_fetch_or_explicit(p, v, mo) (*(p)) +#define atomic_fetch_and_explicit(p, v, mo) (*(p)) +#define atomic_compare_exchange_weak_explicit(p, e, d, s, f) 1 +#define atomic_compare_exchange_strong_explicit(p, e, d, s, f) 1 +#define atomic_exchange_explicit(p, v, mo) (*(p)) +#define atomic_thread_fence(mo) ((void)0) + +#endif /* _STDATOMIC_BINDGEN_FALLBACK_H */ diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index a97c1413914a02..dd2c4b72d00fe7 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -150,6 +150,14 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat for dir in include_dirs { builder = builder.clang_arg(format!("-I{}", dir.display())); } + + // Provide a fallback for libclang versions that ship a + // broken one (e.g. libclang-18 on Ubuntu 24.04). Using -isystem places + // it after -I paths but before the default system headers, so it only + // takes effect when the real is unusable. + let fallback_dir = manifest_dir.join("bindgen-fallback"); + builder = builder.clang_arg(format!("-isystem{}", fallback_dir.display())); + builder = add_target_clang_args(builder, builddir); let bindings = builder From 78f238912d4cda56c4888a471560f8372fdaa434 Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 17:45:15 +0200 Subject: [PATCH 07/13] what a silly typo --- Modules/cpython-sys/build.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index dd2c4b72d00fe7..a095b48a61368a 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -155,7 +155,8 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // broken one (e.g. libclang-18 on Ubuntu 24.04). Using -isystem places // it after -I paths but before the default system headers, so it only // takes effect when the real is unusable. - let fallback_dir = manifest_dir.join("bindgen-fallback"); + let fallback_dir = PathBuf::from(env::var("CARGO_MANIFEST_DIR").unwrap()) + .join("bindgen-fallback"); builder = builder.clang_arg(format!("-isystem{}", fallback_dir.display())); builder = add_target_clang_args(builder, builddir); From 8979e99eb4e1166e08d879deb5db9d34d55f104b Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 17:48:18 +0200 Subject: [PATCH 08/13] cargo fmt --- Modules/cpython-sys/build.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index a095b48a61368a..4a6106911d0e93 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -155,8 +155,8 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // broken one (e.g. libclang-18 on Ubuntu 24.04). Using -isystem places // it after -I paths but before the default system headers, so it only // takes effect when the real is unusable. - let fallback_dir = PathBuf::from(env::var("CARGO_MANIFEST_DIR").unwrap()) - .join("bindgen-fallback"); + let fallback_dir = + PathBuf::from(env::var("CARGO_MANIFEST_DIR").unwrap()).join("bindgen-fallback"); builder = builder.clang_arg(format!("-isystem{}", fallback_dir.display())); builder = add_target_clang_args(builder, builddir); From 712caea0d9748f3d75ea7077e7ba2977f0956858 Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 18:04:14 +0200 Subject: [PATCH 09/13] Prefer a newer libclang if available... --- .../cpython-sys/bindgen-fallback/stdatomic.h | 44 ------------------- Modules/cpython-sys/build.rs | 42 ++++++++++++++---- 2 files changed, 34 insertions(+), 52 deletions(-) delete mode 100644 Modules/cpython-sys/bindgen-fallback/stdatomic.h diff --git a/Modules/cpython-sys/bindgen-fallback/stdatomic.h b/Modules/cpython-sys/bindgen-fallback/stdatomic.h deleted file mode 100644 index 8e14df84aae997..00000000000000 --- a/Modules/cpython-sys/bindgen-fallback/stdatomic.h +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Fallback for bindgen. - * - * Some libclang builds ship a that silently provides no - * declarations. This makes any header that relies on C11 atomics - * (e.g. mimalloc) unparseable by bindgen. - * - * This file provides the standard C11 atomics API with non-atomic stubs. - * Bindgen only needs correct type layouts -- it never executes atomic - * operations -- so plain loads/stores are sufficient. - * - * The build script adds this directory via -isystem so it shadows a - * broken system header while remaining invisible when the real header - * works (libclang picks whichever it finds first on the include path). - */ -#ifndef _STDATOMIC_BINDGEN_FALLBACK_H -#define _STDATOMIC_BINDGEN_FALLBACK_H - -/* Strip _Atomic qualifier -- bindgen cares about layout, not atomicity. */ -#define _Atomic(tp) tp - -typedef enum { - memory_order_relaxed, - memory_order_consume, - memory_order_acquire, - memory_order_release, - memory_order_acq_rel, - memory_order_seq_cst -} memory_order; - -#define ATOMIC_VAR_INIT(value) (value) - -#define atomic_load_explicit(p, mo) (*(p)) -#define atomic_store_explicit(p, v, mo) ((void)(*(p) = (v))) -#define atomic_fetch_add_explicit(p, v, mo) (*(p)) -#define atomic_fetch_sub_explicit(p, v, mo) (*(p)) -#define atomic_fetch_or_explicit(p, v, mo) (*(p)) -#define atomic_fetch_and_explicit(p, v, mo) (*(p)) -#define atomic_compare_exchange_weak_explicit(p, e, d, s, f) 1 -#define atomic_compare_exchange_strong_explicit(p, e, d, s, f) 1 -#define atomic_exchange_explicit(p, v, mo) (*(p)) -#define atomic_thread_fence(mo) ((void)0) - -#endif /* _STDATOMIC_BINDGEN_FALLBACK_H */ diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 4a6106911d0e93..c8e90a6ccb6f95 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -10,6 +10,7 @@ fn main() { let out_path = PathBuf::from(env::var("OUT_DIR").unwrap()); let builddir = env::var("PYTHON_BUILD_DIR").ok(); emit_rerun_instructions(builddir.as_deref()); + prefer_newest_libclang(); if gil_disabled(srcdir, builddir.as_deref()) { println!("cargo:rustc-cfg=py_gil_disabled"); } @@ -40,6 +41,39 @@ fn emit_rerun_instructions(builddir: Option<&str>) { } } +/// When LIBCLANG_PATH is not already set, scan /usr/lib/llvm-*/lib for the +/// newest available libclang and point bindgen at it. Ubuntu 24.04 ships +/// libclang-18 by default, which has broken headers (stdatomic.h, mmintrin.h). +/// CI jobs that install a newer LLVM (e.g. clang-20) also get a working +/// libclang in /usr/lib/llvm-20/lib -- we just need to tell bindgen about it. +fn prefer_newest_libclang() { + if env::var_os("LIBCLANG_PATH").is_some() { + return; + } + let base = Path::new("/usr/lib"); + let mut best: Option<(u32, PathBuf)> = None; + if let Ok(entries) = std::fs::read_dir(base) { + for entry in entries.flatten() { + let name = entry.file_name(); + let name = name.to_string_lossy(); + if let Some(ver_str) = name.strip_prefix("llvm-") { + if let Ok(ver) = ver_str.parse::() { + let lib_dir = entry.path().join("lib"); + if lib_dir.is_dir() { + if best.as_ref().map_or(true, |(v, _)| ver > *v) { + best = Some((ver, lib_dir)); + } + } + } + } + } + } + if let Some((ver, lib_dir)) = best { + eprintln!("cpython-sys: using libclang from llvm-{ver}"); + env::set_var("LIBCLANG_PATH", &lib_dir); + } +} + fn gil_disabled(srcdir: &Path, builddir: Option<&str>) -> bool { let mut candidates = Vec::new(); if let Some(build) = builddir { @@ -151,14 +185,6 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat builder = builder.clang_arg(format!("-I{}", dir.display())); } - // Provide a fallback for libclang versions that ship a - // broken one (e.g. libclang-18 on Ubuntu 24.04). Using -isystem places - // it after -I paths but before the default system headers, so it only - // takes effect when the real is unusable. - let fallback_dir = - PathBuf::from(env::var("CARGO_MANIFEST_DIR").unwrap()).join("bindgen-fallback"); - builder = builder.clang_arg(format!("-isystem{}", fallback_dir.display())); - builder = add_target_clang_args(builder, builddir); let bindings = builder From bc026f5919f1b81ed3143b1e93e2e1341b6c9828 Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 18:11:10 +0200 Subject: [PATCH 10/13] add safety comment --- Modules/cpython-sys/build.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index c8e90a6ccb6f95..56170e9d92879d 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -70,7 +70,8 @@ fn prefer_newest_libclang() { } if let Some((ver, lib_dir)) = best { eprintln!("cpython-sys: using libclang from llvm-{ver}"); - env::set_var("LIBCLANG_PATH", &lib_dir); + // SAFETY: build scripts are single-threaded. + unsafe { env::set_var("LIBCLANG_PATH", &lib_dir) }; } } From af4a15e9e03312c48a2ba2005d2f68a9044d5b38 Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 18:58:20 +0200 Subject: [PATCH 11/13] use another way --- Modules/cpython-sys/build.rs | 61 +++++++++++++++++++----------------- 1 file changed, 33 insertions(+), 28 deletions(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 56170e9d92879d..0da3a248b34a77 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -10,7 +10,6 @@ fn main() { let out_path = PathBuf::from(env::var("OUT_DIR").unwrap()); let builddir = env::var("PYTHON_BUILD_DIR").ok(); emit_rerun_instructions(builddir.as_deref()); - prefer_newest_libclang(); if gil_disabled(srcdir, builddir.as_deref()) { println!("cargo:rustc-cfg=py_gil_disabled"); } @@ -41,38 +40,32 @@ fn emit_rerun_instructions(builddir: Option<&str>) { } } -/// When LIBCLANG_PATH is not already set, scan /usr/lib/llvm-*/lib for the -/// newest available libclang and point bindgen at it. Ubuntu 24.04 ships -/// libclang-18 by default, which has broken headers (stdatomic.h, mmintrin.h). -/// CI jobs that install a newer LLVM (e.g. clang-20) also get a working -/// libclang in /usr/lib/llvm-20/lib -- we just need to tell bindgen about it. -fn prefer_newest_libclang() { - if env::var_os("LIBCLANG_PATH").is_some() { - return; - } +/// Find the newest clang resource directory on the system. +/// +/// Ubuntu 24.04 ships libclang-18 whose built-in headers (stdatomic.h, +/// mmintrin.h) are broken. CI jobs install a newer clang (e.g. clang-20) +/// whose resource directory at /usr/lib/llvm-20/lib/clang/20 has working +/// headers. We pass -resource-dir to bindgen's clang so it picks up those +/// headers instead of the broken libclang-18 ones. +fn newest_clang_resource_dir() -> Option { let base = Path::new("/usr/lib"); let mut best: Option<(u32, PathBuf)> = None; - if let Ok(entries) = std::fs::read_dir(base) { - for entry in entries.flatten() { - let name = entry.file_name(); - let name = name.to_string_lossy(); - if let Some(ver_str) = name.strip_prefix("llvm-") { - if let Ok(ver) = ver_str.parse::() { - let lib_dir = entry.path().join("lib"); - if lib_dir.is_dir() { - if best.as_ref().map_or(true, |(v, _)| ver > *v) { - best = Some((ver, lib_dir)); - } - } - } + for entry in std::fs::read_dir(base).ok()?.flatten() { + let name = entry.file_name(); + let name = name.to_string_lossy(); + if let Some(ver_str) = name.strip_prefix("llvm-") + && let Ok(ver) = ver_str.parse::() + { + // Resource dir: /usr/lib/llvm-/lib/clang/ + let resource_dir = entry.path().join("lib").join("clang").join(ver_str); + if resource_dir.join("include").is_dir() + && best.as_ref().map_or(true, |(v, _)| ver > *v) + { + best = Some((ver, resource_dir)); } } } - if let Some((ver, lib_dir)) = best { - eprintln!("cpython-sys: using libclang from llvm-{ver}"); - // SAFETY: build scripts are single-threaded. - unsafe { env::set_var("LIBCLANG_PATH", &lib_dir) }; - } + best.map(|(_, p)| p) } fn gil_disabled(srcdir: &Path, builddir: Option<&str>) -> bool { @@ -98,6 +91,18 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // Suppress all clang warnings (deprecation warnings, etc.) builder = builder.clang_arg("-w"); + // Use the newest clang resource directory available on the system. + // Bindgen links against whatever libclang it finds (often an older + // system version), but the built-in headers in that version may be + // broken (e.g. libclang-18 on Ubuntu 24.04 has broken stdatomic.h + // and mmintrin.h). Overriding -resource-dir makes clang use a + // newer set of built-in headers without changing which libclang.so + // is loaded. + if let Some(resource_dir) = newest_clang_resource_dir() { + eprintln!("cpython-sys: using clang resource dir {}", resource_dir.display()); + builder = builder.clang_arg(format!("-resource-dir={}", resource_dir.display())); + } + // Tell clang the correct target triple for cross-compilation when we have // an LLVM-specific triple. Otherwise let bindgen translate Cargo's TARGET // itself (e.g. aarch64-apple-ios-sim -> arm64-apple-ios-simulator). From 5d7a44fdc73ad5ee989d225f7a12b610e525188d Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 19:04:51 +0200 Subject: [PATCH 12/13] again cargo fmt!!! --- Modules/cpython-sys/build.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Modules/cpython-sys/build.rs b/Modules/cpython-sys/build.rs index 0da3a248b34a77..08508ad4cf0f4f 100644 --- a/Modules/cpython-sys/build.rs +++ b/Modules/cpython-sys/build.rs @@ -99,7 +99,10 @@ fn generate_c_api_bindings(srcdir: &Path, builddir: Option<&str>, out_path: &Pat // newer set of built-in headers without changing which libclang.so // is loaded. if let Some(resource_dir) = newest_clang_resource_dir() { - eprintln!("cpython-sys: using clang resource dir {}", resource_dir.display()); + eprintln!( + "cpython-sys: using clang resource dir {}", + resource_dir.display() + ); builder = builder.clang_arg(format!("-resource-dir={}", resource_dir.display())); } From a10fb22dbb04affce0de3a57046e256a08f64327 Mon Sep 17 00:00:00 2001 From: Kirill Podoprigora Date: Tue, 24 Mar 2026 20:12:01 +0200 Subject: [PATCH 13/13] Port skip from upstream --- Lib/test/test_import/__init__.py | 1 + 1 file changed, 1 insertion(+) diff --git a/Lib/test/test_import/__init__.py b/Lib/test/test_import/__init__.py index fe669bb04df02a..fd9750eae80445 100644 --- a/Lib/test/test_import/__init__.py +++ b/Lib/test/test_import/__init__.py @@ -3261,6 +3261,7 @@ def test_basic_multiple_interpreters_main_no_reset(self): # * m_copy was copied from interp2 (was from interp1) # * module's global state was updated, not reset + @unittest.skip("gh-131229: This is suddenly very flaky") @no_rerun(reason="rerun not possible; module state is never cleared (see gh-102251)") @requires_subinterpreters def test_basic_multiple_interpreters_deleted_no_reset(self):