Question presented to candidate: "You have probably heard that Python is getting rid of the GIL. What exactly is the free-threaded build, which version brought it, and what changes for someone writing threaded Python code or maintaining a C extension?"
What a strong answer should cover:
- The GIL lets only one thread run Python bytecode at a time; the free-threaded build (PEP 703) is a separate CPython build, configured with
--disable-gil, in which threads run Python code truly in parallel on several cores. - Version facts: it is not in 3.12 (3.12 brought immortal objects, PEP 683, and a per-interpreter GIL, PEP 684). It first shipped as experimental in 3.13 (
python3.13t), and became officially supported, still optional, in 3.14 (PEP 779). The default download still has a GIL. - What changed inside: biased reference counting, immortal objects, deferred reference counting, the mimalloc allocator, and per-object locks so built-in
list/dictstay internally consistent. - What it means for your code: race conditions that were rare become common, so
+=on shared state needs aLockexactly as before; single-threaded code ran about 40% slower in 3.13 and the 3.14 target is at most 10%. - C extensions must declare free-threading support (
Py_mod_gil); importing one that does not re-enables the GIL with a warning. Detect the build withsysconfig.get_config_var("Py_GIL_DISABLED")and the runtime state withsys._is_gil_enabled()(3.13+); control it withPYTHON_GILor-X gil.
Clarifying questions expected:
- Do you mean what is in the default CPython download, or the separate free-threaded build?
Code / implementation expected: Optional β detect the build, and show that shared counters still need a lock.