Skip to content
KitploitKITPLOIT
工具漏洞利用博客
Log in
提交
工具漏洞利用博客
提交

黑客、渗透测试和网络安全工具,武装您的安全武器库!

Kitploit 是一个黑客、网络安全和渗透测试工具的目录。发现最新的项目更新,查找漏洞、分析系统、自动化测试并加强你的安全。

··订阅源·联系·隐私·© 2026 Kitploit

工具目录

分类

查看所有分类
Loading categories
工具/GitHubGitHub/quantumworld-dpdns-io/cve-2026-42945
漏洞分析漏洞利用Web安全模糊测试渗透测试学习与教育事件响应二进制利用实验室与实践
GitHubquantumworld-dpdns-io/cve-2026-42945

CVE-2026-42945

完整的 CVE-2026-42945 研究仓库,包含堆缓冲区溢出分析、RCE 漏洞利用(堆喷射 + Feng Shui)、检测脚本以及针对 NGINX rewrite 模块漏洞的修补指南。

查看仓库
134个月前尚未审核

最受欢迎

查看全部 →

发现我们社区最常用的工具。

探索所有工具

浏览我们的工具集合

查看所有工具 →
分享
Screenshot 2026-05-28 at 4 09 53 PM

CVE-2026-42945 — NGINX Rift

NGINX ngx_http_rewrite_module 中的堆缓冲区溢出

指标值
CVSS v4.09.2(严重)
CVSS v3.18.1(高危) — AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
CWE122 — 基于堆的缓冲区溢出
引入时间2008年6月 — v0.6.27
发现时间2026年4月 — DepthFirst Research
修复时间2026年5月13日 — v1.30.1, v1.31.0
CVE 发布时间2026年5月21日
存在周期约18年(未被发现)
修复提交524977e7c534e87e5b55739fa74601c9f1102686

目录

  1. 漏洞概述
  2. 根本原因分析
  3. 利用机制
  4. 修复分析
  5. 受影响版本
  6. 检测
  7. 缓解措施
  8. 项目结构
  9. 快速开始
  10. 构建并运行易受攻击版本
  11. 触发溢出
  12. RCE 漏洞利用
  13. 反弹 Shell 验证
  14. 打补丁
  15. 测试
  16. 模糊测试
  17. CI 流水线
  18. 文档索引
  19. 项目统计
  20. 参考资料

1. 漏洞概述

未经认证的远程攻击者可以通过向具有特定 rewrite + set/if/rewrite 配置模式的服务器发送特制 HTTP 请求,在 NGINX worker 进程中触发确定性的堆缓冲区溢出。该溢出会破坏堆元数据(ngx_pool_cleanup_t 指针),从而通过堆喷(Heap Spray)和堆风水(Feng Shui)技术实现远程代码执行(RCE)。

触发模式```nginx

server { listen 19321;

location ~ ^/api/(.*)$ {
    rewrite ^/api/(.*)$ /internal?migrated=true;
    set $original_endpoint $1;
}

}

**关键要求:**
- 一个 `rewrite` 指令,其替换内容中含有 `?`(查询字符串分隔符)
- 后续的 `set`、`if` 或 `rewrite` 指令引用了**未命名的 PCRE 捕获组**(`$1`、`$2` 等)
- 重写替换内容中的 `?` 会触发 `ngx_http_script_start_args_code`,从而设置 `e->is_args = 1`

### 攻击者可以实现什么

| 能力 | 描述 |
|-----------|-------------|
| **拒绝服务** | 确定性地使工作进程崩溃,导致进程循环重启(无论是否启用 ASLR 都有效) |
| **远程代码执行** | 在 ASLR 被禁用(或通过部分覆盖绕过)的情况下,以 nginx 用户身份实现完整的 RCE |
| **数据泄露** | 通过内存读取原语,从工作进程堆中提取敏感数据 |
| **持久化** | 通过在工作进程内存中执行代码植入后门 |

---

## 2. 根本原因分析

### 两遍脚本引擎

NGINX 的 `ngx_http_rewrite_module` 在 `src/http/ngx_http_script.c` 中使用**两遍脚本引擎**:

1. **长度遍历** (`ngx_http_script_run`):遍历所有脚本代码以计算所需的总缓冲区大小。将长度写入 `le.ip` 和 `le.pos`。
2. **复制遍历** (`ngx_http_script_copy_len`/`_code`):再次遍历,将实际字节写入 `e->ip` 和 `e->pos` 处的预分配缓冲区。

每个脚本代码都有两个处理函数:每个遍历对应一个。例如:
- `ngx_http_script_copy_len` → `ngx_http_script_copy_code`
- `ngx_http_script_start_args_len` → `ngx_http_script_start_args_code`

### `is_args` 标志

**引擎结构** (`ngx_http_script_engine_t`) 上的标志 `e->is_args` 控制复制遍历如何处理某些字符:```c
typedef struct {
    u_char                  *ip;
    u_char                  *pos;
    ngx_http_variable_value_t *sp;
    ngx_str_t               buf;
    int                     flushed;
    unsigned                is_args:1;    // <-- THE BUG
    unsigned                ncaptures:1;
    ngx_uint_t              captures_size;
    // ...
} ngx_http_script_engine_t;

当 e->is_args = 1 时,$N 捕获引用的复制代码调用 ngx_escape_uri() 并传入 NGX_ESCAPE_ARGS,该函数会展开:

  • + → %2B(1 字节 → 3 字节,+200%)
  • % → %25(1 字节 → 3 字节,+200%)
  • & → %26(1 字节 → 3 字节,+200%)

漏洞:标志跨遍次泄漏

漏洞模式的执行流程:``` rewrite ^/api/(.*)$ /internal?migrated=true;

1. 在**重写评估**期间,引擎在替换字符串中遇到 `?`,这会触发 `ngx_http_script_start_args_code`,设置 `e->is_args = 1`。
2. 重写会修改请求 URI,然后继续执行下一条指令。
3. **`e->is_args` 永远不会被清除**。

然后:```
set $original_endpoint $1;
  1. 为长度遍历创建一个全新的子引擎 (le): ```c ngx_memzero(&le, sizeof(ngx_http_script_engine_t));

这会正确地将 le.is_args 归零为 0,因此长度传递返回的是原始、未转义的捕获长度。

  1. 复制传递复用了主引擎 e,而 e 在步骤 1 中仍具有 e->is_args = 1。复制传递应用 URI 转义,将每个可转义字符从 1 字节扩展为 3 字节,而缓冲区的大小却按原始长度分配——堆溢出。

可视化演练```

Pass 1 (Length — sub-engine le): le.is_args = 0 capture $1 = "A+++++B" → length = 7

Buffer allocated: 7 bytes

Pass 2 (Copy — main engine e): e.is_args = 1 ← LEAKED from rewrite capture $1 = "A+++++B" ngx_escape_uri("A+++++B", NGX_ESCAPE_ARGS): A → A (1 byte) + → %2B (3 bytes) ← EXPANSION + → %2B (3 bytes) + → %2B (3 bytes) + → %2B (3 bytes) + → %2B (3 bytes) B → B (1 byte) total written: 17 bytes buffer size: 7 bytes OVERFLOW: 10 bytes

扩展比例为 `7 + (n_escapable * 2)`,其中 `n_escapable` 是捕获中 `+`、`%` 和 `&` 的数量。

---

## 3. 利用机制

### 概述

| 步骤 | 技术 | 描述 |
|------|-----------|-------------|
| 1 | 溢出 | 发送带有 `+` 填充的精心构造的 URI,以溢出堆缓冲区 |
| 2 | 堆喷射 | 向 `/spray` POST 大体积请求体,用受控数据填充堆 |
| 3 | 堆风水 | 精心安排分配,使溢出目标(`ngx_pool_cleanup_t`)位于相邻位置 |
| 4 | 破坏处理器 | 溢出用 `system()` 地址覆盖 `ngx_pool_cleanup_t.handler` |
| 5 | 触发清理 | 等待池销毁 → `system(cmd)` 执行攻击者命令 |
| 6 | 反向 Shell | 串联反向 Shell 载荷以获得交互式访问 |

### 跨请求堆风水

**单请求堆风水会失败**,因为溢出在到达 `cleanup` 指针之前就破坏了池的元数据(`->d.next`、`->d.failed`)。当请求结束时池被销毁,损坏的元数据会导致**在调用 `system()` 之前崩溃**。

相反,该漏洞利用采用**跨请求堆风水**:

1. **请求 1(喷射)**:向 `/spray` POST 大体积请求体。后端(`server.py`)使用 `X-Delay` 响应头挂起响应,保持连接打开,从而保留堆分配。喷射用伪造的 `ngx_pool_cleanup_t` 块填充堆。
2. **请求 2(溢出)**:发送溢出 URI。溢出仅损坏 `cleanup` 指针(而非池元数据),使其指向喷射的伪造块。
3. **池销毁**:当喷射响应完成(延迟到期)时,池的清理链会遍历到伪造块并调用 `system(cmd)`。

### 地址要求

| 符号 | 数值(Docker,ASLR 关闭) | 描述 |
|--------|--------------------------|-------------|
| `HEAP_BASE` | `0x555555659000` | nginx 堆的基址 |
| `system@libc` | `0x7ffff6f6e420` | glibc 中的 `system()` |
| `NGX_CYCLES_POOL` | `0x5555556a4040` | 指向 cycles 池的指针 |
| 伪造清理地址 | `0x5555556a4030` | 喷射目标地址 |

### ASLR 绕过

即使不禁用 ASLR,**DoS**(崩溃)仍能确定性触发。对于启用 ASLR 的 RCE,有两种方法:

1. **部分覆盖**:使用 1 字节或 2 字节覆盖,在同一页内移动指针,并暴力破解剩余的半字节(16–256 次尝试)。
2. **信息泄露**:读取 `/proc/self/maps`,或使用 `log_parser.py` 内存分析来确定内存布局。

---

## 4. 修复分析

### 官方修复

**提交**:`524977e7c534e87e5b55739fa74601c9f1102686`  
**文件**:`src/http/ngx_http_script.c`  
**行**:~1205(位于 `ngx_http_script_regex_end_code` 中)```diff
 void
 ngx_http_script_regex_end_code(ngx_http_script_engine_t *e)
 {
     ngx_http_script_regex_code_t *code;

     code = (ngx_http_script_regex_code_t *) e->ip;

+    e->is_args = 0;    /* ← THE FIX */

     e->ip += sizeof(ngx_http_script_regex_code_t);
     // ...
 }

Why This Location Is Correct

ngx_http_script_regex_end_code 在长度传递和复制传递期间每次正则表达式求值之后运行。在此处重置 e->is_args = 0 可确保:

  • 标志在正则表达式代码执行完毕后立即被清除
  • 后续的脚本代码(set、if、rewrite)以干净的 is_args = 0 开始
  • ngx_http_script_start_args_code 在替换字符串中遇到 ? 时仍然可以设置 is_args = 1 —— 该修复不会破坏这一功能

Defense-in-Depth Patch

patches/0002-hardening-bounds-check.patch 在 ngx_http_script_copy_capture_code 中添加了边界检查:```c if (e->pos + len > e->buf.data + e->buf.len) { return; /* gracefully truncate instead of overflowing */ }

### 向后移植补丁

| 补丁 | Nginx 版本 |
|-------|---------------|
| `patches/0001-fix-is_args.patch` | 1.22.x, 1.24.x, 1.26.x, 1.30.0 |
| `patches/backport-1.22.x.patch` | 1.22.0–1.22.1 |
| `patches/backport-1.24.x.patch` | 1.24.0–1.24.1 |
| `patches/backport-1.26.x.patch` | 1.26.0–1.26.1 |

---

## 5. 受影响版本

### NGINX 开源版

| 范围 | 状态 |
|-------|--------|
| **0.1.0 – 0.6.26** | 不受影响(重写模块早于未命名捕获) |
| **0.6.27 – 1.30.0** | **易受影响**(18 年窗口期) |
| **1.30.1** | 首个修复版本 |
| **1.31.0+** | 已修复(主线版) |

### NGINX Plus

| 版本 | 受影响 | 已修复 |
|---------|----------|-------|
| R32 | R32–R32 P5 | R32 P6 |
| R33 | R33–R33 P5 | R33 P6 |
| R34 | R34–R34 P4 | R34 P5 |
| R35 | R35–R35 P1 | R35 P2 |
| R36 | R36–R36 P3 | R36 P4 |

### NGINX 生态

| 产品 | 受影响版本 | 状态 |
|---------|----------|--------|
| NGINX Instance Manager | 2.16.0–2.21.1 | 安全公告待发布 |
| F5 NGINX WAF | 5.9.0–5.12.1 | 安全公告待发布 |
| NGINX Ingress Controller | 3.5.0–3.7.2, 4.0.0–4.0.1, 5.0.0–5.4.1 | 安全公告待发布 |
| NGINX Gateway Fabric | 1.3.0–1.6.2, 2.0.0–2.5.1 | 安全公告待发布 |
| NGINX Service Mesh | 1.6.0–1.6.2, 2.0.0–2.1.0 | 安全公告待发布 |
| NGINX Agent | 2.0.0–2.35.0 | 安全公告待发布 |

---

## 6. 检测
下载工具