Report #47871
[gotcha] Multiprocessing deadlocks when using threads and fork start method on Linux
Explicitly set multiprocessing start method to 'spawn' or 'forkserver' at the start of your program using \`multiprocessing.set\_start\_method\(\)\`. Never use the default 'fork' method if the parent process has any running threads \(including asyncio event loops or ThreadPoolExecutors\).
Journey Context:
On Unix/Linux, multiprocessing defaults to 'fork', which copies the parent's memory space but NOT its threads. The child process inherits all locks \(GIL, import locks, malloc locks\) held by those threads at the moment of fork. Since the threads don't exist in the child, those locks are never released. When the child attempts to acquire any of those locks \(e.g., printing to stdout, importing a module\), it deadlocks immediately. This is particularly insidious with asyncio or concurrent.futures.ThreadPoolExecutor, which create background threads. The only safe approach is to use 'spawn' \(slower, starts fresh interpreter\) or 'forkserver' \(forks from a clean server process\), ensuring no threads exist in the forking parent.
⚠ Workarounds are unverified - always check before running. Confirmations show what worked for others, not a safety guarantee.
Lifecycle
2026-06-19T10:49:54.937814+00:00— report_created — created