php搭建文件上传靶场漏洞

PASS 01 前端js绕过 (本pass在客户端使用js对不合法图片进行检查!)

方法一:第一关上传区要求上传一张图片,但是我们需要上传一句话木马到后台,更改一句话木马后缀名为jpg然后利用bp抓包将文件名称改回php

通关页面打开一句话木马的路径发现上传成功,接下来试试蚁剑能不能连接登录,发现不能登陆,尝试把文件名的空格去掉试试,也不行,什么原因呢?原来是一句话木马里的POST必须大写,改成大写之后重试一次,成功连接。
方法二:通过直接上传php发现抓不掉包,但是上传一个jpg却可以抓到包,这说明验证文件的一个类型是在页面前端进行验证,这里右键检查元素找到JS绑定的form表单 ,删除onsubmit后面的代码,上传php文件然后通过蚁剑连接就能连接成功

PASS 02 Content-type绕过 (MIME验证)

如法炮制,上传一个jpg文件接着抓数据包,尝试把它的Content-Type删掉,结果发现文件上传不成功了,说明这个语句起一个jpg身份的作用,那么尝试将这个Content-Type: image/jpeg,改到php文件里然后能不能上传成功呢,上传成功!那么接下来通过蚁剑打开连接即可

知识点:MIME(Multipurpose Internet Mail Extensions)多用途互联网邮件扩展类型。是设定某种扩展名的文件用一种应用程序来打开的方式类型,当该扩展名文件被访问的时候,浏览器会自动使用指定应用程序来打开。多用于指定一些客户端自定义的文件名,以及一些媒体文件打开方式。
媒体类型通常是通过 HTTP 协议,由 Web 服务器告知浏览器的,更准确地说,是通过 Content-Type 来表示的,例如:Content-Type: text/HTML

PASS 03 特殊后缀绕过(php3、phtml绕过黑名单)

首先配置靶场的环境,PHP打开配置文件http-conf添加识别文件php3 php5等,尝试上传一个php文件,发现不许上传很多类型的文件,http-conf是全局配置文件,快速检索ctrl+f搜索Addtype且去除注释重启php服务

通过看源代码,这应该是加入黑名单了,黑名单可以用php2 php3 php5 php7 phtml 等绕过

PHP5文件实际上就是.PHP文件,只不过代码由PHP5引擎解析。

PHP5是一种PHP版本间的区分,该后缀名并不常见,另外还有.PHP2.PHP3.PHP4文件。而当前最新的PHP版本为PHP7。

$deny_ext = array('.asp','.aspx','.php','.jsp');

但是它覆盖范围不充分,我们可以利用后缀名为php3进行上传

成功上传!尝试用蚁剑进行连接,发现连接不上,打开php运行模式切换版本,选一个没有nts版本的再次连接,发现上传成功!Non Thread Safe是非线程安全,在执行时不进行线程(Thread)安全检查。 因此,如果是使用ISAPI的方式来运行PHP就必须用ThreadSafe (线程安全)的版本;而用FastCGI模式运行PHP的话就没有必要用线程安全检查了,用None Thread Safe (NTS,非线程安全)的版本能够更好的提高效率。

PASS 04 .htaccess绕过 点加空格点绕过

前置知识 .htaccess 分布式配置文件

.htaccess文件(或者"分布式配置文件"),全称是Hypertext Access(超文本入口)。htaccess文件是Apache服务器中的一个配置文件,它负责相关目录下的网页配置。通过htaccess文件,可以帮我们实现:网页301重定向、自定义404错误页面、改变文件扩展名、允许/阻止特定的用户或者目录的访问、禁止目录列表、配置默认文档等功能。

    Unix、Linux系统或者是任何版本的Apache Web服务器都是支持.htaccess的,但是有的主机服务商可能不允许你自定义自己的.htaccess文件。

    启用.htaccess,需要修改httpd.conf,启用AllowOverride,并可以用AllowOverride限制特定命令的使用。如果需要使用.htaccess以外的其他文件名,可以用AccessFileName指令来改变。例如,需要使用.config ,则可以在服务器配置文件中按以下方法配置:AccessFileName .config 。

    笼统地说,.htaccess可以帮我们实现包括:文件夹密码保护、用户自动重定向、自定义错误页面、改变你的文件扩展名、封禁特定IP地址的用户、只允许特定IP地址的用户、禁止目录列表,以及使用其他文件作为index文件等一些功能。

方法一:通过查看源代码发现黑名单禁用了很多文件后缀,通过观察发现他没有禁用htaccess文件,htaccess是一个文件配置文件,但是他的作用非常局部,只影响该目录及其子目录,每个文件都有自己的htaccess文件

AddHandler php5-script .jpg

AddType application/x-httpd-php .jpg

SetHandler application/x-httpd-php


.htaccess AddType appllication/x-httpd-php .jpg .txt

但是发现没有进行成功,反而报错说是解决办法就是检查一下htaccess的前置配置以及配置文件内容

.htaccess文件内容如下

 
  1. <FilesMatch "111.jpg">

  2. SetHandler application/x-httpd-php

  3. </FilesMatch>
    111.jpg是文件的命名


 注意:在php的nts版本下面无法解析4.jpg为php文件 该运行模式为CGI/FastCGI
 nts版本会报500 服务器内部错误

方法二:将该目录及其子目录的所有文件因均映射为php文件类型,除了这个方法之外,我们尝试观察源代码通过它的逻辑来修改文件后缀到达上传的目的,我们上传php文件并且抓包修改文件后缀名为. .进行上传,他的原理是windows系统会自动去除文件末尾的句号和空格,发现上传成功,接着用蚁剑进行连接,记得把文件最后面的.进行删除,发现连接成功

利用PHP 和 Windows环境的叠加特性,以下符号在正则匹配时的相等性:

    双引号"     =   点号.
    大于符号>   =   问号?
    小于符号<   =   星号*

先上传一个名为4.php:.jpg的文件,上传成功后会生成4.php的空文件,大小为0KB.

这一步 我成功了 原理就是在windows环境下 不允许文件命名中含有( \ / : * ? "   < > | )

如果有 会自动截断 并生成一个空文件

然后将文件名改为4.<或4.<<<或4.>>>或4.>><后再次上传,重写4.php文件内容,Webshell代码就会写入原来的4.php空文件中。再访问4.php

经过测试 在php非nts版本下 运行模式为 Apache 2.0 Handler  成功

PASS 05 user.ini绕过 点加空格点绕过 大小写绕过

因为文件夹里面已经存在一个php文件且 .htaccess文件被列入黑名单,就考虑用user.ini配置文件来更改配置,优势跟.htaccess后门比,适用范围更广,nginx/apache/IIS都有效,而.htaccess只适用于apache
使用条件:
(1)服务器脚本语言为PHP
(2)对应目录下面有可执行的php文件
(3)服务器使用CGI/FastCGI模式

注意:这里要修改php.ini配置文件

分号是注释 改成和我一样的即可 

然后访问readme.php 效果如下 也可以用一句话木马

如果在php.ini里面的配置文件中找不到需要修改的代码,将php版本调到高版本之后刷新在进去查找

img

user.ini

auto_prepend_file=a.jpg

.user.ini文件里的意思是:所有的php文件都自动包含a.jpg文件。.user.ini相当于一个用户自定义的php.ini

方法一:在上传目录下存在readme.php的php文件,可以利用 .user.ini 文件 使得运行 readme.php 时 包含上传的图片,相当于readme.php也有Onehorse.php。 在这里插入图片描述

上传user.ini Onehorse.jpg,成功上传打开readme.php然后复制路径通过蚁剑上传发现上传成功

观察发现可以通过点加空格加点绕过,也发现源代码中没有修改为小写这个处理,同时PHP也可以运行,采用改大小写方式绕过 如果发现有乱码或者是出现无法显示的问题,更换nts或者是非nts,低版本或者是高版本的php试试

方法二:

 5.php. .绕过(点空格点绕过)

代码运行最后得到的后缀为"." 不在黑名单中 然而又用原来的5.php. .来拼接路径 由于windows在

文件命名中会删除.和空格 所以最终得到的是5.php 因此绕过了黑名单限制

    $file_name = trim($_FILES['upload_file']['name']);
    $img_path = UPLOAD_PATH.'/'.$file_name

Pass-06(大小写绕过黑名单)

本关禁止上传.htaccess .user.ini

阅读代码 我这里只截取了关键部分的代码

            $file_name = trim($_FILES['upload_file']['name']);// 首尾去除空格
            $file_name = deldot($file_name);//删除文件名末尾的点
            $file_ext = strrchr($file_name, '.');//截取最后一个点到末尾的字符串(包含.)
            $file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA
            $file_ext = trim($file_ext); //首尾去空
     
            # 判断是否在黑名单数组中
            if (!in_array($file_ext, $deny_ext)) {
                $temp_file = $_FILES['upload_file']['tmp_name'];
                 # 拼接../upload/xxx.xxx 并对文件进行重命名 用的是截取的文件后缀名
                $img_path = UPLOAD_PATH.'/'.date("YmdHis").rand(1000,9999).$file_ext;
                if (move_uploaded_file($temp_file, $img_path)) {
                    $is_upload = true;
                }

没有禁止phP 、Php 所以将文件名字大小写就绕过了限制

注意:这里php版本选非nts版本的 才能成功,php nts版本会报 http 500 服务器内部错误

PASS 07 -空格

if (file_exists(UPLOAD_PATH)) {
        $deny_ext = array(".php",".php5"," 
        .......
        ,".ini");
        $file_name = $_FILES['upload_file']['name'];
        $file_name = deldot($file_name);//删除文件名末尾的点
        $file_ext = strrchr($file_name, '.');
        $file_ext = strtolower($file_ext); //转换为小写
        $file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA

利用PHP 和 Windows环境的叠加特性  windows系统自动删除文件名后缀的空格  绕过黑名单,通关观察源代码发现后端检测没有去掉首尾空格,于是上传 Onehorse.php抓包在后缀+空格通过蚁剑连接,连接成功!

PASS 08 点空格绕过

$file_name = trim($_FILES['upload_file']['name']);
        $file_ext = strrchr($file_name, '.');
        $file_ext = strtolower($file_ext); //转换为小写
        $file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA
        $file_ext = trim($file_ext); //首尾去空

对与源码分析,不存在去除文件名末尾的点,所以采用点加空格绕过

PASS 09 ::$DATE后缀绕过

 $deny_ext = array(".php",".php5",".php4",".php3",".php2",".html",".htm",".phtml",".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");
        $file_name = trim($_FILES['upload_file']['name']);
        $file_name = deldot($file_name);//删除文件名末尾的点
        $file_ext = strrchr($file_name, '.');
        $file_ext = strtolower($file_ext); //转换为小写
        $file_ext = trim($file_ext); //首尾去空

发现没有对字符串::$DATE处理,故加此后缀进行绕过

PASS 10 点空格点绕过 过滤不全

        $file_name = trim($_FILES['upload_file']['name']);
        $file_name = deldot($file_name);//删除文件名末尾的点
        $file_ext = strrchr($file_name, '.');
        $file_ext = strtolower($file_ext); //转换为小写
        $file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA
        $file_ext = trim($file_ext); //首尾去空

在php非nts版本下  运行模式为 Apache 2.0 Handler ;在php的nts版本中 运行模式为cgi/fastcgi

代码运行最后得到的后缀为"." 不在黑名单中 然而又用原来的10.php. .来保存文件 由于windows在

文件命名中会自动删除.和空格 所以最终得到的是10.php 因此绕过了黑名单限制

使用 deldot() 删除文件名末尾的点

deldot() 函数从末尾向前检测,检测到第一个点后,会继续向前检测,但遇到空格会停下来

可以构造文件名: Onehorse.php. . 绕过检测

PASS 11 (双写php绕过黑名单)

str_ireplace() 函数不区分大小写,大小写绕过不适用,因此使用双写绕过,

如果文件名含有黑名单里面的字符串 就替换为空

但是只替换一次 并没有进行正则匹配或者是循环匹配敏感字符  因此只要双写php即可 因为是从左往右读的 所以替换为空后 还是php,   pphphp、phphpp都可以尝试 

img

将抓包后缀名改为.pphphp,发现上传成功

PASS 12 白名单绕过 00绕过GET型

条件: php版本 < 5.3.4

00截断的限制条件是PHP<5.3.29,且GPC关闭

因为当 magic_quotes_gpc 打开时,所有的 ' (单引号), " (双引号), \ (反斜线) and 空字符会自动转为含有反斜线的转义字符。magic_quotes_gpc 着重偏向数据库方面,是为了防止sql注入,但magic_quotes_gpc开启还会对$_REQUEST, $_GET,$_POST,$_COOKIE 输入的内容进行过滤url中的%00(只要是这种%xx)的形式,webserver会把它当作十六进制处理,然后把16进制的hex自动翻译成ascii码值“NULL”,实现了截断burpsuite中16进制编辑器将空格20改成了00。本质上来说,都是利用0x00是字符串的结束标识符,进行截断处理。只不过GET传参需要url编码成%00而已

本关提示:本pass上传路径可控!

strrpos(string,find,start) 函数查找字符串在另一字符串中最后一次出 现的位置(区分大小写)。 substr(string,start,length) 函数返回字符串的一部分*(从start开始 ,长度为 length)

$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;

源码中对后缀进行白名单检测,只允许 jpg ,png,gif

但上传的路径可控,这里可以使用 %00截断 ,上传webshell.jpg的一句话木马save_path=../upload/webshell.php%00成功上传后,%00后缀的不会被识别

代码漏洞点就在于 用$_GET['save_path']来组成上传的文件路径 而这个get传参是我们可以控制的地方 

因此我们考虑用是否能进行截断 例如形成../upload/12.php/截断后面的(xxx.jpg)

这样就通过了白名单校验  并且保存成了php文件

PASS 13 (白名单绕过 00截断POST型)

image.png

php的一些函数的底层是C语言,而move_uploaded_file就是其中之一,遇到0x00会截断,0x表示16进制,URL中%00解码成16进制就是0x00。

上传路径在$_POST数据中 不需要url编码, 不需要修改hex值那么麻烦 只要在burp里面输入%00 然后进行url解码即可 得到就是0x00,或者是HEX查找70(php)后面的 修改为00即可(在content-disposition附近查找)

Pass-14 (文件包含+图片马)

image-20240718134235213

读取文件头的两字节 将二进制数据转换为ASCII值 进行switch比较 也就是说只验证文件头信息

图⽚⽂件头以及解码(16进制)

1.JPEG

- ⽂件头标识 (2 bytes): 0xff, 0xd8 (SOI) (JPEG ⽂件标识)

- ⽂件结束标识 (2 bytes): 0xff, 0xd9 (EOI)

2.PNG

- ⽂件头标识 (8 bytes)   89 50 4E 47 0D 0A 1A 0A

3.GIF

- ⽂件头标识 (6 bytes)   47 49 46 38 39(37) 61

 GIF89A

本关将一句话木马转换为jpg,gif(最简单),png的形式然后利用文件包含漏洞进行加载木马
?file=upload/xxx.png或者是?file=./upload/xxx.png
可以直接用可以用Notepad++打开图片 在图片末尾添加一句话木马
也可以用代码copy 1.png /b + shell.php shell.png
也可以打开在文件开头加上文件的前缀
文件包含就相当于将其他目录的php文件复制粘贴到所在的php文件 减少代码的重复书写

PASS 15(文件包含+图片马)

让我们上传图片马到服务器,也就是说肯定会检测是不是真的为图片,而不是仅仅检测后缀名,这个时候我们就需要用到GIF89a进行伪造图片

https://i-blog.csdnimg.cn/blog_migrate/9a95e51159e7adbbeb6c2499d0cde79e.png

所以上图片码,图片码制作比较简单。需要一张真的图片, 需要一个php文件。 然后将图片和php文件组合在一起即可。 准备一张图片和一句话木马: image.png 然后在cmd中执行:

copy 1.png /b + shell.php shell.png

JPEG (jpg),文件头:FFD8FF

PNG (png),文件头:89504E47

GIF (gif),文件头:47494638

TIFF (tif),文件头:49492A00

Windows Bitmap (bmp),文件头:424D

CAD (dwg),文件头:41433130

Adobe Photoshop (psd),文件头:38425053 放在一个文件夹里然后在文件夹里打开cmd进行合成,要不然可能会找不到指定文件 注意用文件包含漏洞输入路径的时间不能用输入法 做图片马的时候尽量不要使用复杂且内存大图片,尽量使用小体积的,避免发生错误 我们采用文件包含的模式将这个gif文件包含进代码中,以当作php文件进行执行 注意修改php为较高版本且去掉多线程安全nts

Pass-16(文件包含+图片马)

需要开启php_exif模块。 做法和第14关相同

pass 17 (二次渲染)

二次渲染说白了就是上传的图片,他会重新创建画布 然后把里面的东西重新渲染一边,如果你的代码在里面也可能被渲染一遍,代码变成图片一部分那就失效了
方法一:所以需要找到渲染后的图片里面没有发生变化的Hex地方,添加一句话,通过文件包含漏洞执行一句话,使用蚁剑进行连接,可以用010editor查看上传后的图片和未上传的图片中没变的部分,然后在其中进行修改。或者是采用二次渲染过的图片进行插入木马,因为理论上来说二次渲染过的图片不会再渲染

方法二:由于他的代码存在逻辑缺陷 是先上传保存的图片 然后再去验证 如果不满足就删除上传的文件。由于代码执行是一步步来的 需要时间 那我们不停的上传文件 就会产生并发 服务器会不停的对每个文件都执行相关的代码,由于他先上传 然后又原封不动的保存我们上传的文件  所以有一瞬间原本的文件存在 如果上传目录和文件名字已知的话 我们就可以通过url访问我们上传的文件,但是一会被删除怎么办?我们在访问上传的php文件就相当于执行了php代码 只要自动写一个木马文件到文件夹就成功了

代码如下 插入到png图片中即可

<?php fputs(fopen('../upload/shell.php','w'),'<?php phpinfo();?>');?>

所以需要一边不停用burp不停地上传 然后另一边不断的访问  访问的文件需要有写的权限 不然还是不行 还好这里靶场

访问的py脚本如下 不会脚本的话可以用浏览器插件不停的刷新网页 间隔设置的短一点 0.25秒这种

    import requests
     
    url = "http://192.168.114.200/upload-labs-master/include.php?file=upload/17.png"
    while True:
        html = requests.get(url)
        if ('Warning' not in str(html.text)):
            print('ok')
            break
        else:
            print("发包中")

然后用burp的Intruder模块不停的发包就行了

两边同时运行就行了

然后查看我们的文件夹 发现有shell.php就成功了

Pass-18(条件竞争)

和17关一样,也是先上传,再进行验证的,不符合就删除,依旧利用时间差来攻击 直接上传php文件

<?php fputs(fopen('../upload/shell18.php','w'),'<?php phpinfo();?>');?>

py脚本如下:

    import requests
    url = "http://192.168.114.200/upload-labs-master/upload/18.php"
    while True:
        html = requests.get(url)
        if html.status_code == 200:
            print("OK")
            break
        else:
            print("发包中")

burp不停地发包

最后得到shell18.php

Pass-19(条件竞争+白名单+其他漏洞配合)

 

upload()函数大致思路如下:

    判断文件是否为http post方式上传
    建立文件夹
    白名单验证后缀名
    检查大小
    检查上传文件夹是否存在
    移动临时文件到上传目录
    对文件进行重命名

     同样的逻辑缺陷 不过是白名单 上传路径不可控制 所以上传含有木马的白名单文件 配合条件竞争和其他漏洞来实现写入木马  白名单+条件竞争+Apache未知后缀名解析漏洞,上传一个Apache不识别的后缀名 通过条件竞争访问php文件 写入木马成功,这里用19.php.ppt

注意Apache未知后缀名解析漏洞适用 php ts 版本

py脚本如下

    import requests
     
    url = "http://192.168.114.200/upload-labs-master/upload/19.php.ppt"
    while True:
        html = requests.get(url)
        if html.status_code == 200:
            print("OK")
            break
        else:
            print("发包中")

burp不断发包,成功访问shell19.php

Pass-20(黑名单+上传路径可控)

move_uploaded_file会忽略末尾的/.,本关用move_uploaded_file函数执行上传动作,该函数会忽略文件末尾的/.,因此可以在文件名后加/.这两个符号来绕过黑名单的限制。

​​​​​​​Pass-21(MIME验证+白名单+上传路径可控)

这一关白名单,
验证过程:
--> 验证上传路径是否存在
--> 验证['upload_file']的content-type是否合法(可以抓包修改)
--> 判断POST参数是否为空定义$file变量(关键:构造数组绕过下一步的判断)
--> 判断file不是数组则使用explode('.', strtolower($file))对file进行切割,将file变为一个数组
--> 判断数组最后一个元素是否合法
--> 数组第一位和$file[count($file) - 1]进行拼接,产生保存文件名file_name
--> 上传文件

上传shell.php和POST参数,抓包,修改content-type,修改POST参数为数组类型,索引[0]为shell.php,索引[2]为jpg|png|gif。
只要第二个索引不为1,$file[count($file) - 1]就等价于$file[2-1],值为空
发包,使用蚁剑连接../upload/shell.php

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值