PT-2026-48343 · Packagist · Symfony/Runtime+1

Published

2026-06-09

·

Updated

2026-06-09

·

CVE-2026-47767

CVSS v4.0

6.9

Medium

VectorAV:N/AC:L/AT:N/PR:N/UI:N/VC:L/VI:L/VA:L/SC:N/SI:N/SA:N

Description

CVE-2024-50340 (GHSA-x8vp-gf4q-mw5j) addressed an issue where, with register argc argv=On, a crafted query string let an unauthenticated GET change the kernel environment and debug flag by feeding --env/--no-debug through $ SERVER['argv']. The fix shipped in symfony/runtime 5.4.46 / 6.4.14 / 7.1.7 gated the argv read on empty($ GET) as a proxy for "is this a CLI invocation".
That proxy is unsafe: parse str() (which builds $ GET) and the web SAPI (which builds $ SERVER['argv'] from the raw query when register argc argv=On) do not agree on every input, so an attacker can craft a query that leaves $ GET empty while $ SERVER['argv'] carries the attacker's flags. SymfonyRuntime::getInput() then parses them, restoring the exact primitive CVE-2024-50340 was meant to prevent.
Preconditions and impact match the original CVE: web SAPI, register argc argv=On, app booted through symfony/runtime; from an unauthenticated GET an attacker can flip APP ENV and toggle APP DEBUG.

Resolution

SymfonyRuntime now gates the argv read on isset($ SERVER['QUERY STRING']) rather than on empty($ GET). QUERY STRING is the same input the SAPI uses to build argv, so the security check and the thing it protects no longer parse different sources. Worker SAPIs (FrankenPHP / RoadRunner / Swoole) keep working because the runtime constructor runs once at boot when QUERY STRING is unset.
The patch for this issue is available here for branch 5.4.

Credits

SymfonyRuntime would like to thank 0xEr3n for reporting the issue and Nicolas Grekas for providing the fix.

Fix

Special Elements Injection

RCE

Weakness Enumeration

Related Identifiers

CVE-2026-47767
GHSA-FQC7-9XJW-JRH3

Affected Products

Symfony/Runtime
Symfony/Symfony