Media

Locutus Prototype Pollution due to incomplete fix for CVE-2026-25521

  • Publicada: 27.03.2026
  • Actualizado: 11.10.2026 10:22

Summary

A prototype pollution vulnerability exists in the parse_str function of the npm package locutus. An attacker can pollute Object.prototype by overriding RegExp.prototype.test and then passing a crafted query string to parse_str, bypassing the prototype pollution guard.

This vulnerability stems from an incomplete fix for CVE-2026-25521. The CVE-2026-25521 patch replaced the String.prototype.includes()-based guard with a RegExp.prototype.test()-based guard. However, RegExp.prototype.test is itself a writable prototype method that can be overridden, making the new guard bypassable in the same way as the original — trading one hijackable built-in for another.

Package

locutus (npm)

Affected versions

= 2.0.39, <= 3.0.24

Tested and confirmed vulnerable on 2.0.39 and 3.0.24 (latest). Version 2.0.38 (pre-fix) uses a different guard (String.prototype.includes) and is not affected by this specific bypass.


Description

Details

The vulnerability resides in parse_str.js where the RegExp.prototype.test() function is used to check whether user-provided input contains forbidden keys:

js
if (/__proto__|constructor|prototype/.test(key)) {
  break
}

The previous guard (fixed in CVE-2026-25521) used String.prototype.includes():

js
if (key.includes('__proto__')) {
  break
}

The CVE-2026-25521 fix correctly identified that String.prototype.includes can be hijacked. However, the replacement guard using RegExp.prototype.test() suffers from the same class of weakness — RegExp.prototype.test is a writable method on the prototype chain and can be overridden to always return false, completely disabling the guard.

The robust fix is to use direct string comparison operators (===) in native control flow (for/if) instead of prototype methods like RegExp.prototype.test(), since === is a language-level operator that cannot be overridden.

PoC

Steps to reproduce

  1. Install locutus using npm install locutus
  2. Run the following code snippet:
js
const parse_str = require('locutus/php/strings/parse_str');

// Hijack RegExp.prototype.test (simulates a prior prototype pollution gadget)
const original = RegExp.prototype.test;
RegExp.prototype.test = function () { return false; };

// Payload
const result = {};
parse_str('__proto__[polluted]=yes', result);

// Check
RegExp.prototype.test = original;
console.log(({}).polluted); // 'yes' — prototype is polluted

Expected behavior

Prototype pollution should be prevented and ({}).polluted should print undefined.

undefined

Actual behavior

Object.prototype is polluted. This is printed on the console:

yes

Impact

This is a prototype pollution vulnerability with the same impact as CVE-2026-25521. The attack requires a chaining scenario — an attacker needs a separate prototype pollution gadget (e.g., from another npm package in the same application) to override RegExp.prototype.test before exploiting parse_str. This is realistic in Node.js applications that use multiple npm packages, where one package's vulnerability can disable another package's defenses.

Any application that processes attacker-controlled input using locutus/php/strings/parse_str may be affected. It could potentially lead to:

  1. Authentication bypass
  2. Denial of service
  3. Remote code execution (if polluted property is passed to sinks like eval or child_process)

Resources

Maintainer response

Thank you for the follow-up report. This issue was reproduced locally against locutus@3.0.24, confirming that the earlier parse_str guard was incomplete: if RegExp.prototype.test was already compromised, the guard could be bypassed and parse_str('__proto__[polluted]=yes', result) could still pollute Object.prototype.

This is now fixed on main and released in locutus@3.0.25.

Fix Shipped In

What the Fix Does

The new fix no longer relies on a regex-prototype guard for safety. Instead, src/php/strings/parse_str.ts now rejects dangerous key paths during parsed-segment assignment, so the sink itself is hardened even if RegExp.prototype.test has been tampered with beforehand.

Tested Repro Before the Fix

  • Override RegExp.prototype.test to always return false
  • Call parse_str('__proto__[polluted]=yes', result)
  • Observe ({}).polluted === 'yes'

Tested State After the Fix in 3.0.25

  • Dangerous key paths are skipped during assignment
  • The same chained repro no longer pollutes Object.prototype
  • The regression is covered by test/custom/parse_str-prototype-pollution.vitest.ts

The locutus team is treating this as a real package vulnerability with patched version 3.0.25. The vulnerable range should end at < 3.0.25.

Software afectado

Haz clic en una tecnología para ver todas sus vulnerabilidades.

PlataformaPaqueteVersiones vulnerablesCorregida en
Paquete de npm locutus >= 2.0.39, < 3.0.25 3.0.25

Referencias

Puntuación CVSS -
Vector CVSS
CVSS:4.0/AV:N/AC:L/AT:P/PR:N/UI:N/VC:N/VI:L/VA:N/SC:N/SI:L/SA:N
Debilidad (CWE)
CWE-1321
Plataforma
npm
Paquete
locutus
Publicada
27.03.2026
Actualizado
11.10.2026 10:22

Fuentes y licencias

OSV / GitHub Advisory Database - GHSA-vc8f-x9pp-wf5p - CC BY 4.0

Historial de vulnerabilidades: locutus

Todas las vulnerabilidades publicadas de este paquete (Paquete de npm), de la más reciente a la más antigua. Muestra si es un fallo aislado o un paquete que hay que vigilar.

Entradas en total
8
Primera → última
05.2021 03.2026
Sin corrección
1
Explotada en ataques
0

Distribución por gravedad

  • Crítica 4
  • Alta 2
  • Media 2

Divulgaciones por año

  1. 2021: 3
  2. 2022: 0
  3. 2023: 0
  4. 2024: 0
  5. 2025: 0
  6. 2026: 5
  1. Locutus Prototype Pollution due to incomplete fix for CVE-2026-25521 esta entrada
    Media CVE-2026-33994 >= 2.0.39, < 3.0.25 3.0.25
  2. Crítica · 9.8 CVE-2026-32304 < 3.0.14 3.0.14
  3. Crítica CVE-2026-25521 >= 2.0.12, < 2.0.39 2.0.39
  4. Crítica · 9.8 CVE-2020-13619 <= 2.0.11 sin corrección
  5. Alta · 7.5 CVE-2021-23392 < 2.0.15 2.0.15
  6. Crítica · 9.8 CVE-2020-7719 < 2.0.12 2.0.12

Identifica las vulnerabilidades de tu aplicación

Con la integración de DockRay y el inventario de software activado, DockRay compara las versiones notificadas de los componentes con las vulnerabilidades conocidas y avisa de las coincidencias confirmadas. La cobertura depende de la tecnología compatible y de los avisos disponibles.

Conectar tu aplicación
Newsletter DockRay

La seguridad de tus aplicaciones en tu correo

Vulnerabilidades importantes, recomendaciones concretas y consejos prácticos para tus aplicaciones. Elige tus tecnologías y sigue lo que importa para tu proyecto.

  • Un resumen diario de nuevas vulnerabilidades, también las críticas.
  • Avisos sobre actualizaciones importantes.
  • Consejos prácticos sobre seguridad y monitorización de aplicaciones.

Déjalo vacío para recibir avisos de todas las tecnologías.

Suscripción gratuita. Date de baja con un clic en cualquier correo.