从历史漏洞学习漏洞挖掘
字数 1663 2025-08-23 18:31:24
从历史漏洞学习漏洞挖掘:以MrDoc任意文件读取漏洞为例
漏洞概述
本文以MrDoc(一个开源在线文档系统)的任意文件读取漏洞为例,详细讲解如何通过分析历史漏洞来学习漏洞挖掘的思路和方法。
漏洞基本信息
- 影响版本:v0.9.2及以下版本
- 漏洞类型:任意文件读取
- 漏洞文件:
app_doc/report_utils.py - 修复提交:b634cf84eedb669fc1f11ce87558b0b045301af1
漏洞分析
漏洞定位
通过查看修复提交记录,发现对变量media_filename进行了安全处理,这表明问题出在该变量的处理上。
漏洞代码分析
漏洞位于app_doc/report_utils.py第152行附近,主要功能是从Markdown文件中查找静态资源并进行路径处理:
pattern = r'!
$$
.*?
$$
$(.*?)$'
media_list = re.findall(pattern, md_content)
for media in media_list:
try:
media_filename = media.replace('//', '/').split("(")[-1].split(")")[0]
if media_filename.startswith("/media"):
sub_folder = "/" + media_filename.split("/")[2]
is_sub_folder = os.path.exists("/Users/xxx/language/python_floder/MrDoc/media/reportmd_temp" + sub_folder)
md_content = md_content.replace(media_filename, "." + media_filename)
new_file_path = pathlib.Path("/Users/xxx/language/python_floder/", unquote(media_filename)[1:])
漏洞原理
- 使用正则表达式`!
\[.*? \]
\((.*?)\)匹配Markdown中的图片链接格式`` 2. 提取括号中的路径内容到media_filename 3. 虽然检查了路径以/media开头,但未对路径中的../进行过滤 4. 最终使用shutil.copy`复制文件时,可利用路径穿越读取系统任意文件
漏洞复现
复现步骤
-
注册账号并编辑一篇文章,插入恶意Markdown内容:
或使用HTML标签:
-
将文章保存到文集中
-
进入"我的文集" → "文集管理" → 选择文集 → "批量导出"
-
下载并解压导出的压缩包,可看到成功读取了目标文件
触发路径
漏洞触发调用栈:
导出文集MD文件功能 → 调用存在漏洞的路径处理函数 → 导致任意文件读取
扩展测试:类似项目分析
作者尝试在类似项目mm-wiki中寻找相同漏洞:
-
mm-wiki分析:
- 文件导出功能中,图片地址从数据库检索
- 使用
filepath.Join拼接路径 - 理论上如果
attachment["path"]包含../可造成目录穿越 - 但上传时进行了文件存在性校验,无法覆盖已有文件,因此无法利用
-
结论:
- 不同项目对路径处理方式不同
- 需要具体分析每个项目的实现细节
- 鼓励读者用相同思路测试其他类似项目
Markdown相关漏洞挖掘技巧
XSS漏洞挖掘
历史上Markdown编辑器常见的漏洞是HTML渲染导致的XSS:
-
测试payload示例:
<iframe src=javascript://%0aalert('iframe')> <embed src="https://c0olw.github.io/pic/1.html"> <audio src=x onerror=confirm("casrc")> -
测试方法:
- 尝试各种HTML标签和JavaScript执行方式
- 重点关注
<iframe>,<embed>,<audio>等标签 - 测试各种事件处理器(onerror等)
-
历史案例:
- Typora XSS到RCE漏洞
- CVE-2023-2317: Typora命令执行漏洞
- editor.md项目的多个XSS问题
黑盒测试建议
- 尝试使用不常见的HTML标签
- 测试各种JavaScript执行方式
- 关注Markdown到HTML的转换过程
- 检查是否对特殊字符进行了适当过滤
漏洞挖掘方法论
-
从修复提交入手:
- 查看项目的commit历史,关注安全修复
- 分析修复前后的代码差异
-
变量追踪:
- 识别关键变量(如本例中的
media_filename) - 追踪变量的传递和处理过程
- 识别关键变量(如本例中的
-
正则表达式分析:
- 理解项目使用的正则表达式匹配规则
- 测试正则表达式是否可以被绕过
-
路径处理检查:
- 检查所有文件路径拼接操作
- 测试是否可以使用
../进行路径穿越
-
功能点测试:
- 重点关注文件导出/导入功能
- 测试各种用户输入点
防御建议
- 对用户提供的路径进行规范化处理
- 检查路径是否包含
../等穿越序列 - 限制文件访问范围(chroot或指定根目录)
- 对Markdown中的HTML内容进行严格过滤
- 使用安全的路径拼接函数(如
os.path.join)
总结
通过分析MrDoc的任意文件读取漏洞,我们可以学习到:
- 如何从修复提交中发现漏洞线索
- 如何分析关键变量的处理过程
- 路径穿越漏洞的常见模式和测试方法
- 如何将这种思路应用到其他类似项目中
- Markdown相关漏洞的挖掘技巧
这种分析方法可以推广到其他类型的漏洞挖掘中,帮助安全研究人员更高效地发现潜在的安全问题。