# If you run Apache with mod_php, stop reading and patch now: upgrade to PHP 8.5.12, 8.4.27, 8.3.36 or 8.2.35.

> Source: <https://semgrep.dev/blog/2026/php2shell-php-runtime-rce>
> Published: 2026-10-21 00:00:00+00:00

Hello, I spent many years defending a large modern PHP application. The new bugs are bad! You should fix them. The runtime will be fine. I promise. Just do it.

So, what exactly happened? LLM-assisted vulnerability discovery found some novel applications of memory corruption problems that let you abuse improper cleanup of failed/broken/interrupted web requests.

It’s very clever! Sometimes, LLMs and humans together do *amazing* things.

## **GHSA-w8hw-w9fx-j79w - RCE via OOM corruption**

The *really not so good one* is [__GHSA-w8hw-w9fx-j79w__](https://github.com/php/php-src/security/advisories/GHSA-w8hw-w9fx-j79w), because it lets you write arbitrary memory state into a place where it will be read (and potentially executed) during request shutdown, a normal part of the PHP request lifecycle. Some common PHP deployment strategies *always* exercise a shutdown branch *before* any application code is handled - meaning it *does not matter what your application does - if it receives requests it is vulnerable.*

Due to mod_php’s behavior, you can *reliably* trigger this by simply exhausting request memory. There are a few ways to do this, none of which I will describe to you, but I will tell you that someone with a journeyman familiarity with PHP could figure it out given some breadcrumbs. Apache and mod_php unfortunately let this trigger before *any* application code runs: any PHP application that can receive web requests is exposed. If you are using Apache with `mod_php` you have to fix this NOW; the validated exploit targets unpatched Apache/mod_php. Source analysis indicates it is likely that FPM, FrankenPHP, and LSAPI are also affected; PoCs will surface soon if they haven’t already.

## **GHSA-6wmf-4rv5-p3rp - RCE via stale global state**

**Let me be perfectly clear - this bug being harder to exploit does not make it less dangerous. Once somebody does it once, a tool will arise to make replaying that gadget trivial. We have done this dance already with BinaryFormatter et al.****Patching is the only defense.**

I have a somewhat old-school view of bugs that require heap grooming, which is that doing it is hard and gross. LLMs have probably changed the calculus on this a little, but I suspect a skilled operator will do *much* better than a novice: successful exploits of LLM-assisted heap grooming attacks will be launched by…people who were gonna do it anyway after writing the exploits by hand for months. Therefore, while [__GHSA-6wmf-4rv5-p3rp__](https://github.com/php/php-src/security/advisories/GHSA-6wmf-4rv5-p3rp) is also Not Good, I am somewhat less worried about it *in the short term* compared to its evil twin.

It is also NEATO and a cool variant of my favorite bug class: insecure deserialization.

Basically, it is a language behavior primitive that lets you abuse improper state cleanup to write to global state. This is an *incredibly* dangerous primitive because it’s related to our first bug via the request lifecycle. 

A PHP worker has its own memory heap, and as part of *normal* behavior zeroes it out when it dies. Except for when it doesn’t. This is a *Producer* of a potentially hazardous state.

A PHP worker has its own memory heap, and as part of *normal* behavior zeroes it out on initialization before it ever reads from it. Except for when it doesn't. This is a *Consumer* of potentially hazardous state. This is akin to a deserialization gadget - functionality that allows Bad Things To Happen.

There are two *known* consumers of potentially poisoned state: INI diagnostics and session upload progress. Some runtimes, like mod_php, also do things like read php.ini once on startup then persist forever. This is Very Super Not Good if you can, you know, use a known producer to write arbitrary stuff to that state.

This bug *is harder to exploit*. Both the producer and the consumer must reside in the same worker. Both consumer types have been shown to be exploitable vs Apache/mod_php, and session upload progress has been shown to be exploitable against Apache/mod_php and FPM. It’s probable that we’ll end up finding exploitable cases in FrankenPHP and LSAPI too.

This is how it is now. Weird edge case “you’d need to be clairvoyant to…” bugs are getting unearthed. There will be more.

## **What to do and what we’re doing**

**What to do now:** upgrade to PHP 8.5.12, 8.4.27, 8.3.36 or 8.2.35. On end-of-life 8.1, 8.0 or 7.4, apply the available backports *and then immediately plan an upgrade* - do not depend on cherry-picked commits for bugs in core runtimes, *ever*. While you are upgrading there are partial mitigations such as setting `session.upload_progress.enabled=0` and leveraging relevant firewall rules which attempt to block known payloads however this is `not` a strategy we recommend to rely on as both can be bypassed.

**What we’re doing:** [__Semgrep Guardian__](https://semgrep.dev/products/semgrep-guardian/) now flags vulnerable PHP versions when your agent starts working on a project, and coverage for source-code defined usages of PHP is on the way.
