IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> PHP知识库 -> 文件上传漏洞靶场upload-labs学习(pass11-pass15) -> 正文阅读

[PHP知识库]文件上传漏洞靶场upload-labs学习(pass11-pass15)

0x00 Pass11(str_ireplace复写绕过)

Pass11主要考察str_ireplace函数

$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","jsp","jspa","jspx","jsw","jsv","jspf","jtml","asp","aspx","asa","asax","ascx","ashx","asmx","cer","swf","htaccess","ini");

        $file_name = trim($_FILES['upload_file']['name']);
        $file_name = str_ireplace($deny_ext,"", $file_name);
        $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 = UPLOAD_PATH . '文件夹不存在,请手工创建!';
    }
}

在PHP中

str_replace() 函数
定义:使用一个字符串替换字符串中的另一些字符,对大小写敏感的搜索
语法:str_replace(find,replace,string,count)

str_ireplace() 函数
定义:使用一个字符串替换字符串中的另一些字符,对大小写不敏感的搜索
语法:str_ireplace(find,replace,string,count)

可见无法通过后缀名的大小写绕过,但对于replace函数中直接替换为空的场景通常可以用复写来绕过,例如本关中的test1.pphphp即可在replace后变成test1.php

在这里插入图片描述

0x01 Pass12(GET方式%00截断)

本题考查%00截断,相当于复现CVE-2006-7243,所以需将php版本设置为PHP 5.3.4以下, 并关闭magic_quotes_gpc选项。
具体代码为:

$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类型文件!";
    }
}

可见保存的路径也可以由用户所控制,GET类型的传参。因此在保存路径中修改为:

save_path=../upload/test.php%00

再上传一个正常的jpg图片即可。

在这里插入图片描述这时由于受空字符%00的影响,后面所有的内容均被截断。
最终上传test.php文件。

在这里插入图片描述

0x02 Pass13(POST方式%00截断)

上一关中看到save_path变量是通过GET形式传参接受的,因此在url中直接使用%00截断使得后面的路径拼接不被读取。

$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类型文件!";
    }
}

而在13关中,$_POST['save_path']以POST形式传参时,直接使用%00无法截断,因为POST的数据不会被直接解码,需要手动使用burp中的URL-decode解码。

在这里插入图片描述
解码后就变为了不可见字符,绕过POST形式的00截断。

在这里插入图片描述

0x03 Pass14(文件头截取判断)

可以看到题目的要求为:

1.保证上传后的图片马中仍然包含完整的一句话或webshell代码。
2.使用文件包含漏洞能运行图片马中的恶意代码。
3.图片马要.jpg,.png,.gif三种后缀都上传成功才算过关!

代码如下:

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_PATH."/".rand(10, 99).date("YmdHis").".".$file_type;
        if(move_uploaded_file($temp_file,$img_path)){
            $is_upload = true;
        } else {
            $msg = "上传出错!";
        }
    }
}

可见每次上传的文件都会被读取前两个字节来判断文件类型,这里判断的也就是文件头。
这里把三种文件类型的文件头加上:

PNG文件:hex格式8950,取值输出为13780

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

JPG文件:hex格式FFD8,取值输出为255216。

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

GIF文件:GIF89a,当文件第一行为GIF头时,取值输出为7173。

在这里插入图片描述
在burp中,GIF文件我们只需要在要发送的数据包前面加上文件头即可。
而png和jpg文件受不可见字符的影响,建议以copy /b 1.png+test.php upload.png的命令制作图片木马。
打开后如图所示:
在这里插入图片描述

上传成功后使用题目中给出的链接测试文件包含是否可以执行图片木马。
在这里插入图片描述

0x04 Pass15(getimagesize函数绕过)

判断是否为图片的代码为:

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)>=0){
            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_PATH."/".rand(10, 99).date("YmdHis").$res;
        if(move_uploaded_file($temp_file,$img_path)){
            $is_upload = true;
        } else {
            $msg = "上传出错!";
        }
    }
}

使用 $info = getimagesize($filename);和 $ext = image_type_to_extension($info[2]);取文件后缀名。
在php中getimagesize会获取7个元素的值,分别为:

索引 0 给出的是图像宽度的像素值
索引 1 给出的是图像高度的像素值
索引 2 给出的是图像的类型,返回的是数字,其中1 = GIF,2 = JPG,3 = PNG,4 = SWF,5 = PSD,6 = BMP,7 = TIFF(intel byte order),8 = TIFF(motorola byte order),9 = JPC,10 = JP2,11 = JPX,12 = JB2,13 = SWC,14 = IFF,15 = WBMP,16 = XBM
索引 3 给出的是一个宽度和高度的字符串,可以直接用于 HTML 的<image>标签
索引 bits 给出的是图像的每种颜色的位数,二进制格式
索引 channels 给出的是图像的通道值,RGB 图像默认是 3
索引 mime 给出的是图像的 MIME 信息,此信息可以用来在 HTTP Content-type 头信息中发送正确的信息,如: header(“Content-type: image/jpeg”);

上传一张示例图片返回结果为:
在这里插入图片描述可以看到info[2]的值为2,也就是JPG,与返回的相同。
在本关中,使用刚刚copy /b 1.png+test.php upload.png生成的图片马即可绕过。
在这里插入图片描述

  PHP知识库 最新文章
Laravel 下实现 Google 2fa 验证
UUCTF WP
DASCTF10月 web
XAMPP任意命令执行提升权限漏洞(CVE-2020-
[GYCTF2020]Easyphp
iwebsec靶场 代码执行关卡通关笔记
多个线程同步执行,多个线程依次执行,多个
php 没事记录下常用方法 (TP5.1)
php之jwt
2021-09-18
上一篇文章      下一篇文章      查看所有文章
加:2022-03-16 22:03:36  更:2022-03-16 22:04:04 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年12日历 -2024/12/26 16:13:18-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码
数据统计