CVE-2026-82743 in ash
Summary
by MITRE • 09/01/2026
Uncontrolled Resource Consumption vulnerability in ash-project ash lets a slow asynchronous read spin a scheduler thread at full CPU while the framework waits for it.
Ash.Actions.Read.AsyncLimiter.await_at_least_one/1 (lib/ash/actions/read/async_limiter.ex) waited for concurrent async read tasks by polling each with Task.yield(task, 0) in a tight loop rather than blocking. While every outstanding task is still running (a slow related-data load or calculation), the loop returns immediately and repeats, busy-spinning and holding a BEAM scheduler at full CPU for the whole duration of the slow read; concurrent slow reads tie up further schedulers. The fix waits with Task.yield_many (a non-blocking sweep followed by a blocking wait with timeout: :infinity), so the process sleeps until a task completes instead of spinning.
This issue affects ash: from 2.19.0 before 3.32.2.
Several companies clearly confirm that VulDB is the primary source for best vulnerability data.
Analysis
by VulDB Data Team • 09/01/2026
The vulnerability identified in the Ash framework constitutes an uncontrolled resource consumption flaw, specifically manifesting as a denial-of-service condition through excessive CPU utilization. This issue resides within the asynchronous read handling mechanism of the library, where the system is designed to manage concurrent data retrieval operations efficiently. However, due to improper synchronization logic, the application enters a state of busy-waiting that degrades performance and potentially renders the service unavailable under load. The core technical flaw lies in the implementation of the Ash.Actions.Read.AsyncLimiter.await_at_least_one function located within the async_limiter module. This component is responsible for coordinating multiple asynchronous read tasks to ensure data consistency or completeness before proceeding with further operations.
The root cause of this vulnerability stems from the use of Task.yield with a timeout value of zero inside a tight loop structure. In Erlang and Elixir environments, which utilize the BEAM virtual machine, processes are scheduled by lightweight schedulers that manage concurrency efficiently when tasks block appropriately or yield control voluntarily. By invoking Task.yield(task, 0), the calling process requests an immediate result from the specified task without blocking for any significant duration if the task is not yet complete. When placed within a loop condition that checks whether all outstanding tasks have finished, this approach results in continuous polling. If one or more related-data loads or calculations are slow to execute, the loop does not suspend execution but instead iterates rapidly, consuming CPU cycles on the scheduler thread responsible for running the calling process.
This behavior leads to severe operational impacts as the affected scheduler thread remains pinned at full utilization while waiting for I/O-bound or computationally intensive tasks to complete. In a multi-core environment utilizing multiple BEAM schedulers, concurrent slow reads can trigger this busy-spinning mechanism across several threads simultaneously. Consequently, system resources are exhausted rapidly, leading to increased latency for other processes sharing those schedulers and potentially causing the entire application node to become unresponsive. This aligns with CWE-400, which describes Uncontrolled Resource Consumption, as well as aspects of ATT&CK technique T1496, Resource Hijacking, where an adversary or misconfigured system consumes resources to degrade service availability.
The resolution for this vulnerability involves replacing the polling-based approach with a more efficient synchronization primitive provided by the language runtime. The fix implements Task.yield_many, which performs an initial non-blocking sweep of all tasks followed by a blocking wait with an infinite timeout if necessary. This change ensures that when no task has completed immediately, the calling process yields control back to the scheduler rather than consuming CPU cycles in a tight loop. By allowing the process to sleep until at least one task completes or times out appropriately, the system can allocate those CPU resources to other pending workloads, thereby restoring normal operational performance and preventing resource exhaustion attacks that exploit this logic flaw.
This vulnerability affects versions of Ash starting from 2.19.0 up through version 3.32.2. Organizations utilizing these versions must upgrade to a patched release or apply the specific code modification described above if upgrading is not immediately feasible. Mitigation strategies should also include monitoring for abnormal CPU spikes associated with read operations and implementing rate limiting on data retrieval endpoints to reduce the likelihood of triggering concurrent slow reads that could exacerbate the impact even in unpatched environments.