# Pre-PEP: Rust for CPython

**URL:** <https://discuss.python.org/t/pre-pep-rust-for-cpython/104906>\
**Category:** Core Development\
**Created:** [November 17, 2025, 4:14pm UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906 "2025-11-17T16:14:10Z")\
**Posts on this page:** 20\
**Page:** 4

<div class="post-metadata">

**Author:** ![rtpg](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/rtpg/32/14068_2.png) [@rtpg](https://discuss.python.org/u/rtpg)\
**Post date:** [November 18, 2025, 4:22am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/61 "2025-11-18T04:22:28Z")

</div>

> [@corona10](#):
>
> @emmatyping What I’m curious about is this: in the current PoC, [most of the code uses](https://github.com/emmatyping/cpython/blob/c9deee600d60509c5da6ef538a9b530f7ba12e05/Modules/_base64/src/lib.rs#L114-L181) `unsafe` blocks. I understand this isn’t Rust’s fault but rather a limitation of the CPython API. Still, how do these modules become memory-safe in the PoC, and how much less do we need to worry about memory safety compared to writing the same code in C? For example, if you could say something like “X% of the code in the `base64` module becomes memory-safe,” that would be a helpful metric to highlight.

To expand on this point, I see Rust as a potential usability gain here, much more than the security aspect.

I think the argument to use Rust for CPython here would be much stronger if we could see `standard_b64encode` implemented in a way that takes advantage of Rust’s RAII to reduce the book-keeping we have to do in the C code right now.

Without a “Rust API” here for writing these extensions, this becomes _purely_ a security argument (that I find fairly unconvincing at some level). If `standard_b64encode` was returning a ` Result` and we were able to use `?` and all this other stuff with a wrapper that did “the right thing” that would be, at least to me, much more interesting

EDIT: though a point against this being easy might be the memory allocation story here… though the error allocation failure paths are about allocation failures in the Python arena, not sure if that means we really have no stack left over. Still think it’s worth proving the point that this has ergonomics improvements, because that feels like a pretty big deal all things considered!

---

<div class="post-metadata">

**Author:** ![emmatyping](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/emmatyping/32/36516_2.png) [@emmatyping](https://discuss.python.org/u/emmatyping)\
**Post date:** [November 18, 2025, 4:40am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/62 "2025-11-18T04:40:03Z")

</div>

> [@rtpg](#):
>
> I think the argument to use Rust for CPython here would be much stronger if we could see `standard_b64encode` implemented in a way that takes advantage of Rust’s RAII to reduce the book-keeping we have to do in the C code right now.
> 
> Without a “Rust API” here for writing these extensions, this becomes _purely_ a security argument (that I find fairly unconvincing at some level). If `standard_b64encode` was returning a ` Result` and we were able to use `?` and all this other stuff with a wrapper that did “the right thing” that would be, at least to me, much more interesting

One example of reducing mental bookkeeping is the `BorrowedBuffer` abstraction in the implementation [cpython/Modules/\_base64/src/lib.rs at c9deee600d60509c5da6ef538a9b530f7ba12e05 · emmatyping/cpython · GitHub](https://github.com/emmatyping/cpython/blob/c9deee600d60509c5da6ef538a9b530f7ba12e05/Modules/_base64/src/lib.rs#L81-L111). As mentioned previously, the current example is pretty bare-bones as it is a proof of concept. There is a large room for improvement in ergonomics. But even with raw FFI bindings, it’s possible to have a safe, idiomatic Rust core of an extension module then expose that via unsafe wrappers. And I think even that will improve the safety and utility of writing extensions in CPython.

---

<div class="post-metadata">

**Author:** ![rtpg](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/rtpg/32/14068_2.png) [@rtpg](https://discuss.python.org/u/rtpg)\
**Post date:** [November 18, 2025, 4:56am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/63 "2025-11-18T04:56:49Z")

</div>

Yeah I think the `BorrowedBuffer` is a good example of helping a bit with its `Drop`.

I guess this would be more convincing to me (random person who has little stake in this beyond poking in CPython internals from time to time but wants to see some idea of this succeed!) if we go a bit further in the barebones interpretation to prove some idea of improved ergonomics, focused entirely on this `encode` implementation, which includes just enough bookkeeping futzing that would be nice to not see anymore:

```rust

    let result = unsafe {
        PyBytes_FromStringAndSize(ptr::null(), output_len as Py_ssize_t)
    };
    if result.is_null() {
        return ptr::null_mut();
    }

```

instead being something like:

```rust
let Ok(result) = PyBytes::from_string_and_size(ptr::null(), output_len as Py_ssize_t) else { return ptr::null_mut() } ;

```

Or even, if there’s some way to make `PyResult`-y thing that could collapse the common CPython errors nicely (maybe not a possible thing!):

`let result = PyBytes::uninit_from_size(output_len)?`

Just like `BorrowedBuffer`, it feels like there could be some single-field wrapper structs, and smart constructors that could operate in a “Rust API”-y level to work off of results

Similarly in:

```python
let dest_ptr = unsafe { PyBytes_AsString(result) };
if dest_ptr.is_null() {
    unsafe {
        Py_DecRef(result);
    }
    return ptr::null_mut();
}

```

I would have expected we could have some Rust-y wrapper on references that would give us that `Py_DecRef` call for free just through RAII. And maybe I’m too optimistic of Rust’s compiler toolchain, but if the wrapper was a single field struct, my impression is we would be able to get that for free.

The thing I would assume is that within the extension module we could go full Rust API goodness, and it’s only really at the entry and exit points that one would need to go back to acknowledging CPython’s realities a bit more.

Anyways yeah, I’m very curious what the ‘pie in the sky most of the APIs used in the encoding example have a nice API’ version of the `encode` port looks like, because jumping from C to Rust could make the maintenance barrier seem way lower. We don’t have to port everything, just enough and enough smoke and mirrors to say “this is what it looks like in practice for this one method”. Because right now beyond the platform support tradeoffs etc, the PoC example is also presenting as generally more code, not less. In my mind’s eye we wouldn’t even have a tradeoff here, and the code _would_ be simpler.

---

<div class="post-metadata">

**Author:** ![emmatyping](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/emmatyping/32/36516_2.png) [@emmatyping](https://discuss.python.org/u/emmatyping)\
**Post date:** [November 18, 2025, 5:05am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/64 "2025-11-18T05:05:28Z")

</div>

Interactions between Python objects and borrows is rather complicated. I don’t think this thread is a great place to go over detailed API design discussion as that isn’t the goal of the PEP, but I’d be happy to chat in another forum like the Python Discord or via DM. I will say a pie-in-the-sky API will look somewhat like an implementation using [PyO3](https://pyo3.rs/). I can write up such an implementation and share that if people think it would informative.

---

<div class="post-metadata">

**Author:** ![CEXT-Dan](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/cext-dan/32/18897_2.png) [@CEXT-Dan](https://discuss.python.org/u/CEXT-Dan)\
**Post date:** [November 18, 2025, 5:09am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/65 "2025-11-18T05:09:12Z")

</div>

` but eventually will become a required dependency of CPython`

What does this mean for projects that embed CPython inside their C++ projects? Boost::python or pybind11?

---

<div class="post-metadata">

**Author:** ![emmatyping](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/emmatyping/32/36516_2.png) [@emmatyping](https://discuss.python.org/u/emmatyping)\
**Post date:** [November 18, 2025, 5:18am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/66 "2025-11-18T05:18:14Z")

</div>

You would need Rust to build any Rust extension modules you want in your embedded Python. I believe most embedding links to libpython so that would already be built and wouldn’t require Rust.

---

<div class="post-metadata">

**Author:** ![CEXT-Dan](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/cext-dan/32/18897_2.png) [@CEXT-Dan](https://discuss.python.org/u/CEXT-Dan)\
**Post date:** [November 18, 2025, 5:26am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/67 "2025-11-18T05:26:57Z")

</div>

> [@emmatyping](#):
>
> You would need Rust to build any Rust extension modules you

Thank you, I know nothing of Rust, I see the word ‘dependency’ and I immediately get scared. Python and all the 3rd party modules must load into the host application’s process. In my case, I’m running Python inside AutoCAD for windows. If this is optional, or something that’s not going load some sort of runtime, or something that could cause issues, then great

---

<div class="post-metadata">

**Author:** ![monk-time](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/monk-time/32/516_2.png) [@monk-time](https://discuss.python.org/u/monk-time)\
**Post date:** [November 18, 2025, 5:40am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/68 "2025-11-18T05:40:40Z")

</div>

> [@merwok](#):
>
> Can you expand on this with some specific examples? I can only interpret this as a suggestion that Python releases would include uv and ruff, and it doesn’t make much sense to me.

We do already ship with pip and pymanager, and there’s no denying that Rust/Go have created an expectation for modern languages to include quality standard dev tooling. And it is equally apparent that the best Python tooling for the next decade will be written in Rust\[1\]. So I don’t see a future where Python also ships with such tools as outside the realm of possibility\[2\].

So I don’t see why not. This is clearly out of scope for this proposal, which is why I framed it only as a future possibility – one that would require its own difficult discussion and the platform/build support this PEP addresses. So I won’t pursue this further here.

* * *

1. regardless of if it’s still Astral tools like uv and ruff (or ty when it reaches stable) or something else like pyrefly 

2. I do believe replacing pip with uv might just be the most widely applauded move Python can make

---

<div class="post-metadata">

**Author:** ![youknowone](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/youknowone/32/19382_2.png) [@youknowone](https://discuss.python.org/u/youknowone)\
**Post date:** [November 18, 2025, 7:32am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/69 "2025-11-18T07:32:25Z")

</div>

To achieve good ergonomics, we’ll need not only `cpython-sys` but also another crate built on top of it that provides proper Rust abstractions. (Following naming conventions, it would be called `cpython`, but that name is already taken.)

Right now, the PEP only covers `cpython-sys`, but if we expect Rust ergonomics by this PEP, I think some consideration of this additional crate should also be included.

---

<div class="post-metadata">

**Author:** ![mgorny](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/mgorny/32/34029_2.png) [@mgorny](https://discuss.python.org/u/mgorny)\
**Post date:** [November 18, 2025, 7:39am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/70 "2025-11-18T07:39:20Z")

</div>

This would be unfortunate for Gentoo. We’re currently one of the few Linux distributions that aim to provide a reasonable working experience for people with older, weaker or more niche hardware that is not supported by Rust; and given that we’re largely talking about volunteers with no corporate backing, there is practically zero chance of ever porting LLVM and Rust to the relevant platforms, let alone providing long-term maintenance needed for keeping them working in projects with such a high rate of code churn.

I do realize that these platforms are not “supported” by CPython right now. Nevertheless, even though there historically were efforts to block building on them, they currently work and require comparatively little maintenance effort to keep them working. Admittedly, the wider Python ecosystem with its Rust adoption puts quite a strain on us and the user experience worsens every few months, we still manage to provide a working setup.

The moment CPython starts requiring Rust, this will no longer be possible. Of course, we will still be able to provide older versions of CPython for a few years, at least until some major package starts requiring the newer Python version.

That said, I do realize that we’re basically obsolete and it’s just a matter of time until some projects pulls the switch and force us to tell our users “sorry, we are no longer able to provide a working system for you”.

I don’t expect to change anything here. Just wanted to share the other perspective.

---

<div class="post-metadata">

**Author:** ![ssokolow](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/ssokolow/32/32572_2.png) [@ssokolow](https://discuss.python.org/u/ssokolow)\
**Post date:** [November 18, 2025, 8:27am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/71 "2025-11-18T08:27:56Z")

</div>

I hope nobody will mind if my first post as a complete newcomer to the forum (though very far from one with Python or Rust) is letting my designed-to-win-trivia-games brain provide some context, clarifications, etc. for various things across the thread as a whole.

Also, sorry for splitting this across multiple posts but, even after pessimizing all my citations to “Search for …” annotations, it was still claiming I had more than two links in it. (If this posts, then I guess it meant two reply-to-post embeds.)

> [@Pre-PEP: Rust for CPython](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/4):
>
> I’m not a core dev nor expert in the internals of CPython, but I wanted to chime in to resonate with the question from @MegaIng , pointing out though that it looks to me (as a Python user) that the community in general is more “approachable” in comparison to what happened during the integration of some Rust in the Linux kernel. Out of curiosity, what would this mean for both PyO3 and [RustPython](https://github.com/RustPython/RustPython)? Have you reached out to the mantainers of the latter for feedback on how to approach this possibilit…

> Finally, if I recall rust applications tend to be a bit “bloated” in binary size, although there are some tricks that can be done at compile time to reduce this - what do these tricks imply on performance I have no idea.

The answer depends on how long ago you remember that from. Rust’s history has been a tale of improving defaults on this front and I don’t know where you draw the line on “bloated”.

For example, prior to Rust 1.28 (Search for `“Announcing Rust 1.28” site:blog.rust-lang.org`), some platforms embedded a copy of jemalloc but it now defaults to the system allocator.

Rust still statically links its standard library, which is distributed as a precompiled “release + debug symbols” artifact to be shared between release and debug profiles and, for much of its life, there was no integrated support for stripping the resulting binaries. According to the Profiles (Search for `“The Cargo Book” “Profiles” site:doc.rust-lang.org`) section of The Cargo Book, `strip = "none"` is still the default setting for the release profile.

If I do a simple `cargo new` and then `cargo build --release` the resulting “Hello, World!”, the binary is 463K, which drops to 354K if the debuginfo is stripped.

That remaining size includes things like a statically linked copy of libunwind which wouldn’t be needed if using abort on panic as mentioned by Emma Smith… but I’m not up to speed on how much of that will get stripped out without rebuilding the standard library to ensure _it_ isn’t depending on them.

(See my later mention of how the Rust team are currently prioritizing stabilizing `-Zbuild-std` as part of letting “remove kernelspace Rust’s dependency on nightly features” shape much of the 2025 roadmap.)

Beyond that, one potentially relevant piece of tooling is dragonfire (`amyspark/dragonfire` on the FreeDesktop Gitlab) as introduced in Linking and shrinking Rust static libraries: a tale of fire. (Search for `“Linking and shrinking Rust static libraries: a tale of fire” site:centricular.com`) (Which is concerned with deduplicating the standard library when building Rust-based plugins as static libraries.)

> [@Pre-PEP: Rust for CPython](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/9):
>
> Doesn’t “C“ in the name of “CPython“ means “C programming language”? If so, shouldn’t the project be eventually renamed when a significant part of it is (re)written in Rust? /joke, but who knows

Just declare “CPython” to be referring to the stable ABI exposed rather than the implementation language.

After all, the `abi_stable` crate for dynamically linking higher-level Rust constructs does it by marshalling through the C ABI.

---

<div class="post-metadata">

**Author:** ![ssokolow](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/ssokolow/32/32572_2.png) [@ssokolow](https://discuss.python.org/u/ssokolow)\
**Post date:** [November 18, 2025, 8:28am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/72 "2025-11-18T08:28:34Z")

</div>

> [@Pre-PEP: Rust for CPython](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/16):
>
> I have long liked the idea of doing something like this, and as someone who always introduces memory leaks and segfaults and such any time he writes any kind of C extension code, I welcome the idea of more modern zero-cost abstractions for that[[1]](#footnote-277497-1). However, one cost I think that has not been mentioned here is the effect that this could have on build times. In my experience, compile times for Rust (and C++) are much slower than for C. On my 2019 Thinkpad T480, from a fresh clone of CPython, I ca…

> I guess the question is a dual one: can we write Rust in a way that it will not cause build times to explode and if we cannot, is the plan to keep the scope of Rust in CPython to a level where building is still very accessible?

I don’t see why it needs to be slow.

As laid out in The Rust compiler isn’t slow; we are. (Search for `"The Rust compiler isn't slow; we are." site:blog.kodewerx.org`), `rustc` is already faster than compiling C++ with GCC and the reason builds are slow has more to do with how much the Rust ecosystem enjoys the creature comforts of macros and monomorphized generics.

> [@Pre-PEP: Rust for CPython](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/18):
>
> In my experience incremental Rust builds are also very fast–the initial setup (including downloading and building all the dependencies) can be slow, but it’s able to do fast incremental builds just fine. Also, there’s a big difference between debug and release mode–building in debug mode is way faster. I would be surprised if this impacted iteration time unless you’re trying to rebuild the world every time.

…and they’re working on making it faster still. Aside from “Relink, Don’t Rebuild”, as mentioned by Jubilee, there are two bottlenecks which disproportionately affect incremental rebuilds right now:

First, while there’s parallelism between crates and in the LLVM backend, the `rustc` frontend is single-threaded. Work is in progress and testable in nightly (Search for `“Faster compilation with the parallel front-end in nightly” site:blog.rust-lang.org`) for making the frontend multithreaded.

They’re also working on rustc\_codegen\_cranelift (`rust-lang/rustc_codegen_cranelift` on GitHub) which is a non-LLVM backend for rustc which makes more Go-like trade-offs for compile-time vs. runtime performance and is intended to eventually become the default for the debug profile.

Second, linking. They’ve been rolling out LLD as a faster default linker on a platform-by-platform basis and it came to Linux in 1.90. (Search for `“Announcing Rust 1.90.0” site:blog.rust-lang.org`)

Beyond that, `mold` is faster still (it’s what I use on my system) and wild (`davidlattimore/wild` on GitHub), yet faster, is being developed with an eye toward becoming default for debug builds alongside rustc\_codegen\_cranelift. (i.e. Doesn’t cover all the needs of a _fully_ general-purpose linker, but does make debug builds for the majority of them very quick.)

---

<div class="post-metadata">

**Author:** ![ssokolow](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/ssokolow/32/32572_2.png) [@ssokolow](https://discuss.python.org/u/ssokolow)\
**Post date:** [November 18, 2025, 8:29am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/73 "2025-11-18T08:29:38Z")

</div>

> I claim that one of the major reasons for this failure is that cargo is almost unique among build systems in providing absolutely no structured mechanisms for:  
> (1) communicating with other package build scripts in the same dependency graph  
> (2) communicating with the downstream user who invokes cargo (such as a distro packager, or a github actions pipeline)

This is a known problem that’s been discussed more or less since v1.0 came out in 2015 but more pressing issues keep jumping ahead of it in the queue.

(eg. The 2025H2 roadmap is prioritizing stabilizing an MVP of `-Zbuild-std` so that embedded and low-level projects like Rust for Linux (i.e. kernelspace Rust) don’t need to use either a nightly compiler or the secret switch to use API-unstable features on stable channel.)

If you want to search up existing discussions, what was done to incorporate Rust builds into Bazel got mentioned a lot.

> [@Pre-PEP: Rust for CPython](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/30):
>
> Nothing in particular. PEP 11’s requirements for each tier’s support are broad enough (language-agnostic enough) that it’s very possible that no changes are required, but I did raise my eyebrows at the intersection with Rust’s own support tiers.

It should be noted that, if I understand `“GCC Testing Efforts” site:gnu.org` correctly, GCC’s support for all platforms would count as “Tier 3, at varying degrees of stubbornness” by Rust testing standards since I don’t see any mention of any of the “Current efforts” entries being integrated to the same “CI on every push and will block merging into `main` if it fails” degree.

Rust’s approach to Tiers 1 and 2 leans in the direction of “We don’t trust our testing to be sufficient for Continuous Deployment, but we’ll do it as diligently as if we were pushing directly to stable channel”.

**EDIT:** …and, apparently, there’s also a limit on number of posts for new users so I can’t get it all in without breaking the rule about no substantial edits. I’ll drop an in-reply-to-embed and add a [GitHub Gist](https://gist.github.com/ssokolow/2850af89926fd5843ed829a16693e930) containing the source for the entire thing as it was before I started making any changes to try to crunch it in.

In total, the posts being replied to, as represented in the auto-updating Discourse permalink URLs, are 4, 9/12, 15, 16, 18, 19, 30, and 38, and a few I forgot to grab URLs for while blockquoting, and the bits which don’t fit include an answer to the concern about Trusting Trust attacks, a clarification about “Rust guarantees that code outside an `unsafe {}` block is safe”, a mention of `#[repr(transparent)]`, and a few other little things.

---

<div class="post-metadata">

**Author:** ![GalaxySnail](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/galaxysnail/32/5655_2.png) [@GalaxySnail](https://discuss.python.org/u/GalaxySnail)\
**Post date:** [November 18, 2025, 8:30am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/74 "2025-11-18T08:30:27Z")

</div>

If python cannot be built without rust in the future, I believe the difficulties this would bring to bootstrapping are being underestimated. Python is such a widely used programming language that many projects have started to use python during the build stage. For example, glibc and gcc require python to build ([https://github.com/fosslinux/live-bootstrap/commit/69fdc27d64ec56ad59b83b99aab0747c9d9f81ed](https://github.com/fosslinux/live-bootstrap/commit/69fdc27d64ec56ad59b83b99aab0747c9d9f81ed)). If python depends on rust, it would mean that all projects using the meson build system would also need rust to bootstrap (I know muon can be a replacement, but muon isn’t 100% compatible with meson). The live-bootstrap project has already completed the bootstrap of python, and it currently requires a total of 11 builds to obtain CPython 3.11.1, including regenerating all generated code ([https://github.com/fosslinux/live-bootstrap/blob/master/parts.rst#159python-201](https://github.com/fosslinux/live-bootstrap/blob/master/parts.rst#159python-201)). And even when using mrustc to build rust 1.74.0, it still requires 18 builds to obtain rust 1.91, especially since the time required to build rustc is much longer than CPython. Moreover, rust releases a new version every 6 weeks, so this number will grow quickly.

Compilation time is also an issue. Although incremental builds in debug mode may be fast, this is not always possible, for example when doing distribution packaging, when using `git bisect`, or when debugging bugs that only reproduce in release mode. Currently, a full CPython build is still relatively fast, and I agree that it would be acceptable if the full build time were up to 2x slower.

Regarding the previously mentioned issue with `os.fork`, I am not sure whether using fork in a single-threaded process is safe. If using fork in a single-threaded process would still break rust’s safety guarantees, then `os.fork` and `multiprocessing.get_context("fork")` would become completely unusable, and that would break many third-party libraries that depend on it.

On the other hand, rust occasionally introduces breaking changes outside of editions, for example [https://github.com/rust-lang/rust/issues/127343](https://github.com/rust-lang/rust/issues/127343), and the potential impact of such risks on CPython should be considered carefully.

---

<div class="post-metadata">

**Author:** ![davidhewitt](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/davidhewitt/32/3502_2.png) [@davidhewitt](https://discuss.python.org/u/davidhewitt)\
**Post date:** [November 18, 2025, 9:21am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/75 "2025-11-18T09:21:31Z")

</div>

> [@Eclips4](#):
>
> Can we integrate [MIRI](https://github.com/rust-lang/miri) into our workflow?

I spoke to some of the Miri maintainers about running PyO3 through Miri a while ago, I believe back then there were limitations due to all the C FFI being opaque to Miri. I vaguely recall the conversation concluded those limitations could be lifted, would just need some work. I’m not aware of anything to make me think that work has been done yet.

> [@steve.dower](#):
>
> I’d rather see people discussing things like how Rust provides any protection/benefit at all when we have to interop _everything_ with “unsafe” C code at a level _below_ anywhere PyO3 could help (which is only safe because it relies on our public C API, which is the safety barrier with guaranteed semantics that can be mapped into Rust’s semantics).

At the moment PyO3 has two abstractions, the low level FFI which this pre-PEP proposes generating with bindgen and the high-level abstractions which are totally safe. I’ve wondered about a third level which sits between the two; it would still use `unsafe extern “C”` ABI and call the C symbols directly, but the types for input & output could encode the possible states, e.g. `BorrowedPtr(*mut PyObject)` or even `Option<NonNull<PyObject>>` to force null checking. As long as these are layout identical with the actual C type passed through the FFI, it would just improve type safety without actually introducing any overheads or much “high level” API. There is a lot of scope to experiment here.

> [@Gankra](#):
>
> In practical specific terms, it’s often reported that Rust often makes implicit ownership/lifetime constraints in C APIs explicit and easier to work with. The Rust bindings to C functions can include lifetimes that enforce these contracts (and yes a _lot_ of C APIs map onto lifetimes and ownership well).

I agree fully with this - in particular a huge win is that you don’t need to remember to call `Py_Clear` / `Py_DecRef` / `Py_XDecRef` on every error pathway, RAII abstractions can just solve this for you. Your point here also speaks to what I was musing about in the point above.

> [@barry](#):
>
> The former is surely a smaller number, and my guess is that even fewer are comfortable in Rust _today_ .

Absolutely true that while many core devs may not currently be comfortable in Rust, there is a lot of anectotal evidence that after an initial learning curve many people find Rust relatively easy to feel productive and comfortable in. (Google’s experience with Android strongly supports this, for example.)

> [@CEXT-Dan](#):
>
> Thank you, I know nothing of Rust, I see the word ‘dependency’ and I immediately get scared. Python and all the 3rd party modules must load into the host application’s process. In my case, I’m running Python inside AutoCAD for windows. If this is optional, or something that’s not going load some sort of runtime, or something that could cause issues, then great

Many Python packages are already built in Rust, they’re precompiled and uploaded to PyPI as binary distributions which users can use without any awareness they’re built in Rust. CPython using Rust as an implementation detail would be no different for anyone not building from source.

> [@mgorny](#):
>
> Admittedly, the wider Python ecosystem with its Rust adoption puts quite a strain on us and the user experience worsens every few months, we still manage to provide a working setup.

@mgorny the Python ecosystem user experience is important to me and I’m aware there have been pains as tooling has adopted to Rust support. Gentoo particularly runs into these pains due to so much from-source building and extensive hardware support.

I’m sure I’m not aware of every possible configuration, please always do feel free to ping me / direct me at things and I will do my best to help. I build PyO3 / integrate Python & Rust to empower more people to write software, not to alienate.

---

<div class="post-metadata">

**Author:** ![ssokolow](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/ssokolow/32/32572_2.png) [@ssokolow](https://discuss.python.org/u/ssokolow)\
**Post date:** [November 18, 2025, 9:33am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/76 "2025-11-18T09:33:34Z")

</div>

> On the other hand, rust occasionally introduces breaking changes outside of editions, for example

I don’t think it’s fair to call Rust out for that specifically, given that it’s not a Rust-specific problem and that, as demonstrated in places like graydon2’s [retrobootstrapping rust for some reason](https://graydon2.dreamwidth.org/317484.html), my prior mention of which got spilled into the GitHub Gist because “New users can’t…”,

> - "Modern clang and gcc won’t compile the LLVM used back then (C++ has changed too much – and I tried several CXXFLAGS=-std=c++NN variants!)
> - Modern gcc won’t even compile the gcc used back then (apparently C as well!)
> - Modern ocaml won’t compile rustboot (ditto)

While I don’t have numbers, given that Rust’s regression suite became a bottleneck on development before Microsoft started donating Azure time, and that they have Crater (a bot for testing proposed changes against slices of the public crate registry up to and including “all of it”), I suspect Rust introduces breaking changes less than C and C++ do.

---

<div class="post-metadata">

**Author:** ![Shnatsel](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/shnatsel/32/32574_2.png) [@Shnatsel](https://discuss.python.org/u/Shnatsel)\
**Post date:** [November 18, 2025, 10:26am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/77 "2025-11-18T10:26:36Z")

</div>

> [@Rosuav](#):
>
> open questions such as the impact of a potential [Ken Thompson style compiler hack](https://aeb.win.tue.nl/linux/hh/thompson/trust.html). Will CPython lose trust by becoming dependent on a single specific compiler that might be subject to such a hack?

There is an alternative Rust compiler implementation in C++, [mrustc](https://github.com/thepowersgang/mrustc/), that implements just enough Rust to compile the official Rust the compiler without relying on it in any capacity. The official Rust compiler bootstrapped both ways (original chain and mrustc) produce identical binaries, which is sufficient to prove the absence of the Ken Thompson hack.

---

<div class="post-metadata">

**Author:** ![thesamesam](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/thesamesam/32/10616_2.png) [@thesamesam](https://discuss.python.org/u/thesamesam)\
**Post date:** [November 18, 2025, 10:42am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/78 "2025-11-18T10:42:34Z")

</div>

> It should be noted that, if I understand `“GCC Testing Efforts” site:gnu.org` correctly, GCC’s support for all platforms would count as “Tier 3, at varying degrees of stubbornness” by Rust testing standards since I don’t see any mention of any of the “Current efforts” entries being integrated to the same “CI on every push and will block merging into `main` if it fails” degree.

> Rust’s approach to Tiers 1 and 2 leans in the direction of “We don’t trust our testing to be sufficient for Continuous Deployment, but we’ll do it as diligently as if we were pushing directly to stable channel”.

I don’t really want to derail this thread into a discussion on models of testing, but a similar discussion was had the other week on [lobste.rs](https://lobste.rs/s/xj4ncv/hard_rust_requirements_from_may_onward#c_fwf8lw). I don’t think it’s a accurate summary to say Rust’s ‘testing standards’ just mean ‘Tier 3’ for GCC.

---

<div class="post-metadata">

**Author:** ![ssokolow](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/ssokolow/32/32572_2.png) [@ssokolow](https://discuss.python.org/u/ssokolow)\
**Post date:** [November 18, 2025, 10:45am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/79 "2025-11-18T10:45:00Z")

</div>

Thank you. Is there any chance that clarification could be added to [GCC Testing Efforts - GNU Project](https://www.gnu.org/software/gcc/testing/) since that’s what shows up in search results?

---

<div class="post-metadata">

**Author:** ![thesamesam](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/thesamesam/32/10616_2.png) [@thesamesam](https://discuss.python.org/u/thesamesam)\
**Post date:** [November 18, 2025, 10:45am UTC](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906/80 "2025-11-18T10:45:32Z")

</div>

In the thread, I did promise to work on improving documentation, so yes, it will be done.

EDIT: Filed [PR122742](https://gcc.gnu.org/PR122742) for that.

[Previous page](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906.md?page=3)

[Next page](https://discuss.python.org/t/pre-pep-rust-for-cpython/104906.md?page=5)
