mantis-report

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Reporter (/mantis-report)

报告生成器(/mantis-report)

System Goal

系统目标

Security Reporting Expert. Synthesizes complex, technical finding logs into a high-quality, human-readable review packet for developers and stakeholders.
安全报告专家。将复杂的技术漏洞发现日志整合为高质量、易读的审查报告包,供开发人员和利益相关者使用。

Command Definition

命令定义

  • Command:
    /mantis-report
  • Description: Generates a human-readable security review packet containing confirmed findings and exploit chains.
  • 命令:
    /mantis-report
  • 描述: 生成包含已确认漏洞发现和利用链的易读性安全审查报告包。

Input/Output Contract

输入/输出约定

  • Reads:
    • workspace/findings/*.json
      (all active finding files for this pass).
    • workspace/archive/findings_pass_*/*.json
      (archived findings from prior passes) and legacy
      workspace/archive/loop*_findings/*.json
      . The report is a campaign-wide view: this pass's full findings plus carried-forward findings that prior passes stopped retrying (e.g. hit the retry cap) so they do not vanish from the report.
    • workspace/.mantis_state.json
      (to track current loop pass, and to read
      vcs_info
      and
      active_snapshot
      {
      root
      ,
      snapshot_id
      ,
      snapshot_pinned
      } for provenance).
    • Per-finding snapshot provenance fields, all OPTIONAL:
      discovery_commit
      ,
      repro_snapshot_id
      ,
      patch_base_snapshot
      . When any is absent/empty it is rendered as "(not recorded)" — never a reason to drop a finding.
  • Writes:
    • workspace/report/review_packet_pass_<N>_<snapshot_tag>.md
      (pass- and snapshot-tagged markdown report). Falls back to the unsuffixed
      review_packet_pass_<N>.md
      on a legacy pass with no recorded snapshot.
    • Updates copy/symlink at
      workspace/report/review_packet-latest.md
      .
  • Preconditions:
    • Calibrated and reproduced findings exist in
      workspace/findings/
      or
      workspace/archive/
      . The report is a campaign-wide view: it reports the current state of every unresolved finding discovered in this or any prior pass, de-duplicated to each finding's latest state. A confirmed-but-unfixed finding that plan stopped carrying back (e.g. it hit the 2-attempt retry cap) does NOT vanish — it appears here at its most recent archived state.
  • Idempotency Guarantee:
    • Writes to pass-and-snapshot-tagged files. In-place overwrite of
      review_packet-latest.md
      . Re-running the SAME pass on the SAME snapshot updates the same tagged file. Re-running the same pass number on a DIFFERENT snapshot writes a DISTINCT file (the
      <snapshot_tag>
      suffix prevents cross-snapshot overwrite). Legacy passes with no recorded snapshot keep the unsuffixed
      review_packet_pass_<N>.md
      name and overwrite in place, exactly as before.
  • 读取:
    • workspace/findings/*.json
      (本次审查的所有活跃漏洞发现文件)。
    • workspace/archive/findings_pass_*/*.json
      (过往审查的归档漏洞发现)以及旧版
      workspace/archive/loop*_findings/*.json
      。报告覆盖整个审查周期:包含本次审查的完整漏洞发现,以及过往审查中因达到重试上限而停止重试、但未被修复的遗留漏洞发现,确保这些内容不会从报告中消失。
    • workspace/.mantis_state.json
      (用于跟踪当前循环审查次数,读取
      vcs_info
      active_snapshot
      {
      root
      ,
      snapshot_id
      ,
      snapshot_pinned
      } 以记录溯源信息)。
    • 每个漏洞发现的快照溯源字段(均为可选):
      discovery_commit
      repro_snapshot_id
      patch_base_snapshot
      。若任何字段缺失/为空,则显示为“(未记录)”——绝不能因此丢弃漏洞发现。
  • 写入:
    • workspace/report/review_packet_pass_<N>_<snapshot_tag>.md
      (带有审查次数和快照标签的Markdown报告)。若为无快照记录的旧版审查,则回退使用无后缀的
      review_packet_pass_<N>.md
    • 更新
      workspace/report/review_packet-latest.md
      的副本或符号链接。
  • 前置条件:
    • workspace/findings/
      workspace/archive/
      中存在已校准和复现的漏洞发现。报告覆盖整个审查周期:展示本次或过往审查中发现的所有未解决漏洞发现的当前状态,并按每个漏洞发现的最新状态去重。已确认但未修复、且审查计划停止重试的漏洞发现(例如达到2次重试上限)不会消失——将以其最新的归档状态呈现在报告中。
  • 幂等性保证:
    • 写入带有审查次数和快照标签的文件。原地覆盖
      review_packet-latest.md
      。针对同一快照重新运行同一审查次数时,会更新同一标签文件。针对不同快照重新运行同一审查次数时,会写入一个独立文件(
      <snapshot_tag>
      后缀可防止跨快照覆盖)。无快照记录的旧版审查保留无后缀的
      review_packet_pass_<N>.md
      名称,并原地覆盖,与之前的行为完全一致。

Instructions

操作说明

Step 0 — Locator Resolution.
LOCATOR RESOLUTION (before reading ANY target code or artifact):
0. ROLE: If this skill NEVER reads target source (report, calibrate, reflect),
   you are a FINDINGS-ONLY stage: skip steps 2-6; still read active_snapshot from
   state for provenance/annotation; NEVER stop merely because a code root is unset.
1. Determine CODE_ROOT, in this priority order:
   a. If --target_root is passed on THIS invocation, CODE_ROOT = --target_root.
      It is AUTHORITATIVE and OVERRIDES SNAPSHOT_ROOT and the state fallback
      (used when a caller hands you a prepared tree, e.g. a patched shadow).
   b. Else if --snapshot_root (or SNAPSHOT_ROOT) is passed, use it.
   c. Else read state_root/workspace/.mantis_state.json (state_root from
      --state_root if passed, else ./workspace/... relative to the current dir)
      -> active_snapshot.root / .snapshot_id / .snapshot_pinned.
   d. Else (no arg AND no readable active_snapshot): CODE_ROOT = current directory,
      treat snapshot_pinned = false (MODE-OFF). Do NOT stop.
2. SENTINEL CHECK (only if snapshot_pinned is true AND you did NOT take path 1a):
   verify CODE_ROOT/.mantis_snapshot_id exists and equals SNAPSHOT_ID. If missing
   or different -> STOP "snapshot sentinel mismatch". (A --target_root tree (1a) is
   deliberately mutated and is sentinel-EXEMPT.)
3. PATH FIELDS:
   - SNAPSHOT-RELATIVE (read under CODE_ROOT): code_paths entries; plan target_files
     that are file paths. Strip ONLY a trailing ":<digits>". A code_paths entry
     containing "://" is a URL/endpoint, NOT a file read. A code_paths entry that is
     NOT of the form <existing-path>:<integer> is a non-source LOCATOR
     (symbol/offset/endpoint): only check that the artifact/symbol exists; skip ALL
     line-range and line-existence logic.
   - STATE-RELATIVE (read/write under state_root/workspace, NEVER prefix CODE_ROOT):
     kb_references, repro_file_path, reattack_file_path, helper scripts, report
     files, and all state/findings JSON.
4. Never WRITE under CODE_ROOT when snapshot_pinned is true. Any command that
   compiles, generates, or writes artifacts MUST run in a PRIVATE SHADOW copy
   (mktemp -d from CODE_ROOT), never with cwd=CODE_ROOT. Read-only inspection may
   cd into CODE_ROOT.
5. VCS-METADATA CARVE-OUT: history-log extraction and any VCS diff/blame command
   run in the LIVE repository root (which still has .git/.hg/.repo), NOT CODE_ROOT
   (the snapshot copy strips VCS metadata). Do NOT stop merely because CODE_ROOT
   lacks .git/.hg/.repo.
6. Every shell command uses ABSOLUTE paths and sets its own working directory on
   that call. Do NOT assume the working directory persists between calls.
Then the following FINDINGS-ONLY notes apply to the Reporter:
  • The Reporter is a FINDINGS-ONLY stage (Block A, ROLE step 0): it SKIPS locator steps 2–6, does NOT require or resolve a CODE_ROOT, and NEVER stops because a code root or sentinel is unset.
  • It STILL reads
    active_snapshot
    (
    root
    ,
    snapshot_id
    ,
    snapshot_pinned
    ) and
    vcs_info
    from
    workspace/.mantis_state.json
    for provenance — used to build the header, the top banners, and the output file name.
  • Every path the Reporter touches (
    workspace/findings/*.json
    ,
    workspace/.mantis_state.json
    ,
    workspace/report/*
    ,
    workspace/archive/*
    ) is STATE-RELATIVE and is NEVER prefixed with CODE_ROOT.
Compile a professional Markdown report detailing the verified/reproduced vulnerabilities and exploit chains.
Execute the reporting stage as follows:
  1. Load findings — this pass in full, plus carried-forward open findings (newest-first fold; no script). Build a working set keyed by finding identity, each finding once at its most-recent state:
    SAME-BUG PREDICATE (used for ALL current↔archived dedup, fold, and suppression in this stage; over-reporting is always safe here, hiding a real finding is never acceptable): two findings are the SAME BUG only if EITHER (i) they have the exact same
    id
    (UUID); OR (ii) ALL THREE hold — they share a non-empty
    lineage_id
    , they share a non-empty
    signature
    , AND at least one
    code_paths
    entry compared WITH its trailing
    :line
    (line-inclusive) is identical between them. Otherwise they are DISTINCT — render BOTH. NEVER treat two findings as the same bug on
    lineage_id
    alone or
    signature
    alone: both are coarser than a bug's true identity (basename-derived lineage can link two distinct same-named files; a
    signature
    strips the line number so it collides between distinct same-file bugs), and collapsing on either alone can silently drop a real finding.
    Design note (re-anchoring vs fold):
    mantis-plan
    's re-anchoring (Phase 2) only provides a line hint that steers RE-DISCOVER — it does NOT rewrite the carried finding's
    code_paths
    . A re-discovered finding surfaces at its NEW line on the current snapshot. Because the fold predicate requires a line-inclusive
    code_paths
    match, the re-discovered finding will NOT fold with its ancestor (the line numbers differ). This is SAFE over-reporting — both entries render, the current one shows the new location. A future phase could relax the predicate to path-only matching when BOTH findings carry the same
    signature
    AND
    lineage_id
    AND the ancestor's line is confirmed absent on the current snapshot, but the conservative line-inclusive match is used today to prevent any silent-drop risk.
    1. Read all active
      workspace/findings/*.json
      and add every active finding to the working set, keyed by its
      id
      (UUID) — all remediation statuses, so this pass's
      VERIFIED_SECURE
      /
      MITIGATION_PROPOSED
      fixes still render with their patches in Categories 1/2. NEVER collapse two ACTIVE findings, even if they share a
      lineage_id
      or
      signature
      — keep each active
      id
      as its own entry.
    2. Scan
      workspace/archive/findings_pass_<N>/
      (and legacy
      loop<N>_findings/
      ) in descending pass order. Add an archived finding only if it is still OPEN (see 4) AND NO finding already in the working set is the SAME BUG as it (per the predicate above) AND no earlier (higher-pass) archived copy of the SAME BUG was already added. First copy met = latest state; ignore later same-bug copies in lower dirs. (An archived finding is suppressed ONLY when a genuine same-bug supersedes it; a mere
      lineage_id
      or
      signature
      coincidence does NOT suppress it.)
    3. Supersession fold (Phase 3): When an archived finding IS the SAME BUG (predicate ii) as a current finding, the current finding supersedes it — show a single entry at the current (most-recent) state; do not also render the archived copy. When the predicate is NOT satisfied (different
      signature
      , e.g. a file rename, or
      lineage_id
      absent), render both as separate entries (safe over-reporting, never hiding).
      • Under-reporting safeguard: If the current (superseding) finding FAILS the actionable predicate (step 4 below) but the archived ancestor would have PASSED it (e.g., the ancestor was
        reproduced
        and OPEN, but the current pass's reproduce resulted in
        not_attempted
        due to a transient build/environment failure on the new snapshot), do NOT let the transient downgrade suppress the confirmed-open bug. Instead, keep the ancestor's last confirmed state visible in the report (render it with a note "Open — repro pending on new snapshot") so a previously-confirmed bug can never silently disappear from the report. The current finding's newer metadata (e.g., updated
        code_paths
        line numbers) may still be attached as an annotation, but the verdict/status shown must be the ancestor's last confirmed state, never the transient downgrade.
    4. Actionable / quality predicate (applies to active AND archived): include a finding only if it is an exploit chain (
      constituent_findings
      present, or "Exploit Chain" in title/history) OR
      repro_status
      is
      reproduced
      OR (
      repro_status
      is
      statically_confirmed
      AND it carries empirical execution evidence — an external stack trace, sanitizer trace (ASan/UBSan/MSan/TSan), or crash log). Do not include false positives,
      NON_VIABLE
      ,
      DUPLICATE
      ,
      failed_to_reproduce
      , or ordinary
      statically_confirmed
      findings lacking empirical traces.
    5. Open predicate (archived carry-forward in step 2 only): an archived finding is "still open" if it satisfies (4) AND
      patch_status
      is NOT
      VERIFIED_SECURE
      /
      MITIGATION_PROPOSED
      AND
      status
      is not
      FALSE_POSITIVE
      /
      DUPLICATE
      AND
      production_viability
      is not
      NON_VIABLE
      . (Active findings are loaded regardless of
      patch_status
      so this pass's fixes still appear; archived fixed findings are not re-listed every pass — use the optional "Resolved this campaign" rollup for a cumulative fixed view.)
    6. Scale: process one directory at a time, newest-first; never load the whole archive at once.
    • Severity Filtering: Exclude findings with a priority of
      "LOW"
      from the main report body. You must place these lower-priority issues into a separate, dedicated "Appendix: Low Priority Findings" section at the very end of the report, keeping the main report focused on high-risk issues.
  2. Extract Key Artifacts: For each reproduced finding, extract and format:
    • Header Metadata: Title, ID (UUID), Inferred Exposure, Final Risk Score, and Qualitative Priority.
    • Campaign Provenance: Annotate each open finding with the pass it was first discovered in vs. the current pass (e.g.
      discovered pass 2 · still open as of pass 7
      ), so carried-over findings are visible as such. First-seen = the lowest
      pass_number
      in the finding's
      history
      entries (or the pass_number of the lowest-numbered archive dir that contains it); current state = the copy you kept from the fold above.
    • Duplicate Advisory: If the finding has a
      possible_duplicate_of
      field (set by
      mantis-dedupe
      when a cross-pass candidate was NOT_MATCHED), emit an advisory note:
      Possibly related to finding <UUID> (cross-pass candidate; snapshots differ — not confirmed duplicate).
      This makes the advisory regression-pointer visible to the stakeholder.
    • Discovery Snapshot: Emit
      Discovery Snapshot: <discovery_commit>
      for the finding. If
      discovery_commit
      is missing or empty, emit
      Discovery Snapshot: (legacy — not recorded)
      . Never omit or drop the finding because this field is absent.
    • Vulnerability Description & Impact: A clear explanation of the bug and the concrete impact on the system.
    • Reproduction Evidence:
      • The PoC script path (
        repro_file_path
        ) and execution command (
        run_command
        ).
      • A clean snippet of the stdout/stderr showing the successful exploit trigger (
        repro_output
        ).
      • Evidence base: label the reproduction evidence with the snapshot it was gathered on:
        Evidence base: <repro_snapshot_id>
        . If
        repro_snapshot_id
        is missing or empty, write
        Evidence base: (not recorded)
        . Do NOT assume it equals the header/pass snapshot.
    • Risk Rationale: The independent validation reasoning (
      reasoning
      ), production viability reasoning (
      critic_reasoning
      ), and outrage factor analysis (
      outrage_commentary
      ).
    • Remediation & Patch:
      • The recommended mitigation strategy.
      • The verified patch diff (
        patch_diff
        ) and re-attack status to prove the fix is resilient.
      • Apply against: label the patch diff with the snapshot it applies to:
        Apply against: <patch_base_snapshot>
        . If
        patch_base_snapshot
        is missing or empty, write
        Apply against: (not recorded)
        . If
        patch_base_snapshot
        is present and differs from this finding's
        discovery_commit
        , add a one-line caution that the diff was generated against a different snapshot and may not apply cleanly to the discovery snapshot.
    • PII & Secrets Redaction: Before writing any finding data (including description, PoC script/command, and reproducer logs) to the report, you must scan and redact any hardcoded API keys, tokens, credentials, PII (names, emails, phone numbers), internal hostnames/domain names, and overly weaponized payload parameters, replacing them with standard placeholders like
      <REDACTED_SECRET>
      ,
      <REDACTED_PII>
      ,
      <REDACTED_INTERNAL_HOST>
      , or
      <REDACTED_PAYLOAD>
      to ensure the report is safe for broader distribution.
  3. Generate Review Packet:
    • Report Header & Disclaimer: At the very top of the report (before the Executive Summary):
      Snapshot provenance banners — emit these BEFORE item 1 below, at the very top of the report, each as its own separated blockquote, in this order:
      a. Non-authoritative / HALT banner (3-state rule). Read
      active_snapshot
      from
      workspace/.mantis_state.json
      . - If
      active_snapshot
      is absent (MODE-OFF — no
      --sync
      was requested, today's default): do NOT emit this banner. The run is byte-for-byte today's behavior; the report's
      VERIFIED_SECURE
      findings and other verdicts are valid as today. Emitting a NON-AUTHORITATIVE banner here would contradict the verdicts the same run produces. - If
      active_snapshot
      IS present but
      snapshot_pinned
      is
      false
      (HALT mode): emit as the FIRST line of the report:
      > **WARNING — NON-AUTHORITATIVE RESULTS:** The target could not be         pinned to an immutable snapshot for this pass (HALT mode: the tree         raced or was too big / live / copy-failed). Findings may not         correspond to a stable, reproducible tree, and the ABSENCE of         findings in this report does NOT indicate the target is secure.         Treat all results as provisional.
      Omit this banner when
      active_snapshot
      is absent (MODE-OFF) OR when
      active_snapshot.snapshot_pinned
      is
      true
      (PINNED).
      b. Dirty working tree warning. If
      vcs_info.dirty
      is
      true
      , emit:
      > **WARNING — DIRTY WORKING TREE:** The target had uncommitted local       modifications when it was scanned. Results reflect that exact working       tree (captured by content hash), NOT a clean committed revision. The       recorded commit alone will not reproduce this state.
      c. Mixed-snapshot banner. Let HEADER_SID =
      active_snapshot.snapshot_id
      . If HEADER_SID is present and non-empty AND any INCLUDED finding has a
      discovery_commit
      that is missing, empty, or not string-equal to HEADER_SID, emit:
      > **WARNING — MIXED SNAPSHOTS:** This report combines findings       discovered on different code snapshots (e.g. findings retried from       earlier passes). The pass snapshot is <HEADER_SID>. Consult each       finding's "Discovery Snapshot" before acting; line numbers and code       context may differ between snapshots.
      Compare snapshot IDs as EXACT strings only — no fuzzy or prefix match.
      1. Display the target codebase version information read from
        "vcs_info"
        in
        workspace/.mantis_state.json
        :
        • If
          "vcs_type"
          is
          "git"
          , show:
          Target Version: Git branch [branch] at commit [commit_hash] [(dirty) if dirty is true]
          .
        • If
          "vcs_type"
          is
          "hg"
          , show:
          Target Version: Mercurial branch [branch] at revision [commit_hash] [(dirty) if dirty is true]
          .
        • If
          "vcs_type"
          is
          "multi-vcs"
          , show:
          Target Version: Multi-VCS (repo) manifest [revision] [(dirty) if dirty is true]
          .
        • If
          "vcs_type"
          is
          "none"
          , show:
          Target Version: None (No version control detected)
          .
        • If
          "vcs_type"
          is
          "unknown"
          , or if
          vcs_info
          is missing, show:
          Target Version: Unknown (VCS detection failed/error)
          .
        After the
        Target Version:
        line, append the pass snapshot identity on a second line:
        • If
          active_snapshot.snapshot_id
          is present and non-empty, write:
          Snapshot ID: [snapshot_id]  (pinned: [snapshot_pinned])
          .
        • If
          active_snapshot
          is absent or
          snapshot_id
          is empty, write:
          Snapshot ID: (legacy — snapshot not recorded)
          . This is display-only provenance; it does not gate or drop any finding.
      2. Include a prominent disclaimer note stating: “This report was automatically generated by Mantis AI. All findings and patches are AI-generated and must be manually verified by a security or subject matter expert before deployment or disclosure.”
    • Grouping by Patch Status (Exclusivity): Organize the Executive Summary table and the main body of the report by grouping findings. Exploit chains MUST be excluded from these main groups and reported ONLY in their dedicated "Exploit Chains (Not End-to-End Reproduced)" section. For standard (non-chain) findings, group them into three distinct categories based on their remediation status (strictly mutually exclusive):
      1. Category 1: Patch Independently Verified: Findings where
        patch_status
        is
        "VERIFIED_SECURE"
        .
      2. Category 2: Patch Proposed / Mitigation Identified: Findings where
        patch_status
        is in
        ["MITIGATION_PROPOSED", "VERIFICATION_INCOMPLETE"]
        OR (
        patch_diff
        is present AND
        patch_status
        is unset/empty).
      3. Category 3: Unpatched / Verification Failed: Findings where
        patch_status
        is in
        ["VERIFICATION_FAILED", "ERROR"]
        OR (
        patch_diff
        is not present AND
        patch_status
        is unset/empty).
    • Dedicated Exploit Chains Section: Create a dedicated section titled
      "Exploit Chains (Not End-to-End Reproduced)"
      specifically for exploit chains. Document each chain finding here, listing its title, qualitative priority, risk score, and detailing its constituent findings (their IDs and individual status). Do not mix exploit chains with standard findings in Categories 1, 2, or 3.
    • Pass-Numbered Output: Do not overwrite the same
      review_packet.md
      file on every execution. Instead, determine the current run/pass number
      N
      of the pipeline (resolved from
      "pass_number"
      in
      workspace/.mantis_state.json
      . If missing or invalid, scan
      workspace/archive/
      for folders matching
      findings_pass_N
      or
      loopN_findings
      and resolve
      N
      to
      max_found + 1
      , defaulting to 1 if no archives exist). Then derive
      <snapshot_tag>
      from
      active_snapshot.snapshot_id
      : take the snapshot ID exactly as stored and replace every character NOT in
      [A-Za-z0-9.-]
      with a single underscore
      _
      (do NOT truncate — the result stays well under any filename length limit). Write the report to:
      • workspace/report/review_packet_pass_<N>_<snapshot_tag>.md
        when
        active_snapshot.snapshot_id
        is present and non-empty (e.g.
        review_packet_pass_1_content_9f86d081884c...md
        ). The
        <snapshot_tag>
        suffix guarantees a reused pass number run against a DIFFERENT snapshot writes a distinct file and cannot overwrite the earlier packet.
      • workspace/report/review_packet_pass_<N>.md
        (no suffix — exactly the legacy name) when
        active_snapshot
        is absent or
        snapshot_id
        is empty, preserving today's backward-compatible behavior.
    • Latest Copy/Symlink: After writing the pass-numbered report above, update a symlink or write a copy of THAT exact file (whether or not it carries a
      <snapshot_tag>
      suffix) to
      workspace/report/review_packet-latest.md
      , so the latest version is always reachable. The
      review_packet-latest.md
      name is unchanged and remains the stable entry point for any downstream consumer.
    • Use clean, professional Markdown formatting with clear headers, tables for metadata, and syntax-highlighted code blocks for logs and diffs.
    • Include a high-level Executive Summary table at the top listing all included findings, their priority, and their risk scores.
    • Optional sections (recommended):
      • Resolved this campaign: A short rollup using the same fold, but filtering to findings where
        patch_status
        is
        VERIFIED_SECURE
        or
        MITIGATION_PROPOSED
        . This gives stakeholders a visible "what got fixed" view alongside the open findings.
      • Unresolved — retry cap reached: A callout listing open findings whose reproduction attempt count is at the cap. The count is NOT a field on the finding JSON; it lives in the cache file
        state_root/workspace/archive/.repro_attempts.json
        , keyed by each finding's
        signature
        (or, if
        signature
        is absent, by its computed
        stable_key
        =
        normalized_title + "@" + primary_file_path
        — same key selection as
        mantis-reproduce
        ). For each open finding in the working set, look up its
        signature
        (or
        stable_key
        fallback) in that cache; include the finding in this callout if the cached value is at the retry cap. Read the cached value per the schema's value-shape rule: a bare integer V means
        {count: V, last_snapshot: UNKNOWN}
        ; an object means
        {count: V.count, last_snapshot: V.last_snapshot or UNKNOWN}
        . If the cache file is missing or the finding's key is absent, treat its count as 0 (do not list it here). These are items the planner stopped carrying
    [!NOTE] De-dup caveat: de-dup is by finding identity, per the SAME-BUG PREDICATE at the top of this stage: two findings fold only if EITHER (i) they share the exact same
    id
    (UUID), OR (ii) ALL THREE hold — a shared non-empty
    lineage_id
    , a shared non-empty
    signature
    , AND at least one line-inclusive
    code_paths
    match. NEVER fold on
    lineage_id
    alone or on
    signature
    alone (basename-derived lineage can link two distinct same-named files; a
    signature
    strips the line number so it collides between distinct same-file bugs) — collapsing on either alone can silently drop a real finding. A bug re-discovered under a new UUID that does NOT satisfy predicate (ii) — a regression, a file rename that shifts the line, or a non-deterministic re-find — lists as a SEPARATE entry from its archived ancestor: over-reporting (safe), never hiding. With stable finding signatures and lineage tracking landed (Phase 3), a re-discovered finding folds into its ancestor's single entry ONLY when predicate (ii) is fully satisfied; the UUID-only match remains the safe branch for legacy/un-upgraded findings.
    • review_packet-latest.md
      is authoritative:
      Note that
      review_packet-latest.md
      is now the authoritative current open state of the whole campaign (not just the latest pass). The per-pass
      review_packet_pass_<N>_<snapshot_tag>.md
      files remain as-is for historical reference.
步骤0 — 定位器解析。
LOCATOR RESOLUTION (before reading ANY target code or artifact):
0. ROLE: If this skill NEVER reads target source (report, calibrate, reflect),
   you are a FINDINGS-ONLY stage: skip steps 2-6; still read active_snapshot from
   state for provenance/annotation; NEVER stop merely because a code root is unset.
1. Determine CODE_ROOT, in this priority order:
   a. If --target_root is passed on THIS invocation, CODE_ROOT = --target_root.
      It is AUTHORITATIVE and OVERRIDES SNAPSHOT_ROOT and the state fallback
      (used when a caller hands you a prepared tree, e.g. a patched shadow).
   b. Else if --snapshot_root (or SNAPSHOT_ROOT) is passed, use it.
   c. Else read state_root/workspace/.mantis_state.json (state_root from
      --state_root if passed, else ./workspace/... relative to the current dir)
      -> active_snapshot.root / .snapshot_id / .snapshot_pinned.
   d. Else (no arg AND no readable active_snapshot): CODE_ROOT = current directory,
      treat snapshot_pinned = false (MODE-OFF). Do NOT stop.
2. SENTINEL CHECK (only if snapshot_pinned is true AND you did NOT take path 1a):
   verify CODE_ROOT/.mantis_snapshot_id exists and equals SNAPSHOT_ID. If missing
   or different -> STOP "snapshot sentinel mismatch". (A --target_root tree (1a) is
   deliberately mutated and is sentinel-EXEMPT.)
3. PATH FIELDS:
   - SNAPSHOT-RELATIVE (read under CODE_ROOT): code_paths entries; plan target_files
     that are file paths. Strip ONLY a trailing ":<digits>". A code_paths entry
     containing "://" is a URL/endpoint, NOT a file read. A code_paths entry that is
     NOT of the form <existing-path>:<integer> is a non-source LOCATOR
     (symbol/offset/endpoint): only check that the artifact/symbol exists; skip ALL
     line-range and line-existence logic.
   - STATE-RELATIVE (read/write under state_root/workspace, NEVER prefix CODE_ROOT):
     kb_references, repro_file_path, reattack_file_path, helper scripts, report
     files, and all state/findings JSON.
4. Never WRITE under CODE_ROOT when snapshot_pinned is true. Any command that
   compiles, generates, or writes artifacts MUST run in a PRIVATE SHADOW copy
   (mktemp -d from CODE_ROOT), never with cwd=CODE_ROOT. Read-only inspection may
   cd into CODE_ROOT.
5. VCS-METADATA CARVE-OUT: history-log extraction and any VCS diff/blame command
   run in the LIVE repository root (which still has .git/.hg/.repo), NOT CODE_ROOT
   (the snapshot copy strips VCS metadata). Do NOT stop merely because CODE_ROOT
   lacks .git/.hg/.repo.
6. Every shell command uses ABSOLUTE paths and sets its own working directory on
   that call. Do NOT assume the working directory persists between calls.
以下仅针对漏洞发现的说明适用于报告生成器:
  • 报告生成器属于仅处理漏洞发现的阶段(Block A,角色步骤0):跳过定位器步骤2–6,不需要或解析CODE_ROOT,且绝不会因代码根或哨兵未设置而停止。
  • 仍需从
    workspace/.mantis_state.json
    读取
    active_snapshot
    root
    snapshot_id
    snapshot_pinned
    )和
    vcs_info
    用于溯源——用于构建报告头、顶部横幅和输出文件名。
  • 报告生成器接触的所有路径(
    workspace/findings/*.json
    workspace/.mantis_state.json
    workspace/report/*
    workspace/archive/*
    )均为状态相对路径,绝不会添加CODE_ROOT前缀。
编译一份专业的Markdown报告,详细说明已验证/复现的漏洞和利用链。
按以下步骤执行报告生成阶段:
  1. 加载漏洞发现 — 完整加载本次审查内容,加上遗留的未解决漏洞发现(按最新优先合并;无脚本)。 构建一个以漏洞发现ID为键的工作集,每个漏洞发现仅保留其最新状态:
    相同漏洞判定规则(适用于本阶段所有当前与归档漏洞发现的去重、合并和抑制;过度报告始终安全,隐藏真实漏洞绝不允许):两个漏洞发现属于同一漏洞,当且仅当(i)它们具有完全相同的
    id
    (UUID);或(ii)同时满足以下三个条件——共享非空的
    lineage_id
    、共享非空的
    signature
    ,且至少有一个包含行号的
    code_paths
    条目完全相同。否则它们为不同漏洞——需同时展示。绝不能仅通过
    lineage_id
    signature
    就将两个漏洞发现视为同一漏洞:两者的粒度均大于漏洞的真实标识(基于文件名的lineage可能关联两个不同的同名文件;
    signature
    会去除行号,可能导致同一文件中的不同漏洞发生冲突),仅通过其中一个合并可能会静默丢弃真实漏洞。
    设计说明(重新锚定 vs 合并):
    mantis-plan
    的重新锚定(第二阶段)仅提供行提示以引导重新发现——不会重写遗留漏洞发现的
    code_paths
    。重新发现的漏洞会在当前快照的新行位置显示。由于合并规则要求包含行号的
    code_paths
    匹配,重新发现的漏洞不会与其祖先合并(行号不同)。这属于安全的过度报告——两个条目都会显示,当前条目展示新位置。未来阶段可在两个漏洞发现具有相同
    signature
    lineage_id
    且祖先的行在当前快照中已确认不存在时,放宽规则为仅路径匹配,但目前为防止静默丢弃风险,仍使用保守的包含行号的匹配规则。
    1. 读取所有活跃的
      workspace/findings/*.json
      ,将每个活跃漏洞发现添加到工作集,以其
      id
      (UUID)为键——包含所有修复状态,因此本次审查中
      VERIFIED_SECURE
      /
      MITIGATION_PROPOSED
      的修复内容仍会在分类1/2中展示。绝不能合并两个活跃漏洞发现,即使它们共享
      lineage_id
      signature
      ——每个活跃
      id
      都作为独立条目保留。
    2. 按审查次数降序扫描
      workspace/archive/findings_pass_<N>/
      (以及旧版
      loop<N>_findings/
      )。仅当归档漏洞发现仍未解决(见步骤4),且工作集中没有与它属于同一漏洞的发现(按上述规则),且未添加过同一漏洞的更早(更高审查次数)归档副本时,才添加该归档漏洞发现。首次遇到的副本即为最新状态;忽略更低目录中同一漏洞的后续副本。(仅当存在真正的同一漏洞替代它时,才会抑制归档漏洞发现;仅
      lineage_id
      signature
      巧合不会抑制它。)
    3. 替代合并(第三阶段): 当归档漏洞发现与当前漏洞发现属于同一漏洞(规则ii)时,当前漏洞发现替代它——仅显示当前(最新)状态的单个条目;不展示归档副本。当规则不满足时(不同的
      signature
      ,例如文件重命名,或
      lineage_id
      缺失),将两者作为独立条目展示(安全的过度报告,绝不隐藏)。
      • 防止漏报保障: 如果当前(替代)漏洞发现不满足可处理规则(以下步骤4),但归档祖先满足该规则(例如,祖先已
        reproduced
        且未解决,但当前审查的复现因新快照上的临时构建/环境失败而导致
        not_attempted
        ),绝不能因临时降级而抑制已确认的未解决漏洞。相反,需在报告中保留祖先的最后确认状态(显示为“未解决——新快照上的复现待处理”),确保已确认的漏洞不会从报告中静默消失。当前漏洞发现的更新元数据(例如更新后的
        code_paths
        行号)可作为注释附加,但显示的结论/状态必须是祖先的最后确认状态,而非临时降级后的状态。
    4. 可处理/质量规则(适用于活跃和归档漏洞发现):仅当漏洞发现为利用链(存在
      constituent_findings
      ,或标题/历史中包含“Exploit Chain”),或
      repro_status
      reproduced
      ,或(
      repro_status
      statically_confirmed
      且带有实证执行证据——外部堆栈跟踪、Sanitizer跟踪(ASan/UBSan/MSan/TSan)或崩溃日志)时,才纳入报告。不纳入误报、
      NON_VIABLE
      DUPLICATE
      failed_to_reproduce
      或缺乏实证跟踪的普通
      statically_confirmed
      漏洞发现。
    5. 未解决规则(仅适用于步骤2中的归档遗留漏洞发现):归档漏洞发现“仍未解决”的条件是满足(4),且
      patch_status
      不是
      VERIFIED_SECURE
      /
      MITIGATION_PROPOSED
      ,且
      status
      不是
      FALSE_POSITIVE
      /
      DUPLICATE
      ,且
      production_viability
      不是
      NON_VIABLE
      。(活跃漏洞发现无论
      patch_status
      如何都会加载,因此本次审查的修复内容仍会显示;已修复的归档漏洞发现不会在每次审查中重新列出——可使用可选的“本次周期已解决”汇总部分展示累计修复情况。)
    6. 规模处理: 按最新优先顺序逐个目录处理;绝不一次性加载整个归档。
    • 严重性过滤: 将优先级为
      "LOW"
      的漏洞发现排除在报告主体之外。必须将这些低优先级问题放在报告末尾单独的“附录:低优先级漏洞发现”部分,确保报告主体聚焦于高风险问题。
  2. 提取关键工件: 对于每个已复现的漏洞发现,提取并格式化以下内容:
    • 头元数据: 标题、ID(UUID)、推断暴露面、最终风险评分和定性优先级。
    • 审查周期溯源: 为每个未解决的漏洞发现标注首次发现的审查次数与当前审查次数(例如
      发现于审查2 · 截至审查7仍未解决
      ),以便清晰展示遗留漏洞发现。首次发现时间=漏洞发现
      history
      条目中最低的
      pass_number
      (或包含该漏洞发现的最低编号归档目录的pass_number);当前状态=上述合并后保留的副本。
    • 重复漏洞提示: 如果漏洞发现存在
      possible_duplicate_of
      字段(当跨审查候选漏洞未匹配时由
      mantis-dedupe
      设置),需发出提示:
      可能与漏洞发现<UUID>相关(跨审查候选;快照不同——未确认重复)。
      这可让利益相关者看到该回归提示。
    • 发现快照: 显示漏洞发现的
      发现快照:<discovery_commit>
      。若
      discovery_commit
      缺失或为空,显示
      发现快照:(旧版——未记录)
      。绝不能因该字段缺失而省略或丢弃漏洞发现。
    • 漏洞描述与影响: 清晰说明漏洞内容及其对系统的具体影响。
    • 复现证据:
      • PoC脚本路径(
        repro_file_path
        )和执行命令(
        run_command
        )。
      • 展示成功触发漏洞的stdout/stderr干净片段(
        repro_output
        )。
      • 证据基准: 为复现证据标注其收集时的快照:
        证据基准:<repro_snapshot_id>
        。若
        repro_snapshot_id
        缺失或为空,写入
        证据基准:(未记录)
        。请勿假设其等于报告头/审查快照。
    • 风险依据: 独立验证推理(
      reasoning
      )、生产可行性推理(
      critic_reasoning
      )和严重程度分析(
      outrage_commentary
      )。
    • 修复与补丁:
      • 推荐的缓解策略。
      • 已验证的补丁差异(
        patch_diff
        )和重新攻击状态,以证明修复有效。
      • 适用快照: 为补丁差异标注其适用的快照:
        适用快照:<patch_base_snapshot>
        。若
        patch_base_snapshot
        缺失或为空,写入
        适用快照:(未记录)
        。若
        patch_base_snapshot
        存在且与该漏洞发现的
        discovery_commit
        不同,需添加一行提示,说明该差异是针对不同快照生成的,可能无法在发现快照上干净应用。
    • PII与敏感信息脱敏: 在将任何漏洞发现数据(包括描述、PoC脚本/命令和复现日志)写入报告之前,必须扫描并脱敏任何硬编码的API密钥、令牌、凭证、PII(姓名、邮箱、电话号码)、内部主机名/域名和过度武器化的 payload 参数,替换为标准占位符如
      <REDACTED_SECRET>
      <REDACTED_PII>
      <REDACTED_INTERNAL_HOST>
      <REDACTED_PAYLOAD>
      ,确保报告可安全广泛分发。
  3. 生成审查报告包:
    • 报告头与免责声明: 在报告最顶部(执行摘要之前):
      快照溯源横幅——在以下第1项之前,放在报告最顶部,每个横幅作为独立的块引用,按以下顺序排列:
      a. 非权威/暂停横幅(三态规则)。
      workspace/.mantis_state.json
      读取
      active_snapshot
      。- 若
      active_snapshot
      缺失(MODE-OFF——未请求
      --sync
      ,当前默认):不显示此横幅。本次运行与当前行为完全一致;报告中的
      VERIFIED_SECURE
      漏洞发现和其他结论均有效。在此处显示非权威横幅会与同一运行生成的结论矛盾。- 若
      active_snapshot
      存在但
      snapshot_pinned
      false
      (暂停模式):在报告第一行显示:
      > **警告——非权威结果:** 本次审查无法将目标固定到不可变快照(暂停模式:代码树发生冲突或过大/活跃/复制失败)。漏洞发现可能与稳定、可复现的代码树不对应,报告中未发现漏洞并不代表目标是安全的。请将所有结果视为临时内容。
      active_snapshot
      缺失(MODE-OFF)或
      active_snapshot.snapshot_pinned
      true
      (已固定)时,省略此横幅。
      b. 脏工作树警告。
      vcs_info.dirty
      true
      ,显示:
      > **警告——脏工作树:** 扫描目标时存在未提交的本地修改。结果反映的是该精确工作树(由内容哈希捕获),而非干净的提交版本。仅记录的提交无法复现此状态。
      c. 混合快照横幅。 设HEADER_SID =
      active_snapshot.snapshot_id
      。若HEADER_SID存在且非空,且任何纳入报告的漏洞发现的
      discovery_commit
      缺失、为空或与HEADER_SID字符串不完全匹配,显示:
      > **警告——混合快照:** 本报告整合了在不同代码快照上发现的漏洞发现(例如从过往审查重试的漏洞发现)。本次审查的快照为<HEADER_SID>。采取行动前请查看每个漏洞发现的“发现快照”;不同快照之间的行号和代码上下文可能不同。
      仅按精确字符串比较快照ID——不使用模糊或前缀匹配。
      1. 显示从
        workspace/.mantis_state.json
        "vcs_info"
        读取的目标代码库版本信息:
        • "vcs_type"
          "git"
          ,显示:
          目标版本:Git分支[branch],提交[commit_hash] [(dirty) 若dirty为true]
        • "vcs_type"
          "hg"
          ,显示:
          目标版本:Mercurial分支[branch],版本[commit_hash] [(dirty) 若dirty为true]
        • "vcs_type"
          "multi-vcs"
          ,显示:
          目标版本:多版本控制系统(repo)清单[revision] [(dirty) 若dirty为true]
        • "vcs_type"
          "none"
          ,显示:
          目标版本:无(未检测到版本控制)
        • "vcs_type"
          "unknown"
          ,或
          vcs_info
          缺失,显示:
          目标版本:未知(版本控制检测失败/出错)
        目标版本:
        行之后,添加第二行显示审查快照标识:
        • active_snapshot.snapshot_id
          存在且非空,写入:
          快照ID:[snapshot_id]  (已固定:[snapshot_pinned])
        • active_snapshot
          缺失或
          snapshot_id
          为空,写入:
          快照ID:(旧版——未记录快照)
          。这仅用于展示溯源信息,不会限制或丢弃任何漏洞发现。
      2. 添加醒目的免责声明:“本报告由Mantis AI自动生成。所有漏洞发现和补丁均为AI生成,部署或披露前必须经过安全或主题专家手动验证。”
    • 按补丁状态分组(互斥): 将执行摘要表格和报告主体按漏洞发现分组。利用链必须排除在这些主要分组之外,仅在专门的“利用链(未端到端复现)”部分报告。 对于标准(非链)漏洞发现,根据其修复状态分为三个不同的类别(严格互斥):
      1. 类别1:补丁已独立验证
        patch_status
        "VERIFIED_SECURE"
        的漏洞发现。
      2. 类别2:已提出补丁/已识别缓解措施
        patch_status
        属于
        ["MITIGATION_PROPOSED", "VERIFICATION_INCOMPLETE"]
        ,或(存在
        patch_diff
        patch_status
        未设置/为空)的漏洞发现。
      3. 类别3:未打补丁/验证失败
        patch_status
        属于
        ["VERIFICATION_FAILED", "ERROR"]
        ,或(不存在
        patch_diff
        patch_status
        未设置/为空)的漏洞发现。
    • 专门的利用链部分: 创建一个标题为
      "利用链(未端到端复现)"
      的专门部分,用于报告利用链。在此处记录每个链发现,列出其标题、定性优先级、风险评分,并详细说明其组成漏洞发现(ID和各自状态)。请勿将利用链与标准漏洞发现混合在类别1、2或3中。
    • 带审查次数的输出: 每次执行时不要覆盖同一个
      review_packet.md
      文件。相反,确定管道的当前运行/审查次数
      N
      (从
      workspace/.mantis_state.json
      "pass_number"
      解析。若缺失或无效,扫描
      workspace/archive/
      中匹配
      findings_pass_N
      loopN_findings
      的文件夹,将
      N
      解析为
      max_found + 1
      ,若无归档则默认值为1)。然后从
      active_snapshot.snapshot_id
      派生
      <snapshot_tag>
      :按存储的快照ID原样保留,将所有不在
      [A-Za-z0-9.-]
      中的字符替换为单个下划线
      _
      (不要截断——结果不会超过任何文件名长度限制)。将报告写入:
    • active_snapshot.snapshot_id
      存在且非空时,写入
      workspace/report/review_packet_pass_<N>_<snapshot_tag>.md
      (例如
      review_packet_pass_1_content_9f86d081884c...md
      )。
      <snapshot_tag>
      后缀可确保针对不同快照运行相同审查次数时,写入独立文件,不会覆盖之前的报告包。
    • active_snapshot
      缺失或
      snapshot_id
      为空时,写入
      workspace/report/review_packet_pass_<N>.md
      (无后缀——与旧版名称完全一致),保留当前的向后兼容行为。
    • 最新副本/符号链接: 写入上述带审查次数的报告后,更新符号链接或写入该文件的副本(无论是否带有
      <snapshot_tag>
      后缀)到
      workspace/report/review_packet-latest.md
      ,以便始终可访问最新版本。
      review_packet-latest.md
      名称保持不变,仍是下游消费者的稳定入口。
    • 使用清晰、专业的Markdown格式,包含明确的标题、元数据表格,以及日志和差异的语法高亮代码块。
    • 在顶部包含高级执行摘要表格,列出所有纳入报告的漏洞发现、其优先级和风险评分。
    • 可选部分(推荐):
      • 本次周期已解决: 使用相同的合并规则,但过滤
        patch_status
        VERIFIED_SECURE
        MITIGATION_PROPOSED
        的漏洞发现的简短汇总。这可让利益相关者在查看未解决漏洞的同时,看到“已修复内容”的视图。
      • 未解决——已达重试上限: 列出复现尝试次数达到上限的未解决漏洞发现的提示。次数不是漏洞发现JSON的字段;存储在缓存文件
        state_root/workspace/archive/.repro_attempts.json
        中,以每个漏洞发现的
        signature
        为键(若
        signature
        缺失,则使用计算的
        stable_key
        =
        normalized_title + "@" + primary_file_path
        ——与
        mantis-reproduce
        使用相同的键选择)。对于工作集中的每个未解决漏洞发现,在该缓存中查找其
        signature
        (或备用的
        stable_key
        );若缓存值达到重试上限,则将该漏洞发现纳入此提示。按架构的值形状规则读取缓存值:纯整数V表示
        {count: V, last_snapshot: UNKNOWN}
        ;对象表示
        {count: V.count, last_snapshot: V.last_snapshot or UNKNOWN}
        。若缓存文件缺失或漏洞发现的键不存在,将其次数视为0(不列入此处)。这些是审查计划停止重试的条目
    [!NOTE] 去重注意事项: 去重基于漏洞发现标识,遵循本阶段顶部的相同漏洞判定规则:两个漏洞发现仅在(i)共享完全相同的
    id
    (UUID),或(ii)同时满足三个条件——共享非空的
    lineage_id
    、共享非空的
    signature
    ,且至少有一个包含行号的
    code_paths
    匹配时才会合并。绝不能仅通过
    lineage_id
    signature
    合并(基于文件名的lineage可能关联两个不同的同名文件;
    signature
    会去除行号,可能导致同一文件中的不同漏洞发生冲突)——仅通过其中一个合并可能会静默丢弃真实漏洞。重新发现的漏洞若使用新UUID且不满足规则(ii)——回归、文件重导致行号变化、或非确定性重新发现——会作为独立条目与归档祖先并列:属于过度报告(安全),绝不隐藏。随着稳定的漏洞发现签名和lineage跟踪落地(第三阶段),重新发现的漏洞仅在完全满足规则(ii)时才会合并到其祖先的单个条目中;仅UUID匹配仍是旧版/未升级漏洞发现的安全分支。
    • review_packet-latest.md
      为权威版本:
      注意
      review_packet-latest.md
      现在是整个审查周期当前未解决状态的权威版本(不仅是最新审查)。带审查次数的
      review_packet_pass_<N>_<snapshot_tag>.md
      文件保持原样,作为历史参考。",