Skip to content

refactor: split the context state to render and control threads - #1239

Open
mdydek wants to merge 3 commits into
mainfrom
refactor/split-context-states
Open

refactor: split the context state to render and control threads#1239
mdydek wants to merge 3 commits into
mainfrom
refactor/split-context-states

Conversation

@mdydek

@mdydek mdydek commented Aug 18, 2026

Copy link
Copy Markdown
Member

Problem

Only js state:

resume() flips the single state to RUNNING synchronously. The actual driver open is async and takes a few ms (Oboe/AVAudioSession — normal, not a failure). JS calls suspend() in that window. The guard reads RUNNING (not SUSPENDED), so it correctly decides to call audioPlayer_->suspend() — but the stream hasn't finished opening yet, so there's nothing real to stop. The stop call lands on a half-initialized stream (no-op, or worse, undefined behavior depending on the SDK); the open then completes moments later and audio starts playing — after suspend() already resolved and JS believes the context is suspended.

Only audio-thread state:

JS calls ctx.close() twice back-to-back (e.g. a cleanup effect firing twice). The "already closed" guard reads the engine-confirmed value, which hasn't updated yet because the engine hasn't processed either call. Both calls pass the guard and both proceed to release the same driver resources — double-free/double-release.

Solution

Two unrelated states, one serves as the guard for the unlogic calls, the second one guards internal audio engine to not call two things at the same time

@mdydek mdydek added the refactor Code restructuring without altering external behavior or fixing bugs label Aug 18, 2026
@github-actions

github-actions Bot commented Aug 18, 2026

Copy link
Copy Markdown

WPT non-regression comparison

PASS — no regressions · 2 improved section(s) · overall 2586 → 2632 (+46)

Spec section Base pass Head pass Delta
AudioContext 55 58 +3
BiquadFilterNode 232 275 +43
Unchanged sections (26)
Spec section Base pass Head pass Delta
Processing model 0 0 0
Other 52 52 0
AnalyserNode 138 138 0
AudioBuffer 140 140 0
AudioBufferSourceNode 208 208 0
AudioNode 261 261 0
AudioParam 599 599 0
ChannelMergerNode 30 30 0
ChannelSplitterNode 7 7 0
ConstantSourceNode 59 59 0
ConvolverNode 170 170 0
DelayNode 104 104 0
DestinationNode 0 0 0
DynamicsCompressorNode 4 4 0
GainNode 15 15 0
IIRFilterNode 87 87 0
MediaElementAudioSourceNode 0 0 0
MediaStreamAudioDestinationNode 1 1 0
MediaStreamAudioSourceNode 0 0 0
OfflineAudioContext 35 35 0
OscillatorNode 104 104 0
PannerNode 75 75 0
PeriodicWave 33 33 0
ScriptProcessorNode 0 0 0
StereoPannerNode 102 102 0
WaveShaperNode 75 75 0

Baseline: 6f579e9de254e0fc7910babdab5bccc82c9d475a · Candidate: e3fff995fdd7372fb38ef31ccfc28d5458dbfd61

Workflow run · this comment is updated on every push.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

refactor Code restructuring without altering external behavior or fixing bugs

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant