关于 trailmark-finding-triage
使用 Trailmark 图证据对单个候选代码问题进行安全分诊,帮助审计人员评估可达性与影响,并标明仍需人工审查之处。
主要功能
- 01规范化问题输入
- 02将问题绑定到图节点
- 03分析入口点可达性
- 04检查污点与信任边界
- 05生成结论和证据包
适用场景
- 01分诊静态分析结果
- 02检查函数是否可由入口点到达
- 03在编写 PoC 前整理证据
- 04确定可疑代码问题的优先级
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ trailofbits/ skills --skill trailmark-finding-triage安装后在 Claude Code 中输入/trailmark-finding-triage确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
agents/openai.yamlassets/trail-of-bits-mark.svgreferences/input-normalization.mdoutput-format.mdquery-recipes.mdscripts/evidence_packet.pytest_evidence_packet.py详细介绍
Trailmark Finding Triage
为单个候选发现构建简洁的图证据包。本技能用于判断受影响的代码是否可达、哪些图证据支持或削弱这一主张,以及在判定问题可利用之前还需要进行哪些人工审查。
适用场景
- 在投入时间编写 PoC 之前,对一项静态分析结果进行分类
- 检查人工发现的问题是否可从入口点到达
- 为 PoC 工作构建证据包
- 审查人工审计中发现的单个可疑函数
- 决定是否应提升某个问题的优先级、降低其优先级,或将其视为更广泛链分析的一部分
不适用场景
- 多个较弱的发现可能组合成更强的攻击链。请改用链分析或组合工作流。
- 用户需要完整审计。请改用审计或设计审查工作流。
- 用户需要验证已知问题的修复情况。请改用修复审查工作流。
- 目标是 PR 或分支差异。请结合
graph-evolution使用差异审查工作流。 - 尚无具体发现、函数、文件/行号或可疑汇点。请先使用发现类技能。
应当驳斥的借口
| 借口 | 错误原因 | 必须采取的行动 |
|---|---|---|
| “扫描器标记为高严重性,所以显然可达” | 静态分析发现需要结合图和代码上下文才能提升优先级 | 将发现关联到图节点,并检查入口点路径 |
| “没有入口点路径就意味着不可能” | 这可能是解析器、代理或动态分派的局限 | 将这一局限与可达性分开报告 |
| “路径上有身份验证检查,所以问题是安全的” | 该检查可能验证了错误的条件,也可能被其他路径绕过 | 将验证和身份验证视为审查目标,而非安全性证明 |
| “只要有一条可达路径,就足以声称能编写 PoC” | 该路径仍需满足攻击者可控输入和兼容的前置条件 | 将图可达性与可利用性分开判断 |
| “这大概是一条攻击链” | 单个发现的分类仅处理一个候选项 | 将相关发现交由组合工作流处理 |
工作流
Finding Triage Progress:
- [ ] Step 1: Normalize the candidate
- [ ] Step 2: Build or reuse the Trailmark graph
- [ ] Step 3: Bind the candidate to graph node(s)
- [ ] Step 4: Analyze reachability, taint, boundaries, and blast radius
- [ ] Step 5: Decide and emit the evidence packet
第 1 步:规范化候选项
接受文件/行号、函数名、SARIF 结果、weAudit 注释、Markdown 发现摘录或人工提出的主张。将其规范化为:
- 标题
- 来源类型
- 文件路径和行号范围(若存在)
- 函数或节点提示
- 疑似来源、汇点或资产
- 声称的影响
如果没有具体的代码锚点,请停止并要求提供一个。
输入处理详情请参阅 references/input-normalization.md。
步骤 2–4 的快捷方式(文件/行发现)
对于文件/行锚点,运行随附脚本。它会构建图并执行一次预分析,绑定每条发现,并以 JSON 格式打印 Graph Evidence 字段:所有匹配节点及主要节点(包含首行的节点,其次选择范围最窄的节点)、每个入口点的信任级别、tainted /
entrypoint_reachable / privilege_boundary / high_blast_radius 成员关系、调用方、被调用方、下游节点,以及 Trailmark 版本。一次调用中传入多条发现,而不是针对每条发现重新构建图。
uv run --no-project "{baseDir}/scripts/evidence_packet.py" --target <dir> --finding <file>:<line>[-<end>] --out evidence.json [--finding ...] [--language auto]
使用 --out 时,完整数据包会保留在磁盘上,stdout 仅包含交付计数。从该文件中读取相关发现记录。不使用 --out 时,stdout 会输出完整数据包。相对锚点可以相对于目标目录或工作目录;如果存在路径歧义,则会拒绝处理。请选择 --path-base target 或 cwd,也可以使用绝对路径。行号必须为正数且按顺序排列;不支持列号语法。如果没有可调用项与之重叠,容器会涵盖模块/类/契约声明。在判断结果前,请检查 binding(精确、嵌套或有歧义)、binding_kind、所有匹配项、不可用的信号以及解析器诊断限制。节点数为零即表示失败。
批处理只共享图构建工作:必须为每条发现分别撰写人工判定。
未绑定到任何节点的发现会返回 bound_node: null 及原因。脚本不会进行任何判断:请阅读绑定代码及其调用方,判断攻击者是否可控;空路径列表应视为需要说明的限制(动态分派、代理、缺少入口点模型),而非证明。对于脚本不接受的输入(函数名、通过 audit-augmentation 处理的 SARIF)以及脚本不会运行的查询(connect_subgraphs),请使用以下步骤。
步骤 2:构建或复用图
使用公开的 trailmark 技能工作流。如果存在新鲜的已导出图或 .trailmark/ 产物,优先复用。否则,使用 language="auto" 或目标的显式语言列表构建图,然后运行 engine.preanalysis()。
记录所用的 Trailmark 版本或功能探测方式。对于仅限 Trailmark 0.4 的 API,使用 hasattr() 或 CLI 帮助检查进行功能门控。
步骤 3:绑定候选项
优先按文件和行重叠进行绑定,然后按函数名加文件进行绑定。如果有多个节点匹配,请列出所有候选项,并选择范围最窄的包含节点作为主要节点。如果没有节点匹配,请报告绑定限制,不要猜测。
SARIF 和 weAudit 用户应复用 audit-augmentation 工作流进行匹配,然后检查带注释的节点。
步骤 4:分析图证据
运行 references/query-recipes.md 中的查询方法:
- 到绑定节点的入口点路径
- 每条路径的信任级别(如可用)
- 在
tainted、privilege_boundary和high_blast_radius子图中的成员关系 - 直接调用方和被调用方
- 高影响下游汇点
- 值得人工审查的同级或邻近节点
不要将图可达性视为可利用性的证明。
步骤 5:判定并交接
给出一项判定:
| 判定 | 含义 |
|---|---|
Promote | 图证据支持可达性及合理影响 |
Needs manual review | 证据有参考价值,但不足以定论 |
Deprioritize | 未发现可达路径,或仅发现可信/内部路径 |
Blocked | 绑定或 Trailmark 分析失败 |
使用 references/output-format.md 编写证据数据包。
将值得编写 PoC 的已提升问题交接给用户的 PoC 工作流。将相关发现交接给组合工作流。将可复现的根本原因交接给 trailmark-variant-neighborhood、variant-analysis 或自定义 Semgrep/CodeQL 规则工作流。
示例提示词
- “对
src/Vault.sol:148使用 Trailmark 发现项分类;我认为 withdraw 可以绕过余额更新。” - “在我花时间编写 PoC 之前,先对这条 SARIF 结果进行分类:
semgrep:error unchecked-transfer,位于contracts/Bridge.sol第 91 行。” - “这段报告摘录声称攻击者可以触发
parse_packet。请构建 Trailmark 证据包,并告诉我还缺少什么。”