漏洞概述:SSRF过滤器绕过漏洞
在Hemmelig应用的“Secret Requests”功能中,发现了一个服务器端请求伪造(SSRF)过滤器绕过漏洞,该漏洞被分配了编号CVE-2025-69206。这个漏洞存在于应用对Webhook URL的验证逻辑中,使得已经通过身份验证的用户能够利用DNS重绑定或开放重定向服务,绕过应用对内部/私有IP地址的拦截机制,从而让服务器向内部网络资源发起HTTP请求。
核心问题 在于应用的验证逻辑仅对URL的主机名字符串进行模式匹配,而没有实际解析域名并检查其最终指向的IP地址是否属于受保护的私有地址范围。在7.3.3之前的版本中,此漏洞处于未修复状态。
技术细节:漏洞成因分析
脆弱的验证函数
漏洞的核心位于/api/lib/utils.ts文件中的isPublicUrl函数。这个函数的设计初衷是检查用户输入的Webhook URL是否指向公共地址,而非内部资源。以下是该函数存在缺陷的原始代码片段:
|
|
两种主要的绕过方式
1. DNS重绑定绕过
验证函数仅检查主机名字符串是否匹配预定义的黑名单模式(如localhost、127.0.0.1等)。这意味着,攻击者可以使用localtest.me这样的域名,该域名在DNS层面最终会解析到127.0.0.1,但由于其主机名字符串localtest.me本身不在黑名单模式中,因此能轻松通过验证。
2. 开放重定向绕过
攻击者可以提供一个外部公共域名(如httpbin.org)的URL,该URL指向一个会重定向到内部地址的端点(例如 httpbin.org/redirect-to?url=http://127.0.0.1)。由于初始URL的主机名httpbin.org是公共域名,能通过验证。而当服务器后续执行HTTP请求并跟随重定向时,就会访问到被禁止的内部地址。
漏洞复现与影响评估
攻击步骤演示
为了证明此漏洞的可利用性,可以按照以下步骤进行概念验证:
- 设置监听器:在运行Hemmelig应用的容器上,使用Node.js启动一个临时端口监听,用以接收来自服务器的请求。命令示例如下:
1node -e "require('http').createServer((req,res)=>{console.log(req.method,req.url,req.headers);res.end('ok')}).listen(8080,()=>console.log('Listening on 8080'))" - 利用漏洞:以普通用户身份登录,进入“Secret Requests”功能创建新请求。在Webhook URL输入框中,可以尝试以下两种有效载荷之一:
- 使用域名重定向:
http://localtest.me:8080 - 使用httpbin执行重定向:
httpbin.org/redirect-to?url=http://127.0.0.1:8080
- 使用域名重定向:
- 触发请求:在另一个浏览器标签页中确认请求并创建秘密信息。点击保存后,之前设置的监听端口(本例中的8080端口)就会收到来自Hemmelig服务器发起的请求。
实际影响与局限性
虽然攻击者能够完全绕过SSRF过滤器,但此漏洞的实际影响是有限的,因为它属于盲SSRF(Blind SSRF)类型。服务器在发起请求后,并不会将目标的响应内容返回给攻击者,因此攻击者无法直接读取内部服务的响应数据。
尽管如此,攻击者仍然可以利用响应时间差等技术手段,来探测目标网络内部特定端口是否开放,从而获取有价值的情报。
修复方案与安全建议
修复后的安全验证函数
要彻底修复此漏洞,必须将基于主机名的静态字符串匹配,改为基于实际解析出的IP地址的动态检查。以下是推荐的修复后代码:
|
|
额外的安全加固措施
除了核心的IP解析检查外,还应采取以下措施以增强防御:
- 禁用重定向跟随:在用于执行Webhook请求的
fetch调用中,明确配置不自动跟随HTTP重定向。 - 逐跳验证:如果业务上必须允许重定向,则应在服务器处理HTTP响应的每个重定向步骤后,重新对新获得的URL执行完整的
isPublicUrl验证。 - 更新依赖:所有使用Hemmelig的用户应立即升级到7.3.3或更高版本,该版本已包含针对此漏洞的补丁。
参考信息
- 漏洞编号:CVE-2025-69206
- GitHub安全公告:GHSA-vvxf-wj5w-6gj5
- 官方补丁提交:HemmeligOrg/Hemmelig.app@6c909e5
- NVD数据库条目:https://nvd.nist.gov/vuln/detail/CVE-2025-69206