A binary may support free threading yet run with the GIL enabled; inspect build and process state separately.
Python free-threaded diagnostics: separate build capability from current GIL state
Operation contract
The checked standard CPython build reports no free-threaded build support and an enabled GIL. The program reads both values directly from the interpreter rather than inferring them from a version number or thread count. Its output is intentionally tied to the local checked runtime, so another build can print different booleans.
Failure boundary
This machine has no free-threaded interpreter in the test environment, so the disabled-GIL path was not executed. A native extension import may enable the GIL in a free-threaded build. Neither flag tells whether application data races exist or whether a workload scales across cores. Run concurrency tests under every supported mode.
Working program
import sys
import sysconfig
supports_free_threading = sysconfig.get_config_var("Py_GIL_DISABLED") == 1
gil_enabled_now = sys._is_gil_enabled()
print("free_threaded_build", supports_free_threading)
print("gil_enabled_now", gil_enabled_now)Output
free_threaded_build False
gil_enabled_now TrueCosts and limits
Reading these interpreter flags is constant-time. The expensive work is testing shared-state invariants under the actual deployment build and extension set.
Common Mistakes
- Build capability and current process state are different questions.
- A version number does not prove the GIL is disabled.
- A lock-safe fixture on one build is not a stress test on another.
