参考 https://mp.weixin.qq.com/s/atlJ1SFul6ArrHq733blJA
Table of Content
任意文件上传漏洞
原文对于文件上传漏洞已经描述的很清楚了,这里我就根据个人情况随笔记一点:
为什么要设置这三个参数?
前两个参数都很好理解。由于对 uid
没有做校验,甚至可以直接为空。 至于第三个参数,是用来接受服务端返回的文件信息,由于文件名是使用$file_name = 'file_'.$this->getRandomName(16);
随机生成的,如果不设置该条件,即使文件上传成功我们也没办法访问.
由于没有对文件后缀做限制,所以直接上传php也是可以的。
其次跟正下原文中的一个小错误:
这里找他的意思是 server下的start函数是入口点,就要用start的路由去访问(从他的payload中可以猜出来)。但实际上是在 Create
方法中调用了 start
, 所以该文件不能够路由去访问,直接以文件路由的形式去访问就行了.路由只能去访问对应的控制器。
总结 1
原文中的切入点为 move_upload_file
,在代码审计中称之为 slink
也就是所谓的危险函数,随后通过危险函数回溯找到入口点,从而找到整条利用链子,有时候我们也会称之为逆向审计。
当然,有逆向审计就有正向审计。正向审计就是从程序所有接受参数的地方( source
),依次往下分析调用,直到触发 slink
.
下面我们用 source
的方法来进行分析该漏洞:
在PHP中所有参数都是通过 $_GET
$_POST
$_REQUEST
等方法传入的,因此我们可以先全局搜索其中的关键字,去寻找其中可能存在危险调用的地方。
前面两个 $_GET
不知道大家是否熟悉,这就是之前PHP多语言任意PHP文件包含漏洞,如果忘记了可以前往我的博客, 里面也有详细的分析过程:https://www.noel-zero.top/2022/12/23/2022-12-23-TP多语言文件包含/。这里我们直接跳到第三个开始分析:
这段代码可以看到程序会根据 $command
的类型执行对应分支的逻辑,我们先跟进第一个 upload
分支,可以看到里面存在一大堆传入系统的参数,跟进第一个可能存在问题的函数 getUserChunkPath
根据注释可以了解到该函数就是创建目录功能,与目录相关, uid
可控,很自然就会想到此处是否存在目录逃逸,造成任意文件夹覆盖。
继续回到主函数,往下分析就到$info = $this->upload_file($_GET['uid']);
了,这里就不再重复了。
source分析的大概的思路和流程就是这样
接下来我们在尝试通过source去查找其他的漏洞
再尝试:失败的文件下载
同样搜索 $_GET
,留意到case的另外一个分支,似乎是一个文件下载的功能点。
跟进了该分支下的函数,发现没有设置任何过滤,只需要通过 decodeTk()
函数拿到文件名就行。
跟进 decodeTk()
函数,浏览一下,就是对传入的字符串进行自定义的解码从而获得文件名:
系统所设计的功能点一定是存在相应入口点的,我们只需要去找到在哪个地方调用了下载文件这个功能,就知道怎么去构造加密字符串了。
由于该字符串是通过 $_GET['tk']
传入的,这里我直接全局搜索 'tk'
,
更进第一个函数,发现是通过 urlsafe_b64encode()
这个函数来加密了的,于是我们直接复制将相应的功能函数复制出来就行了。
function urlsafe_b64encode($string) {
$data = base64_encode($string);
$data = str_replace(['+','/','='],['-','_',''],$data);
return $data;
}
function encodeTk()
{
$params = [
'file' => "/index.php", // 下载那个文件
'origin' => "/index.php", # 下载的文件名
'speed' => "",
'time' => time()
];
return urlsafe_b64encode(implode(',',$params));
}
构造 tk
和 sign
,得到poc:
/public/server/index.php?md=download&tk=L2luZGV4LnBocCwvaW5kZXgucGhwLCwxNzA3MjAwOTky&sign=17c65088a435fce676d915cf2877f8b0
成功下载 index.php
.
但是如果是使用 ../../../../etc/passwd
尝试目录穿越会发现无法读取。
随后去搜了下 header('X-Accel-Redirect: '. $tk_info['file']);
,这里算是对目录穿越做了限制,所以就没办任意文件读取了.
总结2
这篇文章主要从介绍了代码审计的两种思路,一种是正向审计,一种是逆向审计。从本文提到的一些例子可以看到,针对原文提到的文件上传漏洞,使用逆向分析显然效率更快。但是在大多数情况下两种方法是没有绝对优势的说法的,两种方法我们都得熟练和掌握,只有根据情况选择相应的方法才是最高的效率。
希望这边文章能对刚入门代码升级的师傅们有所帮助