全网最全upload-labs通关攻略(建议收藏)

絕刀狂花
发布: 2025-09-27 08:13:27
原创
1001人浏览过

upload-labs是一个帮你总结所有上传漏洞类型的靶场,学习上传漏洞原理,复现上传漏洞必备靶场环境,玩起来吧!项目地址:https://github.com/c0ny1/upload-labs

环境要求

若要自己亲自搭建环境,请按照以下配置环境,方可正常运行每个Pass。

配置项

配置

描述

操作系统

Window or Linux

推荐使用Windows,除了Pass-19必须在linux下,其余Pass都可以在Windows上运行

PHP版本

推荐5.2.17

其他版本可能会导致部分Pass无法突破

PHP组件

php_gd2,php_exif

部分Pass依赖这两个组件

中间件

设置Apache

以moudel方式连接

第一关思路发现随意上传php木马,发现前端报错,响应速度超快,且数据包未达到服务器,猜测前端js验证
全网最全upload-labs通关攻略(建议收藏)
源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">function checkFile() {    var file = document.getElementsByName('upload_file')[0].value;    if (file == null || file == "") {        alert("请选择要上传的文件!");        return false;    }    //定义允许上传的文件类型    var allow_ext = ".jpg|.png|.gif";    //提取上传文件的类型    var ext_name = file.substring(file.lastIndexOf("."));    //判断上传文件类型是否允许上传    if (allow_ext.indexOf(ext_name + "|") == -1) {        var errMsg = "该文件不允许上传,请上传" + allow_ext + "类型的文件,当前文件类型为:" + ext_name;        alert(errMsg);        return false;    }}</code>
登录后复制
逻辑大致是识别上传文件的后缀名 并查看是否是jpg、png、gif中的一个,否则不允许上传bypass

1.修改前端不使用该checkfile函数

全网最全upload-labs通关攻略(建议收藏)
直接可上传php文件成功第二关思路发现上传php显示文件类型不正确
全网最全upload-labs通关攻略(建议收藏)
抓包查看文件类型字段,猜测会判断Content-Type字段源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists(UPLOAD_PATH)) {        if (($_FILES['upload_file']['type'] == 'image/jpeg') || ($_FILES['upload_file']['type'] == 'image/png') || ($_FILES['upload_file']['type'] == 'image/gif')) {            $temp_file = $_FILES['upload_file']['tmp_name'];            $img_path = UPLOAD_PATH . '/' . $_FILES['upload_file']['name']                        if (move_uploaded_file($temp_file, $img_path)) {                $is_upload = true;            } else {                $msg = '上传出错!';            }        } else {            $msg = '文件类型不正确,请重新上传!';        }    } else {        $msg = UPLOAD_PATH.'文件夹不存在,请手工创建!';    }}</code>
登录后复制
逻辑大致是识别上传文件的类型 并查看是否是image/jpge、image/png、image/gif中的一个,否则不允许上传$_FILES全局变量

$_FILES'myFile'

Softr Studio
Softr Studio

最简单的无代码web开发平台

Softr Studio 55
查看详情 Softr Studio

上传文件的原名称

$_FILES'myFile'

文件的 MIME 类型

$_FILES'myFile'

已上传文件的大小,单位为字节

$_FILES'myFile'

文件被上传后在服务端储存的临时文件名,一般是系统默认。可以在php.ini的upload_tmp_dir 指定

$_FILES'myFile'

和该文件上传相关的错误代码

bypass

直接抓包改Content-Type为image/png,上传成功

全网最全upload-labs通关攻略(建议收藏)
第三关思路发现直接上传php脚本显示提示:不允许上传.asp,.aspx,.php,.jsp后缀文件!
全网最全upload-labs通关攻略(建议收藏)
猜测设置了后缀名黑名单源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists(UPLOAD_PATH)) {        $deny_ext = array('.asp','.aspx','.php','.jsp');        $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); //收尾去空        if(!in_array($file_ext, $deny_ext)) {            $temp_file = $_FILES['upload_file']['tmp_name'];            $img_path = UPLOAD_PATH.'/'.date("YmdHis").rand(1000,9999).$file_ext;// 随机命名            if (move_uploaded_file($temp_file,$img_path)) {                 $is_upload = true;            } else {                $msg = '上传出错!';            }        } else {            $msg = '不允许上传.asp,.aspx,.php,.jsp后缀文件!';        }    } else {        $msg = UPLOAD_PATH . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
逻辑大致是识别上传文件的类型 并查看是否是'.asp','.aspx','.php','.jsp'中的一个,否则不允许上传bypass尝试使用和php一样解析效果的后缀名,如php3、php4、php5、phtml等后缀名
全网最全upload-labs通关攻略(建议收藏)
上传成功,并成功解析
全网最全upload-labs通关攻略(建议收藏)
第四关思路发现直接上传php脚本显示提示:此文件不允许上传!需抓包验证检验的参数源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists(UPLOAD_PATH)) {        $deny_ext = array(".php",".php5",".php4",".php3",".php2",".php1",".html",".htm",".phtml",".pht",".pHp",".pHp5",".pHp4",".pHp3",".pHp2",".pHp1",".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",".ini");        $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); //收尾去空        if (!in_array($file_ext, $deny_ext)) {            $temp_file = $_FILES['upload_file']['tmp_name'];            $img_path = UPLOAD_PATH.'/'.$file_name;            if (move_uploaded_file($temp_file, $img_path)) {                $is_upload = true;            } else {                $msg = '上传出错!';            }        } else {            $msg = '此文件不允许上传!';        }    } else {        $msg = UPLOAD_PATH . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
逻辑大致大致和上一关类似,只是增加了黑名单量,识别上传文件的类型 并查看是否是黑名单量中的一个,否则不允许上传,可见大小写都包括了,常见的一些后缀也包括了,通过查看资料发现.htaccess后缀文件并未在这个黑名单中,可以进行利用。bypass上传一个.htaccess文件内容如下,意思为所有文件都用php来解析代码语言:javascript代码运行次数:0运行复制
<code class="javascript">AddType application/x-httpd-php .png或者<FilesMatch "文件名">SetHandler application/x-httpd-php</FilesMatch></code>
登录后复制
上传一个图片马hacker.png直接访问该图片地址,均成功!第五关思路发现和上一关类似源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists(UPLOAD_PATH)) {        $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");        $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); //首尾去空                if (!in_array($file_ext, $deny_ext)) {            $temp_file = $_FILES['upload_file']['tmp_name'];            $img_path = UPLOAD_PATH.'/'.$file_name;            if (move_uploaded_file($temp_file, $img_path)) {                $is_upload = true;            } else {                $msg = '上传出错!';            }        } else {            $msg = '此文件类型不允许上传!';        }    } else {        $msg = UPLOAD_PATH . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
逻辑大致大致和上一关类似,只是增加了.htaccess黑名单量,识别上传文件的类型 并查看是否是黑名单量中的一个,否则不允许上传,细看大小写过滤并不全,可以混合大小写进行利用。bypass上传shell.PhP上传成功第六关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $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 = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA                if (!in_array($file_ext, $deny_ext)) {            if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $UPLOAD_ADDR . '/' . $_FILES['upload_file']['name'])) {                $img_path = $UPLOAD_ADDR . '/' . $file_name;                $is_upload = true;            }        } else {            $msg = '此文件不允许上传';        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
PHP _FILES 是一个预定义的数组,用来获取通过 POST 方法上传文件的相关信息。如果为单个文件上传,那么 FILES 为二维数组;如果为多个文件上传,那么 代码语言:javascript代码运行次数:0运行复制
<code class="javascript">Array(    [userfile] => Array    (        [name] => Screen Shot 2016-05-12 at 18.13.24.png        [type] => image/png        [tmp_name] => /private/var/tmp/phplVHp3W        [error] => 0        [size] => 344925    ))</code>
登录后复制
是后缀名黑名单,少了这段代码file_ext = trim(file_ext); //首尾去空bypass

可以进行空格绕过,直接抓包修改文件名,再文件名末尾添加空格,成功上传

全网最全upload-labs通关攻略(建议收藏)
直接可上传php文件成功第七关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $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_ext = strrchr($file_name, '.');        $file_ext = strtolower($file_ext); //转换为小写        $file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA        $file_ext = trim($file_ext); //首尾去空                if (!in_array($file_ext, $deny_ext)) {            if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $UPLOAD_ADDR . '/' . $_FILES['upload_file']['name'])) {                $img_path = $UPLOAD_ADDR . '/' . $file_name;                $is_upload = true;            }        } else {            $msg = '此文件不允许上传';        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
没有对后缀名进行去”.”处理,strrchr(file_name, '.')只是截取.后面的后缀名。利用windows特性,会自动去掉后缀名中最后的”.”,可在后缀名中加”.”绕过。少了代码file_name = deldot(bypass

查看源码还是黑名单没有对后缀名进行去.操作利用Windows特性会自动去掉后缀名中最后的.可在后缀名中加 . 绕过

全网最全upload-labs通关攻略(建议收藏)
第八关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $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); //首尾去空                if (!in_array($file_ext, $deny_ext)) {            if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $UPLOAD_ADDR . '/' . $_FILES['upload_file']['name'])) {                $img_path = $UPLOAD_ADDR . '/' . $file_name;                $is_upload = true;            }        } else {            $msg = '此文件不允许上传';        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
逻辑大致是识别上传文件的类型 并查看是否是'.asp','.aspx','.php','.jsp'中的一个,否则不允许上传,少了代码file_ext = str_ireplace('::DATA', '', file_ext);//去除字符串::DATAbypassNTFS文件系统包括对备用数据流的支持,主要包括提供与Macintosh文件系统中的文件的兼容性。备用数据流允许文件包含多个数据流。每个文件至少有一个数据流。在Windows中,此默认数据流称为: DATA。上传.php::DATA绕过。(仅限windows)第九关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript"> $is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $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 = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA        $file_ext = trim($file_ext); //首尾去空                if (!in_array($file_ext, $deny_ext)) {            if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $UPLOAD_ADDR . '/' . $_FILES['upload_file']['name'])) {                $img_path = $UPLOAD_ADDR . '/' . $file_name;                $is_upload = true;            }        } else {            $msg = '此文件不允许上传';        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
查看源码,这里只过滤了一次,所以直接构造 .php. . 绕过bypass

直接构造点加空格加点 .php. . 绕过

全网最全upload-labs通关攻略(建议收藏)

可通过https://localhost/upload-labs/upload/shell1.php访问mm

第十关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $deny_ext = array("php","php5","php4","php3","php2","html","htm","phtml","jsp","jspa","jspx","jsw","jsv","jspf","jtml","asp","aspx","asa","asax","ascx","ashx","asmx","cer","swf","htaccess");        $file_name = trim($_FILES['upload_file']['name']);        $file_name = str_ireplace($deny_ext,"", $file_name);        if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $UPLOAD_ADDR . '/' . $file_name)) {            $img_path = $UPLOAD_ADDR . '/' .$file_name;            $is_upload = true;        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
file_name = str_ireplace(deny_ext,"", bypass

1.双写绕过

全网最全upload-labs通关攻略(建议收藏)
第十一关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$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;        if(move_uploaded_file($temp_file,$img_path)){            $is_upload = true;        }        else{            $msg = '上传失败!';        }    }    else{        $msg = "只允许上传.jpg|.png|.gif类型文件!";    }}</code>
登录后复制
strrpos() 函数查找字符串在另一字符串中最后一次出现的位置是后缀名白名单,截取后缀名并随机命名拼接bypass

$_GET['save_path'] 有传入参数可控,可以使用%00截断

全网最全upload-labs通关攻略(建议收藏)
第十二关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$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 = $_POST['save_path']."/".rand(10, 99).date("YmdHis").".".$file_ext;        if(move_uploaded_file($temp_file,$img_path)){            $is_upload = true;        }        else{            $msg = "上传失败";        }    }    else{        $msg = "只允许上传.jpg|.png|.gif类型文件!";    }}</code>
登录后复制
与前一关类似,只是变成了POST提交bypass

%00截断进行拼接

全网最全upload-labs通关攻略(建议收藏)
第十三关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">function getReailFileType($filename){    $file = fopen($filename, "rb");    $bin = fread($file, 2); //只读2字节 读取文件头    fclose($file);    $strInfo = @unpack("C2chars", $bin);        $typeCode = intval($strInfo['chars1'].$strInfo['chars2']);        $fileType = '';        switch($typeCode){              case 255216:                        $fileType = 'jpg';            break;        case 13780:                        $fileType = 'png';            break;                case 7173:                        $fileType = 'gif';            break;        default:                        $fileType = 'unknown';        }            return $fileType;}$is_upload = false;$msg = null;if(isset($_POST['submit'])){    $temp_file = $_FILES['upload_file']['tmp_name'];    $file_type = getReailFileType($temp_file);    if($file_type == 'unknown'){        $msg = "文件未知,上传失败!";    }else{        $img_path = $UPLOAD_ADDR."/".rand(10, 99).date("YmdHis").".".$file_type;        if(move_uploaded_file($temp_file,$img_path)){            $is_upload = true;        }        else{            $msg = "上传失败";        }    }}</code>
登录后复制
会读取文件头和文件类型,已提示传入图片mmbypass

制作图片mm上传

全网最全upload-labs通关攻略(建议收藏)

结合文件包含进行解析

第十四关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript"> function isImage($filename){    $types = '.jpeg|.png|.gif';    if(file_exists($filename)){        $info = getimagesize($filename);        $ext = image_type_to_extension($info[2]);        if(stripos($types,$ext)){            return $ext;        }else{            return false;        }    }else{        return false;    }}$is_upload = false;$msg = null;if(isset($_POST['submit'])){    $temp_file = $_FILES['upload_file']['tmp_name'];    $res = isImage($temp_file);    if(!$res){        $msg = "文件未知,上传失败!";    }else{        $img_path = $UPLOAD_ADDR."/".rand(10, 99).date("YmdHis").$res;        if(move_uploaded_file($temp_file,$img_path)){            $is_upload = true;        }        else{            $msg = "上传失败";        }    }}</code>
登录后复制

这里用getimagesize获取文件类型

bypass

还是直接就可以利用图片马就可进行绕过

第十五关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">function isImage($filename){    //需要开启php_exif模块    $image_type = exif_imagetype($filename);    switch ($image_type) {        case IMAGETYPE_GIF:            return "gif";            break;        case IMAGETYPE_JPEG:            return "jpg";            break;        case IMAGETYPE_PNG:            return "png";            break;            default:            return false;            break;    }}$is_upload = false;$msg = null;if(isset($_POST['submit'])){    $temp_file = $_FILES['upload_file']['tmp_name'];    $res = isImage($temp_file);    if(!$res){        $msg = "文件未知,上传失败!";    }else{        $img_path = $UPLOAD_ADDR."/".rand(10, 99).date("YmdHis").".".$res;        if(move_uploaded_file($temp_file,$img_path)){            $is_upload = true;        }        else{            $msg = "上传失败";        }    }}</code>
登录后复制

这里用到php_exif模块来判断文件类型

bypass

还是直接就可以利用图片马就可进行绕过

第十六关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$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_ADDR.basename($filename);    // 获得上传文件的扩展名    $fileext= substr(strrchr($filename,"."),1);    //判断文件后缀与类型,合法才进行上传操作    if(($fileext == "jpg") && ($filetype=="image/jpeg")){        if(move_uploaded_file($tmpname,$target_path))        {            //使用上传的图片生成新的图片            $im = imagecreatefromjpeg($target_path);            if($im == false){                $msg = "该文件不是jpg格式的图片!";            }else{                //给新图片指定文件名                srand(time());                $newfilename = strval(rand()).".jpg";                $newimagepath = $UPLOAD_ADDR.$newfilename;                imagejpeg($im,$newimagepath);                //显示二次渲染后的图片(使用用户上传图片生成的新图片)                $img_path = $UPLOAD_ADDR.$newfilename;                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格式的图片!";            }else{                 //给新图片指定文件名                srand(time());                $newfilename = strval(rand()).".png";                $newimagepath = $UPLOAD_ADDR.$newfilename;                imagepng($im,$newimagepath);                //显示二次渲染后的图片(使用用户上传图片生成的新图片)                $img_path = $UPLOAD_ADDR.$newfilename;                unlink($target_path);                $is_upload = true;                           }        }        else        {            $msg = "上传失败!";        }    }else if(($fileext == "gif") && ($filetype=="image/gif")){        if(move_uploaded_file($tmpname,$target_path))        {            //使用上传的图片生成新的图片            $im = imagecreatefromgif($target_path);            if($im == false){                $msg = "该文件不是gif格式的图片!";            }else{                //给新图片指定文件名                srand(time());                $newfilename = strval(rand()).".gif";                $newimagepath = $UPLOAD_ADDR.$newfilename;                imagegif($im,$newimagepath);                //显示二次渲染后的图片(使用用户上传图片生成的新图片)                $img_path = $UPLOAD_ADDR.$newfilename;                unlink($target_path);                $is_upload = true;            }        }        else        {            $msg = "上传失败!";        }    }else{        $msg = "只允许上传后缀为.jpg|.png|.gif的图片文件!";    }}</code>
登录后复制
本关综合判断了后缀名、content-type,以及利用imagecreatefromgif判断是否为gif图片,最后再做了一次二次渲染bypass
全网最全upload-labs通关攻略(建议收藏)
第十七关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if(isset($_POST['submit'])){    $ext_arr = array('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_ADDR . '/' . $file_name;    if(move_uploaded_file($temp_file, $upload_file)){        // 先移动图片,有条件竞争的前提条件        if(in_array($file_ext,$ext_arr)){             $img_path = $UPLOAD_ADDR . '/'. rand(10, 99).date("YmdHis").".".$file_ext;             rename($upload_file, $img_path);             unlink($upload_file);             $is_upload = true;        }else{            $msg = "只允许上传.jpg|.png|.gif类型文件!";            unlink($upload_file);        }    }else{        $msg = '上传失败!';    }}</code>
登录后复制
这里先将文件上传到服务器,然后通过rename修改名称,再通过unlink删除文件,因此可以通过条件竞争的方式在unlink之前,访问webshellbypass

首先在burp中不断发送上传webshell的数据包,然后不断在浏览器中访问,发现通过竞争可以访问到。

第十八关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">/index.php$is_upload = false;$msg = null;if (isset($_POST['submit'])){    require_once("./myupload.php");    $imgFileName =time();    $u = new MyUpload($_FILES['upload_file']['name'], $_FILES['upload_file']['tmp_name'], $_FILES['upload_file']['size'],$imgFileName);    $status_code = $u->upload($UPLOAD_ADDR);    switch ($status_code) {        case 1:            $is_upload = true;            $img_path = $u->cls_upload_dir . $u->cls_file_rename_to;            break;        case 2:            $msg = '文件已经被上传,但没有重命名。';            break;         case -1:            $msg = '这个文件不能上传到服务器的临时文件存储目录。';            break;         case -2:            $msg = '上传失败,上传目录不可写。';            break;         case -3:            $msg = '上传失败,无法上传该类型文件。';            break;         case -4:            $msg = '上传失败,上传的文件过大。';            break;         case -5:            $msg = '上传失败,服务器已经存在相同名称文件。';            break;         case -6:            $msg = '文件无法上传,文件不能复制到目标目录。';            break;              default:            $msg = '未知错误!';            break;    }}//myupload.phpclass MyUpload{..................   var $cls_arr_ext_accepted = array(      ".doc", ".xls", ".txt", ".pdf", ".gif", ".jpg", ".zip", ".rar", ".7z",".ppt",      ".html", ".xml", ".tiff", ".jpeg", ".png" );..................    /** upload()   **   ** Method to upload the file.   ** This is the only method to call outside the class.   ** @para String name of directory we upload to   ** @returns void  **/  function upload( $dir ){        $ret = $this->isUploadedFile();        if( $ret != 1 ){      return $this->resultUpload( $ret );    }    $ret = $this->setDir( $dir );    if( $ret != 1 ){      return $this->resultUpload( $ret );    }    $ret = $this->checkExtension();    if( $ret != 1 ){      return $this->resultUpload( $ret );    }    $ret = $this->checkSize();    if( $ret != 1 ){      return $this->resultUpload( $ret );        }        // if flag to check if the file exists is set to 1        if( $this->cls_file_exists == 1 ){            $ret = $this->checkFileExists();      if( $ret != 1 ){        return $this->resultUpload( $ret );          }    }    // if we are here, we are ready to move the file to destination    $ret = $this->move();    if( $ret != 1 ){      return $this->resultUpload( $ret );        }    // check if we need to rename the file    if( $this->cls_rename_file == 1 ){      $ret = $this->renameFile();      if( $ret != 1 ){        return $this->resultUpload( $ret );          }    }        // if we are here, everything worked as planned :)    return $this->resultUpload( "SUCCESS" );    }.................. };</code>
登录后复制
需要上传一个图片mm本关对文件后缀名做了白名单判断,然后会一步一步检查文件大小、文件是否存在等等bypass

将文件上传后,对文件重新命名,同样存在条件竞争的漏洞。可以不断利用burp发送上传图片马的数据包,由于条件竞争,程序会出现来不及rename的问题,从而上传成功:

第十九关源码解读代码语言:javascript代码运行次数:0运行复制
<code class="javascript">$is_upload = false;$msg = null;if (isset($_POST['submit'])) {    if (file_exists($UPLOAD_ADDR)) {        $deny_ext = array("php","php5","php4","php3","php2","html","htm","phtml","pht","jsp","jspa","jspx","jsw","jsv","jspf","jtml","asp","aspx","asa","asax","ascx","ashx","asmx","cer","swf","htaccess");        $file_name = $_POST['save_name'];        $file_ext = pathinfo($file_name,PATHINFO_EXTENSION);        if(!in_array($file_ext,$deny_ext)) {            $img_path = $UPLOAD_ADDR . '/' .$file_name;            if (move_uploaded_file($_FILES['upload_file']['tmp_name'], $img_path)) {                 $is_upload = true;            }else{                $msg = '上传失败!';            }        }else{            $msg = '禁止保存为该类型文件!';        }    } else {        $msg = $UPLOAD_ADDR . '文件夹不存在,请手工创建!';    }}</code>
登录后复制
file_name = _POST['save_name'];中有变量可控发现move_uploaded_file()函数中的img_path是由post参数save_name控制的,因此可以在save_name利用00截断绕过:

以上就是全网最全upload-labs通关攻略(建议收藏)的详细内容,更多请关注php中文网其它相关文章!

热门游戏推荐
热门游戏推荐

最近有什么好玩的游戏?最近哪些游戏比较好玩?这里为大家带来热门游戏合集,汇聚了最新最好玩的高分爆款游戏,还在为不知道玩什么游戏而烦恼的玩家,快来保存下载体验吧!

下载
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
开源免费商场系统广告
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号