Cyber security
LiveEngineering

PHP ships emergency patches today for two critical RCEs

Two PHP flaws rated 9.2, CVE-2026-109618 and CVE-2026-109619, allow unauthenticated RCE before your code runs. Patches land 21 October at 14:00 UTC.

All times UTC. Newest update first.

Bar chart of PHP 8 websites by branch: 8.3 leads at 34.8%.
Share of PHP 8 websites by branch on 21 October 2026. Source: W3Techs. Only 8.2 and newer are expected to receive today's fix.

Two flaws in PHP itself, each rated 9.2 out of 10 by the PHP security team, get their fix at 14:00 UTC today. The identifiers are CVE-2026-109618 and CVE-2026-109619. Both are believed to be unauthenticated remote code execution, both reach you through a plain HTTP request, and both sit in code that runs while PHP is still parsing the request body. Your framework, your CMS and your application get no say in the matter.

The scale is the reason to clear your afternoon. W3Techs puts PHP on 69.3% of every website whose server-side language is known as of this morning, with WordPress alone at 39.6% of all sites. Roughly 1.9 million internet-facing hosts announce a PHP service to scanners, and one scan of 20 October found about 79% of those services running a branch that will never receive this fix.

Here is where things stand at 12:58 UTC. The release has not landed. PHP's own announcement, posted to the php.announce list at 19:33 UTC yesterday, gives a score, a time and nothing else. No CVE IDs, no affected versions, no component, no fix numbers. Everything else you have read today comes from a Hacker News post that broke the embargo at 15:20 UTC on 20 October and admitted in its own body that it had "no evidence beyond 'source: trust me, bro'", from CERT-EU, or from security vendors working the same incomplete picture. The first update below separates what is confirmed from what is rumour, and it is worth reading before you quote a version number to anyone.

Four things to do before 14:00 UTC.

  • Book the patch window anyway. You cannot name the fix version yet. You can still get a change approved and an engineer scheduled, and that is the step that actually determines whether this is a Tuesday or a Friday.
  • Pick your stopgap and write its expiry date. Blocking multipart/form-data at the web server is the one mitigation with real evidence behind it, and it breaks every file upload you run. Know which of your forms that kills.
  • Turn on process detection for PHP workers. Prevention is thin for the next hour. A php-fpm or php-cgi process spawning sh, curl, wget or a reverse shell pattern is the signal that matters.
  • Find out who builds your PHP. php.net, Debian, Ubuntu, Sury, Remi, Docker, cPanel and every appliance vendor have different queues and different lags, and one of them has already said it will not publish today.

We will post here as the release lands, as the fix commits name the component, and as vendors confirm or deny the mechanism. Newest entry at the top.

Sources

  1. Latestupdate

    14:00 UTC has not arrived: nothing is patched yet

    At 12:58 UTC the newest php-src tag is still php-8.5.11 from September 24, the changelog has no 8.5.12 section, and PHP's own advisory pages for both CVEs return 404. Every fix version in circulation is a prediction.

    Read the full update Show less

    The 12:58 UTC check on October 21 confirms that the emergency release has not shipped. Three independent checks say the same thing, every one of them is public, and you can re-run all three yourself in under a minute before you repeat any of the version numbers now circulating in Slack threads, vendor advisories and social posts.

    The php-src release list tops out at php-8.5.11, published 24 September 2026. The PHP 8 changelog still has no 8.5.12 section. And php.net/security/cve-2026-109618, along with the matching page for CVE-2026-109619, returns 404, so PHP has not published its own advisory text for either flaw.

    That leaves you in a strange hour where half the internet is quoting patch numbers that do not exist yet. Here is the honest split.

    Claim you have read today Status
    Both flaws rated CVSS v4.0 9.2 Confirmed by PHP
    Release at 14:00 UTC on 21 October Confirmed by PHP
    CVE-2026-109618 and CVE-2026-109619 CERT-EU and the leak, not PHP
    Fixes in 8.5.12, 8.4.27, 8.3.36, 8.2.35 Third-party prediction
    All PHP from version 5 affected CERT-EU assessment, unverified
    Unauthenticated RCE Inferred from the score, not stated

    Read the fourth row carefully. Researcher Kevin Beaumont and Tenable expect fixes in 8.5.12, 8.4.27, 8.3.36 and 8.2.35. The tag list shows php-8.5.12RC1 and php-8.4.27RC1, both cut on 6 October as part of the normal monthly cycle, but no RC tag exists for 8.3.36 or 8.2.35. Two of those four numbers have no build behind them at all. Print them as expected and never as fact.

    If you are holding a change ticket, the useful move in this hour is the boring one. Confirm which branches you run, confirm who builds your PHP (php.net tarball, distro package, Sury, Remi, a container image, or a vendor appliance), and get the restart command ready. When the tags land you want to be applying a fix, not investigating your estate.

    Booking that window before anyone can name a version number is the right call here, and it is not a close judgement. A patch that arrives at 14:00 and is applied on Thursday has lost most of its value.

  2. analysis

    The bug everyone is describing sits in PHP's upload progress handler

    Researchers point at php_session_rfc1867_callback in ext/session/session.c, where two cached zval pointers outlive the arrays they address. The handler runs before your application code, which is why the CMS you run does not help you.

    Read the full update Show less

    PHP has published no technical detail at all. Everything below is researcher analysis of a hypothesis that several independent teams have converged on. It is a hypothesis, not a vendor statement, and the two are easy to confuse once it has been paraphrased a dozen times.

    The component is php_session_rfc1867_callback in ext/session/session.c. It backs session.upload_progress, the feature that lets a page show a moving bar while a file is still uploading. Two properties of it matter far more than the feature.

    The handler runs in the request parsing layer, before your code. PHP parses multipart/form-data as the body arrives, and the progress callback fires during that parse. By the time wp-load.php or your Laravel front controller or index.php executes, the vulnerable code has already run. There is no application-level check to write, because the application is not in the loop yet. A maintenance mode that boots your framework is useless against a parser bug.

    It has been on by default since PHP 5.4. That default is the reason the affected range keeps being described as reaching back to PHP 5, and the reason a hardened WordPress install on PHP 7.4 is still in scope.

    The reported mechanism is a heap use-after-free built on two cached raw zval * pointers, post_bytes_processed and current_file_bytes_processed, which the callback keeps while the request lifecycle reallocates the arrays they address. A write-up published on 21 October in the Zer061 repository works through the arithmetic against PHP 8.4.4 and lands on a multipart body of about 258 bytes plus a socket stall longer than one second, which forces a second update pass and a re-decode over freed memory.

    That write-up is careful about its own limits, which is more than most coverage has been. Arming both pointers is confirmed there. Turning that into code execution needs a separate heap-groom stage, and without one AddressSanitizer does not flag a crash. Treat it as the state of public understanding rather than as an exploit guide.

    The vendor positions on exploitability genuinely differ. watchTowr says it reproduced CVE-2026-109618 and is withholding detail until patches ship. Huntress says it has not built or reproduced a proof of concept and is not aware of public exploit code that works. Tenable says exploit code is circulating publicly and that it has verified none of it. Three postures on the same incomplete picture, which is the accurate description of where we are at 11:30 UTC.

    A second claimed path sits in PHP's multipart parser itself, and it would matter for a different reason. From PHP 8.4, request_parse_body() parses multipart bodies on PUT and PATCH as well as POST. Any stopgap that only inspects POST is narrower than the parser it is trying to fence off.

  3. analysis

    The stopgap that works, and the three that do not

    Blocking multipart/form-data at the web server is the only mitigation with real evidence behind it, and it breaks every file upload on the site. The ini settings people are pasting into team channels do not close the path.

    Read the full update Show less

    If you cannot patch within hours of 14:00 UTC, here is the mitigation ranking, sorted by how much each option actually moves the risk.

    Block multipart/form-data at the web server. This is the stopgap Sansec recommends and it has the advantage of tracking the mechanism. If the vulnerable handler only fires while parsing a multipart body, refusing those bodies removes the trigger.

    map "$request_method:$content_type" $block_upload_progress {
        default 0;
        "~*^(POST|PUT|PATCH):\s*multipart/form-data([;,\s]|$)" 1;
    }
    server {
        if ($block_upload_progress) { return 444; }
    }
    

    Three details in that rule earn their place. It covers PUT and PATCH because PHP 8.4 parses multipart on both. It treats a comma as a delimiter alongside semicolon and whitespace, because PHP truncates the content type at the first ;, , or space and then hunts for boundary anywhere in the remainder, so multipart/form-data,boundary=x still counts and slips past a naive match. It returns 444 rather than 403, because an error_page that bounces 403s back into PHP re-enters the handler you were avoiding.

    The cost is blunt, so plan for it. WordPress media uploads, Magento admin image upload, contact forms with attachments, and every JavaScript FormData request stop working. Treat this as an emergency measure, test it against a real order before trusting it in production, and remove it the moment you are patched. Those two steps are the difference between a stopgap and an outage.

    Cloudflare's WAF rules, with a caveat the size of your origin IP. Cloudflare pushed emergency rules to all plans and its CTO said the company was "seeing early attacks emerging" at 07:43 UTC. Rules of the shape http.request.method eq "POST" and any(http.request.headers["content-type"][*] contains "multipart/form-data") buy time. They buy nothing if an attacker can reach your origin address directly, so lock origin access to Cloudflare's IP ranges or the rule is decoration. Dane Knecht called the rules a stopgap in the same breath that he announced them.

    session.upload_progress.enabled = Off will not close the path. Fastest to circulate and weakest to support, that setting is a workaround rather than a control, and it is the one most likely to burn the four hours you needed for the patch window. PHP core developers including Gina Peter Banyard and Joe Ferguson have said in public that configuration changes will not close these flaws and that upgrading PHP is the mitigation. Aikido separately reports that disabling the setting did not protect a test target. The second claimed path, in the multipart parser itself, would fire whether or not the progress handler is armed.

    disable_functions, open_basedir and expose_php = Off are not this kind of control. The PHP manual is unusually direct about the first two: disable_functions "can be circumvented and should not be considered a sufficient security measure", and open_basedir is "in no way comprehensive". Keep them as defence in depth. Do not file them as remediation on a ticket that says CVE-2026-109618.

  4. update

    Remi's RPM repo will not publish a fix today

    The PHP Foundation warned that Remi Collet's repository will not carry updated packages on 21 October. If that is where your PHP comes from, you are waiting on someone else's build queue and need to know it now.

    Read the full update Show less

    At 08:48 UTC the PHP Foundation warned that Remi's repository will not publish updates on 21 October. That matters more than it sounds, because Remi's repo is where a large share of RHEL, Alma, Rocky and Fedora hosts get their PHP. If your php package comes from rpms.remirepo.net, waiting for dnf update to save you this afternoon is not a plan.

    The specific repo is the general problem in miniature. PHP ships source tarballs at 14:00 UTC. Everything downstream is somebody's build queue.

    Channel What happens after 14:00 UTC
    php.net source tarballs Immediate, if you build it yourself
    Debian and Ubuntu packages Hours to days, then unattended-upgrades
    Sury's packages.sury.org/php Usually the same day, AMD64 first
    Remi's RPM repo Not today, per the PHP Foundation
    Docker php:*-fpm images Historically one to four days
    cPanel, CloudLinux, appliances Unknown until the vendor announces

    Two traps are worth naming before the queue starts moving. Adding a third-party repo does not put it under unattended-upgrades, because that tool only pulls from origins named in /etc/apt/apt.conf.d/50unattended-upgrades, and an origin nobody remembered to add is an update nobody will receive until somebody runs apt by hand while the queue is already on fire. Debian and Ubuntu also backport fixes under the same upstream version string, so Ubuntu 24.04 will keep reporting PHP 8.3.6 long after it is patched. Check the package and its changelog rather than php -v.

    apt list --upgradable 2>/dev/null | grep php
    zgrep -E 'CVE-2026-10961[89]' /usr/share/doc/php8.3-fpm/changelog.Debian.gz
    

    Upgrading the package is also not the same as running the fix. php-fpm restarts from its postinst script, so the service recycles as part of the upgrade, while mod_php needs an Apache reload. An upgraded binary on disk alongside a worker still running the old one is the failure mode that turns "we patched on Wednesday" into a postmortem on Friday. For the equivalent on a much larger appliance surface, see how CISA put edge gear on a clock when the patches were already public.

  5. update

    Cloudflare reports early attacks while other vendors report none

    Cloudflare's CTO said the company was seeing early attack traffic at 07:43 UTC. Patchstack reports exploitation from hosting partners. watchTowr, Huntress and the CISA KEV catalogue say otherwise. All of that can hold at once.

    Read the full update Show less

    The exploitation picture is genuinely contradictory this morning, and the disagreement is more useful than a single headline number.

    Cloudflare CTO Dane Knecht posted at 07:43 UTC that PHP sites behind Cloudflare already had WAF rules deployed for the known exploit vectors, that they were available on all plans including the free tier, and that the company was "seeing early attacks emerging" and would update mitigations as new vectors showed up. Patchstack, at 07:34 UTC, said it had received reports of active exploitation from multiple hosting partners.

    Against that, watchTowr's FAQ records exploitation as "none reported" and its CISA KEV status as "not listed". Huntress said it observed no in-the-wild exploitation across its partner environments. The CISA Known Exploited Vulnerabilities catalogue has no entry for either CVE as of this update.

    All four can be true at once, because each is measuring a different thing. Cloudflare sees traffic at its edge, which includes scanners, unverified tooling and one-shot probes that never succeed. Patchstack is relaying what hosting partners told it. watchTowr and Huntress are reporting confirmed compromise. Those are three thresholds along the same timeline.

    The practical read: scanning is already happening, confirmed compromise is not yet demonstrated publicly. That combination justifies the emergency multipart block and an accelerated patch window. It does not justify declaring yourself breached on traffic telemetry alone, which is the kind of call that looks cautious at 08:00 and embarrassing in the incident review.

    One warning holds regardless of which vendor you believe. Tenable says exploit code is circulating publicly and that it has verified none of it to work, and it warns that unverified proof-of-concept repositories are a reliable place to catch malware. Anyone on your team about to clone a php2shell repo to "test exposure" should do it in a sandbox with no credentials attached, or better, not at all.

    For calibration on how fast this normally goes: the 2024 PHP-CGI argument injection, CVE-2024-4577, was under exploitation within about 24 hours of disclosure and inside CISA's KEV catalogue within six days, with TellYouThePass ransomware behind much of it. The 2019 php-fpm flaw, CVE-2019-11043, drew in-the-wild attempts roughly three weeks before a patch existed, because a capture-the-flag write-up leaked early. The clock on this one started before PHP's own announcement.

  6. update

    Sites start going dark on purpose

    The GrapheneOS forum is offline and Dutch properties including Tweakers and the Tweede Kamer site went down while waiting for patches. Wordfence warned that every WordPress site is exposed and that auto-update cannot fix this one.

    Read the full update Show less

    Taking a production site offline is the clearest signal that people are reading the mechanism correctly, and this morning several did.

    The GrapheneOS project posted that its discussion forum, the only software it runs on PHP, was taken down temporarily while waiting for the patches, "due to vulnerability details already being available and proof of concept exploits being developed". The post lists what the team tried first: turning session.upload_progress.enabled off, blocking multipart/form-data, and Zend MM debug hardening. They took the site down anyway. When a security-focused project concludes that its own hardening will not hold, that tells you more than a vendor severity rating does.

    Dutch outlets reported Tweakers, the Tweede Kamer site and NCSC-NL offline in the same window. Treat any wider list of named sites as unconfirmed until each organisation says so itself.

    Wordfence's advisory, aimed at the largest single slice of the PHP ecosystem, makes the WordPress position plain: every WordPress site is exposed, and the fix cannot be auto-installed. WordPress core updates roll out on their own schedule, so a host running an older WordPress on PHP 7.4 does not wake up patched. Against the W3Techs figures from this morning, WordPress is 39.6% of all websites and PHP runs 69.3% of every site whose server-side language is known. Those two numbers together are the reason this is a runtime problem rather than a CMS problem.

    If you operate WordPress or any of the targets named in the leaked demonstration, including MediaWiki, phpBB, Magento, Joomla, Laravel, Symfony, Drupal and WHMCS, your patch plan cannot be "wait for the application to update itself". PHP has to move first. The same ordering applies to the Citrix-style cases where a vendor deadline was the only thing that got estates patched at all, as with the NetScaler RCE and CISA's Saturday deadline.

  7. confirmed

    PHP core developers close the door on configuration workarounds

    Gina Peter Banyard and Joe Ferguson both said in public that ini settings will not close these flaws and that upgrading PHP is the mitigation. That ends the workaround thread before it becomes the plan.

    Read the full update Show less

    Around 02:13 UTC the conversation shifted from "what do we change in php.ini" to "when does the tarball land", and it shifted because PHP core developers said so in public.

    Gina Peter Banyard and Joe Ferguson both stated that configuration changes will not protect you and that patching or upgrading PHP is the mitigation. A PHP 8.6 release manager made the same point in a comment that has been quoted widely: ini settings will not save you.

    This update should end the workaround thread on your team channel. It is very easy at 02:00 on a Tuesday to spend four hours tuning session.upload_progress.enabled and session.use_strict_mode and to come away feeling like something was done. Those settings are cheap to change and they may reduce one path. The people who wrote the code are telling you they are not a boundary.

    The honest version of an interim plan is narrower than most of what is circulating.

    • Block multipart bodies at the web server if you can survive losing uploads.
    • Isolate internet-facing PHP if you cannot, which is what CERT-EU recommends when patching is not immediately feasible.
    • Detect at the process level, because prevention is thin today.
    • Patch at 14:00 UTC, then remove every emergency rule you added.

    That last item is a real deliverable, not a footnote. Every emergency rule installed today becomes somebody else's incident three months from now, when uploads mysteriously fail and the reason is buried in a map block nobody remembers writing. Write the removal into the same ticket as the patch.

  8. confirmed

    PHP's advance notice gives you a score and a time and nothing else

    Jakub Zelenka posted to the php.announce list at 19:33 UTC on 20 October. Two critical vulnerabilities, both CVSS v4.0 9.2, release at 14:00 UTC on 21 October. No CVE IDs, no versions, no component name.

    Read the full update Show less

    This is the whole of PHP's own public statement, and its shape is the story. Jakub Zelenka sent it to the php.announce list at 19:33:47 UTC on 20 October.

    The PHP security team would like to give advance notice of an upcoming security release. It is scheduled for Wednesday, 21 October 2026 at 14:00 UTC. It addresses two critical vulnerabilities, both rated CVSS v4.0 9.2. All PHP users are encouraged to prepare now so they can update as soon as it is available. We reserve the right to release earlier should details of either vulnerability become public, or should evidence of active exploitation appear in the wild. Full details, affected versions, and the fixed versions will be published with the release.

    Count what that does not contain. No CVE identifiers. No affected version range. No component name. No fixed version numbers. No credit to a reporter. Not even a sentence saying the flaws are remotely exploitable. Every one of those facts arrived from somewhere else.

    The sentence carrying real weight is the reservation of the right to release early, which the team wrote before the leak and which saw both of its named triggers fire inside twelve hours: details became public on Hacker News, and by 07:43 UTC Cloudflare was reporting attack traffic against live PHP sites. The release moved from Thursday to today.

    Handle the CVSS figure carefully, because two numbers are circulating. PHP says 9.2 under CVSS v4.0. The Hacker News post that broke the embargo said 10.0, and watchTowr's Benjamin Harris told BleepingComputer he would call them "CVSS10", contradicting the vendor's own rating. Only one of those numbers comes from the organisation that wrote the code. Quote 9.2 and name who disagrees.

    CERT-EU advisory 2026-018, published the same evening, is the first document to put CVE-2026-109618 and CVE-2026-109619 on paper. It states that the two flaws "indicate the potential for unauthenticated remote code execution" and that they "could affect all PHP versions from PHP 5 onwards", and it recommends identifying PHP applications and, where patching is not immediately feasible, isolating internet-facing applications from public networks. CERT-EU is working from the score and the identifiers, exactly as you are. It has no technical detail either.

  9. update

    The embargo breaks on Hacker News

    A post titled 'Tell HN: 2x PHP RCE CVEs with CVSS 10.0 Incoming' published the reserved identifiers and the original Thursday disclosure slot. Its author wrote that the claim rested on 'source: trust me, bro'. The schedule moved up a day.

    Read the full update Show less

    The public record of this incident starts with a Hacker News submission at 15:20:35 UTC on 20 October, four hours ahead of PHP's own notice, titled "Tell HN: 2x PHP RCE CVEs with CVSS 10.0 Incoming".

    The post named the reserved identifiers CVE-2026-109618 and CVE-2026-109619, said an announcement was scheduled for Thursday 22 October at 18:00 CEST, and claimed the flaws affected PHP versions from PHP 5 onwards. Its author also wrote, in the post itself, that they had "no evidence beyond 'source: trust me, bro'". Moderators later pulled the submission. The identifiers stayed public.

    watchTowr's response is the moment the leak stopped being a rumour. The company posted that everyone was supposed to wait until Thursday at 11am ET, that information about embargoed zero-day RCE flaws in PHP had leaked, and that it could confirm the flaws were real. watchTowr later published an FAQ saying it believes it reproduced CVE-2026-109618 and is withholding technical detail until patches ship.

    The disclosure failure is worth sitting with, because the consequences do not fall evenly. The original plan was a Thursday disclosure at 11:00 ET with vendors briefed and fixes ready. What happened instead was a day of public speculation about unverified mechanism, a stream of proof-of-concept repositories of unknown safety, and an accelerated release that left downstream package maintainers less build time to get ready.

    One commenter in the Hacker News thread, a PHP 8.6 release manager, defended the post on the grounds that responsible disclosure is broken in 2026. That may well be true. It still leaves the leak as the wrong instrument for the problem, and the packages that arrive late this week are the receipt.

    What the leak did give you is narrow and real. It is the reason you are patching on Wednesday instead of Thursday, and the reason the release lands in the middle of a public fight rather than before one.

Live coverage by the Data Today Security Desk, reviewed and edited by Lars Cornelissen. How Data Today works and sources its numbers · Report a correction.