|
| 1 | +PEP: 803 |
| 2 | +Title: Stable ABI for Free-Threaded Builds |
| 3 | +Author: Petr Viktorin <encukou@gmail.com> |
| 4 | +Discussions-To: Pending |
| 5 | +Status: Draft |
| 6 | +Type: Standards Track |
| 7 | +Requires: 703, 793, 697 |
| 8 | +Created: 19-Aug-2025 |
| 9 | +Python-Version: 3.15 |
| 10 | + |
| 11 | + |
| 12 | +Abstract |
| 13 | +======== |
| 14 | + |
| 15 | +Version 3.15 of the Stable ABI will be compatible with both free-threaded and |
| 16 | +GIL-enabled builds. |
| 17 | +To allow this, the :c:type:`PyObject` internal structure and related APIs |
| 18 | +will be removed from version 3.15 of the Limited API, requiring migration to |
| 19 | +new API for common tasks like defining modules and most classes. |
| 20 | + |
| 21 | + |
| 22 | +Terminology |
| 23 | +=========== |
| 24 | + |
| 25 | +This PEP uses “GIL-enabled build” as an antonym to “free-threaded build”, |
| 26 | +that is, an interpreter or extension built without ``Py_GIL_DISABLED``. |
| 27 | + |
| 28 | + |
| 29 | +Motivation |
| 30 | +========== |
| 31 | + |
| 32 | +The Stable ABI is currently not available for free-threaded builds. |
| 33 | +Extensions will fail to build when :c:macro:`Py_LIMITED_API` is defined, |
| 34 | +and extensions built for GIL-enabled builds of CPython will fail to load |
| 35 | +(or crash) on free-threaded builds. |
| 36 | + |
| 37 | +In its `acceptance post <https://discuss.python.org/t/84319/123>`__ |
| 38 | +for :pep:`779`, the Steering Council stated that it “expects that Stable ABI |
| 39 | +for free-threading should be prepared and defined for Python 3.15”. |
| 40 | + |
| 41 | +This PEP proposes the Stable ABI for free-threading. |
| 42 | + |
| 43 | + |
| 44 | +Background |
| 45 | +---------- |
| 46 | + |
| 47 | +Python's Stable ABI, as defined in :pep:`384` and :pep:`652`, provides a way to |
| 48 | +compile extension modules that can be loaded on multiple minor versions of the |
| 49 | +CPython interpreter. |
| 50 | +Several projects use this to limit the number of |
| 51 | +:ref:`wheels <packaging:binary-distribution-format>` (binary artefacts) |
| 52 | +that need to be built and distributed for each release, and/or to make it |
| 53 | +easier to test with pre-release versions of Python. |
| 54 | + |
| 55 | +With free-threading builds (:pep:`703`) being on track to eventually become |
| 56 | +the default (:pep:`779`), we need a way to make the Stable ABI available |
| 57 | +to those builds. |
| 58 | + |
| 59 | +To build against the Stable ABI, the extension must use a *Limited API*, |
| 60 | +that is, only a subset of the functions, structures, etc. that CPython |
| 61 | +exposes. |
| 62 | +The Limited API is versioned, and building against Limited API 3.X |
| 63 | +yields an extension that is ABI-compatible with CPython 3.X and *any* later |
| 64 | +version (though bugs in CPython sometimes cause incompatibilities in practice). |
| 65 | +Also, the Limited API is not “stable”: newer versions may remove API that |
| 66 | +were a part of older versions. |
| 67 | + |
| 68 | +This PEP proposes the most significant such removal to date. |
| 69 | + |
| 70 | + |
| 71 | +Rationale |
| 72 | +========= |
| 73 | + |
| 74 | +The design in this PEP makes several assumptions: |
| 75 | + |
| 76 | +One ABI |
| 77 | + A single compiled extension module should support both |
| 78 | + free-threaded and GIL-enabled builds. |
| 79 | + |
| 80 | +No backwards compatibility |
| 81 | + The new limited API will not support CPython 3.14 and below. |
| 82 | + Projects that need this support can build separate extensions specifically |
| 83 | + for the 3.14 free-threaded interpreter, and for older stable ABI versions. |
| 84 | + |
| 85 | +API changes are OK |
| 86 | + The new Limited API may require extension authors to make significant |
| 87 | + changes to their code. |
| 88 | + Projects that cannot do this (yet) can continue using Limited API 3.14, |
| 89 | + which will yield extensions compatible with GIL-enabled builds only. |
| 90 | + |
| 91 | +No extra configuration |
| 92 | + We do not introduce new “knobs” that influence what API is available |
| 93 | + and what the ABI is compatible with. |
| 94 | + |
| 95 | + |
| 96 | +Specification |
| 97 | +============= |
| 98 | + |
| 99 | + |
| 100 | +Opaque PyObject |
| 101 | +--------------- |
| 102 | + |
| 103 | +Version 3.15 of the Limited API will: |
| 104 | + |
| 105 | +- make the following structures *opaque* (or in C terminology, *incomplete |
| 106 | + types*): |
| 107 | + |
| 108 | + - :c:type:`PyObject` |
| 109 | + - :c:type:`PyVarObject` |
| 110 | + - :c:type:`!PyModuleDef_Base` |
| 111 | + - :c:type:`PyModuleDef` |
| 112 | + |
| 113 | +- no longer include the following macros: |
| 114 | + |
| 115 | + - :c:macro:`PyObject_HEAD` |
| 116 | + - :c:macro:`!_PyObject_EXTRA_INIT` |
| 117 | + - :c:macro:`PyObject_HEAD_INIT` |
| 118 | + - :c:macro:`PyObject_VAR_HEAD` |
| 119 | + |
| 120 | +- no longer include these function-like macros: |
| 121 | + |
| 122 | + - :c:func:`Py_SIZE` |
| 123 | + - :c:func:`Py_SET_SIZE` |
| 124 | + - :c:func:`Py_SET_TYPE` |
| 125 | + |
| 126 | + |
| 127 | +Implications |
| 128 | +^^^^^^^^^^^^ |
| 129 | + |
| 130 | +Making the ``PyObject``, ``PyVarObject`` and ``PyModuleDef`` structures |
| 131 | +opaque means: |
| 132 | + |
| 133 | +- Their fields may not be directly accessed. |
| 134 | + |
| 135 | + For example, instead of ``o->ob_type``, extensions must use |
| 136 | + ``Py_TYPE(o)``. |
| 137 | + This usage has been the preferred practice for some time. |
| 138 | + |
| 139 | +- Their size and alignment will not be available. |
| 140 | + Expressions such as ``sizeof(PyObject)`` will no longer work. |
| 141 | + |
| 142 | +- They cannot be embedded in other structures. |
| 143 | + This mainly affects instance structs of extension-defined types, |
| 144 | + which will need to be defined using API added in :pep:`697` -- that is, |
| 145 | + using a ``struct`` *without* ``PyObject`` (or other base class struct) at |
| 146 | + the beginning, with :c:func:`PyObject_GetTypeData` calls needed to access |
| 147 | + the memory. |
| 148 | + |
| 149 | +- Variables of these types cannot be created. |
| 150 | + This mainly affects static ``PyModuleDef`` variables needed to define |
| 151 | + extension modules. |
| 152 | + Extensions will need to switch to API added in :pep:`793`. |
| 153 | + |
| 154 | +The following functions will become unusable in practice (in the new Limited |
| 155 | +API), since an extension cannot create valid, statically allocated, input |
| 156 | +for them. To ease the transition for extension developers, |
| 157 | +they will not yet be removed from the Limited API: |
| 158 | + |
| 159 | +- :c:func:`PyModuleDef_Init` |
| 160 | +- :c:func:`PyModule_Create`, :c:func:`PyModule_Create2` |
| 161 | +- :c:func:`PyModule_FromDefAndSpec`, :c:func:`PyModule_FromDefAndSpec2` |
| 162 | + |
| 163 | + |
| 164 | +New Export Hook (PEP 793) |
| 165 | +------------------------- |
| 166 | + |
| 167 | +Implementation of this PEP requires :pep:`793` (``PyModExport``: |
| 168 | +A new entry point for C extension modules) to be |
| 169 | +accepted, providing a new “export hook” for defining extension modules. |
| 170 | +Using the new hook will become mandatory in Limited API 3.15. |
| 171 | + |
| 172 | + |
| 173 | +Runtime ABI checks |
| 174 | +------------------ |
| 175 | + |
| 176 | +Users -- or rather the tools they use for building and installing extensions -- |
| 177 | +will continue to be responsible for not putting incompatible extensions on |
| 178 | +Python's import paths. |
| 179 | +This decision makes sense since tools typically have much richer metadata than |
| 180 | +what CPython can check. |
| 181 | + |
| 182 | +However, CPython will add a line of defense against outdated or misconfigured |
| 183 | +tools, or human mistakes, in the form of a new *module slot* containing |
| 184 | +basic ABI information. |
| 185 | +This information will be checked when a module is loaded, and incompatible |
| 186 | +extensions will be rejected. |
| 187 | +The specifics are left to the C API working group |
| 188 | +(see `issue 72 <https://github.com/capi-workgroup/decisions/issues/72>`__). |
| 189 | + |
| 190 | +This slot will become *mandatory* with the new export hook added in |
| 191 | +:pep:`793`. |
| 192 | +(That PEP currently says “there are no required slots”; it will be updated.) |
| 193 | + |
| 194 | + |
| 195 | +Check for older ``abi3`` |
| 196 | +^^^^^^^^^^^^^^^^^^^^^^^^ |
| 197 | + |
| 198 | +Additionally, in free-threaded builds, :c:func:`PyModuleDef_Init` will detect |
| 199 | +extensions using the pre-free-threading Stable ABI, emit an informative |
| 200 | +message when one is loaded, *and* raise an exception. |
| 201 | +(Implementation note: A message will be printed before raising the exception, |
| 202 | +because extensions that attempt to handle an exception using incompatible ABI |
| 203 | +will likely crash and lose the exception's message.) |
| 204 | + |
| 205 | +This check for older ``abi3`` relies on internal bit patterns and may be |
| 206 | +removed in future CPython versions, if the internal object layout needs |
| 207 | +to change. |
| 208 | + |
| 209 | + |
| 210 | +Wheel tags |
| 211 | +---------- |
| 212 | + |
| 213 | +PyPA build tools should not need changes: if they allow the user to set the |
| 214 | +limited API version, setting it to 3.15 should define :c:macro:`Py_LIMITED_API` |
| 215 | +to ``0x030f0000``. |
| 216 | +The resulting wheel should be tagged with the Python-ABI tag ``cp315-abi3``. |
| 217 | + |
| 218 | +Installers and other tools should assume that wheels with a *python tag* |
| 219 | +``cp315`` and above and ABI tag ``abi3`` are compatible with free-threaded |
| 220 | +builds. |
| 221 | + |
| 222 | + |
| 223 | +New API |
| 224 | +------- |
| 225 | + |
| 226 | +Implementing this PEP will make it possible to build extensions that |
| 227 | +can be successfully loaded on free-threaded Python, but not necessarily ones |
| 228 | +that are thread-safe without a GIL. |
| 229 | + |
| 230 | +Limited API to allow thread-safety without a GIL -- presumably ``PyMutex``, ``PyCriticalSection``, and |
| 231 | +similar -- will be added via the C API working group, or in a follow-up PEP. |
| 232 | + |
| 233 | + |
| 234 | +Backwards Compatibility |
| 235 | +======================= |
| 236 | + |
| 237 | +Limited API 3.15 will not be backwards-compatible with older CPython releases, |
| 238 | +due to removed structs and functions. |
| 239 | + |
| 240 | +Extension authors who cannot switch may continue to use Limited API 3.14 |
| 241 | +and below. |
| 242 | +For compatibility with free-threaded builds, they can compile using |
| 243 | +version-specific ABI -- for example, compile on CPython 3.15 without defining |
| 244 | +``Py_LIMITED_API``. |
| 245 | + |
| 246 | + |
| 247 | +Security Implications |
| 248 | +===================== |
| 249 | + |
| 250 | +None known. |
| 251 | + |
| 252 | + |
| 253 | +How to Teach This |
| 254 | +================= |
| 255 | + |
| 256 | +A porting guide will need to explain how to move to APIs added in |
| 257 | +:pep:`697` (Limited C API for Extending Opaque Types) |
| 258 | +and :pep:`793` (``PyModExport``). |
| 259 | + |
| 260 | + |
| 261 | +Reference Implementation |
| 262 | +======================== |
| 263 | + |
| 264 | +This PEP combines several pieces, implemented individually: |
| 265 | + |
| 266 | +- Opaque ``PyObject`` is available in CPython main branch after defining the |
| 267 | + ``_Py_OPAQUE_PYOBJECT`` macro. |
| 268 | + Implemented in GitHub pull request `python/cpython#136505 |
| 269 | + <https://github.com/python/cpython/pull/136505>`__. |
| 270 | +- For ``PyModExport``, see :pep:`793`. |
| 271 | +- For a version-checking slot, see GitHub pull request `python/cpython#137212 |
| 272 | + <https://github.com/python/cpython/pull/137212>`__. |
| 273 | +- For a check for older ``abi3``, see GitHub pull request `python/cpython#137957 |
| 274 | + <https://github.com/python/cpython/pull/137957>`__. |
| 275 | +- For wheel tags, there is no implementation yet. |
| 276 | +- A porting guide is not yet written. |
| 277 | + |
| 278 | + |
| 279 | +Rejected Ideas |
| 280 | +============== |
| 281 | + |
| 282 | + |
| 283 | +Add an alternative stable ABI for free-threading |
| 284 | +------------------------------------------------ |
| 285 | + |
| 286 | +It would be possible to: |
| 287 | + |
| 288 | +- Keep the current stable ABI (“``abi3``”) unchanged (except additions, as done |
| 289 | + in each release). Extensions would need no code changes and builds would be |
| 290 | + compatible with old and new GIL-enabled CPython versions. |
| 291 | +- Add a new stable ABI (“``abi3t``”) specifically for free-threading. |
| 292 | + Extensions would need no code changes and builds would be |
| 293 | + compatible with free-threaded CPython (3.14 and above). |
| 294 | +- Defining an additional macro (“``Py_OPAQUE_PYOBJECT``”) would make |
| 295 | + ``PyObject`` opaque as in this PEP. Extensions would need code changes as in |
| 296 | + this PEP, and compiled extensions (“``abi3.abi3t``”) would be compatible with |
| 297 | + all builds of CPython 3.15+. |
| 298 | + |
| 299 | +This scheme was rejected as too complex. |
| 300 | +It would also make the free-threading memory layout of ``PyObject`` part |
| 301 | +of the stable ABI, preventing future adjustments. |
| 302 | + |
| 303 | + |
| 304 | +Shim for compatibility with CPython 3.14 |
| 305 | +---------------------------------------- |
| 306 | + |
| 307 | +The issue that prevents compatibility with Python 3.14 is that with |
| 308 | +opaque ``PyObject`` and ``PyModuleDef``, it is not feasible to initialize |
| 309 | +an extension module. |
| 310 | +The solution, :pep:`793`, is only being added in Python 3.15. |
| 311 | + |
| 312 | +It is possible to work around this using the fact that the 3.14 ABIs (both |
| 313 | +free-threading and GIL-enabled) are “frozen”, so it is possible for an |
| 314 | +extension to query the running interpreter, and for 3.14, use |
| 315 | +a ``struct`` definition corresponding to the detected build's ``PyModuleDef``. |
| 316 | + |
| 317 | +This is too onerous to support and test in CPython's Limited API. |
| 318 | +It would also require adding a new wheel tag (e.g. ``abi3t``) that all install |
| 319 | +tools would need to recognize. (This PEP's ``cp315-abi3`` is incompatible |
| 320 | +with Python 3.14.) |
| 321 | + |
| 322 | + |
| 323 | +Open Issues |
| 324 | +=========== |
| 325 | + |
| 326 | +[See discussion for now.] |
| 327 | + |
| 328 | + |
| 329 | +Copyright |
| 330 | +========= |
| 331 | + |
| 332 | +This document is placed in the public domain or under the |
| 333 | +CC0-1.0-Universal license, whichever is more permissive. |
0 commit comments