短短一夜,整个 PHP 社区炸开了锅。
北京时间 10 月 21 日晚 22 点,PHP 官方赶工推出紧急更新,一口气堵上两个 CVSS 评分 9.2 的远程代码执行漏洞,业界给这对漏洞起了个绰号——PHP2Shell。
问题并不出在某个插件或第三方框架上,而是埋在 PHP 解释器内核里。换句话说,哪怕你的业务代码再干净,服务器上只跑着一个 Hello World,只要 PHP 版本没更新,攻击者发出一个请求就可能把整台机器拿下。
更麻烦的是,受影响范围从 PHP 5.4 一路延伸到 8.5,而官方只给 8.2 至 8.5 这几个版本发了正式补丁。那些还在跑 PHP 7 乃至 PHP 5 的“祖传项目”,接下来怕是要忙得不可开交了。
这两天究竟发生了什么
按照原定计划,漏洞细节要到 10 月 22 日才对外公布;但由于消息提前走漏,PHP 团队被迫把发版日期提前了一天,结果补丁还没正式发出,就已经有人开始尝试利用。
下述时间均为 UTC 时区,换算成北京时间请加 8 小时。
10 月 20 日,Hacker News 上有用户贴出了两个 CVE 编号以及原定 22 日的披露日期;当晚,PHP 官方发出预告,宣布发版提前至 21 日。
10 月 20 日 20 时左右,研究团队 Calif 不慎把一段展示完整利用链的演示视频公开了出来。
10 月 21 日 03:02,Cloudflare 宣布为所有 WAF 用户默认开启拦截规则,免费版用户同样包含在内。
10 月 21 日 07:41,厂商 Chainguard 抢先放出了已含补丁的镜像,等于把修复代码直接摆在世人面前。
10 月 21 日 14:00,PHP 官方正式推出 8.5.12、8.4.27、8.3.36、8.2.35。
10 月 21 日 14:19,watchTowr 通报称,已经监测到针对这两个漏洞的真实利用尝试。
顺便纠正一个流传的错误:泄露消息中有人声称漏洞评分为满分 10.0,这并不属实,官方对这两个漏洞给出的评分均为 CVSS v4.0 9.2。当然,9.2 也足以令人警觉了。
这两个漏洞到底有多危险
一句话概括:不需要登录,不挑应用类型,一个请求就可能直接拿到服务器控制权。
CVE-2026-109618:内存耗尽时“收尾”环节出错。PHP 在处理请求的过程中,若内存恰好在内部数据只完成一半初始化时耗尽,随后的清理流程会把这些未完成的数据当作正常数据继续使用,攻击者可借此实现代码执行。打个比方,后厨备菜备到一半突然断电,收拾的人却把半成品当成成品端上了餐桌。
CVE-2026-109619:前一个请求留下的“旧房卡”并未注销。请求结束后,残留的状态仍然指向已经释放的内存,同一个 worker 处理下一个请求时会继续沿用,这是教科书式的 use-after-free。官方证实,该漏洞既能泄露内存内容,也能实现远程代码执行。
之所以说它凶狠,有下面几点原因。
第一,跟你的代码毫无关系。漏洞处在引擎层,PHP-FPM、Apache mod_php、php-cgi、FrankenPHP、LiteSpeed,只要在处理 Web 请求,全部都在打击范围之内。
第二,mod_php 场景下风险最高。官方做过演示:一条未经认证的请求,在任何应用代码执行之前就能完成攻击。
第三,即使不拿 shell 也能窃取数据。攻击者可以直接读出 worker 进程的内存,其中往往存有其他请求的密码、登录令牌、API Key 以及证书。
第四,主流 CMS 无一幸免。研究团队证实,针对特定版本的 WordPress、Drupal、Joomla、Magento,都可以做到无需登录的远程代码执行。
第五,波及面极广。有安全研究人员粗略估算,公网上可能受影响的主机数量超过 130 万台。
对照版本,看看自己属于哪一类
官方只维护 8.2 到 8.5 这几个分支;7.4 到 8.1 只提供需要自行处理的源码补丁;更久远的版本则彻底没人管了。
8.5.x:官方已发布正式修复版 8.5.12,请马上升级。
8.4.x:官方已发布正式修复版 8.4.27,请马上升级。
8.3.x:官方已发布正式修复版 8.3.36,请马上升级。
8.2.x:官方已发布正式修复版 8.2.35,先补上;另外 8.2 会在 2026 年 12 月 31 日终止支持,不妨顺手规划迁移。
7.4、8.0、8.1:不会有正式版本,只放出最小化的源码补丁。需要自己动手编译打补丁,或者转向发行版、商业 LTS 供应商;从长远看,迁移是躲不掉的。
5.4 到 7.3:什么资源都没有。唯一的路就是迁移;在完成迁移之前,先把公网入口隔离或下线。
使用 Linux 发行版自带软件包的用户需要留意:各发行版早已提前拿到补丁,软件包的版本号看上去可能依然是“旧”的,但实际上漏洞已经修复。判断时应当查看包 changelog 里是否出现这两个 CVE 编号,而不能只盯着版本号。
老版本钉子户,该直面现实了
先看一份统计。W3Techs 在 2026 年 8 月 22 日的数据显示,在使用已知服务端语言的网站里,PHP 占据 70.3%。其中 PHP 8 占 63.1%,PHP 7 仍占 28.9%,PHP 5 还有 7.9%,甚至有 0.1% 的网站还在跑 PHP 4。
换一种说法:三分之一以上的 PHP 网站还停留在官方早已放弃维护的版本上。PHP 7.4 早在 2022 年 11 月就停止支持了,PHP 5.6 更是 2018 年底就已退役。
这些站点为什么一直没升级?做过外包的人多半心知肚明。
验收就是终点。项目交付上线、尾款结清,服务器从此再也没有人登过。
能跑就别折腾。“又没坏,升什么级?”这句话是不少甲方的口头禅,也是许多开发商的内心写照。
一升就全白屏。祖传代码里堆满 mysql_ 系列函数、each()、create_function(),这些东西在 PHP 7、PHP 8 里早已移除,升级就等于推倒重写。

升级没有人为之买单。维护合同里写的只是“保证正常运行”,从来没承诺过“保证运行时版本在支持期内”。
这次最让人哭笑不得的地方在于:7.4 到 8.1 官方虽然给了源码补丁,却要求自行编译。可现实是,具备从源码编译 PHP 能力的团队,当年多半不会停在 7.4 上。而 5.x 到 7.3,连源码补丁都没有。
更别提,就在一个月前(9 月 24 日),PHP 刚刚发布过一轮安全更新,修掉了 11 个 CVE。长期停留在旧版本,等同于这些年的补丁一个都没打上,PHP2Shell 不过是动静最响的那一次。
可以预见,未来几周不少开发商的日常大概会是这样的:翻出十年前的老项目清单,挨台登录服务器查版本;一个接一个给客户打电话,解释为什么“原本好好运行的网站”突然要追加预算升级;最后在 PHP 8 的报错信息里熬夜改代码。
这一回,真的有得忙了。
几个不容忽视的细节
细节一:这个漏洞早在 2024 年就露出过端倪。PHP 基金会承认,2024 年开展外部安全审计时,一位核心开发者就注意到了与内存不足相关的可疑迹象,只是当时没能找到真正可行的利用路径。几套修复方案各有隐患:可能损害兼容性,可能带来拒绝服务风险,也可能迫使第三方扩展随之改动;小团队议而不决,一拖就是好几个月。基金会把这次拖延归结为决策机制和资源层面的结构性问题,并表示已经扩充人员、补齐工具、优化流程。
细节二:AI 正在给漏洞挖掘按下加速键。该漏洞由 Wiz、Calif 和 OpenAI 的研究人员共同发现并上报。研究者透露,借助 AI,一个人在大约一周内就能完成过去一个团队要几个月才能做到的事。Calif 还把该漏洞的根源追溯到了 2004 年的 PHP 研究,相关代码在 PHP 中潜伏了十多年。也就是说,老漏洞被重新翻出的速度只会不断加快,留给管理员打补丁的窗口只会越来越窄。
细节三:一批网站选择先掐断网络。美国 HR 软件 BambooHR 在美国、加拿大、爱尔兰暂停了服务,连工资发放都受到影响;荷兰的政务门户、数字身份系统 DigiD、议会下院官网以及多套教育平台也临时关闭;日本的 BASE、Codmon 等服务紧急停机,不少主机商则连夜完成升级。这些均属于预防性措施,并不说明它们已经遭到入侵。
细节四:攻防博弈已经拉开。Cloudflare 透露,攻击者正在持续变换载荷以绕开其规则。截至发稿时,公开信息中尚未出现确认的成功入侵案例,但千万别因此掉以轻心。
细节五:网上的 PoC 切勿随意下载。漏洞泄露之后,大量号称可用的利用代码涌现,安全公司提醒:来源不明的利用代码,有时本身就捆绑了木马。
别光围观,今天必须做的事
官方的表态非常直白:升级是唯一彻底的修复手段,其他措施都只是争取时间。PHP 核心开发者 Gina Peter Banyard 在发版前回复网友时也表达了同样的立场:除了打补丁升级,不存在真正有效的缓解办法。
第一步,搞清楚自己跑的是什么。确认 Web 服务实际使用的 PHP 版本,不能只跑一下 php -v,因为命令行与 PHP-FPM 用的未必是同一个版本。宝塔之类的管理面板、主机商后台以及 WordPress 的“站点健康”页面都能查到。
把手上的所有项目整理成一份清单:客户网站、内部系统、接口服务、Docker 镜像,一个都不能落下。
第二步,具备条件的马上升级。升级到 8.5.12、8.4.27、8.3.36 或 8.2.35。
升级结束后,重启 Apache、PHP-FPM 以及全部常驻 PHP worker;不重启就等于白升级。
用发行版软件包的用户,要到 changelog 中核对这两个 CVE 编号,别只看版本号。
提醒一下:升级 WordPress、Laravel 并不会连带升级 PHP,运行时必须在服务器、主机商或容器镜像这一层进行更新。
升级后要复核内存配置:新版本加入了内存硬上限,一旦触及上限进程会被立即终止,shutdown 回调也不会执行,所以要根据业务的真实需要核对 memory_limit 和 post_max_size。
第三步,暂时升不了级的,先止血。以下手段只能压缩部分攻击路径,无法取代升级。
针对 109618:把 memory_limit 设为 -1,并以应用无法改写的方式配置,比如 FPM 池配置里的 php_admin_value;同时降低 post_max_size,并在 Nginx 或网关层限制请求体大小。内存兜底交给容器或 cgroup 处理。不要拿 RLIMIT_AS、RLIMIT_DATA 来替代,它们反而可能触发同一条漏洞路径。
针对 109619:配置 session.upload_progress.enabled = 0;如果是 PHP 8.5,还要追加 fatal_error_backtraces = 0。改完后记得重启所有 worker。
开启 WAF。Cloudflare 免费版也已经有规则了,但官方自己也承认这只是临时应急,而且只覆盖经过其的流量。
实在没有别的办法,就先把面向公网的服务隔离或下线,修复完成后再重新上线。
第四步,排查此前有没有被探测过。检查日志里是否出现异常的 multipart 请求,紧接着伴随内存超限报错或一连串 500。
响应中有没有体积异常离谱的 PHPSESSID Cookie。
PHP worker 有没有发生过原因不明的重启。
给开发商的长期建议:在维护合同中写明“运行时版本必须保持官方支持范围内”,并按年计费。这次的补丁账单,与其临时去找客户讨要,不如以后提前谈好。
写在最后
技术债好比信用卡,刷的时候很痛快,账单总会找上门。PHP2Shell 不是第一张账单,也绝不会是最后一张。
PHP 本身没那么糟糕,它一直在持续发版、持续修复,真正拖累全局的,是那些“上线即遗忘”的服务器。今晚正在连夜升级的人辛苦了;还在观望的人,请记住一句话:补丁不要钱,被黑可不是。
参考来源
PHP Issues Emergency Patches for Two Critical PHP2Shell RCE Flaws as Exploit Attempts Emerge,The Hacker News,2026 年 10 月 21 日
php2shell (CVE-2026-109618, CVE-2026-109619): Frequently asked questions,Tenable,2026 年 10 月 21 日
PHPに認証不要のコード実行につながる重大な脆弱性2件「php2shell」,セキュリティ対策Lab,2026 年 10 月 21 日
PHP 8.2.34・8.3.35・8.4.26・8.5.11で11件の脆弱性を修正,セキュリティ対策Lab,2026 年 9 月 28 日
Usage statistics of PHP for websites,W3Techs,2026 年 8 月 22 日数据
修复方案请以 PHP 官方安全公告为准。


Open2Hub 热榜