mcpField
G
genotoxic

genotoxic

github.com/trailofbits测试与质量7.9k3.9k 次安装今天更新
代码仓库

关于 genotoxic

genotoxic 是面向测试改进的技能,结合变异测试、可选的 necessist 检查与代码图分析,将发现归类为误报、缺失单元测试或模糊测试目标。

主要功能

  1. 01结合变异测试与代码图分析
  2. 02识别未被杀死的变异
  3. 03可选检测冗余测试语句
  4. 04按风险归类测试缺口
  5. 05生成 Markdown 分类报告

适用场景

  1. 01为存活变异确定后续测试方向
  2. 02定位单元测试最能发挥作用的位置
  3. 03找出适合模糊测试的复杂入口函数

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/trailofbits/skills --skill genotoxic

安装后在 Claude Code 中输入/genotoxic确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

agents/
openai.yaml
assets/
trail-of-bits-mark.svg
references/
graph-analysis.md
mutation-frameworks.md
triage-methodology.md

详细介绍

Genotoxic

结合变异测试、necessist(删除测试语句)和代码图分析,将发现分类为可采取行动的类别:误报、缺少单元测试,以及模糊测试目标。

适用场景

  • 变异测试发现了存活的变异体,需要进行分类
  • 确定单元测试最能发挥作用的位置
  • 找出需要模糊测试测试框架而非单元测试的函数
  • 利用数据流上下文确定测试改进的优先级
  • 从可采取行动的变异体中筛除无害的变异体
  • 找出表明断言薄弱的不必要测试语句(necessist)

不适用场景

  • 代码库没有现有测试套件(请先编写测试)
  • 纯文档或配置变更
  • 逻辑简单的单文件脚本

前置条件

  • 已安装 trailmark — 如果 uv run trailmark 执行失败,请运行:
    uv tool install trailmark
    

Python snippets: uv run --with trailmark python - (a tool env is not importable)

**不要**以“手动验证”或“手动分析”替代运行 trailmark。请先安装。如果安装失败,请报告错误,而不是改用手动分析。
- 目标语言的**变异测试框架** — 如果框架命令执行失败(未找到或未安装),请按照 [references/mutation-frameworks.md](references/mutation-frameworks.md) 中的说明安装。
**不要**改用“手动变异分析”,也不要跳过变异测试。请先安装框架。如果安装失败,请报告错误,而不是改用手动变异分析。
- **necessist**(可选,推荐)— 如果支持目标语言(Go、Rust、Solidity/Foundry、TypeScript/Hardhat、TypeScript/Vitest、Rust/Anchor),请运行 `cargo install necessist` 安装。
详情请参阅 [references/mutation-frameworks.md](references/mutation-frameworks.md)。
- 已有且能通过测试的测试套件
- **macOS 环境**:每次调用 `mull-runner` 之前运行 `ulimit -n 1024`。macOS Tahoe(26+)默认将文件描述符设为无限,这会导致 Mull 创建子进程时崩溃。详情请参阅 [references/mutation-frameworks.md](references/mutation-frameworks.md)。

---

## 应拒绝的托辞

| 托辞 | 错误原因 | 必须采取的行动 |
|-----------------|----------------|-----------------|
| “所有存活的变异体都需要测试” | 其中许多是无害或等价的 | 编写测试前先分类 |
| “变异测试噪声太多” | 噪声说明你没有进行分类 | 使用图数据进行筛选 |
| “单元测试能覆盖所有情况” | 复杂的数据流需要模糊测试 | 检查入口点的可达性 |
| “死代码变异体无关紧要” | 应删除死代码 | 标记以便清理 |
| “复杂度低 = 风险低” | 边界错误可能藏在简单代码中 | 检查变异体的位置 |
| “工具没安装,我手动分析” | 手动分析会遗漏工具能捕获的问题 | 先安装工具 |
| “Necessist 不是变异测试,跳过吧” | Necessist 能发现变异测试遗漏的问题:测试薄弱 | 如果语言支持,两者都运行 |

---

## 快速入门

```bash
# 1. Build the code graph
uv run trailmark analyze --language auto --summary {targetDir}

# 2. Run mutation testing (language-dependent)
# Python:
uv run mutmut run --paths-to-mutate {targetDir}/src
uv run mutmut results

# 2b. Run necessist (if language supported)
necessist

# 3. Analyze results with this skill's workflow (Phase 3)

工作流概览

Phase 1: Graph Build      → Parse codebase with trailmark
      ↓
Phase 2: Mutation Run     → Execute mutation testing framework
Phase 2b: Necessist Run   → Remove test statements (optional, parallel)
      ↓
Phase 3: Triage           → Classify findings using graph data
      ↓
Output: Categorized Report
  ├── Corroborated         (both tools flag same function — highest value)
  ├── False Positives      (harmless, skip)
  ├── Missing Tests        (write unit tests)
  └── Fuzzing Targets      (set up fuzz harnesses)

决策树

├─ Need to set up mutation testing for a language?
│  └─ Read: references/mutation-frameworks.md
│
├─ Need to set up necessist or find weak test statements?
│  └─ Read: references/mutation-frameworks.md (Necessist section)
│
├─ Need to understand the triage criteria in depth?
│  └─ Read: references/triage-methodology.md
│
├─ Need to understand how graph data informs triage?
│  └─ Read: references/graph-analysis.md
│
└─ Already have results + graph? Use Phase 3 below.

阶段 1:构建代码图并运行预分析

使用 trailmark 解析目标代码库,并在变异测试之前运行预分析。预分析会计算影响范围、入口点、权限边界和污点传播情况,阶段 3 将利用这些信息进行分类。

uv run trailmark analyze --language auto --summary {targetDir}

使用 QueryEngine API 构建图并运行预分析:

  1. QueryEngine.from_directory("{targetDir}", language="auto")
  2. 调用 engine.preanalysis() — 分类前必须运行
  3. 使用 engine.to_json() 导出,以便与变异测试结果交叉比对

如果自动检测出的目标语言不正确,请使用显式语言名称重新运行,或传入逗号分隔的语言列表,例如 python,rust。

完整 API 说明请参阅 references/graph-analysis.md,包括节点映射、可达性查询、影响范围和预分析子图查询。


阶段 2:运行变异测试

选择并运行合适的框架。有关特定语言的配置,请参阅 references/mutation-frameworks.md。

记录存活的变异体。 每种框架的报告方式各不相同,但请提取每个变异体的以下字段:

字段描述
文件路径包含变异体的源文件
行号应用变异的位置
变异类型更改内容(运算符、值等)
状态存活、被杀死、超时、错误

在阶段 3 中仅筛选存活的变异体。


阶段 2b:运行 Necessist(可选)

如果目标语言受支持(Go、Rust、Solidity/Foundry、 TypeScript/Hardhat、TypeScript/Vitest、Rust/Anchor),请运行 Necessist, 以查找不必要的测试语句。此步骤独立于阶段 2 运行,也可以并行执行。

# Auto-detect framework
necessist

# Or target specific test files
necessist tests/test_parser.rs

# Export results
necessist --dump

筛选出删除后测试仍通过的发现项。有关特定框架的配置和标准化记录格式,请参阅 references/mutation-frameworks.md。

使用 references/graph-analysis.md 中的算法,将每项删除映射到一个生产函数。


阶段 3:对发现项分类

对于每个存活的变异体和每项 Necessist 删除项,使用图数据确定其分类类别。Necessist 删除项必须先映射到一个生产函数(参阅 references/graph-analysis.md)。

快速分类(变异测试)
信号类别判断依据
图中没有调用方误报死代码,变异体不可达
只有测试调用方误报测试基础设施,不属于生产代码
日志/显示字符串误报仅影响外观,不影响行为
等效变异体误报尽管发生变异,行为仍未改变
函数简单、圈复杂度低,且无入口点路径缺少测试单元测试很容易编写
错误处理路径缺少测试应有负向测试用例
边界条件(差一错误)缺少测试可考虑使用基于属性的测试
纯函数、结果确定缺少测试易于测试,价值高
圈复杂度高(>10),且可从入口点到达模糊测试目标复杂且对外暴露,应进行模糊测试
解析器/验证器/反序列化器模糊测试目标处理结构化输入
调用方众多(>10)且圈复杂度中等模糊测试目标影响范围大
二进制/线协议处理模糊测试目标模糊测试器擅长测试格式
快速分类(Necessist)
信号类别判断依据
冗余的设置或调试调用误报该语句确实没有必要
无法映射到生产函数误报没有图上下文可用于分类
调用已删除,但没有断言检查其效果缺少测试测试断言较弱
断言已删除,测试仍然通过缺少测试覆盖冗余或不足
映射到圈复杂度高且可从入口点到达的函数模糊测试目标复杂、对外暴露且测试较弱

如果变异测试和 Necessist 都标记了同一个生产函数,则标记为相互印证——这是置信度最高的发现。

详细标准请参阅 references/triage-methodology.md。

用于分类的图查询

对于每个变异体,将其映射到所在的图节点,并使用阶段 1 中预分析的子图(tainted、high_blast_radius、privilege_boundary)进行分类。分类逻辑会检查:没有调用方 → 误报;权限边界 → 模糊测试;圈复杂度高且受污染 → 模糊测试;影响范围大 → 模糊测试;否则 → 缺少测试。

有关 batch_triage 实现和节点映射函数,请参阅 references/graph-analysis.md。


输出格式

生成一份 Markdown 报告:

# Genotoxic Triage Report

## Summary
- Total survived mutants: N
- Total necessist removals: N
- Corroborated findings: N
- False positives: N (N%)
- Missing test coverage: N (N%)
- Fuzzing targets: N (N%)

## Corroborated Findings
| File | Line | Function | Mutation Signal | Necessist Signal | Action |
|------|------|----------|----------------|------------------|--------|

## False Positives
| File | Line | Mutation | Reason | Source |
|------|------|----------|--------|--------|

## Missing Test Coverage
| File | Line | Function | CC | Callers | Suggested Test | Source |
|------|------|----------|----|---------|----------------|--------|

## Fuzzing Targets
| File | Line | Function | CC | Entrypoint Path | Blast Radius | Source |
|------|------|----------|----|-----------------|--------------|--------|

Source 列的值为 mutation、necessist 或 corroborated。

将报告写入工作目录中的 GENOTOXIC_REPORT.md。


质量检查清单

交付前:

  • 已为目标语言构建 Trailmark 图
  • 变异测试框架已运行完毕
  • 已运行 Necessist(如果支持该语言),或注明不适用
  • 已对所有存活的变异进行分类(无未分类项)
  • 已对所有 Necessist 移除项进行分类(如适用)
  • 已识别交叉验证的发现(如果两个工具都已运行)
  • 误报均有明确的理由说明
  • 缺失的测试项包含建议的测试类型
  • 模糊测试目标包含入口点路径和影响范围
  • 已将报告写入 GENOTOXIC_REPORT.md
  • 已向用户告知统计摘要

集成

trailmark 技能:

  • 阶段 1:构建代码图,查询复杂度和入口点
  • 阶段 3:调用方分析、可达性、影响范围

基于属性的测试技能:

  • 涉及边界条件的缺失测试覆盖项
  • 序列化变异的往返/幂等属性

testing-handbook-skills(模糊测试):

  • 模糊测试目标项:使用 harness-writing、cargo-fuzz、atheris

参考文档


首次使用的用户: 从阶段 1(构建图)开始,然后运行变异测试, 接着使用阶段 3 中的快速分类表。

有经验的用户: 直接跳到阶段 3,使用决策树加载 特定的参考资料。

评论

支持 Markdown