pikachu-PHP反序列化
程序员文章站
2022-05-11 18:08:31
...
PHP对象需要表达的内容较多,如类属性值的类型、值等,所以会存在一个基本格式。下面则是PHP序列化后的基本类型表达:
- 布尔型(bool):b:value=>b:0 整数型(int):i:value=>i:1
- 整数型(int):i:value=>i:1
- 字符串型(str):s:length:“value”;=>s:4:“aaaa”
- 数组型(array):a:
<length>
:{key,value pairs};=>a:1:{i:1;s:1:“a”} - 对象型(object):O:<class_name_length>
- NULL型:N
(出自《从0到1CTFer成长之路》)
class S{
public $test="pikachu";
}
$s=new S(); //创建一个对象
serialize($s); //把这个对象进行序列化
序列化后得到的结果是这个样子的:O:1:"S":1:{s:4:"test";s:7:"pikachu";}
O:代表object
1:代表对象名字长度为一个字符
S:对象的名称
1:代表对象里面有一个变量
s:数据类型
4:变量名称的长度
test:变量名称
s:数据类型
7:变量值的长度
pikachu:变量值
下面是本地实验
<?php
//定义类
class test
{
//在对象被销毁时候自动调用destruct函数
function __destruct()
{
echo "<br>__destruct()<br>";
//在此函数中添加eval()以达到命令执行的目的
eval($_GET['cmd']);
}
}
//echo serialize($test);方便将序列化后的test写进u参数中传参
$test = new test;
echo serialize($test);
//执行完这个echo后会被垃圾回收器回收,也就是销毁
unserialize($_GET['u']);
//反序列化执行完后又会被回收
// 所以会出现两次destruct
?>
1)
2)传参并命令执行
明白了反序列化原理再来看pikachu
直接看源码
class S{
var $test = "pikachu";
function __construct(){
echo $this->test;
}//construct函数是当对象被创建时会自动调用的
}
这是他源码里的类定义
我们复制下来把他序列化后填进api里提交一下
O:1:"S":1:{s:4:"test";s:7:"pikachu";}
第一个属性是字符串,字符串长度为4,属性名为test,他的值是字符串型,长度7,名为pikachu
输出pikachu
当我们改下序列化的对象O:1:"S":1:{s:4:"test";s:29:"<script>alert('xss')</script>";}
这样的话当他创建对象时就会弹窗