泛微云桥e-Bridge文件上传漏洞分析
type
status
date
slug
summary
tags
category
icon
password
AI summary
漏洞分析
通过官网公告可得知漏洞路径为:/wxclient/app/recruit/resume/addResume?fileElementld=aaa
根据路径可以很快定位到漏洞点为:
weaver.weixin.app.recruit.controller.ResumeController#addResume()
跟进
getWxBaseFile()
这里因为显式传入的filepath为空,所以进入
FileUploadTools.getRandomFilePath()
这里尝试通过GCONST.getFileRootPath()获取缓存目录,如果不存在,则获取Web根目录。
所以这里构造的_filePath为
/upload/年月/随机2位大写字母/
继续跟进
uf = this.getFile(parameterName, _filePath, _fileMaxSize, _fileEncoding);
在getFiles()中,判断检查当前request是否为MultipartRequest类型,如果不是,则将其包装成MultipartRequest,MultipartRequest会处理文件上传,将文件保存到指定目录
使用
MultipartRequest
类处理多部分请求,并遍历所有上传的文件。这里已经上传了文件了。后面的代码则主要是遍历上传的文件,并将其信息存储在
UploadFile
对象中,构造一个上传文件的列表- 获取文件名、文件系统名、原始文件名和内容类型。
- 创建
UploadFile
对象。
- 检查文件是否安全,若安全则添加到上传文件列表。
这里重点关注isSafeFile()函数
如果上传的文件以jsp结尾,则会把刚刚已经上传成功的对象删掉。虽然理论上可以条件竞争,但路径还需要爆破2位大写字符,估计很难实现。
绕过isSafeFile
方法一
这里禁止了jsp,但是没有禁止jspx,所以可以上传jspx绕过
方法二
仔细观察代码不难发现,传入isSafeFile函数的uploadfile对象的name来源于
this.multipartRequest.getFilesystemName(name);
this.multipartRequest.getFilesystemName(name)
只会获取 name
对应的最后一个文件的文件名,因为 files.get(name)
返回的是与 name
关联的最后一个 UploadedFile
对象。这是因为
MultipartRequest
内部存储文件的方式是基于一个哈希表,其中键是表单字段的名称(name
),而值是 UploadedFile
对象。在这种情况下,如果表单中有多个文件输入域具有相同的名称,后续的文件会覆盖之前的文件,导致哈希表中仅保留最后一个文件。
详细解释
假设表单上传了两个文件,两个文件的表单字段名称都叫
file
。当 MultipartRequest
处理这些文件时:- 第一个文件
file
被添加到哈希表中,键为file
,值为第一个UploadedFile
对象。
- 第二个文件
file
也被添加到哈希表中,键仍然为file
,值为第二个UploadedFile
对象。
由于哈希表中的键是唯一的,因此第二个文件会覆盖第一个文件的值。
所以构造如下表单即可绕过
绕过jfinal
由于jfinal的限制,导致不能直接访问jsp文件
通过这篇文章的姿势:https://forum.butian.net/share/1899
使用request.getRequestURI()这两个方法进行访问path的获取时,是不会进行URL解码操作的,利用这一点同样可以进行Bypass
Loading...