One Shot, One Kill: Race Condition UAF in Rust's oneshot Crate
Vulnerability ID: GHSA-RVR2-R3PV-5M4P
CVSS Score: 8.1
Published: 2026-01-27
A high-severity Use-After-Free vulnerability in the oneshot Rust crate allows for memory corruption during the teardown of asynchronous channels. By racing the deallocation of the Sender against the cleanup of the Receiver's Waker, an attacker can trigger a read/write to freed memory.
TL;DR
The oneshot crate, a popular high-performance channel for Rust, contained a race condition in its Drop implementation. When an async receiver was dropped (cancelled), it signaled 'DISCONNECTED' to the sender before it finished cleaning up its internal Waker. If the sender reacted instantly and freed the channel memory, the receiver would subsequently attempt to access that freed memory, resulting in a Use-After-Free (UAF). Fixed in version 0.1.12.
⚠️ Exploit Status: POC
Technical Details
- Attack Vector: Local / Concurrency
- CVSS: 8.1 (High)
- CWE: CWE-416 (Use After Free)
- Impact: Memory Corruption, DoS, Potential RCE
- Exploitability: Race Condition (Time-sensitive)
- Fix Commit: d1a1506010bc48962634807d0dcca682af4f50ba
Affected Systems
- Rust applications using 'oneshot' crate < 0.1.12
- Asynchronous Rust services using tokio/async-std with oneshot channels
-
oneshot: < 0.1.12 (Fixed in:
0.1.12)
Code Analysis
Commit: d1a1506
Fix UAF in Receiver drop implementation by reordering state transitions
@@ -115,7 +115,7 @@ impl<T> Drop for Receiver<T> {
- let old_state = channel.state.swap(DISCONNECTED, Acquire);
- if old_state == RECEIVING {
- unsafe { channel.drop_waker() };
- }
+ if channel.state.load(Relaxed) == RECEIVING
+ && channel.state.compare_exchange(RECEIVING, EMPTY, Relaxed, Relaxed).is_ok()
+ {
+ unsafe { channel.drop_waker() };
+ }
+ let _ = channel.state.swap(DISCONNECTED, Release);
Exploit Details
- GitHub Issue: Original bug report detailing the race condition in drop implementation
Mitigation Strategies
- Update the 'oneshot' crate to version 0.1.12 or higher.
- Audit other unsafe blocks in async channel implementations for similar state-transition race conditions.
Remediation Steps:
- Open your terminal in the project root.
- Run
cargo update -p oneshot. - Verify the version with
cargo tree -p oneshot. - Rebuild and redeploy the application.
References
Read the full report for GHSA-RVR2-R3PV-5M4P on our website for more details including interactive diagrams and full exploit analysis.
Top comments (0)