Akiba's blog Akiba's blog
首页
  • web

    • PHP
    • Python
    • JavaScript
  • misc

    • 隐写
  • 比赛
  • 网站
  • 资源
  • 分类
  • 标签
  • 归档
关于

Kagami

萌新 Web 手,菜鸡一个
首页
  • web

    • PHP
    • Python
    • JavaScript
  • misc

    • 隐写
  • 比赛
  • 网站
  • 资源
  • 分类
  • 标签
  • 归档
关于
  • Web

    • 各种弹shell
    • XML外部实体注入从入门到入土
    • PHP

      • php中异常原生类的应用
      • php代码投毒事件RCE
      • php反序列化字符逃逸
        • 前言
        • 逃逸
          • 一句话能搞明白么
          • 细说
        • 后记
      • php常见伪协议总结
    • JavaScript

    • Python

    • sql注入

  • Misc

  • JavaScript文章

  • Vue文章

  • 代码审计

  • 知识库
  • Web
  • PHP
Kagami
2021-07-22

php反序列化字符逃逸

# 前言

这玩意真挺离谱的.jpg

知识点来源:GYCTF2020 Easyphp

弄完pop链被反序列化卡住,查了一圈才知道居然还有这种骚操作。

# 逃逸

先抽象出这段简单的程序

<?php
function safe($str)
{
    return str_replace('bb', 'ccc', $str);
}
class A
{
    public $name = 'aaaa';
    public $pass = '123456';
}
$AA = new A();
$res = safe(serialize($AA));
echo $res."\r\n";
$c = unserialize($res);
echo $c->pass;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

image-20210722211114410

# 一句话能搞明白么

简单来说,就是通过在内容中,使用特殊字符闭合这段变量(结束符号 ";} ),让你后面的东西插进去成为这串反序列化字符串内的玩意,而且还可以把后面的挤掉。

# 细说

但是,和上图写的一样,php会按照这个长度进行解析,在长度内的就按照普通字符串解析了。

那既然有了长度规定,只要让你的payload在长度范围之外就好了!

但是一般来说,长度是根据内容计算出来的,怎么会有长度和内容不统一的问题?

这就要归功于上面那段代码的 safe 函数,某些特殊字符会被替换掉。一个bb->ccc,这就多出来1位!

那么我们只要构造相应个的bb,就可以注入相应长度的内容啦

比如说我们要注入这段 ";s:4:"pass";s:6:"hacker";} ,将 pass 的值改成了 hacker ,这段payload长度为27,我们只需要在前面加上27*bb就可以达到这个效果了

具体过程是:

aaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb";s:4:"pass";s:6:"hacker";} ,长度为4+27*2+27,

aaaa长度4,27个bb长度2*27,payload长度27。这段作为 $name 变量,交给php进行序列化。

php在序列化时候,会 strlen(name) ,得到4+27*2+27=85。于是就有了下面这个

O:1:"A":2:{s:4:"name";s:85:"aaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb";s:4:"pass";s:6:"hacker";}";s:4:"pass";s:6:"123456";}
1

在经历 filter() 函数时,这串字符串的bb会被替换成ccc、

O:1:"A":2:{s:4:"name";s:85:"aaaaccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc";s:4:"pass";s:6:"hacker";}";s:4:"pass";s:6:"123456";}
1

显然,这85可就出问题了。我们精心构造的长度起了作用,现在85正好是aaaaccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc,闭合成功。

image-20210722214649043

这破图做了我半天麻烦死了

# 后记

php 真可怕啊

远离 php 从我做起

参考:PHP反序列化字符逃逸详解 (opens new window)

上次更新: 2021/07/22, 22:50:48
php代码投毒事件RCE
php常见伪协议总结

← php代码投毒事件RCE php常见伪协议总结→

Theme by Vdoing | Copyright © 2020-2021 秋葉
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式