• [网鼎杯 2020 青龙组]AreUSerialz


    [网鼎杯 2020 青龙组]AreUSerialz

    1.将源代码放到本地php环境中进行调试

    process();
        }
    
        public function process() {
            if($this->op == "1") {
                $this->write();
            } else if($this->op == "2") {
                $res = $this->read();
                $this->output($res);
            } else {
                $this->output("Bad Hacker!");
            }
        }
    
        private function write() {
            if(isset($this->filename) && isset($this->content)) {
                if(strlen((string)$this->content) > 100) {
                    $this->output("Too long!");
                    die();
                }
                $res = file_put_contents($this->filename, $this->content);
                if($res) $this->output("Successful!");
                else $this->output("Failed!");
            } else {
                $this->output("Failed!");
            }
        }
    
        private function read() {
            $res = "";
            if(isset($this->filename)) {
                $res = file_get_contents($this->filename);
            }
            return $res;
        }
    
        private function output($s) {
            echo "[Result]: 
    "; echo $s; } function __destruct() { if($this->op === "2") $this->op = "1"; $this->content = ""; $this->process(); } } function is_valid($s) { for($i = 0; $i < strlen($s); $i++) if(!(ord($s[$i]) >= 32 && ord($s[$i]) <= 125)) return false; return true; } if(isset($_GET{'str'})) { $str = (string)$_GET['str']; if(is_valid($str)) { $obj = unserialize($str); } }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82

    2.解题思路

    1.通过GET方式进行传参,传给变量str;
    2.通过is_valid()函数判断进来的数据大于等于32并且小于等于125;
    3.通过反序列化将str的字符串转换成对象。 我们想成功读取文件flag.php的话,需要判断以下条件 (1)我们在写保护的函数中,需要满足的条件是变量content不能大于100; (2)要想触发写保护的话,需要满足的条件是public
    function process() 中的op == “1”; (3)要想到写保护的话,需要触发__construct函数
    (4)__construfct函数,构造函数,当创建对象时自动调用

    4.根据上述代码分析,当$op值强比较=\==不等于str(2),弱比较==等于2
    (\$this->op === "2")//不等于字符串类型的 2
    (\$this->op == "2") //弱等于2 即可为int(2)

    3.所以触发__destruct()方法也没关系,正常构造即可

    op == "1") {
                $this->write();
            } else if($this->op == "2") {
                $res = $this->read();
                $this->output($res);
            } else {
                $this->output("Bad Hacker!");
            }
        }
    
        private function write() {
            if(isset($this->filename) && isset($this->content)) {
                if(strlen((string)$this->content) > 100) {
                    $this->output("Too long!");
                    die();
                }
                $res = file_put_contents($this->filename, $this->content);
                if($res) $this->output("Successful!");
                else $this->output("Failed!");
            } else {
                $this->output("Failed!");
            }
        }
    
    
        private function output($s) {
            echo "[Result]: 
    "; echo $s; } function __destruct() { if($this->op === "2") $this->op = "1"; $this->content = ""; $this->process(); } } function is_valid($s) { for($i = 0; $i < strlen($s); $i++) if(!(ord($s[$i]) >= 32 && ord($s[$i]) <= 125)) return false; return true; } if(isset($_GET{'str'})) { $str = (string)$_GET['str']; if(is_valid($str)) { $obj = unserialize($str); } } $test = new FileHandler; var_dump(urlencode(serialize($test)));
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71

    4.通过URL解码,我们发现了在属性opfilename前面有乱码
    在这里插入图片描述
    5.使用十六进制进行和查看,可以看到%00%2A%00,因为opfilenameprotected的属性,
    在序列化的过程中会被转换成%00*%00,然而浏览器会将%00当成空值,因此无法获得flag

    在这里插入图片描述
    6.我还以为抓包就能绕过这题,但是思路错了,使用bp或者yakit进行传参后面发现这种方法不得行
    在这里插入图片描述
    在这里插入图片描述
    7.只能利用php7的版本对属性的不敏感绕过,需要纠正前面payload的错,op的应该是整型,及int()的类型,正确的payload如下所示

    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23

    在这里插入图片描述

    在这里插入图片描述

    8.查看源代码,即可获得flag
    在这里插入图片描述

    在这里插入图片描述

  • 相关阅读:
    Netty源码学习2——NioEventLoop的执行
    GFS分布式文件系统
    MYSQL介绍——数据库查询
    redis持久化机制
    Protobuf: 高效数据传输的秘密武器
    B-2:Linux系统渗透提权
    Windows 11 电脑黑屏 + Office软件打不开?
    因为一行Log日志导致的线上P1事故
    sam和mobilesam导出预处理的onnx
    Sketch macOS 支持m1 m2 Sketch 2023最新中文版
  • 原文地址:https://blog.csdn.net/m_de_g/article/details/137854492