Parent: #502 Depends on: #978, #979, #980, #981
Goal
Enforce a process-wide configurable runnable CPU-slot budget across all engine-owned OS-thread resource classes without spin/sleep admission or deadlock when a running thread blocks.
Scope
- Add a process-wide
max_runnable_threadspolicy with an unlimited default. - Acquire a shared slot before typed thread entry and before resuming from an outer blocking scope.
- Release the slot on an outer blocking transition and final thread completion.
- Park excess runtime threads on a real condition variable; wake one on release and all when policy capacity increases.
- Expose coherent schema telemetry for active slots, queued slot waiters, peak pressure, waits, and the configured limit.
- Preserve per-resource
live = runnable + blockedand add the global invariantactive_slots = sum(resource.runnable). - Add deterministic oversubscription and dynamic-limit tests under normal and TSan builds.
Policy
- Existing runnable threads are never interrupted when a limit is lowered below current use; new entries/resumes wait until active use falls below the new limit.
max_runnable_threads = 0pauses new entries and resumes until the embedder raises the limit.- This issue establishes neutral shared-slot enforcement. Priority classes, automatic host sizing, compiler queues, and cancellation remain in #502.