Bootstrap

文件上传漏洞(思路,绕过,修复)

文件上传漏洞:

1.思维导图

在这里插入图片描述
在这里插入图片描述

2.上传思路

在这里插入图片描述

3.概念

在这里插入图片描述

4.绕过

文件上传常见验证:
后缀名,类型、文件头等。

  • 后缀名:黑名单、白名单(phtml/php4,双写,空字节,双扩展等等
  • 文件类型:MIME信息(抓包修改)
  • 文件头:内容头信息(修改文件头)

方法:查看源码、抓包修改包信息

%00截断:可以把这个放在文件名内,绕过检测。可见upload-labs-Less11、12关,修改的是文件路径上(url)的,而非文件名上截断。
get传输:会自动解码。
post传输:不会自动解码。
所以想以post提交数据%00需要把它进行url编码变成%25%30%30,或直接在burp中改十六进制为00,%00对应的十六进制为20改为00。

在这里插入图片描述
5.
在这里插入图片描述
6.

靶场

老版靶场:

upload-labs通关指南

新版靶场:

upload-labs练习文件上传靶场

内容/逻辑/数组绕过

在这里插入图片描述

1)cmd制作图片马,这样不会损坏文件:

copy 1.png /b + shell.php /a webshell.jpg

2)
Pass-15-getimagesize()函数-图片马,该函数会验证返回图片信息,若不是图片则会返回为空,之后代码也就不会执行,所以必须上传图片。

Pass-16-exif_imagetype()函数-图片马

两者都是判断文件类型的函数,可以图片马绕过,攻击方式同pass-14.

3)二次渲染/条件竞争:

1.逻辑安全=二次渲染:指的是网站接受目标后会再进行操作,也就是说会对文件进行二次操作(比如缩略图和头像框都被渲染过),其中的php代码可能会被渲染掉,主要是imagecreatefromjpeg()函数 ! upload-labs-Less-17
2.逻辑安全-条件竞争:有的网站会对上传的文件进行上传后再验证(上传过程不进行验证),这样文件会暂时保存到服务器上,可以趁程序未对此文件进行操作(例如改名,移位等),访问文件进行占用,产生条件竞争。 upload-labs-Less-18

4)Less-17源码:

$is_upload = false;
$msg = null;
if (isset($_POST['submit'])){
   
    // 获得上传文件的基本信息,文件名,类型,大小,临时文件路径
    $filename = $_FILES['upload_file']['name'];
    $filetype = $_FILES['upload_file']['type'];
    $tmpname = $_FILES['upload_file']['tmp_name'];

    $target_path=UPLOAD_PATH.'/'.basename($filename);

    // 获得上传文件的扩展名
    $fileext= substr(strrchr($filename,"."),1);

    //判断文件后缀与类型,合法才进行上传操作
    if(($fileext == "jpg") && ($filetype=="image/jpeg")){
    //if与else if语句分别判断是否为三种图片类型
        if(move_uploaded_file($tmpname,$target_path)){
    //将客户端生成的临时文件移动到服务器指定文件目录下
            
            $im = imagecreatefromjpeg($target_path);//使用上传的图片生成新的图片,新的图层,这是二次渲染的关键。

            if($im == false){
   
                $msg = "该文件不是jpg格式的图片!";
                @unlink($target_path);
            }else{
   
                //给新图片指定文件名
                srand(time());
                $newfilename = strval(rand()).".jpg";
                
                $img_path = UPLOAD_PATH.'/'.$newfilename;//显示二次渲染后的图片并在html中打印(使用用户上传图片生成的新图片)
                imagejpeg($im,$img_path);//php输出jpg图片文件函数
                @unlink($target_path);//删除文件
                $is_upload = true;
            }
        } else {
   
            $msg = "上传出错!";
        }

    }else if(($fileext == "png") && ($filetype=="image/png")){
   
        if(move_uploaded_file($tmpname,$target_path)){
   
            //使用上传的图片生成新的图片
            $im = imagecreatefrompng($target_path);

            if($im == false){
   
                $msg = "该文件不是png格式的图片!";
                @unlink($target_path);
            }else{
   
                 //给新图片指定文件名
                srand(time());
                $newfilename = strval(rand()).".png";
                //显示二次渲染后的图片(使用用户上传图片生成的新图片)
                $img_path = UPLOAD_PATH.'/'.$newfilename;
                imagepng($im,$img_path);

                @unlink($target_path);
                $is_upload = 
;