All articles
21 October 2026
12 min read

php2shell: what is confirmed about the critical PHP flaws

By Tim Rutte, Cloud & Software ArchitectTopicLegacy & ModernizationUpdated

A weathered white picket fence with gaps; a blue replacement picket leans in one of them.

As of 21 October 2026, 07:00 UTC. The security release has not been published at that point.

Update 21 October, 18:30 UTC: The release is out. What is confirmed since then is at the end of the article.

Today at 14:00 UTC the PHP team publishes a security release for two critical vulnerabilities. Both are rated CVSS v4.0 9.2. Since yesterday, screenshots, claims and guesses have been circulating under the name “php2shell”.

Much of it is unproven. This article separates what the primary sources say from what individual people claim. And it describes what I prepare before the release, so that the update this afternoon takes minutes.

What is officially confirmed

On 20 October at 19:33 UTC the PHP security team published an advance notice on the php.announce mailing list and on php.net. It says exactly five things:

  • A security release fixes two critical vulnerabilities, both rated CVSS v4.0 9.2.
  • It is scheduled for Wednesday, 21 October 2026, at 14:00 UTC.
  • All PHP users should prepare now so they can update as soon as it is available.
  • The team reserves the right to release earlier if details become public or active exploitation is seen.
  • Full details, the affected versions and the fixed versions will only be published with the release.

The CVE numbers are not in that notice. They come from advisory 2026-018 by CERT-EU, the cybersecurity service of the EU institutions: CVE-2026-109618 and CVE-2026-109619. CERT-EU states explicitly that no technical details are available. The score of 9.2 indicates the potential for unauthenticated remote code execution. All versions from PHP 5 onwards could be affected; as evidence for that, CERT-EU cites a post on Mastodon, not a statement by the PHP team.

CERT-EU recommends identifying PHP applications, preparing to patch immediately and, where that is not feasible, isolating internet-facing applications from public networks until the fix is applied.

How the leak happened

The vulnerabilities were under embargo. The sequence as far as the sources support it, all times in UTC:

TimeEventSource
20 Oct, 15:20A Hacker News post announces two upcoming PHP remote code execution disclosuresSansec
20 Oct, 16:39Kevin Beaumont writes on Mastodon that somebody leaked CVE-2026-109618 and CVE-2026-109619 before the patchMastodon
20 Oct, 18:26watchTowr confirms the vulnerabilities are real; everyone was supposed to wait until Thursday at 11am US Eastern timeX
20 Oct, 19:33Advance notice from the PHP security teamphp.announce
20 OctCERT-EU publishes advisory 2026-018CERT-EU
21 Oct, 14:00Scheduled security releasephp.net

That Thursday would have been 22 October, and 11am Eastern time is 15:00 UTC. The release therefore comes 25 hours ahead of the date watchTowr mentions.

What is claimed but not confirmed

Three statements appear in almost every report. The PHP team has confirmed none of them.

A ready-made exploit tool. According to Sansec, a screenshot of a tool named “PHP2Shell”, credited to a group called Calif.IO, leaked alongside the information. Its banner claims it works against every PHP release from 5.4.0 on. That is what a banner says, not a list of versions.

The cause in session upload progress. A user named J4ck3LSyN claims on X to have recreated and tested both vulnerabilities. By his account they are two heap use-after-free bugs in the handler for session.upload_progress, in the function php_session_rfc1867_callback in ext/session/session.c. He has published no evidence.

Mass attacks within minutes. Sansec expects mass attacks within 15 minutes of the release. That is an expectation, not an observation. It is plausible, because attackers can work out from a published patch what it closes.

Why no framework update helps

According to everything published so far, the vulnerabilities sit in the PHP interpreter itself, not in a library. That changes who has to act.

A composer update does not close them, and neither does an up-to-date Laravel, Symfony or WordPress. Sansec puts it plainly for shop systems: the fix has to happen at the infrastructure level, by updating PHP on the server. Even Sansec's own application firewall, Shield, comes too late by their assessment, because the attack hits PHP before the shop's code runs.

If you run your own servers or containers, this is on you today. If PHP comes from your hosting provider, ask them.

Which PHP versions can expect a fix

Which versions are affected and which are fixed will only be known with the release. What is certain is which branches the PHP project still supports with security updates today:

BranchSecurity updates untilLatest version before the release
PHP 8.231 Dec 20268.2.34
PHP 8.331 Dec 20278.3.35
PHP 8.431 Dec 20288.4.26
PHP 8.531 Dec 20298.5.11

The right-hand column matters: if you are on one of these versions this morning, you are fully up to date and still not protected. After the release, the only number that counts is the one in the official announcement.

PHP 8.1 and older no longer receive security updates from the PHP project. Whether a fix arrives for those versions depends on your Linux distribution or your provider, if they maintain backported packages. Ask today, not tomorrow.

PHP 8.2 drops off this list at the end of December. If you are on it, you get a fix today, but not next time: PHP 8.2 ends on 31 December.

What I prepare before the release

Nothing can be patched before the release. But almost everything that would slow the patch down this afternoon can be done now.

1. Find every PHP installation. Not in the repository, but on every environment: web servers, workers, cron servers, CI runners, container images. The command-line version need not be the PHP-FPM version, so check both.

php -v
php-fpm -v   # depending on the distribution e.g. php-fpm8.4 -v
grep -rn "^FROM php:" --include=Dockerfile* .

2. Settle how the update happens. With official Docker images, patching means pulling the new base image, rebuilding and rolling out. A tag like php:8.4-fpm only points to the new version once the maintainers have rebuilt the image. With system packages the fix arrives through the package repository, with managed hosting through the provider. By midday it should be clear for every environment who triggers the update.

3. Check the pipeline while things are quiet. Is the build green right now? Can someone roll out this afternoon, and do they have the permissions? A red build that has been left for days is the real risk today.

4. Ask your hosting provider. When will they apply the release, and what happens to PHP versions the PHP project no longer maintains?

5. A plan for whatever cannot be patched in time. For that case CERT-EU recommends isolating internet-facing applications from public networks until the fix is applied. It is uncomfortable, but it is the recommendation on the table.

A stopgap that rests on an unconfirmed assumption. If the claim about session upload progress is true, switching that feature off closes the attack path. Nobody outside the PHP team knows today whether it is true. According to the PHP manual the setting is enabled by default and can be set in php.ini, in the PHP-FPM pool configuration or via .user.ini, but not via ini_set():

session.upload_progress.enabled = Off

Then reload PHP-FPM. It only costs you something if your application reads upload progress through the session. Check the effect through the web server, because php -i on the command line shows the CLI configuration. This does not replace the update; at most it bridges the hours until then.

After the release: read the official announcement, compare the fixed versions against your own list, update, and check the version again on every environment. And in the days after, watch whether PHP processes start programs that have no business there, such as a shell or curl. A broader view of where an old PHP system is open elsewhere is in Ten holes that sit in every old PHP system.

Frequently asked questions

My framework and all packages are up to date. Am I safe? No, not because of that. What matters is the PHP version on the server, not the state of your code.

I run PHP 7.4. What now? The PHP project has not maintained 7.4 since the end of 2022. Ask your distribution or provider about a backported fix, and plan the move to a maintained branch instead of waiting for the next incident. What that move involves is in PHP 7.4 to PHP 8.4.

Are there attacks already? The PHP team reserved the right to release earlier if exploitation is seen. As of this article, it has not done so.

What does CVSS v4.0 9.2 mean? A severity score on a scale up to 10. Scores from 9.0 are rated critical. What exactly lies behind it, the PHP team only publishes with the release.

Sources

If you want to keep track of your versions continuously rather than just today, you need patch management that does not only kick in when something leaks.

Today it does not matter how good your code is. Today it matters how fast you can replace PHP.

Update: what is confirmed since the release

As of 21 October 2026, 18:30 UTC. All times in UTC.

The fixed versions

The PHP team has released PHP 8.5.12, 8.4.27, 8.3.36 and 8.2.35. Both advisories on GitHub carry the timestamp 13:34. According to the advisories, every version below these four is affected. For PHP 7.4, 8.0 and 8.1 the security team has provided minimal source backports; there are no official releases for these branches.

What the vulnerabilities are

CVETitleCause according to the advisoryConfirmed exploitation
CVE-2026-109618RCE via OOM corruptionOut-of-memory handling interrupts PHP while internal request data is only partially initialized. Request cleanup then treats it as valid.Code execution over HTTP against mod_php with default input and memory limits. No complete exploit has been demonstrated for PHP-FPM.
CVE-2026-109619RCE via stale global stateRequest state survives after its memory has been freed. A later request on the same worker can use it before it is reset (use-after-free).Via the session lifecycle against mod_php and PHP-FPM, via the fatal error backtrace path against mod_php.

Both are rated CVSS v4.0 9.2, vector AV:N/AC:H/AT:P/PR:N/UI:N: over the network, without authentication and without user interaction, with high attack complexity. According to php.net, every PHP installation serving web requests is affected: PHP-FPM, Apache with mod_php, php-cgi, FrankenPHP and LiteSpeed. The PHP team considers the risk highest for mod_php, because there a single unauthenticated request triggers the attack before any application code runs. Both advisories name the update as the only complete mitigation.

What became of the claims

  • Session upload progress: partly confirmed. The advisory for CVE-2026-109619 names paths through the session lifecycle, and php.net recommends session.upload_progress.enabled=0 as a stopgap. The specific function J4ck3LSyN named does not appear in any official source.
  • All versions from 5.4.0: not confirmed. What is certain: the PHP team has published backports down to 7.4, and Ubuntu has shipped fixed packages through Ubuntu Pro down to PHP 5.5.9 (Ubuntu 14.04).
  • CVSS 10.0: wrong. According to the PHP Foundation, the CVE numbers circulated from around 15:00 on 20 October with a wrong score of 10.0 and a wrong release time. The official score is 9.2.
  • Mass attacks within 15 minutes: not evidenced. See the next section.

Attacks

TimeReportSource
21 Oct, 03:02Cloudflare enables firewall rules for the known attack vectors by default and calls them a stopgapThe Hacker News
21 Oct, 11:26watchTowr reports no exploitation; the CVEs are not in the CISA KEV catalogThe Hacker News
21 OctCloudflare CTO Dane Knecht: “We are seeing early attacks emerging”. According to Cloudflare, attackers change their payloads to get around the rulesX, The Hacker News
21 Oct, 14:19watchTowr observes “active exploitation attempts” against both CVEs in its honeypot networkwatchTowr
21 Oct, 14:28Sophos: no active exploitation reported; a user on X claims a working exploitSophos

The PHP security team says it found no functional exploit among the leaked proofs of concept at the time of release. No confirmed compromise of a specific server has been reported as of this update. Neither CVE is in the CISA KEV catalog as of 14:04.

How the embargo broke

The PHP Foundation published the sequence on the day of the release:

  • A core developer found the first signs of the memory problem in 2024 during an audit by Quarkslab. No concrete attack vector was found at the time.
  • On 11 August 2026 Calif and OpenAI independently reported code execution with the same root cause, Wiz followed on 24 August, OpenAI reported further attack vectors on 18 September.
  • After the CVE numbers leaked, the team moved the release from 22 to 21 October. No technical details had become public with the leak.
  • Around 20:00 on 20 October Calif mistakenly published a video of its proof of concept. According to the Foundation, it accelerated the development of further PoCs.
  • On 21 October at 07:41 Chainguard published images containing the fix, ahead of the coordinated release. That made the patch available for study before others could update.

The Foundation calls the delay in fixing the flaw “a structural failure”, caused by the security team’s decision process and a lack of resources.

Packages and images

SourceStatus
Official Docker imagesphp:8.2 to php:8.5 rebuilt with 8.2.35, 8.3.36, 8.4.27 and 8.5.12; the -fpm tags between 16:47 and 17:30
Debian 13 (trixie)php8.4 8.4.27-1~deb13u1, DSA-6574-1
Debian 12 (bookworm)php8.2 8.2.35-1~deb12u1, DLA-4848-1
Debian sidnot fixed yet
Ubuntu 26.04 LTSphp8.5 8.5.4-0ubuntu1.5
Ubuntu 24.04 LTSphp8.3 8.3.6-0ubuntu0.24.04.13
Ubuntu 22.04 LTSphp8.1 8.1.2-1ubuntu2.28
Ubuntu 20.04 and olderthrough Ubuntu Pro
AlmaLinux 8, 9, 10at 14:36: packages in progress, testing repository first
rpms.remirepo.netno updates on release day, according to the PHP team

Ubuntu lists the fixes under USN-8948-1 and USN-8948-2. Distribution version numbers look old but contain the backported fix. What counts is the package changelog with both CVE numbers, not the output of php -v.

Stopgaps from the PHP team

For installations that cannot be updated right away, php.net lists these settings. According to the PHP team they reduce exposure but do not make an installation safe:

  • memory_limit=-1, set so that it cannot be overridden, for example via php_admin_value in the FPM pool or the Apache configuration. Do not substitute RLIMIT_AS or RLIMIT_DATA; both can trigger the very failure.
  • A low post_max_size: 8M without uploads, 32M with uploads, upload_max_filesize below it. In addition, limits at the web server or proxy for request size, field count, multipart parts, headers and nesting depth.
  • session.upload_progress.enabled=0 in php.ini, the FPM pool or the server configuration, then restart every worker.
  • On PHP 8.5, additionally fatal_error_backtraces=0.
  • Remove invalid or deprecated per-request settings that emit diagnostics before initialization, and fix fatal errors and timeouts that can be triggered from outside.

Correction to the section “What I prepare before the release”: It says session.upload_progress.enabled can be set via .user.ini. According to php.net that is not enough for this purpose: neither ini_set() nor the FPM .user.ini applies early enough. The setting belongs in php.ini, the FPM pool or the server configuration.

Sources for the update