抽象技术插图,背景为浅暖灰色:中心偏左是一块高大的米白色设置面板,上面带有淡淡的横线行,其最下方的字段中包含两个小型嵌套的青色尖括号标记,一个套在另一个里面。一条细青色线条从面板延伸到右侧一个扁平的青灰色服务器块;第二条琥珀色线条从嵌套标记处出发,越过面板边框并到达同一个块,一个小琥珀色方块标示出两条路径分叉处的连接点。第一个服务器块后面还有第二个更暗的服务器块。画面为扁平矢量几何风格,带有柔和阴影和充裕的留白;没有文字、字母、数字、人物或组织徽标出现。OrcaRouter 徽标合成在画面下方白色条带的右下角。
AI Safety Incidents

Zammad 的 AI Agent RCE:一个嵌套模板标签,一个单字母修复

作者

Alistair Wren

发布日期

最新模型 · 20查看全部模型 →
基准测试:Artificial Analysis · 每日更新
返回全部文章

Zammad 是一款开源帮助台,于 2026 年 8 月 4 日发布了 7.1.2 版本,带来十八项安全修复;其中列出的第一项修复了其 AI Agent 功能配置字段中的远程代码执行漏洞。该漏洞为 CVE-2026-84462,同日在 GitHub 安全公告 GHSA-gp3x-9xm8-rcj6 中披露,受影响范围是所有版本至 7.1.1(含 7.1.1)的自托管安装。能够创建或编辑 AI Agent 的管理员可以将特制文本输入该代理的某个字段,绕过旨在中和它的过滤器,并在托管 Zammad 的服务器上执行任意命令——用公告中的话说,这有可能“读取、修改或销毁该服务器上存储的所有数据”。无需其他用户采取行动:公告称,“受影响 AI Agent 下次处理工单时,恶意代码会自动运行”。GitHub 在 CVSS 4.0 中将其评为高危,评分为 8.6。该记录、其严重性和危害标签,以及围绕其提交的条目,均保存在Orca AI Incident Archive中,该档案将本次事件与系列其余部分一并列出。

该公告所确立的内容

2026年8月4日发布的 GitHub 安全公告内容简短,但对机制和前提条件的描述异常具体。公告称,一个“保护 Zammad 的 AI Agent 配置的安全过滤器”“可通过向 AI Agent 的某个字段输入特制文本绕过”,并准确指出了行为主体:“拥有创建或编辑 AI Agents 权限的管理员可利用此漏洞,在托管 Zammad 的服务器上执行任意命令。”受影响范围记录为最高至 7.1.1(含),修复版本为 7.1.2。致谢的报告者为 colinthebomb1;发布账号为 fliebe92。该公告未发布任何概念验证或漏洞利用细节。

GitHub 将该漏洞评为“高危”,在 CVSS 4.0 中评分为 8.6,向量为 AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H,且无范围变更。解读下来,这意味着该漏洞可通过网络以较低复杂度触达,无需任何攻击前置条件,也无需用户交互,但利用者必须已在应用内部拥有高权限,并且会对 Zammad 实例本身的机密性、完整性和可用性造成高影响。该公告列出了三类弱点:CWE-20,输入验证不当;CWE-94,代码注入;以及 CWE-1336,即模板引擎类弱点,MITRE 将其定义为未能对特殊语法进行中和处理,“这些语法在被引擎处理时可能被解释为模板表达式或其他代码指令”。

这个修复改动了一个字母

公开修复是提交 e3b0c8df91ad2108c8305be23e8fe6f73fb9718d,提交信息为“Maintenance: Improve ERB sanitizer”。GitHub 记录的作者日期为 2026 年 7 月 7 日,提交日期为 2026 年 8 月 3 日,比安全公告和发布早一天。它涉及两个文件:lib/erb_sanitizer.rb 的一行,以及规范中新增的十四行。

{{1}}这一行{{/1}}就是整个修复。escape_tag 方法原先使用 Ruby 的 sub,它会替换字符串中某个模式的第一个匹配项;现在改用 gsub,它会替换所有匹配项。两个版本中的替换结果相同:写成 <% 的起始标记会变成 <%%,这种双写形式会被 ERB(Ruby 的模板引擎)渲染为字面文本,而不会被求值。该安全公告未指明是哪个 AI Agent 字段承载该模板;该提交则指出了本应让该模板失效的过滤器。

A dark HTML card titled 'One line, one letter', kicker 'Zammad fix commit e3b0c8f', subtitle 'lib/erb_sanitizer.rb, method escape_tag, authored 7 July 2026 and committed 3 August 2026 - one day before disclosure'. Two code panels: BEFORE, in amber, shows a red minus beside tag.sub with the opener arguments and the note 'Replaces the first opener only'; AFTER, in cyan, shows a green plus beside tag.gsub and the note 'Replaces every opener'. A second panel headed 'WHY ONE LETTER MATTERED' shows the payload, a literal opener followed by an evaluating tag, arrowed to the same string with the first opener doubled, and explains that the inner tag is never touched. A third row headed 'REGRESSION SPEC, SAME COMMIT' shows the two nested payloads the added tests cover, with the note 'Both must render as literal text, not evaluate'. A footer names commit e3b0c8df91ad2108c8305be23e8fe6f73fb9718d and says the card was rendered by OrcaRouter with no vendor logos. The OrcaRouter logo is composited in the bottom-right corner.

使用 sub 时,字符串中只有第一个起始标记被化解。一个在第一个起始标记后紧跟第二个起始标记的载荷能通过过滤器:<%<%= 1 + 1 %> 会变成 <%%<%= 1 + 1 %>,此时 ERB 将前面的起始标记作为文本输出,然后对内部标签求值。同一提交中添加的回归测试规范直白地指出了这个手法——“将嵌套的起始标记夹带进单个标签内(转义所有起始标记的绕过)”——并断言 <%<%= 1 + 1 %> 和双重嵌套的 <%<%<%= 1 + 1 %> 都必须渲染为字面文本。该测试规范是对过滤器如何被绕过的最清晰的公开说明,因为安全公告本身没有提供任何说明。

这个 bug 的形态是通用的,而非 Zammad 的怪癖:一个在首次匹配后便停止的转义器,会被任何携带其所剥离序列之第二个嵌套副本的输入所击破。提交信息将这处改动称作维护性工作,而这正是单字符加固补丁通常的出行方式——也正因如此,承载警告的才必须是安全公告,而非那份 diff。

从发布安全公告到进入 NVD:七周

NVD 于 2026 年 9 月 25 日发布了 CVE-2026-84462 的记录,此时距该公告发布已过去七周,并于 9 月 28 日对其进行了最后修改。该记录被标记为"Deferred"(已推迟),这意味着该机构尚未发布自身的分析;其指标区块将 8.6 分作为次要指标归因于 security-advisories@github.com——这是 GitHub 作为 CVE 编号机构(CNA)给出的评分,而非 NVD 的独立评估。同一记录完全没有 CPE 配置,因此并未将该漏洞映射到带版本的产品标识符。

这两个细节对任何通过订阅源而非发布说明来跟踪自托管软件的人来说都很重要。修复方案在8月4日就已公开并可操作;机器可读记录直到9月25日才出现;而且即便到了那时,它出现时仍缺少基于 CPE 的扫描器所匹配的产品标识符。在长达七周的时间里,关于该漏洞的权威说明一直是供应商的公告和供应商的发布说明。

A dark HTML timeline card titled 'From commit to CVE record', kicker 'Zammad 7.1.2 - CVE-2026-84462', subtitle 'Five dated points, taken from the fix commit, the GitHub advisory, the Zammad release note and the NVD API'. Five rows: 7 July 2026, fix authored in commit e3b0c8f with the message 'Maintenance: Improve ERB sanitizer'; 3 August 2026, fix committed one day before disclosure; 4 August 2026, GitHub advisory GHSA-gp3x-9xm8-rcj6 published and Zammad 7.1.2 shipped the same day with 18 security fixes; 25 September 2026, NVD publishes CVE-2026-84462 with status Deferred and no CPE configuration, 52 days after disclosure; 29 October 2026, FIRST EPSS read at 0.28 percent probability in 30 days, 20th percentile. An amber rule below reads 'The advisory and the CVE record describe the same flaw. The first was actionable on 4 August; the second arrived as a machine-readable record 52 days later.' A footer credits GitHub, Zammad, NVD and FIRST, and says the card was rendered by OrcaRouter. The OrcaRouter logo is composited in the bottom-right corner.

什么是已确立的,什么不是

已确认:安全公告、修复版本、CVSS 评分和代码变更均来自 Zammad 和 GitHub 的公告数据库,且彼此一致。NVD 的记录复述了编号机构的描述,未添加其自身的分析。档案据此将该条目的置信度评为 A,且该事件无可争议。

尚未证实,也未有记录:公告中没有概念验证,也没有在野利用的报告。FIRST 的 EPSS 在 2026 年 10 月 29 日发布的评分中,给 CVE-2026-84462 打出未来三十天内 0.28% 的利用概率,处于第 20 百分位。该档案未记录任何实际损害,并将该条目归为中等严重性——低于公告自身的高危等级。这些是回答不同问题的不同工具:漏洞可能允许发生什么,与已知实际发生了什么;本文同时报告两者,而不试图将它们调和。

独立佐证很有限。检索该 CVE 的相关报道,得到的是转载编号管理机构原文的漏洞数据库,再加上 Zammad 自身的发布说明;似乎没有任何新闻媒体独立报道过该漏洞。这是关于该记录本身的一项发现,而非对它的批评:一个需要管理员账户才能触发的服务台远程代码执行漏洞,并不是那种能引来媒体报道的事件,而独立记述的缺失,本身也正是该记录所记载的内容之一。

谁可能触发它,以及什么发生了变化

Zammad 于 2026 年 8 月 4 日发布的 7.1.2 版本发布说明列出了该版本修复的十八个漏洞,并将 AI Agent 模板绕过漏洞列在首位。对于托管客户,说明中写道:“无需采取任何操作。我们的团队已经为您的实例打上补丁并确保其安全。”对于自托管安装,措辞更为直接:“我们强烈建议立即升级到最新版本的 Zammad,以确保您的系统受到保护。”该公告未提供任何变通方法,记录中除升级外也未给出任何缓解措施。

A dark HTML card titled 'Who can pull the trigger', kicker 'CVE-2026-84462 - preconditions', subtitle 'From the GitHub advisory and the Zammad 7.1.2 release note; the score and exploitation figure are labelled separately'. Left column headed 'THE ATTACKER MUST' lists three conditions: hold administrator rights inside Zammad, specifically permission to create or edit AI Agents; reach the agent configuration over the network; supply no interaction from any other user. Right column headed 'THE PAYLOAD THEN' lists three consequences: runs on the server that hosts Zammad, not in a browser; fires the next time the agent processes a ticket; can read, modify or destroy all data on that server, according to the advisory. A statistics strip reads 8.6 CVSS 4.0 High, PR:H high privileges required, UI:N no user interaction, C:H I:H A:H all three impacts high, and 0.28 percent EPSS on 29 October 2026. Three flags below read Affected: Zammad up to and including 7.1.1; Fixed: 7.1.2, released 4 August 2026; Stated remedy: upgrade, no workaround published. A closing panel notes that the advisory publishes no proof of concept and that the regression spec in the fix commit is the clearest public description of the bypass. A footer says hosted instances were already patched and self-hosted installations must reach 7.1.2. The OrcaRouter logo is composited in the bottom-right corner.

权限要求值得比该向量所体现的更仔细地审视。PR:H 意味着攻击者需要拥有相当大的访问权限,漏洞才有用;而在这里,这种访问权限就是 Zammad 文档所说、要使用 AI Agents 就必须具备的 admin.ai_agent 权限。在帮助台中,这通常是负责调整分类器、标签器和文本提取器的服务团队主管——不一定是管理服务器的人。公告本身的措辞“拥有创建或编辑 AI Agents 权限的管理员”比“任何人”更窄,但比“root”更宽。如果无法立即升级,缩小持有该权限的人员范围,就能减少可触及该代码路径的人群;这是从向量和文档中推断出的结论,并非供应商公布的补救措施。

没有任何一份主要文档把语言模型放在漏洞利用路径上。该命令是在坐席配置被渲染时,于 Zammad 的 Ruby 进程内执行的;无论是安全公告、代码提交还是发布说明,都没有描述模型生成载荷这一环节。AI Agent 功能提供的是管理员可写、经模板处理的字段,AI 是攻击面而非机制本身。这正是该记录所指出的模式:坐席定义——它的指令、模板和过滤器——就是可执行配置,而编辑它的人是做支持工作的,不是做安全审查的。

Zammad 的补救措施恰如其分且平淡无奇:一处方法变更、两项回归测试,以及一个版本号提升,后者在堵上这个漏洞的同时还堵上了另外十七个漏洞。值得延续下去的是其暴露模型。一个允许支持主管定义坐席的帮助台,也就允许该支持主管编写服务器将要执行的内容,而这两者之间唯一的屏障,是一个必须对它剥离的语法的每一层嵌套副本都判断正确的过滤器。