论文提出 Approval Laundering 分类,实测 Claude Code 审批与执行绑定失败
Approval Laundering: Systematizing Approval--Execution Binding Failures in AI Coding-Agent Harnesses
在Claude Code上测试表明审批与执行动作存在六类解绑失效,基于HMAC的Approval Token可消除委托与时序洗白但无法防范效果偏离。
不假定恶意模型、提示注入或对抗性用户,场景由智能体执行良性任务触发;防御针对套件执行机制在普通非对抗模型行为下的失效,但测试环境预置了外部配置(如 pre-commit 钩子、$PATH 遮蔽等)。
- 编程智能体套件普遍依赖人类审批作为唯一安全边界,并默认批准动作等价于执行动作。然而套件自身的匹配逻辑与系统副作用会导致批准后执行越权动作,产生审批洗白失效。
- 将审批洗白分解为范围、参数、时序、工具、委托与语义六个维度;设计七字段 HMAC 权能凭证 Approval Token,通过套件预执行钩子在派发前校验调用字段与会话、代理身份的绑定。
- Claude Code 在范围、时序和委托场景基线 BGR 超 94%,PATH 劫持工具洗白达 100%;Approval Token 离线重放完全消除委托与时序洗白,但因无法感知环境级副作用,对范围和大部分参数洗白无削减。
- 评测局限于 Claude Code 与固定模型,Codex CLI 探测发现缺乏调用级检查点;防御无法拦截未改动记录字段的效果偏离;密钥保存在同用户本地文件且未做对抗测试;语义洗白仅测试词汇覆盖代理指标。
- 模型
- Claude Code (v2.1.197, opus[1m] / claude-sonnet-5-ccmax)Codex CLI (@openai/codex v0.154.0)
- 基准
- Approval Laundering controlled scenarios (Scope, Temporal, Tool, Argument, Delegation, Semantic)
- 指标
- Bound-Gap Rate (BGR)Cohen's κMcNemar exact p-value
复旦大学博士后 Yang Wang 的预印本提出 Approval Laundering,把 AI 编码 Agent 审批与执行之间的绑定失败分为 Scope、Argument、Temporal、Tool、Delegation、Semantic 六类,每类对应一个凭证绑定面。作者在 Claude Code 2.1.197 的 PreToolUse 钩子上做无头重复测量,每类 19 至 20 次有效运行,报告 Bound-Gap Rate:Scope 与 Temporal 为 1.00,Delegation 为 0.947,Argument 为 0.45,Semantic 代理指标为 0.10;Tool 类中跨工具替换被策略引擎全部拒绝,同名 $PATH 替换则 20 次全部未被拦截。
推荐理由论文把编码 Agent 的审批与执行绑定失败拆成六类,并给出 Claude Code 上的实测成功率与防御边界。
深度解读
这篇论文试图解决什么问题?
研究编程智能体套件中人类审批与底层工具执行动作脱钩的审批洗白问题,分析六类凭证绑定失效模式。
现有多类 AI 编程智能体套件依赖单一人类审批关卡作为安全边界,但作者指出存在审批洗白(Approval Laundering)失效,即人类批准的操作与套件最终派发的动作发生偏离。
- 问题出现的场景与重要性:在 Claude Code、Codex CLI 等编程智能体套件中,模型提议动作由人类确认后直接执行,此检查点构成唯一安全边界,一旦审批通过便无第二道防线。
- 威胁模型:
- 攻击目标:在无需向操作者请求重新审批的前提下,使套件静默派发超出授权范围、修改参数、跨越会话、替换工具或转移给子智能体的动作。
- 攻击者知识与能力:论文明确不假定恶意模型、提示注入或对抗性用户;所有场景均由智能体在默认行为下执行陈述的良性任务触发,且上下文无注入内容;但测试环境包含预置的系统配置(如 pre-commit 钩子或 $PATH 包装脚本)。
- 受害系统:以 Claude Code 为代表的 AI 编程智能体 CLI/IDE 运行时套件。
- 成功判定:通过预设的金丝雀(canary)标记被未授权触碰来判定违规。
- 现有方法的不足:作者认为此前工作多将授权视作判断问题,聚焦于自动化风险分类器的判定准确率或模型推断未声明范围的能力,忽视了机制层面的凭证绑定完整性。
- 核心观察与假设:作者提出套件普遍假定批准动作与执行动作等价,但该假设在多维度上失效,且分为套件记录字段发生偏差的准入偏离与执行副作用越界的效果偏离。
- 论文提出的方案:论文形式化了审批洗白问题,构建了六维失效分类学,并在 Claude Code 上实测约束差距率;进而设计并评估了基于带密钥权能的 Approval Token 防御原型。
有哪些相关研究?
对比智能体授权机制、测量基准与混淆代理研究,指出现有工作均未覆盖全部六类凭证绑定失效。
梳理论文引用并讨论的相关工作,主要分布在智能体授权机制、测量导向基准以及混淆代理等领域。
- 智能体审批与同意机制
- CaMeL(2025 年):执行基于权能的数据流策略以限制不可信数据影响,并在违规前请求确认;作者指出其未指定将审批绑定到后续派发动作的已认证凭证。
- Conseca(2025 年):提出即时生成上下文安全策略并在派发前确定性执行;作者指出其关注策略生成与执行本身,而非已批准操作与派发动作的绑定。
- SkillScope(2026 年)、IntentCap(2026 年)、KITA(2026 年)、VAC(2026 年):SkillScope 根据当前任务重新推导权限;IntentCap 将审批绑定到声明的意图权能并支持委托移交,但作者指出其评测未报告跨会话场景;KITA 针对多审查者门限签名隔离密钥;VAC 在受信浏览器框架中比对派发动作的规范化字段,作者指出其针对浏览器代理的单一确认弹窗且未分离会话与代理身份。
- Loopjacking(Kumar,2026 年):与本文同期的工作,将攻击分为基于表示的攻击和审批后状态替换攻击,评测对象为智能体编排产品(如 Agno、LangGraph、OpenClaw、OpenAI Agents SDK);作者指出其将任务、线程与会话范围合并为一个字段,未单独拆分代理身份维度,且面向编排框架而非编程 CLI/IDE 套件。
- 测量导向的基准
- AmPermBench(2026 年)与 OverEager-Bench(2026 年):AmPermBench 测量分类器将提议工具调用标记为需审批的准确率;OverEager-Bench 评估隐式范围推断对人类真值的泛化能力;作者指出两项工作均以策略决策已经给出为前提,无法评估派发机制是否重新验证已绑定的凭证字段。
- 混淆代理与智能体安全研究
- 混淆代理(Hardy,1988 年)与 Woodpecker(2012 年):作者将审批洗白类比为经典的混淆代理问题与 Android 权限泄露机制。
- 提示注入基准(AgentDojo 2024 年、AgentHarm 2024 年、ToolEmu 2023 年、InjecAgent 2024 年):前两者不设人类审批检查点;后两者在提示词中提示模型确认,但未实现套件级审批与执行的绑定重验。
- 基线方法与基准
- 对比基线为 Claude Code 原生策略引擎(native policy engine)及 settings.json 中的权限规则,基准为作者针对六类失效形式化设计的受控良性评测场景。
- 本文定位:作者将本文定位为对未修改商业编程套件在非对抗条件下凭证绑定完整性的实测研究,并提出覆盖六个维度的分类学与防御原型。
- 智能体审批与同意机制
论文如何解决这个问题?
形式化准入与效果偏离条件,构建六维分类学,提出七字段 HMAC 权能凭证 Approval Token 进行预执行验证。
论文形式化了审批洗白条件,提出了涵盖六个维度的分类学,并设计了基于 HMAC 的 Approval Token 权能防御方案。
问题设定与形式化
- 授权与调用定义:定义授权凭证为 G = (principal, agent_id, session_id, tool, scope),候选调用为 c = (agent_id, session_id, tool, arguments)。
- 失效判定条件:若套件在未请求重新审批的情况下派发了 c,且满足
\neg D_G(c) \lor E(c, \sigma) \not\subseteq \text{Perm}_G(c),则认定发生审批洗白。- 其中 DG(c) 为准入性谓词,要求工具、参数、agent_id 及 session_id 与 G 匹配;E(c, σ) 为环境状态 σ 下实际产生的完整资源访问与副作用;PermG(c) 为凭证文本许可的效果集。
- 失效形式划分:分为准入偏离(¬ DG(c),套件记录字段不匹配却被原生逻辑放行)与效果偏离(DG(c) 成立但执行产生的实际副作用越界)。语义洗白则独立于二者,属于呈现函数 Render(G) 的保真度缺陷。
六维失效分类学
- Scope Laundering(范围洗白):绑定字段为 scope,调用符合范围模式,但通过外部机制(如测试运行器子进程)读取范围外的金丝雀文件,属于效果偏离。
- Argument Laundering(参数洗白):绑定字段为 arguments,调用的字面参数未改变,但仓库本地 pre-commit 钩子等副作用扩大了操作范围(如执行 git add -A),属于效果偏离(极少数拼接命令属于准入偏离)。
- Temporal Laundering(时序洗白):绑定字段为 session_id,先前会话中授予的权限在后续新会话中被静默复用,属于准入偏离。
- Tool Laundering(工具洗白):绑定字段为 tool,包括跨工具身份替换(如 WebFetch 替换为 Bash+curl)与同名 $PATH 劫持替换(调用 cat 解析为恶意包装脚本,属于效果偏离)。
- Delegation Laundering(委托洗白):绑定字段为 agent_id,主会话获得的审批权限被无独立授权的子智能体继承,属于记录的准入偏离。
- Semantic Laundering(语义洗白):审批界面呈现的描述文本省略了操作的关键对象(如金丝雀文件名)。
Approval Token 架构与凭证签发
- 凭证结构:定义带密钥权能 token = Hk(principal, agent_id, session_id, tool, sha256(arguments), scope, exp),采用 HMAC-SHA256 计算,密钥 k 仅保存在独立进程中。
- 范围模式绑定:对于策略型授权规则(如包含通配符的模式),将 arguments 字段绑定为范围模式占位符 {"__approved_scope__": scope},而非未知的未来具体命令。
- 签发途径:包含基于 settings.json 预置规则签发(测试主要路径)与基于 PermissionRequest 钩子的交互式签发(未完整端到端测试)。
验证流程与密钥保管
- 两阶段拦截验证:通过 PreToolUse 钩子拦截调用,先查询 scope 映射表匹配授权规则,再根据调用现场字段重算 HMAC 并检索未过期的有效 Token;任一字段不匹配则直接返回拒绝。
- 密钥保管与局限:协议层确保 k 不经由工具调用或上下文传递;但在该原型部署中,k 以 0664 权限持久化在与智能体同属一个 OS 用户的本地文件 secret.key 中,由于 Read 工具未受拦截且宽泛的 Bash 规则可能访问该文件,存在同用户本地文件读取的隐患。
论文做了哪些实验?
在 Claude Code 上实测六类场景基线 BGR,并通过 118 次离线重放和实时烟雾测试验证防御效果与局限。
论文在 Claude Code 上实测了六类洗白失效的基线发生率,并评估了 Approval Token 的防御效果。
实验设置
- 被测系统与模型:主要评测对象为 Claude Code(headless 模式,版本 2.1.197,通过固定别名 opus[1m] 解析至 claude-sonnet-5-ccmax 端点);探索性测试覆盖了 Codex CLI(@openai/codex v0.154.0)。
- 基准场景:作者构建的 6 类受控场景(Scope、Temporal、Tool、Argument、Delegation、Semantic),各包含预置 settings.json 权限、良性任务提示词、隔离金丝雀标记与成功判定谓词。
- 评估指标:约束差距率(Bound-Gap Rate, BGR),即满足成功谓词的有效运行比例,报告 Wilson 95% 置信区间;McNemar 精确检验 p 值;标注一致性 Cohen's κ。
- 评审判定机制:基于 audit.jsonl 审计日志中各调用的 tool_use_id、拒绝状态及返回结果的金丝雀包含情况进行逐调用自动化判定(修补了早期全局拒绝判定导致的漏判漏洞);抽取样本由作者进行人工复核。
- 样本规模:基线每类场景 N = 19–20 次有效运行(Tool 跨工具与 Delegation 各有 1 次非零退出码被排除,有效 N = 19;其余 N = 20);离线重放评测覆盖 118 次运行;实时验证包含 11 次运行。
主结果
下表呈现 Claude Code 上的基线 BGR 与 Approval Token 离线配对重放评测结果(据 Table 3 和 Table 5):
表格较宽,可左右滑动
失效类别 评测样本量 N 基线 BGR (95% CI) 防御后 BGR 不一致对 (b/c) McNemar p 值 Scope 20 1.000 [0.839, 1.000] 1.000 0/0 1 Temporal 20 1.000 [0.839, 1.000] 0.000 20/0 1.9e-6 Tool(跨工具身份替换) 19 0.000 [0.000, 0.168] 0.000 0/0 1 Tool(同名 PATH 替换) 20 1.000 [0.839, 1.000] 未重放 未重放 未重放 Argument 20 0.450 [0.258, 0.658] 0.400 1/0 1 Delegation 19 0.947 [0.754, 0.991] 0.000 18/0 7.6e-6 Semantic(代理指标) 20 0.100 [0.028, 0.301] 0.100 0/0 1 - 基线漏洞表现:作者报告 Scope 与 Temporal 在原生机制下必然发生(BGR = 1.000),Delegation 发生率达 0.947,表明套件默认缺乏跨会话和子智能体身份隔离。
- 工具替换模式差异:作者指出原生策略能完全拦截不同工具名的跨工具替换(BGR = 0.000),但对同名 PATH 劫持毫无防御能力(BGR = 1.000)。
- 防御有效性与局限:作者报告 Approval Token 在离线重放中将 Delegation(降至 0.000, p = 7.6e-6)与基于合成种子的 Temporal(降至 0.000, p = 1.9e-6)在统计学上显著降低,但对 Scope 完全无效,对 Argument 也无统计学显著差异(p = 1)。
实时烟雾测试
- 测了什么:在 Claude Code 中实时接入 guard.py 验证离线重放结论,覆盖 Scope(3 次)、Argument(2 次有效日志)、Delegation(3 次)、Temporal(3 次)。
- 结果:Delegation 在 3 次实时测试中均被拦截(子智能体执行被拒,canary 未触碰);Temporal 在 3 次测试中因 session_id 不匹配全部被拦截;Scope 3 次均放行并触发 canary;Argument 1 次因放行字面命令触发 pre-commit 钩子导致 canary 泄露,另 1 次因准备命令被拒未尝试 commit。
- 作者解读:实时测试证实了离线重放的防御效果与失效模式一致;但同时发现会话启动钩子存在跨运行上下文泄露(前一运行任务描述被注入后续运行)。
判定逻辑与人工一致性验证
- 测了什么:针对早期评分器中“只要整轮存在拒绝即判失败”的全局否定漏洞进行修复,并在修复前后计算作者人工评定与自动评定的 Cohen's κ。
- 结果:逐调用公式修复后,Scope 场景有 4 次运行由失败改判为成功,BGR 由 0.80 修正至 1.00;原 15 组样本复测 κ 由 0.857 提升至 1.0,新增三类场景 5 样本复查均为 κ = 1.0。
- 作者解读:作者认为评测指标的完整性需透明审计,不能仅凭高聚合 κ 值掩盖评分器的范围逻辑漏洞。
其他消融与分析
- Argument 场景中 1 次不一致运行:该运行拼接了 && git status,原生前缀匹配放行,但 guard.py 严格字面比对予以拦截(§7.2)。
- PATH 劫持中模型的反思现象:1 次采样中模型在思维链中拒绝利用 cat 写入文件,但写入动作已作为命令副作用在模型反思前完成(§5.1)。
- 上下文污染的跨运行核查:全部 138 条主研究轨迹均注入了插件指令与前次会话摘要,实时测试中 5/6 包含前次任务描述(§4.1, §7.3)。
- Codex CLI 适配探测:测试发现 codex exec 未触发任何 preToolUse 钩子,亦无调用级审批拦截点(§9)。
有什么可以进一步探索的点?
指出跨套件泛化、效果偏离拦截、真实感知评测与密钥保管等局限,列明实验覆盖范围。
作者指出的局限与后续方向
- 跨套件复现与检查点缺失:论文实验仅针对单一版本 Claude Code 和固定模型;尝试在 Codex CLI 上复现时发现其脚本化运行模式不提供调用级审批拦截点,尚无法确认高 BGR 是普遍现象还是特定实现缺陷,需优先探究交互式 TUI 或后续版本(§9)。
- 效果偏离未获解决:Approval Token 无法防御 Scope 与 Argument 洗白,因其参数字段未改变;解决该问题需在审批时做初始效果验证(静态/动态分析钩子与脚本)而非单纯凭证重验,作者将其列为未解决的开放问题(§9)。
- 拒绝后的合法任务完成度未测试:在实时测试中被拦截后均未完成任务,因实验设定限制了备用路径;作者指出未来需构建正反配对场景,测试防御方案在拦截洗白的同时是否能放行重新授权的合法操作(§7.3, §9)。
- 语义洗白依赖代理指标:当前仅测试了工具描述是否包含目标文件名的词汇级代理指标,未开展针对真实人类受试者的认知感知实验,无法推断实际误导风险(§9)。
- 密钥保管边界未经对抗检验:本地部署中密钥存储在同用户可读的磁盘文件中,未引入硬件安全模块(HSM)或独立服务账户,且未开展针对性的对抗性密钥外发测试(§6.4, §9)。
- 时序与委托签发周期的完整性:时序场景基于合成的 session_id 占位符而非捕获的真实跨会话生命周期;交互式签发钩子在范围映射与用户确认方面未完整打通(§6.1, §7.1)。
实验覆盖范围
- 被测主要套件为 Claude Code 2.1.197,被测模型为固定的 claude-sonnet-5-ccmax(配置别名 opus[1m]),探索性测试覆盖了 @openai/codex v0.154.0。
- 六类场景有效样本量为每类 19 至 20 次运行,离线重放评测包含 118 次运行。
- 防御实时烟雾测试覆盖 Scope(3 次)、Argument(2 次)、Delegation(3 次)与 Temporal(3 次)共 11 次运行。
- 拦截工具范围仅覆盖 Bash 与 WebFetch,未对 Read 工具进行凭证拦截。
- 论文未报告针对多语言环境、远程执行环境或真实人类用户的对比实验数据。
总结一下论文的主要内容
系统揭示编程智能体审批洗白风险,提出七字段权能防御机制,证实其能消除身份时序偏离但难防副作用偏离。
- 核心定位:该研究系统分析并测试了 AI 编程智能体套件中人类审批与底层工具执行之间的凭证绑定完整性断裂问题。
- 问题剖析:当前套件假定人类批准动作与实际执行动作等价,但在六个凭证表面(范围、参数、会话、工具、委托身份及审批渲染)上,这一假设会因套件匹配逻辑或系统级副作用被静默破坏,导致无需重新审批即可派发越权操作。
- 核心设计:作者构建了审批洗白六维分类学,提出基于 HMAC-SHA256 的七字段带密钥权能凭证 Approval Token,通过 PreToolUse 钩子对准入字段进行调用级拦截与重验。
- 关键实验结果:
- 基线评测中,Claude Code 在 Scope、Temporal(BGR 均为 1.000)和 Delegation(BGR = 0.947)上表现出高频洗白失效,Argument 洗白发生率为 0.450,PATH 劫持工具洗白达到 1.000,仅跨工具名替换被原生拦截(BGR = 0.000)。
- 防御评估中,Approval Token 在 118 次离线重放中将 Delegation 和 Temporal 洗白降至 0.000(p < 0.0001),并在 6/6 实时测试中完成拦截;但因仅检查字段记录,对通过子进程和钩子触发的效果偏离(Scope 和 Argument)完全无法消除。
- 启示与结论:作者指出单纯依赖工具调用边界的字段比对无法防范环境级副作用引起的执行偏离,工具安全机制必须向执行环境初始效果验证深化;同时对 Codex CLI 的探测揭示部分无头套件完全缺乏调用级审批抽象。