CVEReports
CVEReports

Automated vulnerability intelligence platform. Comprehensive reports for high-severity CVEs generated by AI.

Product

  • Home
  • Sitemap
  • RSS Feed

Company

  • About
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CVEReports. All rights reserved.

Made with love by Amit Schendel & Alon Barad



CVE-2026-24120

CVE-2026-24120: Remote Code Execution via Promise Species Hijacking in vm2 Sandbox

Amit Schendel
Amit Schendel
Senior Security Researcher

May 5, 2026·6 min read·24 visits

Executive Summary (TL;DR)

vm2 prior to version 3.10.5 contains a critical sandbox escape (CVSS 9.8). Attackers bypass internal security wrappers by overwriting Function.prototype.call and hijacking Promise creation, achieving unauthenticated remote code execution on the host system.

An incomplete mitigation for a previous sandbox escape in the vm2 Node.js module allows attackers to execute arbitrary code on the host system. By manipulating Promise species and intercepting internal method calls via prototype pollution, attackers bypass sandbox protections and gain full host access.

Vulnerability Overview

The vm2 package is a widely used Node.js module designed to run untrusted code within an isolated V8 execution context. Versions prior to 3.10.5 contain a critical vulnerability, tracked as CVE-2026-24120, which enables a complete sandbox escape. The vulnerability represents a failure of internal protection mechanisms (CWE-693) leading to arbitrary code injection (CWE-94) on the host system.

The attack surface involves the execution of untrusted JavaScript input within the sandbox environment. The vulnerability specifically targets the Promise resolution mechanism and the internal security wrappers implemented by the package maintainers. Attackers manipulate standard JavaScript built-in objects before the sandbox completes its secure initialization phase.

Successful exploitation results in arbitrary command execution on the host operating system with the privileges of the executing Node.js process. This completely compromises the application relying on the sandbox for security boundary enforcement. Organizations utilizing vm2 for multi-tenant isolation or untrusted code evaluation face immediate risk of host compromise.

Root Cause Analysis

The vulnerability stems from an incomplete patch for CVE-2023-37466, a prior sandbox escape regarding Promise species hijacking. The vm2 security logic attempts to neutralize attacks by resetting the Symbol.species property on the Promise constructor. This reset process relies on JavaScript internal method execution during sandbox setup.

Prior to version 3.10.5, the vm2 wrapper code utilized standard, mutable prototype lookups to execute original Promise methods. Specifically, internal security wrappers for then and catch invoked globalPromiseThen.call(this, ...). This reliance on .call() introduces an exploitable condition if the prototype chain is altered.

An attacker executing code within the sandbox initializes the exploit by overwriting Object.defineProperty with a no-operation function. This neutralization prevents the subsequent vm2 security fixups from correctly applying immutable properties to internal objects. The sandbox environment remains partially initialized and susceptible to further manipulation.

Concurrently, the attacker overrides Function.prototype.call. When the internal vm2 wrapper processes a Promise, it inadvertently routes execution through the attacker-controlled call function. This exposes internal references and allows the V8 engine to resolve the Promise using a malicious constructor defined via Symbol.species.

Code Analysis

Analyzing the setup-sandbox.js file reveals the exact mechanism of the protection failure. The vulnerable implementation binds the execution of wrapped Promise methods using Function.prototype.call. This design incorrectly assumes the integrity of the prototype chain within the sandbox environment during internal wrapper execution.

The following code illustrates the vulnerable implementation alongside the patch introduced in commit 4b009c2d4b1131c01810c1205e641d614c322a29.

// File: lib/setup-sandbox.js
globalPromise.prototype.then = function then(onFulfilled, onRejected) {
    // ...
-   return globalPromiseThen.call(this, onFulfilled, onRejected);
+   return apply(globalPromiseThen, this, [onFulfilled, onRejected]);
};
 
globalPromise.prototype.catch = function _catch(onRejected) {
    // ...
-   return globalPromiseCatch.call(this, onRejected);
+   return apply(globalPromiseCatch, this, [onRejected]);
};

The fix implements a required architectural shift by replacing .call() with a local apply primordial. This apply reference is derived securely from Reflect.apply during the initial environment capture. Capturing the primordial reference early makes the operation immune to runtime prototype pollution.

By utilizing local primordials, the patch severs the internal dependency on the mutable Function.prototype. Attackers modifying Function.prototype.call no longer intercept the internal execution flow of the vm2 wrappers. This closes the specific execution hijack vector utilized in this escape sequence.

Exploitation Mechanism

The exploitation chain requires the attacker to submit a precisely constructed JavaScript payload into the vm2.run() interface. The payload first neutralizes the environment by redefining Object.defineProperty = () => {}. This action stops vm2 from locking down internal object structures during subsequent execution phases.

The attacker proceeds to define a malicious FakePromise constructor and assigns it to p.constructor[Symbol.species]. Simultaneously, the attacker overrides Function.prototype.call. When the sandbox invokes a native Promise operation, the overridden call method intercepts the V8 internal execution flow.

The interception forces the V8 engine's PromiseResolveThenableJob to utilize the attacker's custom constructor. Inside this malicious constructor, the engine passes contextual arguments originating from the host environment. These arguments typically manifest as Error objects or internal stack structures referencing host-level contexts.

The attacker executes prototype climbing on the leaked host object. By accessing err.constructor.constructor, the payload obtains a direct reference to the host environment's Function object. From this access point, Function('return process')() retrieves the Node.js global process object, enabling direct command execution via process.mainModule.require('child_process').execSync().

Impact Assessment

The vulnerability carries a CVSS v3.1 base score of 9.8, categorizing it as Critical severity. The attack vector is entirely network-based, assuming the target application accepts remote input for evaluation within the sandbox. The complexity is low, as reliable and deterministic proof-of-concept payloads exist.

Exploitation requires no authentication and no user interaction. An attacker successfully executing the payload achieves a complete bypass of the intended security boundary. The confidentiality, integrity, and availability impacts are universally high, resulting in total control of the underlying host environment.

The EPSS score stands at 0.00080 (23.22nd percentile), indicating a lower immediate probability of mass exploitation relative to other vulnerabilities. However, the operational impact remains catastrophic for systems relying on vm2 for multi-tenant isolation or untrusted code execution.

While the vulnerability currently shows no known active exploitation in the wild and is absent from the CISA Known Exploited Vulnerabilities (KEV) catalog, the public availability of the exploitation methodology facilitates rapid weaponization by threat actors.

Remediation and Mitigation

The immediate technical mitigation requires upgrading the vm2 package to version 3.10.5. This release integrates the primordial replacements for the internal Promise wrappers. Engineering teams must verify the version update across all dependency trees within their Node.js environments.

The vm2 project is officially deprecated by its maintainers. The inherent architectural limitations of securing the V8 execution context against recursive prototype escapes render long-term maintenance of this model unfeasible. Organizations must treat the 3.10.5 patch strictly as a temporary, stopgap measure.

A permanent remediation strategy requires migrating away from vm2 entirely. Security architectures must transition to isolated processes utilizing strict operating system boundaries. Valid alternatives include WebAssembly runtimes, Docker containers with dropped capabilities, or Firecracker microVMs for robust isolation.

In environments where immediate migration is impossible, network-level monitoring provides secondary defense. Security teams should deploy Endpoint Detection and Response (EDR) signatures monitoring for anomalous child processes spawning from Node.js applications. Specifically, alerts should trigger on sh, bash, or cmd.exe invocations originating from processes handling untrusted input.

Official Patches

patriksimekGitHub Release v3.10.5
GitHub Security AdvisoryOfficial Security Advisory GHSA-qvjj-29qf-hp7p

Fix Analysis (1)

Technical Appendix

CVSS Score
9.8/ 10
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
EPSS Probability
0.08%
Top 77% most exploited

Affected Systems

Node.js applications running vm2 versions < 3.10.5

Affected Versions Detail

Product
Affected Versions
Fixed Version
vm2
patriksimek
< 3.10.53.10.5
AttributeDetail
CWE IDCWE-94, CWE-693
Attack VectorNetwork
CVSS Score9.8 (Critical)
EPSS Score0.00080 (23.22%)
Exploit StatusProof of Concept Available
KEV StatusNot Listed

MITRE ATT&CK Mapping

T1190Exploit Public-Facing Application
Initial Access
T1059.004Command and Scripting Interpreter: Unix Shell
Execution
CWE-94
Code Injection

Improper Control of Generation of Code ('Code Injection') via Protection Mechanism Failure

Known Exploits & Detection

Maintainer Test Suite PoCProof of concept verifying interception of internal functions via prototype pollution.

Vulnerability Timeline

Fix for Function.prototype.call interception committed
2026-01-17
Multiple bridge-level hardening commits added to repository
2026-02-15
CVE-2026-24120 formally published
2026-05-04
Technical advisory GHSA-qvjj-29qf-hp7p released
2026-05-04

References & Sources

  • [1]GitHub Release v3.10.5
  • [2]GitHub Security Advisory GHSA-qvjj-29qf-hp7p
  • [3]Fix Commit 4b009c2d4b1131c01810c1205e641d614c322a29
  • [4]Red Hot Cyber - Latest Critical Vulnerabilities Analysis
Related Vulnerabilities
CVE-2023-37466

Attack Flow Diagram

Press enter or space to select a node. You can then use the arrow keys to move the node around. Press delete to remove it and escape to cancel.
Press enter or space to select an edge. You can then press delete to remove it or escape to cancel.

More Reports

•about 18 hours ago•GHSA-H5X8-XP6M-X6Q4
7.1

GHSA-H5X8-XP6M-X6Q4: Unvalidated Signature Generation in @jhb.software/payload-cloudinary-plugin

The @jhb.software/payload-cloudinary-plugin exposes an endpoint that performs unvalidated cryptographic signing of Cloudinary API parameters, allowing authenticated users with minimal privileges to forge valid signatures for arbitrary actions. This flaw allows attackers to overwrite remote storage assets, execute unauthorized file uploads, alter asset visibility parameters, trigger SSRF webhooks, and perform directory traversal within Cloudinary repositories.

Alon Barad
Alon Barad
3 views•6 min read
•about 19 hours ago•GHSA-G2GW-Q38M-VJFC
8.7

GHSA-G2GW-Q38M-VJFC: Server-Side Request Forgery and Bearer Token Exfiltration in @merill/lokka

A Server-Side Request Forgery (SSRF) and Bearer Token Exfiltration vulnerability exists in the @merill/lokka (Lokka) Model Context Protocol (MCP) server prior to version 2.1.2. The server constructed Azure Resource Manager request URLs by concatenating user-controlled path parameters directly into destination request strings. By injecting authority-redefinition characters, an attacker can manipulate URL parsing to execute a host-escape attack, forcing the server to send high-privilege Azure Resource Manager (ARM) Bearer tokens to an external attacker-controlled host. This allows complete administrative access to the associated Azure subscriptions.

Alon Barad
Alon Barad
6 views•7 min read
•about 20 hours ago•GHSA-4XGF-CPJX-PC3J
5.3

GHSA-4xgf-cpjx-pc3j: Directory Traversal and Symlink Following in Pydantic Settings

A directory traversal and symlink following vulnerability exists in Pydantic Settings when using the NestedSecretsSettingsSource with nested subdirectory lookups enabled. An attacker capable of writing to the secrets directory can bypass size limitations, read arbitrary host files, or cause a denial-of-service condition via cyclic symlinks.

Amit Schendel
Amit Schendel
2 views•7 min read
•about 22 hours ago•GHSA-H5RG-8P7F-47G2
4.1

GHSA-h5rg-8p7f-47g2: Server-Side Request Forgery (SSRF) in SurrealDB Identity & Access Management (IAM) JWKS Fetcher

A Server-Side Request Forgery (SSRF) vulnerability exists in SurrealDB's Identity & Access Management (IAM) module prior to version 3.1.5. When configuring JSON Web Key Set (JWKS) URLs for token verification, the remote fetcher follows HTTP redirects by default without validating redirect targets against configured network capabilities. This allows high-privileged users to bypass network access limits and perform blind port scanning of internal network resources.

Amit Schendel
Amit Schendel
4 views•6 min read
•about 23 hours ago•GHSA-CC8F-FCX3-GPJR
7.7

GHSA-cc8f-fcx3-gpjr: Arbitrary File Disclosure via DEFINE ANALYZER mapper filter in SurrealDB

A local file disclosure vulnerability exists in SurrealDB's full-text search capabilities, allowing authenticated users with database EDITOR or OWNER roles to read arbitrary files from the host system filesystem. This occurs by abusing the mapper() filter inside a DEFINE ANALYZER statement to point to system files.

Alon Barad
Alon Barad
6 views•6 min read
•about 24 hours ago•GHSA-H4H3-3RFJ-X6FQ
4.3

GHSA-H4H3-3RFJ-X6FQ: Value-Ordering Oracle Side-Channel via Indexed ORDER BY in SurrealDB

SurrealDB versions 3.0.0 through 3.1.4 contain an information exposure vulnerability (CWE-203) where the query planner optimizes sorted queries using indexes on fields with field-level SELECT restrictions. Because the query planner performs index-based sorting before enforcing permission-based redaction, unauthorized users can observe the physical order of returned rows to deduce the relative values of protected fields.

Alon Barad
Alon Barad
4 views•8 min read