martinholovsky/sota-skills · Archived

sota-rust

>- State-of-the-art Rust engineering (2026) for writing and auditing Rust code. Covers idiomatic ownership and API design, error handling and panic policy, unsafe discipline with Miri, async/tokio (cancellation safety, structured concurrency, graceful shutdown), security and supply chain (cargo audit/deny/vet, integer overflow, serde hardening, zeroize), performance (profiling, allocation reduction, release profiles), and tooling/CI (clippy policy, nextest, MSRV, feature hygiene, edition 2024).…

First seen Jun 17, 2026

Installation

$ npx skills add martinholovsky/sota-skills --skill sota-rust

Stronger alternatives

This repository is archived — consider an actively maintained alternative.

Also in this package

Other skills from martinholovsky/sota-skills · top by installs.

npx skills add martinholovsky/sota-skills

Browse all from martinholovsky/sota-skills

More details

Agent compatibility

Declared targets from SKILL.md / docs. Unmarked agents are not listed — the skill may still install via the CLI.

Claude Code Not declared
Cursor Not declared
Codex Not declared
GitHub Copilot Not declared
Windsurf Not declared
Gemini CLI Not declared
Cline Not declared
OpenCode Not declared

Repository health

Stars 18
License LICENSE
Default branch main
Open issues 0
Status Archived

Package contents

Files included with this skill beyond the listing page.

  • skill md SKILL.md 10,635 B
  • docs SUMMARY.md 871 B

History

  1. First seen on skills.sh
  2. First recorded snapshot · 2 installs

SKILL.md

SOTA Rust (2026)

Purpose

This skill encodes the 2026 state of the art for production Rust: the idioms, security posture, performance discipline, and CI baseline expected of an expert Rust codebase. Baseline as of mid-2026: a recent stable Rust toolchain (verify the current release at blog.rust-lang.org), edition 2024 (next edition expected ~2027), tokio still 1.x. It serves two modes — BUILD (write new code to this standard) and AUDIT (find where existing code falls short, with severity and evidence). The detailed rules live in rules/*.md; load only the files relevant to the task (see index below). Every rules file ends with an "Audit checklist" of grep/clippy patterns — use those verbatim in AUDIT mode.

BUILD mode

When writing or modifying Rust code:

  1. Scope the work, load the rules. Pick the relevant rules/ files from

the index. Touching async code? Load 04. Adding a dependency, parsing network input, or spawning an external program? Load 05. Writing any unsafe? Load 03 — no exceptions.

  1. Design types first. Newtypes for domain primitives, errors per

subsystem (thiserror for libs, anyhow for apps), ownership tree before Arc<Mutex<_>>, public API minimal and borrowed (&str/&[T] params). Parse, don't validate: constructors enforce invariants.

  1. Write to the non-negotiables (bottom of this file) without being asked.

They are defaults, not suggestions; deviations carry a written justification at the site (e.g. expect with invariant message, #[allow(lint, reason = "...")]).

  1. Wire the scaffolding with the code, not after: lints in [lints],

deny.toml + cargo deny in CI for anything deployed, Miri job if unsafe exists, nextest, MSRV declared and tested, benches for claimed-hot paths. See rules/07 §9 for the CI shape to copy.

  1. Verify before claiming done: cargo fmt --check, `cargo clippy

--all-targets --all-features -- -D warnings, cargo nextest run + cargo test --doc, and cargo doc warning-free for libraries. If you wrote unsafe: cargo +nightly miri test` over it. If you claimed performance: show the benchmark.

  1. Comment intent at decision points the next reader will question:

justified clones, cancel-safety of select! arms, SAFETY comments, channel-capacity choices, poisoning policy.

AUDIT mode

When reviewing or auditing existing Rust:

  1. Recon first: cargo metadata/workspace layout, Cargo.toml profiles

and features, CI config, rg 'unsafe' --count-matches, dependency tree (cargo tree -d). This decides which rules files to load and where risk concentrates (network input? unsafe? async service?).

  1. Run the audit checklists at the end of each loaded rules file — they

are ordered grep/clippy hunts with pre-calibrated severities.

  1. Validate every finding: read the surrounding code; a grep hit is a

lead, not a finding. Confirm reachability (is the unwrap on an attacker-influenced path?) before assigning severity.

  1. Report with the finding format below. Prefer few, true, prioritized

findings over volume. Note positive observations where the code is already SOTA (prevents "fixes" that regress good decisions).

Severity conventions

Severity Meaning Examples
Critical Exploitable now, or UB reachable UB, unsound safe API, SQLi/path traversal, authn bypass, unwinding across FFI, secrets in logs+repo
High Exploitable under realistic conditions, or correctness loss attacker-reachable panic/OOM (DoS), wrapped arithmetic on untrusted lengths, cancellation data loss, deadlock (block_on in async, lock across await), unbounded channels fed by network, missing dep-audit in deployed-service CI
Medium Latent defect or eroded defense missing SAFETY comments, no Miri CI on unsafe crate, swallowed errors (.ok(), filter_map(Result::ok)) uncommented, untested MSRV, non-additive features, orphaned spawned tasks
Low Hygiene, idiom, maintainability clone-to-satisfy-borrowck, index loops, missing #[non_exhaustive], missing # Errors docs, blanket #[allow] without reason

Severity scales with reachability (attacker-controlled > user > operator > build-time) and blast radius (process death > request failure > slow).

Finding format

[SEVERITY] short title
  Where: path/to/file.rs:123 (fn name / module)
  What:  the defect, in one or two sentences
  Why:   concrete consequence (exploit path, failure mode, cost)
  Fix:   specific change — code sketch or named pattern from rules/NN
  Effort: trivial | small | medium | large
  Refs:  rules/NN §M; clippy lint or RUSTSEC id if applicable

Group findings by severity, Critical first. End with: checklist coverage (which rules files were applied), what was not reviewed, and quick wins (one-line fixes with outsized value).

Rules index

File Read this when...
[rules/01-ownership-and-api-design.md](rules/01-ownership-and-api-design.md) Designing structs/traits/modules/workspaces; fighting the borrow checker; deciding clone vs borrow vs Rc/Arc; newtype, typestate, builder patterns; sealed traits, coherence; comparison-trait (Eq/Ord) invariants; exhaustive matching; iterator-chain idioms
[rules/02-errors-and-panics.md](rules/02-errors-and-panics.md) Choosing thiserror vs anyhow/eyre; designing error enums; unwrap/expect policy and invariant messages; context discipline; panic policy for servers, FFI, and Drop (no panic in destructors); Option/Result combinator flow; not unwrapping an Option back into a sentinel (unwrap_or(-1), serde(default) on numbers)
[rules/03-unsafe-discipline.md](rules/03-unsafe-discipline.md) Writing or reviewing ANY unsafe; SAFETY comment standards; UB catalog (aliasing, uninit, transmute, FFI lifetimes); Miri/sanitizers/loom in CI; cargo-geiger; soundness review protocol
[rules/04-async-tokio.md](rules/04-async-tokio.md) Anything async: tokio, spawn vs spawn_blocking, Send/Sync bound errors, select! and cancellation safety, JoinSet/TaskTracker, channel selection, locks across await, async traits, graceful shutdown
[rules/05-security-supply-chain.md](rules/05-security-supply-chain.md) Network-facing or deployed code; adding dependencies; cargo audit/deny/vet; integer overflow on untrusted input; panic-DoS; zeroize/constant-time for secrets; serde hardening (untagged enums, size limits); service-edge defaults; spawning external programs (std::process::Command — argv vs shell, the Windows .bat CVE, a dropped Child that keeps running, deadlines that don't kill, §9)
[rules/06-performance.md](rules/06-performance.md) Performance work or claims: profiling (samply/perf/flamegraph, criterion/divan), allocation reduction (Cow/SmallVec/buffer reuse), accidental clones, iterator fusion, release profile (LTO, codegen-units, panic=abort), PGO
[rules/07-tooling-ci.md](rules/07-tooling-ci.md) Setting up or auditing repo scaffolding: clippy policy and pedantic triage, rustfmt, nextest, MSRV declaration+testing, additive feature flags, docs.rs discipline, edition 2024 migration, CI baseline. **Test strategy — suite shape, TDD, doubles, test data, flake policy — lives in sota-testing; load it for any build that writes logic. This file owns Rust runner mechanics only.**

Top-10 non-negotiables

  1. No unwrap()/bare expect() on production paths. Propagate with ? +

context; expect("...") only with a message proving the invariant. An attacker-reachable panic is a DoS. (rules/02)

  1. Every unsafe block has a // SAFETY: comment discharging the called

API's documented preconditions, and lives behind a sound safe abstraction. Unsafe code without Miri in CI is unaudited code. (rules/03)

  1. **Libraries: thiserror enums with #[source] chains. Applications:

anyhow with .context().** Never anyhow::Error in a public lib API; never silently swallowed errors. (rules/02)

  1. Never block the async runtime: no sync I/O, std::thread::sleep, or

sustained CPU inside async fn; spawn_blocking or a compute pool. No std::sync::MutexGuard held across .await. (rules/04)

  1. Every select!/timeout/abort path is cancellation-reviewed: futures

dropped at any .await; cancel-unsafe ops don't go in select! arms; invariants spanning awaits get drop guards. Spawned tasks are owned (JoinSet/TaskTracker), never orphaned. (rules/04)

  1. Untrusted input gets checked arithmetic, size limits, and depth limits:

checked*/tryinto on lengths (release mode wraps silently), body-size caps before parsing, no #[serde(untagged)] or uncapped with_capacity on hostile data. (rules/05)

  1. Supply chain is CI-enforced: cargo deny/cargo audit on PRs +

scheduled, Cargo.lock committed, new deps vetted (cargo vet or documented review), git deps pinned by rev. (rules/05)

  1. **Secrets are typed (SecretString/Zeroizing), redacted from

Debug/logs, and compared in constant time** (ct_eq). Key material only from OS randomness. (rules/05)

  1. **Don't clone to satisfy the borrow checker; don't take owned params you

only read.** &str/&[T] in signatures, split borrows, mem::take; newtypes over primitive obsession; exhaustive matches (no lazy _ => on owned enums). (rules/01)

  1. **CI gate: fmt + clippy -D warnings (triaged pedantic) + nextest +

doctests + MSRV job + feature-matrix check.** Performance claims require benchmarks; release profile (LTO/codegen-units/panic strategy) is a deliberate, documented choice. (rules/06, 07)