Skip to content

ByteStream::drain: empty buffer before signal_drained (JS-reader path) - #36879

Open
robobun wants to merge 8 commits into
mainfrom
claude/farm/3cd8fa99/bytestream-drain-order
Open

ByteStream::drain: empty buffer before signal_drained (JS-reader path)#36879
robobun wants to merge 8 commits into
mainfrom
claude/farm/3cd8fa99/bytestream-drain-order

ByteStream: empty buffer before signal_drained in drain()

e386b6b
Select commit
Loading
Failed to load commit list.
Claude / Claude Code Review completed Aug 4, 2026 in 37m 30s

Code review found 1 important issue

Found 1 candidates, confirmed 1. See review comments for details.

Details

Severity Count
🔴 Important 1
🟡 Nit 0
🟣 Pre-existing 0
Severity File:Line Issue
🔴 Important src/runtime/webcore/ByteStream.rs:675-685 drain() reordering enables out-of-order writes to a freshly-wired native sink

Annotations

Check failure on line 685 in src/runtime/webcore/ByteStream.rs

See this annotation in the file changed.

@claude claude / Claude Code Review

drain() reordering enables out-of-order writes to a freshly-wired native sink

Emptying `self.buffer` before `signal_drained()` opens a re-entrancy window for the three callers that set `self.sink` *before* calling `drain()` — `wire_native_sink` (ReadableStream.rs:330), the S3 upload path (s3/client.rs:1027), and `RequestContext` (server/RequestContext.rs:3269). With the buffer now empty when `signal_drained()` → `RewriterPipe::resume()` runs, `output_backpressured()` no longer bails, so `drain_pending_input()` can synchronously produce new output that hits `out.on_data` →