漏洞概述
2026 年 7 月 15 日,NGINX 发布 1.30.4 稳定版和 1.31.3 主线版,修复编号为 CVE-2026-42533 的堆缓冲区溢出漏洞。
该问题影响 NGINX Open Source 0.9.6 至 1.31.2。NGINX 官方将其评为 Major,F5 给出的 CVSS v4.0 评分为 9.2。攻击者无需登录,但服务器必须存在特定的正则map、捕获变量和求值顺序,才可能进入危险路径。
这不是“所有旧版 NGINX 都能被直接接管”,但也绝不只是一个普通的配置错误。风险核心在于:长度计算阶段和实际写入阶段可能读取到不同的变量内容。
漏洞信息
| 项目 | 内容 |
|---|---|
| 漏洞编号 | CVE-2026-42533 |
| 漏洞类型 | 堆缓冲区溢出 |
| 官方评级 | Major |
| CVSS v4.0 | 9.2 |
| 影响版本 | NGINX 0.9.6 至 1.31.2 |
| 修复版本 | 1.30.4+、1.31.3+ |
| 攻击条件 | 无需认证,但依赖特定配置 |
| 可能后果 | Worker 崩溃、拒绝服务、内存泄露、潜在代码执行 |
NGINX 官方将漏洞描述为使用map和正则表达式时发生缓冲区溢出;F5 表示该问题可能造成拒绝服务,并可能进一步触发代码执行。
一次 map 正则,为什么会影响内存安全
NGINX 在生成包含变量的字符串时,通常分成长度计算和实际写入两个阶段。
正常情况下,两次读取的变量应该完全相同。问题在于,正则捕获结果并不是永久绑定在某一条location或rewrite上,而是保存在请求的共享捕获状态中。
例如,正则location先产生$1:
后续如果求值一个使用正则表达式的map,新的正则匹配可能覆盖此前保存的捕获结果:
于是可能出现长度按捕获 A 计算、内存按 A 申请,但真正写入时已经读取捕获 B 的情况。如果 B 比 A 长,写入可能越过缓冲区边界;如果 B 比 A 短,未被覆盖的尾部内存可能被错误返回,形成信息泄露。
这个问题其实早有迹象
2014 年,NGINX Trac 工单 #564 就记录过类似现象:正则map被求值后,原本由rewrite产生的$1被覆盖,导致跳转地址出现错误。
当时它表现为配置结果错误。现在暴露出的危险在于:当捕获状态变化发生在“长度计算”和“实际写入”之间,逻辑错误就会升级为内存安全漏洞。
单独看,map 改变 $1 似乎只是配置行为;进入两阶段缓冲区处理后,它才真正变成堆溢出。
哪些配置需要重点排查
风险通常不是由某一个关键词单独产生,而是多个条件组合。
存在正则捕获来源
这些规则可能产生$1、$2或命名捕获变量。
存在正则 map
普通字符串匹配的map不等于正则map,重点是以~或~*开头的匹配规则。
捕获变量和 map 输出共同参与请求构造
关键不在于两者是否写在同一行,而在于它们是否最终进入同一个两阶段缓冲区,以及捕获变量是否先于 map 输出变量求值。
官方补丁为什么不只修改 map
官方 PR #1561 没有简单地保存和恢复$1,而是直接加强整个脚本执行过程。
- 增加缓冲区结束边界:脚本引擎新增
e->end,记录已分配缓冲区的真实结束位置。 - 每次写入前检查空间:固定文本、普通变量和捕获变量复制前,都必须确认缓冲区仍有足够空间。
- 按实际写入长度返回结果:实际内容较短时,结果字符串按真实写入量截断,不再把未初始化的尾部内存一起返回。
相关保护还被加入 proxy、FastCGI、SCGI、uWSGI、gRPC、index 和 try_files 等直接脚本求值路径。这是针对两阶段脚本执行模型的整体加固。
是否真的能够远程代码执行
F5 的官方结论是,攻击者可以远程、无需认证地触发漏洞;利用需要服务器满足特定配置条件;漏洞可能导致 NGINX Worker 崩溃和拒绝服务;在 ASLR 被关闭或能够被绕过时,可能进一步执行代码。
漏洞报告者 Stan Shaw 则表示,已经构造出信息泄露和堆溢出两种攻击原语,并在特定 Linux 环境中将其组合为预认证远程代码执行链。
更准确的结论不是“所有旧版 NGINX 都能直接 RCE”,而是:该漏洞已经具备远程代码执行所需的内存破坏能力,但实际利用仍取决于 NGINX 配置、运行环境及内存防护条件。
如何快速排查
查看版本和编译信息
导出完整配置
查找正则 map
检查对应map中是否存在~或~*正则规则。
查找捕获变量和常见来源
这些命令只能找出候选配置,不能判断变量是否进入同一个缓冲区,也不能还原真实的求值顺序。简单搜索到$1和map,不能直接判定服务器已经可利用。
修复方法与验证
NGINX Open Source 应升级至稳定版 1.30.4 或更高、主线版 1.31.3 或更高。配置排查只能帮助确定处置优先级,不能代替升级。
升级前备份
升级后验证
容器环境必须进入实际运行的容器确认版本。更新宿主机不会自动替换容器中的旧 NGINX。
与 CVE-2026-42945 有什么区别
| 对比项 | CVE-2026-42945 | CVE-2026-42533 |
|---|---|---|
| 披露时间 | 2026 年 5 月 | 2026 年 7 月 |
| 官方评级 | Medium | Major |
| 主要位置 | rewrite 模块 | 正则 map 与脚本求值路径 |
| 影响版本 | 0.6.27 至 1.30.0 | 0.9.6 至 1.31.2 |
| 修复版本 | 1.30.1、1.31.0 | 1.30.4、1.31.3 |
| 核心问题 | rewrite 长度处理异常 | 两阶段之间变量或捕获状态变化 |
此前升级到 1.30.1、1.30.2、1.30.3、1.31.0、1.31.1 或 1.31.2,仍不能修复 CVE-2026-42533。
结论
CVE-2026-42533 影响范围很广,但风险判断不能只看版本号。真正需要确认的是是否存在正则map、是否使用编号或命名捕获、捕获变量和 map 输出是否进入同一缓冲区、变量求值顺序是否满足危险关系,以及当前运行的二进制是否已经包含修复。
预先计算出来的缓冲区长度,并不一定等于真正写入时需要的长度。
NGINX 官方最终没有继续相信这个假设,而是在写入阶段增加了真正的边界保护。对于仍运行受影响版本的服务器,应优先升级并完成配置与运行状态验证。