Deadbugz:第四种 MCP 攻击类别会潜伏到你信任它为止
关键要点
- 74 分钟内提交 23 个 pull request——2026 年 8 月 10 日,一个 GitHub 账户向互不相关的 AI、MCP 和开发者工具项目提交了活动所需的 PR。没有任何一个通过 GitHub 的评审机制合并,但披露时仍有 4 个处于开启状态(Pillar Security)。
- 三次正常调用之后,元数据被改写——恶意 MCP 服务器维护着一个按客户端计数的调用计数器;在第三次
tools/call请求之后,后续的tools/list与prompts/get响应会指示代理去搜寻 SSH 密钥、AWS 凭证、shell 历史和 Kubernetes 配置,并向用户隐瞒该活动。 - 运行时门控元数据投毒是第四种 MCP 攻击类别——STDIO 命令注入 → 工具投毒 → SHA 固定绕过 → 信任建立后的运行时门控元数据投毒。Deadbugz 的机制之所以在部署前最难检测,是因为服务器能通过初始检查,而恶意载荷只会在客户端建立起使用模式之后才激活。
- 工具定义指纹是防御手段——在审批时点捕获并比对工具定义指纹;对已审批服务器的工具元数据出现的任何变化,一律视为安全事件,要求运维人员重新审批后,被更改的工具才能影响敏感操作。
一个 GitHub 账户在 74 分钟内提交了 23 个 pull request,每个都提供一个能格式化文本、摘要文档的"productivity-suite"MCP 服务器。该服务器在最初三次工具调用中表现完全正常。到第四次,它改写自身元数据,指示所连接的 AI 代理去搜寻 SSH 密钥、AWS 凭证、shell 历史和 Kubernetes 配置——并向运维人员隐瞒这一活动。2026 年 9 月 23 日,Pillar Security 披露了该活动,并以埋在 4 个 pull request 中的投递工件 deadbug-mcp.py 将其命名为 Deadbugz。云安全联盟(Cloud Security Alliance)发布研究简报指出,该攻击在手法上接近此前攻击 73 个 GitHub 仓库(含 Microsoft 的 azure/durabletask)的"Miasma"活动。
本文解析 Deadbugz 机制,将其归位于四类 MCP 攻击的分类体系,并给出堵住缺口的那项控制。它建立在 Plugin4Shell SHA 固定绕过分析与 MCP 安全加固检查清单之上——两者确立的控制恰恰被 Deadbugz 找到了缺口。
机制:按客户端计数的调用计数器
Deadbugz 服务器对外提供两个工具——format_text 和 summarize——功能与名称完全一致。服务器在内存中为 tools/call 请求维护一个按客户端区分的计数器。计数器从零开始,每次普通工具调用加一。当它到达三,后续的 tools/list 与 prompts/get 响应就变了:普通工具文档被替换为一些指令,引导所连接的 AI 代理去读取敏感的本地文件,并指示它向运维人员隐瞒这一活动。
这件事之所以重要,是因为 MCP 的工具定义不是标签。客户端把它们作为上下文提供给模型,帮助模型决定使用哪些工具、执行哪些操作。一个能在安装之后改动这些定义的服务器,可以在不改变工具无害名称的情况下,改掉代理看到的指令。其公开源码声明了 tools.listChanged 这一能力——允许兼容的客户端刷新工具元数据——因此服务器根本不需要客户端重连。它只需通知客户端"工具列表已变更",客户端就会拉取新的、已被投毒的定义。
运行时门控是一种规避研究的技术。简短的检查或有限的自动化测试只会拿到良性元数据。服务器之所以能通过安全评审、沙箱测试与自动化扫描,是因为这些方法都不会在做了三次普通工具调用之后再去看服务器接下来返回什么。Pillar 从公开来源确认了阈值逻辑与被改动的元数据,并通过纯文本的良性请求观测到该远程服务在门控触发后的元数据。
投递路径:看起来很常规的配置变更
该活动的投递机制是向互不相关的仓库提交修改 MCP 配置的 GitHub pull request。在被审阅的 23 个 PR 中,17 个向项目的配置文件添加了远程 MCP 端点(productivity-suite-mcp.onrender.com/mcp);4 个配置 Python 去运行一个隐藏的本地文件(~/.config/.cache/.sys/.deadbug-mcp.py);2 个是目录或清单提交。审阅时 23 个全部未通过 GitHub 的 PR 合并机制合并——19 个关闭、4 个开启——但该投递模式并不需要合并。它只需要一位维护者把配置变更拷贝进自己的环境,或者一位开发者看到 PR 后访问链接的仓库并直接安装该服务器。
账户层面的投递模式是有组织的:同一个公开账户(zellkernel)在 2026 年 8 月 10 日 21:52 UTC 至 23:07 UTC 之间提交的全部 23 个 PR 里,使用了相同的产品名、相同的配置主题和相同的活动标记。该账户在收集时拥有 50 个公开仓库(其中 20 个为 fork),仅 8 月 10 日当天就创建了 21 个仓库。该 GitHub 主页链接到一个 X 主页(@llmgod),后者又回链至该 GitHub 账户——在投递身份与 AI/LLM 相关公开活动之间存在一条公开的、可归属到账户的关联。
这一投递模式扩展了 Plugin4Shell 分析所记录的供应链模式:把基于 PR 的配置变更当作完全绕过市场(marketplace)管控的载体。Plugin4Shell 利用与被固定提交同名的分支来攻破市场的 SHA 固定;Deadbugz 则干脆不使用任何市场——它直接经由开源项目的贡献工作流进入。
四种攻击类别
MCP 安全家族现在有四种不同的攻击类别,各自利用不同的信任边界:
| 类别 | 机制 | 首次记录 | 检测难度 |
|---|---|---|---|
| STDIO 命令注入 | 恶意命令嵌入 STDIO 配置字符串 | 2026 年 4 月,20+ 个 CVE(Practical DevSecOps) | 中等——静态分析可捕获 shell 元字符 |
| 工具投毒 | 良性工具的描述在审批后被更改为操纵代理 | Invariant Labs,2025 年 4 月,WhatsApp 睡眠代理 | 中等——客户端侧的元数据变更检测 |
| SHA 固定绕过 | 以 SHA 命名的分支使市场的固定校验失效 | Plugin4Shell,2026 年 9 月 | 困难——需要在 checkout 之后断言解析到的 HEAD |
| 运行时门控元数据投毒 | 恶意元数据被扣留到第 N 次调用,再经 tools/list 送达 |
Deadbugz,2026 年 9 月 | 最难——部署前测试不越过阈值 |
Deadbugz 的攻击序列与四类分类体系,可视化如下:
每一类攻击都利用同一个结构性缺口:一个在错误的时间做检查、或干脆不做检查的信任机制。STDIO 注入信任未经净化的配置字符串。工具投毒信任工具描述在审批之后不会改变。SHA 固定信任解析到的提交与被固定的名称一致。运行时门控投毒信任测试期间服务器返回的内容就是使用期间会返回的内容。
Deadbugz 之所以部署前最难检测,是因为服务器在检查期间的行为真的无害。恶意载荷并非以静态分析能够标记的方式藏在代码里——它被门控在一个运行时计数器之后,只有客户端建立起使用模式之后才会激活。一支连接服务器、调用一两次 format_text 再检查响应的安全团队,什么问题都看不出。该攻击的设计目标就是通过恰恰这种评审。
为什么现有控制不够
MCP 安全加固检查清单把 12 项控制组织在传输、认证、工具注册、运行时与审计五个层中。Deadbugz 利用的正是工具注册层与运行时层的缺口。该清单的工具注册控制在审批时点验证服务器——在服务器上线前检查工具名称、模式与描述。但 Deadbugz 的工具在审批时点确实无害。运行时控制监视未授权动作,而被投毒的元数据本身并不是一个动作——它是一条指令,把代理引向一个随后由代理执行的动作,而且表面上看仍在代理的授权范围之内。
governed modules 论题——审计日志、速率限制、类型化错误与 kill-switch 架构使治理层成为安全边界——多了一个攻击类别作为证据。Deadbugz 机制从相反方向验证了该论题:一个没有治理控制(没有元数据变更检测、没有工具定义指纹、没有运维可见的"代理看到什么"的差异)的服务器,恰恰是该活动所利用的攻击面。
防御:工具定义指纹
Pillar 的建议具体且可实现:在审批时点捕获并比对工具定义指纹。当 MCP 客户端批准一个服务器时,它会记录服务器返回的每一条工具定义的哈希——名称、描述、输入模式与注解。当服务器随后通知客户端其工具列表已变更(经 tools.listChanged)时,客户端拉取新定义,与指纹比对,并把差异作为安全事件呈现给运维人员。在被重新审批之前,被更改的工具不能影响敏感操作。
这项控制之所以能堵住 Deadbugz 利用的缺口,是因为它不依赖部署前的测试。它监视的是服务器在运行时实际送达的元数据——在信任边界已被跨越之后。无论运行时门控何时触发——三次、三十次还是三百次调用——指纹比对都能捕获元数据改写。该控制同样能捕获更早的工具投毒类别(Invariant Labs 的 WhatsApp 睡眠代理),因为两类攻击共享同一机制:审批后发生变化的工具描述。
对在生产环境运行 MCP 服务器的团队,有四个实施步骤:
- 在审批时点记录工具定义指纹。 对初次连接时服务器返回的每条工具定义做哈希。把这些指纹与该服务器的审批记录一起存入代理的配置管理系统。
- 监视
tools/list与prompts/get响应中的漂移。 当服务器通知客户端工具列表已变更时,拉取新定义并与已存指纹比对。任何差异都标记为元数据漂移事件。 - 对被更改的工具定义要求运维重新审批。 在人类运维审视差异并明确重新批准该服务器之前,被更改的工具定义不能影响代理行为。这把一次无声的元数据改写变成一个可见的安全事件。
- 把敏感文件读取、凭证访问与代码执行关在策略之后——而不是工具元数据之后。 Deadbugz 载荷指示代理去搜寻 SSH 密钥、AWS 凭证与 Kubernetes 配置。这些读取应当是需要显式授权、由策略执行的操作,而不是远程工具元数据所含指令的后果。Shadow AI 代理分析记录了决定"元数据驱动的凭证搜寻是否会被察觉"的运行时控制缺口。
相关阅读
- SHA 固定不是校验:Plugin4Shell 与首例 AI 代理供应链 RCE——第三种 MCP 攻击类别,与 Deadbugz 共享基于 PR 的投递模式和供应链目标
- MCP 安全加固检查清单:1,467 个暴露服务器与封堵它们的控制——12 项控制的基线;工具定义指纹属于工具注册层与运行时层
- MCP 安全:为什么 20 万个漏洞实例使 governed modules 成为采购标准——Deadbugz 所验证的 governed modules 论题:没有治理控制的服务器就是该活动所利用的攻击面
一家中端市场 B2B 分销商运行着一个采购代理,通过 MCP 模块连接 NetSuite、BigCommerce 和三个供应商目录。团队的安全评审会连接每个新 MCP 服务器、调用其工具两次并检查响应。Deadbugz 能通过这样的评审。团队在其 MCP 客户端配置中加入了工具定义指纹——每个服务器的初始工具定义在审批时做哈希,tools/list 响应被监视漂移,被更改的定义会在该工具影响代理行为之前触发运维重新审批门。下一场元数据投毒活动将变成一个被标记的差异与一次评审,而不是一次凭证外泄。
申请一次定范围的构建。 一周调研。你将获得系统清单、工作流映射和确定的范围——无论是否与我们合作构建。
想为您的系统构建这个吗?
这里的每份文档都来自真实的生产工作。如果您有目标系统和工作流想法,我们可以在一周内确定范围。
申请定制开发为期一周的发现阶段。您会拿到系统清单、工作流地图和固定范围——无论您最终是否与我们合作开发。