Claude Skill

chain-vulnerability-scanner

Use when an Algorand, Cairo, Cosmos SDK, Solana, Substrate, or TON codebase needs vulnerability scanning with reachability-backed findings. Not for non-chain review: use security-review.

LLM Mart · 0 points · 0 views 0 listing impressions 0 install-command copies
Virus-scanned Reviewed automatically before listing.

Full trust report

Download outlinedriven-outline-driven-development-.devin_skills_chain-vulnerability-scanner-b0e8ce8.zip · 25 KB
Part of outlinedriven/outline-driven-development — 145 skills

Install

skills CLI npx skills add https://github.com/OutlineDriven/outline-driven-development/tree/main/.devin/skills/chain-vulnerability-scanner
Claude Code claude plugin marketplace add https://llmmart.ai/marketplace.json && claude plugin install outlinedriven-outline-driven-development@llmmart
Git git clone https://github.com/OutlineDriven/outline-driven-development.git

The skills CLI installs just this skill, for any of its supported agents. Claude Code installs the whole outlinedriven/outline-driven-development collection as a plugin from our marketplace. Git is the plain clone.

Skill manifest

Chain vulnerability scanner

A single read-only scan operation that classifies a blockchain codebase by ecosystem, loads only that ecosystem's detector catalog, and emits severity-ranked findings tied to reachable code paths. Six ecosystems are supported; each owns one flat reference file under references/ that holds its detectors, applicability gates, tool requirements, severity distinctions, and ecosystem caveats. This file holds the shared routing, authority, procedure, cross-cutting rules, failure behavior, and output contract.

Ecosystem routing

Ecosystem Source indicators Reference file
Algorand .teal files; .py importing PyTeal or Algorand SDK (from pyteal import *, from algosdk import *, Txn, Gtxn, Global, InnerTxnBuilder, OnComplete, @router.method, @Subroutine); approval_program.py/clear_program.py, contract.teal/signature.teal, Beaker references. references/algorand.md
Cairo / Starknet .cairo files; Scarb.toml; contract markers #[contract], #[storage], #[external(v0)], #[l1_handler], #[constructor], felt252, ContractAddress, get_caller_address(), send_message_to_l1_syscall. Optional L1 bridge Solidity contracts for cross-layer patterns. references/cairo.md
Cosmos SDK Go source with Cosmos SDK x/ modules and go.mod; ibc-go; Ethermint/EVM precompiles (evmutil/feemarket); Rust contracts using cosmwasm_std. references/cosmos-sdk.md
Solana Solana or Anchor Rust (.rs) program files. references/solana.md
Substrate Substrate FRAME pallet Rust source tree or file within a runtime. references/substrate.md
TON FunC or Tact source (function definitions, message handlers, recv_internal, recv_external, op:: constants, @interface annotations). references/ton.md

If the codebase matches none of the indicators above, stop and report that no supported chain surface applies. Do not run any catalog. Route generic non-chain security review to security-review instead: chain-vulnerability-scanner loads ecosystem-specific detector catalogs for six supported blockchain ecosystems; security-review runs STRIDE and OWASP on any codebase. The split is: supported chain ecosystem → chain-vulnerability-scanner; any other codebase → security-review.

Contract

Field Bound contract
Trigger A supported Algorand, Cairo, Cosmos SDK, Solana, Substrate, or TON codebase needs a chain-specific vulnerability sweep.
Authority Read-only. No file, VCS, credential, paid, published, deployed, or remote mutation. Tealer and Caracal, when already installed, run only as read-only analyzers on local source. Never install missing tools; installation is a state-changing action outside read-only authority.
Side effect Severity-ranked, reachability-backed findings emitted as chat output only, each with location, evidence, impact, remediation, and validation status.
Done Every applicable detector in every selected ecosystem reference is checked, and each confirmed finding carries code evidence, a reachable attack path, and remediation.

Inputs

  • Target codebase path (required): a path containing source for one or more supported ecosystems.
  • Ecosystem scope (derived): the scanner classifies every supported ecosystem present under the target path. The user MAY name a detector subset for Algorand, Cairo, Cosmos SDK, Solana, or Substrate; those ecosystems default to all detectors when omitted.
  • TON category scope (required for TON): a non-empty list of categories from references/ton.md, or "all".
  • Optional severity floor (TON): if omitted, all findings are returned.
  • Optional auxiliary source (Cairo): L1 bridge Solidity contracts, needed to evaluate L1-L2 patterns.
  • Optional analyzers already installed: Tealer for Algorand and Caracal for Cairo. Record their absence as a coverage gap; never install them during this read-only skill.

Shared procedure

Run these steps in order. Each ecosystem reference may attach ecosystem-specific sub-steps, detectors, and gates to steps 3, 4, and 6; this file holds only the shared spine.

  1. Classify ecosystems and applicability. Search the supplied path for the source indicators in the routing table. Select every supported ecosystem present and name its reference file. If multiple top-level ecosystems coexist, scan each as one branch of the same invocation. A Cosmos branch uses its own discovery step to enumerate EVM, CosmWasm, and IBC sub-catalogs. If no supported surface matches, stop and report an empty-target result. Done when: every detected ecosystem and reference is recorded, or an empty-target result is reported.

  2. Load only selected references. For each detected ecosystem branch, read its single named reference before scanning that branch. Do not load references for ecosystems absent from the target. Each selected reference supplies the detector list, applicability/version gates, tool commands, severity definitions, rationalization rejections, and ecosystem caveats that govern the branch. Done when: every selected reference is loaded and its applicability gates (e.g., Cosmos version gate, Cairo L1-bridge presence, TON scope validation) have been evaluated.

  3. Inventory trust/state/value boundaries. Enumerate the codebase's transaction-field usage, trust boundaries, state-mutation sites, value-transfer paths, and external entry points, using the reference's detector list as the lens. Record the file list and contract/module inventory. Done when: the boundary inventory is recorded or an empty-target result is reported.

  4. Run source and ecosystem tools. Invoke Tealer for Algorand .teal targets and Caracal for Cairo targets when already installed; capture detector output. If a tool is absent or errors, record the gap in coverage notes and proceed with the manual detector sweep from the selected reference. A tool failure never invalidates manual findings. Done when: tool output is captured for each applicable target or its absence/error is recorded.

  5. Confirm semantic reachability. For every candidate finding, trace from an external entry point (ecosystem-specific: Algorand approval/smart-signature paths; Cairo #[external(v0)], #[l1_handler], #[constructor]; Cosmos consensus-critical paths BeginBlock/EndBlock/FinalizeBlock/msg_server/AnteHandler; Solana instruction entrypoints; Substrate dispatchables; TON message handlers) to the vulnerable statement. A match reachable only from CLI, query, or test code is not a finding; record it as not-applicable with the reason "not consensus-critical" (Cosmos) or the ecosystem's equivalent. Exclude findings that cannot be reached by any caller; mark ambiguous cases as unconfirmed observations, never promoted to confirmed findings. Done when: every candidate finding is traced to a reachable entry point or excluded.

  6. Apply severity rules. Assign severity per the reference's definitions. Each ecosystem owns its own severity ladder and category-to-severity mapping; use the reference's, not a generic one. Where the reference lists rationalization rejections (Cosmos) or caveats (Cairo L1 bridge), apply them verbatim. Done when: every finding has a severity tag drawn from the reference.

  7. Emit normalized findings. Rank findings by severity (Critical first, then High, then Medium, then Low, then Informational where the ecosystem defines it). For each confirmed finding emit the shared finding fields below plus any extra ecosystem fields the reference requires. Append coverage notes listing detectors checked, detectors not applicable, tool availability, and any unassessed detectors with their blocker. Done when: findings are ranked with evidence and remediation, plus coverage notes, and the done predicate is auditable.

Shared finding fields

Every confirmed finding carries all of these:

  • ecosystem: one of algorand, cairo, cosmos-sdk, solana, substrate, ton.
  • component/path and line: file and line range (file:line-range), plus module/function/call-path where the ecosystem reference requires it (Substrate module::function (lines N–M); Cosmos file:line; Solana affected files and line ranges).
  • detector/category: the named detector or pattern category from the reference (e.g., Algorand "Rekeying", Solana "a. Missing signer checks", TON category letter + name).
  • severity: from the reference's severity ladder.
  • confidence: confirmed, unconfirmed, or not-applicable (for coverage notes).
  • reachability: the traced entry point to vulnerable statement path, or not-reachable (excluded).
  • evidence: verbatim vulnerable code excerpt, quoted from source.
  • impact: attack scenario, numbered exploit steps, fund-loss or chain-halt description per the reference.
  • remediation: concrete fix with corrected code; never "review manually" (TON refuses this; all ecosystems require a specific code change or architectural correction).
  • validation status: validated, unvalidated, partial, or error, reflecting whether the finding was confirmed by tool plus manual review, manual only, or could not be fully checked.

Extra ecosystem fields retained from the source:

  • Algorand: contract type (stateful application vs smart signature), transaction-field validation matrix status, Tealer availability.
  • Cairo: Cairo version (1.0+ vs legacy 0), L1-bridge-contracts-present flag, Caracal availability.
  • Cosmos: discovery inventory (PLATFORM, IBC_ENABLED, SDK_VERSION, IBC_GO_VERSION, CUSTOM_MODULES), applicable catalog list.
  • Solana: vulnerability type letter (a–o), failure-mode group.
  • Substrate: pattern family, call-path evidence (module::function (lines N–M)), completeness statement against the five families.
  • TON: scope (category list), severity floor, date.

Cross-cutting rules

  • One coherent scan, not six modes. One invocation may contain one or more detected ecosystem branches. Each branch loads only its own reference and returns findings through the same shared contract. Cosmos EVM, CosmWasm, and IBC surfaces remain sub-catalogs of the Cosmos branch.
  • Record missing tools; fail closed on missing version evidence. If an optional analyzer is absent, record the gap and continue with manual detectors; never install it. If version evidence required by an applicability gate is missing (e.g., Cosmos SDK version undetectable, Cairo version ambiguous), report the affected detectors as blocked rather than guessing.
  • Never fabricate findings. Record a finding only when vulnerable code is located with a concrete file and line reference and traced to a reachable entry point. Ambiguous code is an unconfirmed observation, not a finding.
  • Never swallow errors. A read or search failure is reported as the blocker for the affected detector; it is never silently treated as "no findings."
  • Partial-result rule. Findings are emitted incrementally as confirmed. The report is complete only when every applicable detector has been checked against every applicable target. Never report done while a target file or detector remains unexamined. Explicitly list every unassessed detector with its blocker.
  • Non-mutation rule. No file is created, edited, moved, or deleted. No git, build, install, deploy, or remote action is performed. Recovery from any failure is to report the failure and continue or stop; never to mutate state to work around it.
  • Rationalization rejection (Cosmos, applied where the reference states). The six Cosmos rationalizations ("ValidateBasic catches this", "behind governance, so safe", "IBC counterparty is trusted", "panic can't happen, input is validated", "rounding error is only a few tokens", "EVM precompile handles rollback") are dismissed as reasons a match is safe. Other ecosystems' references state their own caveats (e.g., Cairo L1-bridge-contracts-absent marks L1-L2 patterns incomplete, not clean).

Failure behavior

Failure class Behavior
No supported ecosystem surface Stop. Report the path was searched and no supported chain source indicators were found. Do not fabricate findings.
Ecosystem tool not installed Continue with the manual detector sweep from the reference. Record the tool absence in coverage notes. Do not attempt installation.
Ecosystem tool execution error Capture the error message, include it in coverage notes, and proceed with the manual sweep. A tool failure does not invalidate manual findings.
Missing version evidence for an applicability gate Report the affected detectors/catalogs as blocked with the missing evidence. Do not guess a version.
Missing auxiliary source (Cairo L1 bridge) Report which patterns could not be fully evaluated and mark them incomplete, not clean.
Detector not applicable Record the detector as checked-but-not-applicable in coverage notes rather than omitting it, so the done predicate is auditable.
Ambiguous code (cannot confirm vulnerable or safe) Record as an unconfirmed observation with the code location and the specific check that could not be resolved. Do not promote it to a confirmed finding.
Match not on a consensus/reachable path Not a finding. Record as not-applicable with the reason (e.g., "not consensus-critical" for Cosmos CLI/query/test code).
Scan error (crash, OOM, tool failure halting the run) Stop. Return "Scan failed: [exact error class]. No findings are returned." (TON rule, applied ecosystem-wide for halting errors).
No findings Return the empty-result statement with ecosystem, scope, and date. This is not a failure.
Partial result (source size limit or mid-scan halt) Return assessed detectors and explicitly list every unassessed detector with its blocker. Include the scope-overrun warning where applicable (TON). Never claim the done predicate holds while a detector remains unchecked.

Output

A chat-output report with the following structure:

  • Header: ecosystems, project path, files scanned, contract/module types identified, tool availability, and ecosystem discovery inventory where defined (Cosmos).
  • Findings: one entry per confirmed vulnerability, ranked Critical > High > Medium > Low > Informational (where the ecosystem defines the rung). Each entry carries the shared finding fields above plus any extra ecosystem fields.
  • Coverage notes: for each detector in the loaded reference, state checked / not-applicable / unconfirmed / blocked, and note tool availability and any execution errors. For Cosmos, include a completeness check listing every applicable catalog with its pattern count, confirming none were skipped.

The done predicate holds when every applicable detector in every selected reference is checked and each confirmed finding carries code evidence, a reachable attack path, and remediation.

Files (outline-driven-development)
  • agents
    • openai.yaml 263 B
      interface:
        display_name: "Chain Vulnerability Scanner"
        short_description: "Use when an Algorand, Cairo, Cosmos SDK, Solana, Substrate, or TON codebase needs vulnerability scanning with reachability-backed findings."
      policy:
        allow_implicit_invocation: false
      
  • references
    • algorand.md 6.6 KB
      # Algorand detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as Algorand. Source indicators and routing live in `SKILL.md`. This file holds the eleven Algorand vulnerability patterns, the two auxiliary procedures, the Tealer tool requirement, severity ladder, and Algorand-specific failure notes.
      
      ## Tool requirement
      
      When Tealer is already installed and available on `PATH`, execute `tealer <file> --detect all` for each `.teal` target and capture detector output. If Tealer is absent, record the gap in coverage notes and continue with the manual sweep. Never install Tealer during this read-only skill. Capture a Tealer execution error in coverage notes and continue manually; analyzer failure does not invalidate manual findings.
      
      ## Surface classification
      
      Search the supplied path for `.teal` files and `.py` files containing PyTeal or Algorand SDK imports. Classify each target as a stateful application (approval + clear state programs) or a smart signature (logic signature). Record the file list; if no Algorand files are found, stop and report an empty-target result.
      
      ## The eleven patterns
      
      Check every pattern below in every target file. Search for the relevant transaction-field usage, verify that validation logic exists, and check for bypass conditions. Record a finding only when you locate vulnerable code with a concrete file and line reference.
      
      1. **Rekeying (CRITICAL).** Every payment, asset transfer, and application-call approval path must assert `Txn.rekey_to() == Global.zero_address()` (or an explicit allowed target). Inner transactions (TEAL v6+) must not set `RekeyTo` to a user-controlled value. Flag any approval branch that handles a transaction type without a `rekey_to` check.
      
      2. **Unchecked transaction fee (HIGH).** Smart signatures must enforce `Txn.fee() == Global.min_txn_fee()` or `Txn.fee() == Int(0)` with fee pooling. Flag smart signatures that approve payments or transfers with no fee assertion.
      
      3. **CloseRemainderTo (CRITICAL).** Every payment transaction (outer and inner) must assert `Txn.close_remainder_to() == Global.zero_address()` or an explicit authorized address. Flag payment approval without this check.
      
      4. **AssetCloseTo (CRITICAL).** Every asset transfer must assert `Txn.asset_close_to() == Global.zero_address()` or an explicit authorized target. Flag asset-transfer approval without this check.
      
      5. **Group size check (HIGH).** Atomic transaction group logic must validate `Global.group_size()` against the expected exact or maximum size before using absolute `Gtxn[i]` indices. Flag group-indexed logic with no `group_size` assertion. Prefer ABI relative indexing (TEAL v6+) where present.
      
      6. **Time-based replay (MEDIUM).** Recurring or time-dependent transactions must set and validate `Txn.lease()` to a unique value per logical transaction. Flag periodic-payment or timestamp-gated paths that submit inner transactions without a lease check.
      
      7. **Access controls (CRITICAL).** `UpdateApplication` and `DeleteApplication` completion paths must check `Txn.sender() == Global.creator_address()` (or an admin stored in global state) or explicitly reject (`Return(Int(0))`). Flag any update/delete branch that approves without sender validation. Validate `OnComplete` is checked for all application calls.
      
      8. **Asset ID verification (HIGH).** Every asset-transfer validation must assert `Txn.xfer_asset() == expected_asset_id` where the expected ID is hardcoded or read from global state, never user-supplied. Flag asset-transfer logic that accepts any `xfer_asset` value.
      
      9. **Denial of service via asset opt-in (MEDIUM).** Asset distributions should use a pull pattern (users claim their own transfer) rather than a push loop. Flag batch push transfers to multiple receivers where a single non-opted-in receiver fails the whole group.
      
      10. **Inner transaction fee (MEDIUM).** Every inner transaction must explicitly set `TxnField.fee: Int(0)`. Flag `InnerTxnBuilder.SetFields` blocks that omit the fee field or set a non-zero fee.
      
      11. **Clear state transaction (HIGH).** Group transaction validation that checks `Gtxn[i].type_enum() == TxnType.ApplicationCall` must also check `Gtxn[i].on_completion() == OnComplete.NoOp` (or an explicit allowed value). Flag ApplicationCall checks that omit `on_completion` validation, since a ClearState call can bypass approval logic.
      
      ## Auxiliary procedure A: transaction-field validation matrix
      
      For every transaction type present (Payment, AssetTransfer, ApplicationCall, inner transactions), confirm the checklist: RekeyTo, CloseRemainderTo/AssetCloseTo, fee, asset ID, OnComplete, and group size are each validated or explicitly noted as not applicable. Record any unchecked field as a finding. Done when every transaction type's fields are validated or noted as not applicable.
      
      ## Auxiliary procedure B: group transaction ordering and access control review
      
      For atomic groups, verify group-size bounds, absolute-vs-relative indexing, lease replay protection, and OnComplete fields for every ApplicationCall in the group. Confirm creator/admin privileges on update and delete operations. Done when group-size bounds, indexing, lease protection, and OnComplete are verified for every ApplicationCall.
      
      ## Severity ladder
      
      Critical first, then High, then Medium. The eleven patterns carry fixed severities as named above (Rekeying, CloseRemainderTo, AssetCloseTo, Access controls are CRITICAL; Unchecked transaction fee, Group size check, Asset ID verification, Clear state transaction are HIGH; Time-based replay, DoS via asset opt-in, Inner transaction fee are MEDIUM).
      
      ## Algorand-specific failure notes
      
      - **No Algorand files found.** Stop. Return an empty-target report stating the path was searched and no `.teal` or PyTeal-importing `.py` files were found. Do not fabricate findings.
      - **Pattern not applicable.** Record the pattern as checked-but-not-applicable in coverage notes rather than omitting it, so the done predicate (every applicable pattern checked) is auditable.
      - **Ambiguous code.** Record as an unconfirmed observation with the code location and the specific check that could not be resolved. Do not promote it to a confirmed finding.
      - **Partial-result rule.** Findings are emitted incrementally as confirmed; the report is complete only when all eleven patterns have been checked against every target file. Never report done while a target file or pattern remains unexamined.
      
      ## Algorand output additions
      
      Each finding adds: contract type (stateful application vs smart signature), transaction-field validation matrix status, and Tealer availability. Coverage notes state for each of the eleven patterns `checked` / `not-applicable` / `unconfirmed`, and note Tealer availability and any execution errors.
      
    • cairo.md 6.7 KB
      # Cairo / Starknet detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as Cairo or Starknet. Source indicators and routing live in `SKILL.md`. This file holds the six Cairo vulnerability patterns, the two procedural steps (reachability tie and severity ranking), the Caracal tool requirement, the L1 bridge caveat, and Cairo-specific failure notes.
      
      ## Tool requirement
      
      When Caracal is already installed and available on `PATH`, run its `unchecked-felt252-arithmetic`, `missing-nonce-validation`, and `unchecked-l1-handler-from` detectors. If Caracal is unavailable, skip automated detector runs and rely on the manual pattern checks. State that Caracal was not run so the user knows automated detection was not performed. Never install Caracal during this read-only skill.
      
      ## Surface classification
      
      Confirm Cairo language and StarkNet framework by locating `.cairo` files, `Scarb.toml`, and contract markers (`#[contract]`, `#[storage]`, `#[external(v0)]`, `#[l1_handler]`, `#[constructor]`, `felt252`, `ContractAddress`, `get_caller_address()`, `send_message_to_l1_syscall`). Distinguish Cairo 1.0+ from legacy Cairo 0. Identify L1-L2 bridge contracts if present.
      
      ## L1 bridge caveat
      
      L1 bridge Solidity contracts are optional input, needed to evaluate the L1-L2 patterns (address conversion, message failure, overconstrained interaction, unchecked from_address). If L1 bridge contracts are not supplied, report which L1-L2 patterns could not be fully evaluated and mark those as incomplete rather than passing. Never claim a pattern is clean when the relevant contracts were not available.
      
      ## The six patterns
      
      1. **Felt252 arithmetic overflow/underflow (HIGH).** Search for `felt252` used in arithmetic operations (`+`, `-`, `*`) without bounds checks. Check balance updates, amount transfers, reward calculations, and supply tracking. `felt252` is a field element in range [0, P) where P is the StarkNet prime; unchecked subtraction wraps to ~P and unchecked addition wraps past P. Prefer `u128`/`u256` which have built-in overflow protection. If `felt252` must be used, verify explicit `assert(sender_balance >= amount, 'Insufficient balance')` before subtraction and overflow verification after addition. Run `caracal detect src/ --detectors unchecked-felt252-arithmetic` if Caracal is available.
      
      2. **L1-to-L2 address conversion (HIGH).** For every L1-to-L2 message path, verify the L1 bridge validates `0 < l2Recipient < STARKNET_FIELD_PRIME` (0x0800000000000011000000000000000000000000000000000000000000000001) before calling `sendMessageToL2`. Ethereum addresses are uint256 (256 bits) but StarkNet addresses are felt252 with range [0, P) where P < 2^256; an L1 address >= P maps to zero or an unexpected L2 address. Verify L2 handlers reject zero addresses with `assert(user != zero_address, 'Invalid user address')`.
      
      3. **L1-to-L2 message failure (HIGH).** Check whether the L1 bridge implements message cancellation via `startL1ToL2MessageCancellation` and `cancelL1ToL2Message` with a documented delay period (e.g., 5 days). Without cancellation, funds from L2 messages that the sequencer fails to process are locked permanently. Verify L2 handlers handle replayed messages idempotently after a cancellation attempt.
      
      4. **Overconstrained L1-L2 interaction (MEDIUM).** Compare access control rules on both layers. If L1 enforces a whitelist or blacklist, L2 must enforce the same rules, and vice versa. Asymmetric validation traps funds: deposits succeed on one layer but withdrawals fail on the other. Verify a full deposit-to-withdraw roundtrip is possible for every valid user and that blocked users fail at every step, not just one side.
      
      5. **Signature replay protection (HIGH).** For every signature-verified function, confirm: a per-signer nonce is stored in a `LegacyMap<ContractAddress, felt252>` and incremented after use; the signed message hash includes a domain separator incorporating chain ID (`get_tx_info().unbox().chain_id`) and contract address (`get_contract_address()`); the nonce is validated before execution. Without these, signatures replay on the same chain or across mainnet/testnet. Run `caracal detect src/ --detectors missing-nonce-validation` if Caracal is available.
      
      6. **Unchecked from_address in L1 handler (CRITICAL).** For every `#[l1_handler]` function, confirm `from_address` is validated against a stored authorized L1 bridge address: `assert(from_address == self.l1_bridge_address.read(), 'Unauthorized L1 sender')`. L1-side access control alone is insufficient because an attacker can deploy their own L1 contract to send messages to the handler, bypassing the intended bridge and minting tokens for arbitrary users. Run `caracal detect src/ --detectors unchecked-l1-handler-from` if Caracal is available.
      
      ## Procedural step 1: tie each finding to a reachable code path
      
      For every reported issue, trace from an external entry point (`#[external(v0)]`, `#[l1_handler]`, `#[constructor]`) to the vulnerable statement. Exclude findings that cannot be reached by any caller. A finding that cannot be traced to a reachable entry point is excluded from the report or marked as informational. Never report a vulnerability without a reachable code path.
      
      ## Procedural step 2: rank by severity
      
      - CRITICAL: unchecked `from_address` in L1 handlers (infinite mint), L1-L2 address conversion sending funds to zero address.
      - HIGH: felt252 arithmetic overflow/underflow, missing signature replay protection, L1-L2 message failure without cancellation.
      - MEDIUM: overconstrained L1-L2 interaction (trapped funds).
      
      Every finding gets a severity tag from this ladder.
      
      ## Cairo-specific failure notes
      
      - No Cairo files found. Report that the codebase contains no `.cairo` files and stop. Do not fabricate findings.
      - Caracal unavailable. Skip automated detector runs and rely on manual pattern checks. State that Caracal was not run.
      - L1 bridge contracts not supplied. Report which L1-L2 patterns (address conversion, message failure, overconstrained interaction, unchecked from_address) could not be fully evaluated and mark those as incomplete rather than passing.
      - Finding cannot be traced to a reachable entry point. Exclude it from the report or mark it as informational.
      - Partial result rule. Emit findings for all patterns that could be evaluated. Explicitly list patterns that could not be checked and the reason. Do not swallow errors or pretend the done predicate holds when patterns remain unchecked.
      
      ## Cairo output additions
      
      Each finding adds: Cairo version (1.0+ vs legacy 0), L1-bridge-contracts-present flag, and Caracal availability. Each confirmed finding reports severity tag, location (file:line-range), description, vulnerable code excerpt, attack scenario, and recommended fix with corrected code. Patterns that could not be evaluated are listed as incomplete with the reason.
      
    • cosmos-sdk.md 8.7 KB
      # Cosmos SDK detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as Cosmos SDK, CosmWasm, IBC, or Cosmos-EVM. Source indicators and routing live in `SKILL.md`. This file holds the discovery inventory, the version gate, the six catalogs, the six-item rationalization rejection list, the severity definitions, and Cosmos-specific failure notes.
      
      ## Applicability gate
      
      The codebase must contain Go source with Cosmos SDK `x/` modules and a `go.mod`, or Rust contracts using `cosmwasm_std`; otherwise no Cosmos surface applies and no catalog runs. The scanner derives SDK version, IBC state, and module inventory from the codebase itself.
      
      ## Discovery (technology-routing branch)
      
      Read `go.mod` for the Cosmos SDK version and the `ibc-go` version. Enumerate custom `x/*` modules. Detect an EVM surface (e.g., `evmutil`/`feemarket` precompiles, Ethermint) and a CosmWasm surface (`cosmwasm_std` in Rust contracts). Determine whether IBC is enabled. Produce a discovery inventory with exactly these fields:
      
      - `PLATFORM`: one or more of `cosmos`, `evm`, `wasm`.
      - `IBC_ENABLED`: `true` / `false`.
      - `SDK_VERSION`.
      - `IBC_GO_VERSION` (or `n/a`).
      - `CUSTOM_MODULES`: comma-separated `x/*` list.
      
      This inventory selects which catalogs apply and is never skipped.
      
      ## Version gate
      
      Before applying any pattern, check the SDK version against known breaking changes: v0.47 removed `GetSigners`, v0.50 added ABCI 2.0, v0.53 deprecated `ValidateBasic`. Apply only patterns valid for the detected version. If the SDK version is undetectable, report the affected catalogs as blocked rather than guessing.
      
      ## Per-catalog evidence-backed scan
      
      For each applicable catalog below, search the codebase for its patterns and, for every match, read the surrounding code and verify the match is reachable from a consensus-critical path (`BeginBlock`, `EndBlock`, `FinalizeBlock`, `msg_server` handlers, `AnteHandler`) before treating it as a finding. CLI, query, and test code is not a finding. Each catalog is non-interchangeable; a catalog selected by discovery is checked in full, and a catalog not selected is not substituted by another.
      
      1. **Core** (always applicable): non-determinism, ABCI handling, signers, validation, message handlers, AnteHandler security.
      
      2. **State** (always applicable): bookkeeping, bank, pagination, events, tx replay, governance, arithmetic, encoding, deprecated modules.
      
      3. **Advanced** (always applicable): storage keys, consensus validation, circuit breaker, crypto.
      
      4. **IBC** (applicable when `IBC_ENABLED` is `true`): IBC token handling, packet/acknowledgement, channel, and counterparty patterns.
      
      5. **CosmWasm** (applicable when `PLATFORM` includes `wasm`): CosmWasm contract vulnerability patterns.
      
      6. **EVM** (applicable when `PLATFORM` includes `evm`): EVM/Cosmos state desync, precompile rollback, and EVM-specific patterns.
      
      ## Rationalization rejection list
      
      Dismiss each of these as a reason a match is safe:
      
      1. "`ValidateBasic` catches this" (deprecated and facultative since SDK v0.53).
      2. "behind governance, so safe" (proposals can be malicious).
      3. "IBC counterparty is trusted" (any chain can open a channel).
      4. "panic can't happen, input is validated" (trace the full call chain).
      5. "rounding error is only a few tokens" (compounds and can be looped).
      
      6. "EVM precompile handles rollback" (many have incomplete rollback).
      
      ## Catalog validation and false-positive controls
      
      For every named pattern class in a selected catalog, inspect the source, explain its consensus/state/value effect, and reject matches that do not reach a consensus-critical path:
      
      - Core: inspect iteration over maps/sets or other nondeterministic inputs; ABCI error/panic/latency paths; signer derivation and authorization; message validation/handlers; and AnteHandler ordering/bypass. Confirm deterministic sorting or consensus-safe APIs, version-valid signer/validation mechanisms, and a reachable block/transaction path before reporting. Severity distinguishes fund-loss authorization/Ante bypass (Critical) from halt/non-determinism (High), missing validation DoS (Medium), and stub/order logic (Low).
      - State: inspect conservation bookkeeping, bank keeper calls, unbounded pagination, event emission through cached contexts, replay/idempotency, governance execution, arithmetic/rounding, encoding, and deprecated-module use. Reconcile debits/credits/supply and prove attacker-controlled bounds or replay paths; accept checked arithmetic, explicit rounding invariants, bounded pagination, atomic/cache-safe event handling, and version-supported modules. Severity follows broken bookkeeping/bank misuse/overflow (Critical), event leak halt (High), pagination/replay/governance spam (Medium), or rounding/event override/module ordering (Low).
      - Advanced: inspect storage-key construction, consensus validation gaps, circuit-breaker coverage, and cryptographic/proof verification. Confirm domain-separated collision-free keys, every consensus entry path, breaker enforcement at the actual mutation, and complete proof/domain/input validation. Do not infer a crypto flaw from primitive choice alone. Merkle proof forgery is Critical; consensus gaps that halt are High; breaker bypass or key collision is Medium unless demonstrated impact raises it.
      - IBC: inspect denomination/escrow/mint/burn accounting, packet sequencing/timeouts, acknowledgement determinism and parsing, channel state, and counterparty assumptions. Treat any chain as able to open a channel; validate port/channel/counterparty identity, replay protection, timeout/order semantics, and deterministic acknowledgements. Token inflation is Critical, nondeterministic acknowledgement/consensus halt High, and bounded channel/rate-limit DoS Medium.
      - CosmWasm: inspect contract entrypoints for authorization, funds/denomination checks, reply/submessage handling, arithmetic, storage keys, replay, and cross-contract call results. Confirm the contract is actually reachable from the selected Cosmos surface and that framework/type checks dominate each effect. Assign severity by concrete fund loss, persistent corruption/halt, bounded DoS, or logic impact; never substitute generic Rust lint output for a contract finding.
      - EVM: inspect paired EVM/Cosmos state writes, precompile error/revert paths, gas/value conversion, authorization, and rollback atomicity. Construct the failure path and compare both state domains after revert; do not assume the precompile rolls back. EVM/Cosmos desynchronization is Critical, incomplete rollback that halts consensus High when demonstrated, and bounded precompile DoS Medium.
      
      ## Severity definitions
      
      - Critical (fund loss): signer mismatch, broken bookkeeping, AnteHandler bypass, bank keeper misuse, IBC token inflation, EVM/Cosmos desync, Merkle proof forgery, arithmetic overflow.
      - High (chain halt): non-determinism, ABCI panics, slow ABCI, non-deterministic IBC acks, consensus gaps, CacheContext event leak.
      - Medium (DoS): unbounded pagination, tx replay, missing validation, governance spam, rate limiting, circuit breaker bypass, storage key collisions.
      - Low (logic): rounding errors, stub handlers, event override, module ordering.
      
      ## Report every pattern
      
      For every pattern in every applicable catalog, return one of: a not-applicable entry with a one-line reason, or a finding containing severity, location (`file:line`), description, vulnerable code snippet, attack scenario (numbered steps), and recommendation. No selected catalog is unchecked and no pattern is skipped.
      
      ## Cosmos-specific failure notes
      
      - Non-Cosmos codebase. If the target has no `go.mod` depending on `cosmos-sdk` and no `cosmwasm_std` contracts, stop and report that no Cosmos surface applies. Do not run any catalog.
      - Missing source for a catalog. If a catalog's patterns cannot be assessed because the relevant source files are unavailable or unreadable, report that catalog as blocked with the missing input; do not fabricate findings for it.
      - Match not on consensus path. A match reachable only from CLI/query/test code is not a finding; record it as not-applicable with the reason "not consensus-critical."
      - Partial result. Return the assessed catalogs and explicitly list every unassessed catalog with its blocker. Never claim the done predicate holds while a selected catalog remains unchecked or a pattern is skipped.
      - No errors swallowed. A read or search failure is reported as the blocker for the affected catalog; it is never silently treated as "no findings."
      
      ## Cosmos output additions
      
      The report begins with the discovery inventory (`PLATFORM`, `IBC_ENABLED`, `SDK_VERSION`, `IBC_GO_VERSION`, `CUSTOM_MODULES`). Then per applicable catalog, the pattern assessments (not-applicable reasons or findings with severity, location, vulnerable code, attack scenario, and recommendation). A completeness check lists every applicable catalog with its pattern count, confirming none were skipped.
      
    • solana.md 9.8 KB
      # Solana detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as Solana or Anchor. Source indicators and routing live in `SKILL.md`. This file holds the fifteen Solana vulnerability patterns in six ordered groups, ordered by how often each class drains a program (authority first, because most Solana exploits are authority bugs, not crypto bugs), and Solana-specific failure notes.
      
      ## Surface identification
      
      Identify all Solana Rust (`.rs`) program files under the given path. If no Solana/Anchor program files are found, return that statement and do not fabricate findings.
      
      ## The fifteen patterns in six ordered groups
      
      Check every applicable pattern, grouped by failure mode and ordered by drain frequency.
      
      ### Group 1: authority and ownership (the classic drain path; check before anything clever)
      
      a. **Missing signer checks.** Accounts declared writable or signer but no signer's pubkey validated.
      
      d. **Missing ownership checks.** Account ownership not verified against the expected program.
      
      l. **Anchor discriminator issues.** Discriminator collisions or predictable discriminators.
      
      ### Group 2: external calls (anything that hands control to another program)
      
      b. **Arbitrary CPI.** Invoke calls accepting a program ID derived from user-supplied data without validation.
      
      i. **Unchecked program calls.** `invoke` / `invoke_signed` with unconstrained program IDs.
      
      g. **Reentrancy.** External program calls before state updates are committed.
      
      ### Group 3: account data (parsing and arithmetic on untrusted bytes)
      
      c. **Unsafe account deserialization.** Borsh or other deserializers used without ownership checks.
      
      f. **Type confusion.** Account data parsed under the wrong account type.
      
      k. **Account data size validation.** Bounds not enforced on dynamic account data reads.
      
      h. **Arithmetic overflow/underflow.** Integer operations on account data without checked arithmetic.
      
      j. **Missing rent exemption checks.** Accounts initialized without ensuring rent exemption.
      
      ### Group 4: PDA derivation
      
      e. **PDA collisions.** PDA derivation inputs not hardened; same inputs could yield different PDAs.
      
      ### Group 5: native program and sysvar misuse
      
      m. **Sysvar usage errors.** Incorrect sysvar account types or missing AccountInfo conversions.
      
      n. **System program confusion.** System program instructions processed with wrong discriminators.
      
      ### Group 6: token extensions
      
      o. **Token extensions.** Missing or incorrect MintExtensions, account teleportation protections.
      
      ## Operational validation and false-positive controls
      
      Apply these controls to the correspondingly lettered detector before confirming it. Severity is impact-driven because the source catalog does not assign fixed severities per letter: direct reachable fund loss or authority takeover ranks above persistent corruption/DoS, which ranks above bounded griefing or hardening observations.
      
      - a, signer checks: inspect every writable/authority account and the instruction's signer set. A writable flag or `Signer` declaration alone does not prove the intended authority. Confirm the signer's pubkey is tied to the stored authority, PDA, or protocol role; treat Anchor `has_one`, `constraint`, and equivalent manual comparisons as valid controls. Report the missing binding and the instruction path that lets an attacker substitute a signer.
      - d, ownership checks: inspect every account whose data is read or written. Without an expected owner/program-ID comparison, attacker-owned bytes can impersonate protocol state. Accept Anchor owner/account constraints or an equivalent manual owner check; do not flag executable program or sysvar accounts under their correct native validation. Report the forged-account path and affected state/value.
      - l, Anchor discriminators: inspect custom discriminators, unchecked account loaders, and type dispatch. Collision or predictability matters only when attacker-controlled data can be accepted as another account type. Validate actual discriminator width/value and all surrounding owner/type constraints; do not infer a collision from naming. Report both colliding/ambiguous types and the reachable confused-deputy path.
      - b, arbitrary CPI: inspect CPI program accounts and IDs derived from instruction/account data. User-selected programs can execute attacker logic with the caller's account privileges. Accept equality to the intended program ID or a closed allowlist; distinguish deliberately generic routers whose authority and account capabilities are explicitly constrained. Report the attacker-selected target and delegated privileges.
      - i, unchecked program calls: inspect every `invoke` and `invoke_signed`, including wrapper helpers. An unconstrained executable account can redirect a trusted call. Confirm the called program ID and signer seeds are bound to the intended program and state; avoid duplicating **b** when both describe the same call site. Report the unconstrained ID and reachable invocation.
      - g, reentrancy: inspect state mutation order around every external call/CPI. Control transfer before effects are committed may let a callback observe or reuse stale state. Confirm whether Solana's runtime/account borrowing and the callee graph actually permit re-entry; do not flag checks-effects-interactions-compliant paths or calls after state commit. Report the callback path and duplicated/conflicting effect.
      - c, unsafe deserialization: inspect Borsh and custom byte deserialization sites. Parsing untrusted bytes as trusted state enables forged fields and malformed lengths. Require owner, discriminator/type, and size checks before use; safe framework account loaders count when their constraints apply. Report the untrusted account source and first security-sensitive field use.
      - f, type confusion: inspect casts/loaders that interpret the same account under multiple schemas. A wrong schema can reinterpret authority, balances, or lengths. Confirm discriminator/type-tag and owner checks dominate the parse; do not flag intentional versioned unions with exhaustive tags and bounds. Report expected versus accepted type and the reachable effect.
      - k, account data size: inspect indexing, slicing, and dynamic reads from account data. Missing bounds can panic, abort an instruction, or parse overlapping fields. Accept a dominating exact/minimum length check or a deserializer that proves bounds; demonstrate the attacker-controlled size and failing/read range. Report DoS versus state-confusion impact distinctly.
      - h, arithmetic: inspect integer operations on untrusted account values, balances, counters, and offsets. Wrap, truncation, or panic can corrupt value or halt instructions. Accept checked/saturating arithmetic only when its semantics fit the protocol, plus explicit conversion/range guards; do not flag mathematically bounded operations when the bound is proven on every entry path. Report operands, missing bound, and concrete overflow/underflow impact.
      - j, rent exemption: inspect account creation and initialization funding. A non-exempt account can become invalid or unavailable as rent rules apply. Verify the lamport balance against the current rent sysvar/minimum and account size; do not flag existing accounts whose lifecycle deliberately permits closure. Report persistence/availability impact and initialization path.
      - e, PDA collisions: inspect seed tuples, domain separation, canonical bump handling, and all places reconstructing a PDA. Ambiguous seed concatenation or inconsistent inputs can alias identities or authorize the wrong account. Confirm a single canonical derivation with unambiguous, role-separated seeds and matching bump; do not claim that normal bump search itself creates different valid PDAs. Report both colliding identities/derivations and the authority or state impact.
      - m, sysvar usage: inspect supplied sysvar accounts and conversions to typed sysvars. A forged or mis-typed sysvar can drive false time, rent, or instruction-history decisions. Accept `Sysvar::get`, typed Anchor sysvars, or explicit known-ID plus data validation; report the attacker-controlled substitute and affected decision.
      - n, system program confusion: inspect native System Program instruction decoding and discriminator handling. Processing a native instruction under the wrong variant can transfer lamports or mutate ownership unexpectedly. Validate the program ID, exact instruction discriminator, account ordering, and required signer/writable flags; report the reachable confused instruction and effect.
      - o, token extensions: inspect Token-2022 mint/account extensions, ownership/authority, transfer hooks, and account-reallocation or teleportation paths. Missing extension-aware validation can bypass transfer/authority assumptions or move account state. Confirm required `MintExtensions`, extension compatibility, canonical token program, and anti-teleportation invariants; do not apply Token-2022-only checks to a proven legacy SPL Token surface. Report the extension configuration and resulting authority/value path.
      
      ## Finding fields
      
      For each finding, record: severity, vulnerability type (letter and name), affected files and line ranges, attack path, and recommended fix. No finding lacks any of these five fields. The shared finding fields from `SKILL.md` also apply; the vulnerability type letter (a-o) and failure-mode group are the Solana-specific extra fields.
      
      ## Solana-specific failure notes
      
      - **Codebase not found.** Report the failure and stop without partial results.
      - **No programs found.** Return a statement that no Solana/Anchor program files were found; do not fabricate findings.
      - **Analysis error.** Return partial results if any were produced before the error, prefixed with `[ANALYSIS ERROR]`, and state that the scan could not be completed.
      
      ## Solana output
      
      One severity-ranked vulnerability report; each finding carries severity, vulnerability type, affected files and line ranges, a reachable attack path, and a recommended fix, ordered by severity. Zero findings returns that statement explicitly.
      
    • substrate.md 5.9 KB
      # Substrate detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as a Substrate FRAME pallet. Source indicators and routing live in `SKILL.md`. This file holds the five Trail of Bits pattern families, the pallet-boundary refusal rule, the severity ladder, and Substrate-specific failure notes.
      
      ## Applicability and refusal
      
      - Required: path to the Substrate FRAME pallet source directory or file to scan.
      - Optional: named subset of pattern families to prioritize (origins, weights, arithmetic, panics, unsigned); defaults to all five when omitted.
      - Unreadable path: return `blocked` with the path and error. Do not attempt an alternative path.
      - Pallet boundary violation: return `blocked`. The scan scope is limited to the named pallet and its direct dependencies.
      - No findings confirmed: return `non-converged` only if zero of the five pattern families were reachable for inspection; otherwise return the confirmed findings with `incomplete-scan` noted for the missing families.
      
      ## Validate the pallet path
      
      Confirm the target resolves to a readable Rust source tree or file within a Substrate runtime. Reject paths outside the confirmed pallet boundary immediately.
      
      ## The five Trail of Bits pattern families
      
      Apply the five pattern families (sourced from the ToB Substrate VULNERABILITY_PATTERNS reference) to the pallet's Rust source.
      
      1. **Origin checks**: `ensure_signed`, `ensure_root`, missing `pallet::origin` validation on dispatchable functions; unprivileged `Root` call paths; origin casting bypasses.
      
      2. **Weight accounting**: mismatched `#[pallet::weight]` annotations; underdeclared weight producing out-of-gas in runtime; `TransactionWeight` vs `GasWeight` mismatch; `WeightInfo` trait gaps.
      
      3. **Arithmetic overflow/underflow**: unchecked integer operations in `DispatchResult`; missing `checked_add`/`checked_sub`/`saturating_*` on balance or count fields; `u32`/`u128`/`u256` mixed-width narrowing casts.
      
      4. **Panic invariants**: `unwrap`, `expect`, `panic!` inside dispatchable or storage mutation paths; `Vec::new()` vs `StorageMap::new()` misuse; Option/Result unwrap in `on_initialize`.
      
      5. **Unsigned transaction guard**: missing `ValidateUnsigned` implementation or bypassed `CheckNonce`; `BaseCallFilter` exclusions; `#[pallet::call(no_typed_default)]` on unsigned dispatchables.
      
      ## Enumerate call paths
      
      
      For each finding, trace the exact dispatch path from entry dispatchable to the vulnerable call site. Record the module, function, and line range. Every finding has a call path.
      
      ## Operational validation and false-positive controls
      
      - Origin checks: inspect every dispatchable's origin conversion and every privileged call path. Missing or lossy origin validation can yield privilege escalation or takeover. Accept a dominating `ensure_signed`/`ensure_root`/custom origin check whose resulting identity is bound to the protected action; do not infer safety or vulnerability from function names. Rank direct takeover/fund extraction Critical and reachable escalation High.
      - Weight accounting: compare the declared `#[pallet::weight]`, benchmark/`WeightInfo` implementation, actual storage/execution work, and `TransactionWeight`/`GasWeight` conversions. Underdeclaration enables block exhaustion or griefing. Confirm bounded inputs and benchmark-derived weights before reporting; a mere absent-looking annotation is not enough if the macro supplies a correct equivalent. Rank chain-impacting DoS High and bounded weight/storage griefing Medium.
      - Arithmetic overflow/underflow: inspect balance/count operations and mixed-width conversions on reachable dispatch/storage paths. Wrap, truncation, or panic can corrupt funds/state or halt execution. Accept proven input bounds and checked/saturating operations only when saturation is the intended invariant; demonstrate operands and consequence. Rank direct fund extraction Critical, reachable DoS High, bounded griefing Medium.
      - Panic invariants: trace `unwrap`, `expect`, `panic!`, collection/storage misuse, and `on_initialize` failure sites from dispatch or hooks. A panic can invalidate a block or halt the chain. Exclude provably unreachable invariant assertions and test-only code; require a concrete attacker/state path. Rank chain halt High, bounded griefing Medium, gas-only inefficiency Low.
      - Unsigned transaction guard: inspect every unsigned dispatchable, `ValidateUnsigned`, nonce/replay validation, `BaseCallFilter`, and `no_typed_default` use. Missing validation permits forged/replayed state transitions. Accept a complete equivalent validation path only when it binds payload, signer/authority, freshness, and call; do not assume `CheckNonce` covers unsigned calls. Rank takeover/fund extraction Critical, privilege/replay DoS High, bounded spam Medium.
      
      ## Severity ladder
      
      - Critical: direct fund extraction or chain takeover.
      - High: privilege escalation or DoS.
      - Medium: weight griefing or griefing via storage.
      - Low: informational or gas inefficiency.
      
      Emit a finding only when evidence is concrete; do not infer from naming conventions alone.
      
      ## Remediation
      
      For each confirmed finding, state the specific fix: code change, lint addition, or architectural pattern correction. Ground the remediation in the pallet's actual dispatchable signature and storage layout.
      
      ## Substrate-specific failure notes
      
      - **Partial result.** If inspection halts mid-pallet (e.g. tool error), return `incomplete-scan` with the last confirmed finding and the remaining pattern families listed.
      
      ## Substrate output
      
      A structured chat report. Each finding: `Pattern: <family>`, `Severity: <Critical|High|Medium|Low>`, `Call path: <module>::<function> (lines N–M)`, `Evidence: <concrete observation>`, `Remediation: <specific fix>`. Followed by a summary table (Pattern | Severity | Confirmed) and a completeness statement against the five families. The pattern family and call-path evidence (`module::function (lines N–M)`) are the Substrate-specific extra fields.
      
    • ton.md 8.2 KB
      # TON detectors
      
      Loaded only after `chain-vulnerability-scanner` classifies the target as TON (FunC or Tact). Source indicators and routing live in `SKILL.md`. This file holds the seven TON pattern categories and all 28 checks, the scope-binding rule, the severity ladder, the evidence rule, and TON-specific failure notes.
      
      ## Scope binding
      
      The user-supplied scope is a list of one or more of the pattern categories below, or `"all"` to cover every category. Reject if scope contains a category not listed here. Fail immediately if source is absent or empty. Categories with no scope entry are skipped without warning.
      
      ## Source validation
      
      Confirm the source contains at least one FunC function definition or Tact contract block. Fail if the source does not match any TON source indicator (function definitions, message handlers, `recv_internal`, `recv_external`, `op::` constants, or `@interface` annotations). Do not treat inline assembly comments as function definitions.
      
      ## The seven categories and 28 checks
      
      For each category the scope covers, apply the corresponding checks.
      
      ### a. Replay protection (5 checks)
      
      1. Missing or unconditional `accept_message()` before state-changing operations.
      2. `msg.data` size not validated before signature verification.
      3. Empty signature accepted for privileged operations.
      4. External message without idempotency guard (missing `nonce` or `timestamp` check).
      5. `verify_signature` absent before storage write in operation handlers.
      
      ### b. Access control (4 checks)
      
      1. `op` value used without a whitelist mapping.
      2. `sender_address` read and acted upon without `is_owner` or equivalent admin check.
      3. `admin` storage variable used without a `require` guard.
      4. Internal methods callable without an authentication check.
      
      ### c. Sender validation (3 checks)
      
      1. `bounced` flag not checked in handlers that must differentiate bounced messages from normal receipts.
      2. `sender_address` not validated after cross-contract calls where the caller address matters.
      3. `my_address()` not used to verify destination in proxy-pattern contracts.
      
      ### d. Validation and bounds (4 checks)
      
      1. Arithmetic on `VarInteger` without overflow guards (`mul`, `add`, `sub` on untrusted amounts).
      2. Array or dictionary access without bounds or existence check.
      3. `throw` or `throw_if` absent where the callee reverts on error and the caller ignores the error code.
      4. Unchecked return value from `call` or external contract invocation.
      
      ### e. Data and storage exposure (4 checks)
      
      1. Persistent storage key derived from untrusted input without a namespace prefix.
      2. Sensitive value (private key, seed, admin address) written to a public storage variable.
      3. Get method that returns unrestricted internal state.
      4. Storage layout that allows cross-user data interference through sequential key allocation.
      
      ### f. Logic and state machine flaws (4 checks)
      
      1. State transition that can be reached through two different valid `op` paths with conflicting effects.
      2. Pending async operation assumed complete without a completion event check.
      3. Message ordering dependency without a queue or FIFO guard.
      4. Unconditional `send_raw_message` without error handling in a conditional path.
      
      ### g. Denial of service (4 checks)
      
      1. Unbounded `for` or `while` loop on user-controlled data.
      2. Gas-unlimited external call (missing `gas_remaining` check before `call`).
      3. Storage allocation unbounded by user value (no cap on dictionary or cell growth).
      4. Init function callable after deployment without a migration guard.
      
      ## Evidence rule
      
      For every confirmed finding, extract the exact source lines, quote them verbatim, and state which pattern they violate.
      
      ## Severity ladder
      
      - Critical: direct fund loss or permanent state destruction.
      - High: persistent corruption or persistent DoS.
      
      - Medium: temporary state issue or high-precondition exploit.
      - Low: information disclosure or minor logic anomaly.
      - Informational: best-practice violation with no direct exploit path.
      
      ## Validation and false-positive controls
      
      For every numbered check, inspect the named operation at each reachable message handler, explain why the absent guard changes state/value/authentication, and validate equivalent controls before reporting:
      
      - Replay protection: prove an external-message path reaches a privileged or state-changing operation. Treat a dominating size check, non-empty signature check, valid `verify_signature`, and consumed nonce/timestamp as controls only when they cover the same path; `accept_message()` is not authentication. Rank direct replayed fund loss Critical, persistent replay corruption High, and a non-exploitable best-practice gap Informational.
      - Access control: trace the `op`, sender/admin value, and internal method to its protected effect. A closed operation whitelist and a dominating owner/admin authentication are valid controls; names such as `admin` or `internal` alone are not evidence. Rank reachable unauthorized fund/state destruction Critical and persistent privilege corruption High.
      - Sender validation: establish that bounce status, post-call sender identity, or proxy destination changes the handler's semantics. Accept equivalent canonical-address and bounce-branch validation; do not report when the value is provably unused in a security decision. Rank by the reachable value/state consequence.
      - Validation and bounds: identify the attacker-controlled amount, index/key, ignored error, or call return and its sink. Accept proven range/existence checks, checked arithmetic, or explicit failure propagation that dominates the sink. Distinguish direct value corruption (Critical), persistent corruption/DoS (High), and temporary/high-precondition failure (Medium).
      - Data and storage exposure: prove an untrusted key can collide, the stored/getter value is actually sensitive, or sequential allocation crosses users. Namespace/domain separation, access-restricted getters, and disjoint per-user storage are valid controls. Do not classify a public admin address as secret solely because it is an admin identifier; report authority exposure only when confidentiality matters or mutation/interference is reachable.
      - Logic and state machine flaws: construct the two conflicting operation paths, missing completion transition, ordering permutation, or failed-send branch. Do not report a theoretical sequence when the state machine, queue, or idempotent completion guard makes it impossible. Severity follows permanent destruction/corruption, persistent DoS, or temporary/high-precondition impact.
      - Denial of service: identify the user-controlled loop bound, gas/call budget, growth value, or repeatable initialization entry. Accept hard caps, bounded collections, `gas_remaining` guards, and one-way deployment/migration state. Report persistent DoS High; bounded or high-precondition temporary failure Medium; a best-practice-only observation Informational.
      
      ## Mitigation rule
      
      For each finding, write one concrete remediation: specific code change or architectural correction. Do not defer to "review manually". Every finding gets a concrete mitigation.
      
      ## TON-specific failure notes
      
      | Failure class | Behavior |
      |---|---|
      | Invalid source format | Stop. Return `"Unable to analyze: source does not appear to be TON FunC or Tact code."` |
      | No patterns in scope | Stop. Return `"Scope contains no recognized TON vulnerability categories."` |
      | Scan error (crash, OOM, tool failure) | Stop. Return `"Scan failed: [exact error class]. No findings are returned."` |
      | No findings | Return `"No vulnerabilities found in the requested scope."` with the scope and date. This is not a failure. |
      | Scope partially checked due to source size limit | Stop. Return `"Scan incomplete: source exceeds analysis size limit. Findings below are from the partial scan:"` followed by all findings found. Do not omit the scope overrun warning. |
      
      Rollback rule: no local or remote state is modified by this skill. No rollback required.
      
      ## TON output
      
      A structured report with date, scope, severity floor, and findings ordered Critical to Informational. Each finding names its severity, category, short description, verbatim evidence, location (filename:line range), and concrete mitigation. If no findings, the empty-result message is returned. The scope (category list), severity floor, and date are the TON-specific extra fields.
      
  • SKILL.md 14.8 KB
    ---
    name: chain-vulnerability-scanner
    description: 'Use when an Algorand, Cairo, Cosmos SDK, Solana, Substrate, or TON codebase needs vulnerability scanning with reachability-backed findings. Not for non-chain review: use security-review.'
    disable-model-invocation: true
    ---
    
    # Chain vulnerability scanner
    
    A single read-only scan operation that classifies a blockchain codebase by ecosystem, loads only that ecosystem's detector catalog, and emits severity-ranked findings tied to reachable code paths. Six ecosystems are supported; each owns one flat reference file under `references/` that holds its detectors, applicability gates, tool requirements, severity distinctions, and ecosystem caveats. This file holds the shared routing, authority, procedure, cross-cutting rules, failure behavior, and output contract.
    
    ## Ecosystem routing
    
    | Ecosystem | Source indicators | Reference file |
    |---|---|---|
    | Algorand | `.teal` files; `.py` importing PyTeal or Algorand SDK (`from pyteal import *`, `from algosdk import *`, `Txn`, `Gtxn`, `Global`, `InnerTxnBuilder`, `OnComplete`, `@router.method`, `@Subroutine`); `approval_program.py`/`clear_program.py`, `contract.teal`/`signature.teal`, Beaker references. | `references/algorand.md` |
    | Cairo / Starknet | `.cairo` files; `Scarb.toml`; contract markers `#[contract]`, `#[storage]`, `#[external(v0)]`, `#[l1_handler]`, `#[constructor]`, `felt252`, `ContractAddress`, `get_caller_address()`, `send_message_to_l1_syscall`. Optional L1 bridge Solidity contracts for cross-layer patterns. | `references/cairo.md` |
    | Cosmos SDK | Go source with Cosmos SDK `x/` modules and `go.mod`; `ibc-go`; Ethermint/EVM precompiles (`evmutil`/`feemarket`); Rust contracts using `cosmwasm_std`. | `references/cosmos-sdk.md` |
    | Solana | Solana or Anchor Rust (`.rs`) program files. | `references/solana.md` |
    | Substrate | Substrate FRAME pallet Rust source tree or file within a runtime. | `references/substrate.md` |
    | TON | FunC or Tact source (function definitions, message handlers, `recv_internal`, `recv_external`, `op::` constants, `@interface` annotations). | `references/ton.md` |
    
    If the codebase matches none of the indicators above, stop and report that no supported chain surface applies. Do not run any catalog. Route generic non-chain security review to `security-review` instead: chain-vulnerability-scanner loads ecosystem-specific detector catalogs for six supported blockchain ecosystems; security-review runs STRIDE and OWASP on any codebase. The split is: supported chain ecosystem → chain-vulnerability-scanner; any other codebase → security-review.
    
    ## Contract
    
    | Field | Bound contract |
    |---|---|
    | Trigger | A supported Algorand, Cairo, Cosmos SDK, Solana, Substrate, or TON codebase needs a chain-specific vulnerability sweep. |
    | Authority | Read-only. No file, VCS, credential, paid, published, deployed, or remote mutation. Tealer and Caracal, when already installed, run only as read-only analyzers on local source. Never install missing tools; installation is a state-changing action outside read-only authority. |
    | Side effect | Severity-ranked, reachability-backed findings emitted as chat output only, each with location, evidence, impact, remediation, and validation status. |
    | Done | Every applicable detector in every selected ecosystem reference is checked, and each confirmed finding carries code evidence, a reachable attack path, and remediation. |
    
    ## Inputs
    
    - Target codebase path (required): a path containing source for one or more supported ecosystems.
    - Ecosystem scope (derived): the scanner classifies every supported ecosystem present under the target path. The user MAY name a detector subset for Algorand, Cairo, Cosmos SDK, Solana, or Substrate; those ecosystems default to all detectors when omitted.
    - TON category scope (required for TON): a non-empty list of categories from `references/ton.md`, or `"all"`.
    - Optional severity floor (TON): if omitted, all findings are returned.
    - Optional auxiliary source (Cairo): L1 bridge Solidity contracts, needed to evaluate L1-L2 patterns.
    - Optional analyzers already installed: Tealer for Algorand and Caracal for Cairo. Record their absence as a coverage gap; never install them during this read-only skill.
    
    ## Shared procedure
    
    Run these steps in order. Each ecosystem reference may attach ecosystem-specific sub-steps, detectors, and gates to steps 3, 4, and 6; this file holds only the shared spine.
    
    1. **Classify ecosystems and applicability.** Search the supplied path for the source indicators in the routing table. Select every supported ecosystem present and name its reference file. If multiple top-level ecosystems coexist, scan each as one branch of the same invocation. A Cosmos branch uses its own discovery step to enumerate EVM, CosmWasm, and IBC sub-catalogs. If no supported surface matches, stop and report an empty-target result. **Done when:** every detected ecosystem and reference is recorded, or an empty-target result is reported.
    
    2. **Load only selected references.** For each detected ecosystem branch, read its single named reference before scanning that branch. Do not load references for ecosystems absent from the target. Each selected reference supplies the detector list, applicability/version gates, tool commands, severity definitions, rationalization rejections, and ecosystem caveats that govern the branch. **Done when:** every selected reference is loaded and its applicability gates (e.g., Cosmos version gate, Cairo L1-bridge presence, TON scope validation) have been evaluated.
    
    3. **Inventory trust/state/value boundaries.** Enumerate the codebase's transaction-field usage, trust boundaries, state-mutation sites, value-transfer paths, and external entry points, using the reference's detector list as the lens. Record the file list and contract/module inventory. **Done when:** the boundary inventory is recorded or an empty-target result is reported.
    
    4. **Run source and ecosystem tools.** Invoke Tealer for Algorand `.teal` targets and Caracal for Cairo targets when already installed; capture detector output. If a tool is absent or errors, record the gap in coverage notes and proceed with the manual detector sweep from the selected reference. A tool failure never invalidates manual findings. **Done when:** tool output is captured for each applicable target or its absence/error is recorded.
    
    5. **Confirm semantic reachability.** For every candidate finding, trace from an external entry point (ecosystem-specific: Algorand approval/smart-signature paths; Cairo `#[external(v0)]`, `#[l1_handler]`, `#[constructor]`; Cosmos consensus-critical paths `BeginBlock`/`EndBlock`/`FinalizeBlock`/`msg_server`/`AnteHandler`; Solana instruction entrypoints; Substrate dispatchables; TON message handlers) to the vulnerable statement. A match reachable only from CLI, query, or test code is not a finding; record it as not-applicable with the reason "not consensus-critical" (Cosmos) or the ecosystem's equivalent. Exclude findings that cannot be reached by any caller; mark ambiguous cases as unconfirmed observations, never promoted to confirmed findings. **Done when:** every candidate finding is traced to a reachable entry point or excluded.
    
    6. **Apply severity rules.** Assign severity per the reference's definitions. Each ecosystem owns its own severity ladder and category-to-severity mapping; use the reference's, not a generic one. Where the reference lists rationalization rejections (Cosmos) or caveats (Cairo L1 bridge), apply them verbatim. **Done when:** every finding has a severity tag drawn from the reference.
    
    7. **Emit normalized findings.** Rank findings by severity (Critical first, then High, then Medium, then Low, then Informational where the ecosystem defines it). For each confirmed finding emit the shared finding fields below plus any extra ecosystem fields the reference requires. Append coverage notes listing detectors checked, detectors not applicable, tool availability, and any unassessed detectors with their blocker. **Done when:** findings are ranked with evidence and remediation, plus coverage notes, and the done predicate is auditable.
    
    ## Shared finding fields
    
    Every confirmed finding carries all of these:
    
    - ecosystem: one of `algorand`, `cairo`, `cosmos-sdk`, `solana`, `substrate`, `ton`.
    - component/path and line: file and line range (`file:line-range`), plus module/function/call-path where the ecosystem reference requires it (Substrate `module::function (lines N–M)`; Cosmos `file:line`; Solana affected files and line ranges).
    - detector/category: the named detector or pattern category from the reference (e.g., Algorand "Rekeying", Solana "a. Missing signer checks", TON category letter + name).
    - severity: from the reference's severity ladder.
    - confidence: `confirmed`, `unconfirmed`, or `not-applicable` (for coverage notes).
    - reachability: the traced entry point to vulnerable statement path, or `not-reachable` (excluded).
    - evidence: verbatim vulnerable code excerpt, quoted from source.
    - impact: attack scenario, numbered exploit steps, fund-loss or chain-halt description per the reference.
    - remediation: concrete fix with corrected code; never "review manually" (TON refuses this; all ecosystems require a specific code change or architectural correction).
    - validation status: `validated`, `unvalidated`, `partial`, or `error`, reflecting whether the finding was confirmed by tool plus manual review, manual only, or could not be fully checked.
    
    Extra ecosystem fields retained from the source:
    
    - Algorand: contract type (stateful application vs smart signature), transaction-field validation matrix status, Tealer availability.
    - Cairo: Cairo version (1.0+ vs legacy 0), L1-bridge-contracts-present flag, Caracal availability.
    - Cosmos: discovery inventory (`PLATFORM`, `IBC_ENABLED`, `SDK_VERSION`, `IBC_GO_VERSION`, `CUSTOM_MODULES`), applicable catalog list.
    - Solana: vulnerability type letter (a–o), failure-mode group.
    - Substrate: pattern family, call-path evidence (`module::function (lines N–M)`), completeness statement against the five families.
    - TON: scope (category list), severity floor, date.
    
    ## Cross-cutting rules
    
    - One coherent scan, not six modes. One invocation may contain one or more detected ecosystem branches. Each branch loads only its own reference and returns findings through the same shared contract. Cosmos EVM, CosmWasm, and IBC surfaces remain sub-catalogs of the Cosmos branch.
    - Record missing tools; fail closed on missing version evidence. If an optional analyzer is absent, record the gap and continue with manual detectors; never install it. If version evidence required by an applicability gate is missing (e.g., Cosmos SDK version undetectable, Cairo version ambiguous), report the affected detectors as blocked rather than guessing.
    - Never fabricate findings. Record a finding only when vulnerable code is located with a concrete file and line reference and traced to a reachable entry point. Ambiguous code is an unconfirmed observation, not a finding.
    - Never swallow errors. A read or search failure is reported as the blocker for the affected detector; it is never silently treated as "no findings."
    - Partial-result rule. Findings are emitted incrementally as confirmed. The report is complete only when every applicable detector has been checked against every applicable target. Never report done while a target file or detector remains unexamined. Explicitly list every unassessed detector with its blocker.
    - Non-mutation rule. No file is created, edited, moved, or deleted. No git, build, install, deploy, or remote action is performed. Recovery from any failure is to report the failure and continue or stop; never to mutate state to work around it.
    - Rationalization rejection (Cosmos, applied where the reference states). The six Cosmos rationalizations ("`ValidateBasic` catches this", "behind governance, so safe", "IBC counterparty is trusted", "panic can't happen, input is validated", "rounding error is only a few tokens", "EVM precompile handles rollback") are dismissed as reasons a match is safe. Other ecosystems' references state their own caveats (e.g., Cairo L1-bridge-contracts-absent marks L1-L2 patterns incomplete, not clean).
    
    ## Failure behavior
    
    | Failure class | Behavior |
    |---|---|
    | No supported ecosystem surface | Stop. Report the path was searched and no supported chain source indicators were found. Do not fabricate findings. |
    | Ecosystem tool not installed | Continue with the manual detector sweep from the reference. Record the tool absence in coverage notes. Do not attempt installation. |
    | Ecosystem tool execution error | Capture the error message, include it in coverage notes, and proceed with the manual sweep. A tool failure does not invalidate manual findings. |
    | Missing version evidence for an applicability gate | Report the affected detectors/catalogs as blocked with the missing evidence. Do not guess a version. |
    | Missing auxiliary source (Cairo L1 bridge) | Report which patterns could not be fully evaluated and mark them incomplete, not clean. |
    | Detector not applicable | Record the detector as checked-but-not-applicable in coverage notes rather than omitting it, so the done predicate is auditable. |
    | Ambiguous code (cannot confirm vulnerable or safe) | Record as an unconfirmed observation with the code location and the specific check that could not be resolved. Do not promote it to a confirmed finding. |
    | Match not on a consensus/reachable path | Not a finding. Record as not-applicable with the reason (e.g., "not consensus-critical" for Cosmos CLI/query/test code). |
    | Scan error (crash, OOM, tool failure halting the run) | Stop. Return `"Scan failed: [exact error class]. No findings are returned."` (TON rule, applied ecosystem-wide for halting errors). |
    | No findings | Return the empty-result statement with ecosystem, scope, and date. This is not a failure. |
    | Partial result (source size limit or mid-scan halt) | Return assessed detectors and explicitly list every unassessed detector with its blocker. Include the scope-overrun warning where applicable (TON). Never claim the done predicate holds while a detector remains unchecked. |
    
    ## Output
    
    A chat-output report with the following structure:
    
    - Header: ecosystems, project path, files scanned, contract/module types identified, tool availability, and ecosystem discovery inventory where defined (Cosmos).
    - Findings: one entry per confirmed vulnerability, ranked Critical > High > Medium > Low > Informational (where the ecosystem defines the rung). Each entry carries the shared finding fields above plus any extra ecosystem fields.
    - Coverage notes: for each detector in the loaded reference, state `checked` / `not-applicable` / `unconfirmed` / `blocked`, and note tool availability and any execution errors. For Cosmos, include a completeness check listing every applicable catalog with its pattern count, confirming none were skipped.
    
    The done predicate holds when every applicable detector in every selected reference is checked and each confirmed finding carries code evidence, a reachable attack path, and remediation.
    

Comments (0)

Sign in to join the conversation.

No comments yet.

Reviews (0)

No reviews yet.

Related