Executive brief
vm2 is a JavaScript sandbox that isolates untrusted code execution. The stack-trace formatter in vm2 fails to properly isolate internal operations from sandbox code, allowing sandboxed JavaScript to install custom handlers that intercept the formatter's internal data writes. While the current impact is limited to observing stack frame information, this violates a critical design principle that prevents future sandbox escapes through object-passing channels.
Technical details
The vulnerability is a Defense Invariant #11 violation in defaultSandboxPrepareStackTrace (lib/setup-sandbox.js, lines 605–607), where stack frame data is appended to an internal array using prototype-walking index assignment (lines[lines.length] = value). This pattern allows sandbox-installed Array.prototype[N] setters to fire during the bridge's stack formatting, enabling observation and interception of each appended line. The attack requires no authentication or external network access—only the ability to run code in the sandbox. The current payload is a string after CallSite.toString(), limiting direct impact to a side channel; however, future changes enriching the appended record with host-realm object references would re-expose the GHSA-9qj6 attack shape. The fix mirrors the GHSA-9qj6 patch: use localReflectDefineProperty to create own data properties and bypass the prototype chain.
Affected products
- Patriksimek vm2 <=3.11.3
Timeline
- 2026-05-29: disclosed
- 2026-05-29: patched: Fixed in version 3.11.4