Skip to main content

Threat Model

This document describes the assets Stave protects, the threats it faces, and how each is mitigated.

Assets

AssetSensitivityWhere
Observation snapshotsMay contain infrastructure details, bucket names, ARNs, tagsUser filesystem (input)
Evaluation findingsReveals which assets are unsafe and whystdout or --out file
Stave binaryMust be authentic and untamperedUser filesystem / release download
Control definitionsDefine what "unsafe" means; tampering changes evaluation semanticsUser filesystem or shipped pack

Trust Boundaries

1. File Input Boundary

Stave reads observation and control files from the local filesystem. Observations are treated as untrusted input — they may come from external tools and could be malformed or crafted.

Controls:

  • Full JSON Schema validation with additionalProperties: false — extra fields cause immediate rejection.
  • Path traversal protection on control registry paths.
  • Bucket name validation against S3 naming rules before use in file paths.
  • All user-supplied paths cleaned with filepath.Clean.

2. File Output Boundary

Stave writes findings to stdout or to files specified by --out.

Controls:

  • No-overwrite by default — refuses to write over existing files without --force.
  • No-symlink-write by default — refuses to write through symbolic links without --allow-symlink-output.
  • Restricted permissions: directories 0700, files 0600.
  • No implicit temp files, caches, or config directories.

3. Build and Release Boundary

The release pipeline builds, signs, and publishes artifacts.

Controls:

  • SHA-256 checksums for integrity.
  • Sigstore Cosign keyless signing via GitHub Actions OIDC.
  • SPDX SBOM for dependency transparency.
  • GitHub-native SLSA build provenance attestation.
  • License compliance (go-licenses check) — GPL/AGPL/SSPL/LGPL fail the build.
  • Dependabot for dependency monitoring.
  • govulncheck on every PR.

Attacker Profiles

A1: Malicious Input

Goal: Exploit Stave through crafted observation or control files.

Attack VectorControl
Schema injection (extra fields)additionalProperties: false rejects unknown fields
Path traversal vian asset IDsBucket name validation; filepath.Clean on all paths
Path traversal via control registryRegistry validates relative paths stay within root
Oversized input (DoS)Go's JSON/YAML parsers have bounded memory; no unbounded buffering
Malformed timestampsRFC 3339 parsing rejects invalid dates

A2: Supply-Chain Attack

Goal: Replace the Stave binary or its dependencies with a malicious version.

Attack VectorControl
Artifact tampering in transitSHA-256 checksums detect modification
Malicious release replacementCosign signature binds artifacts to CI workflow identity
Compromised build hostGitHub provenance attestation proves CI origin
Hidden dependenciesSBOM provides full dependency audit trail
Vulnerable dependenciesgovulncheck on every PR; Dependabot monitoring
Unauthorized releaseSigstore OIDC ties signing to GitHub Actions context

A3: Local Attacker

Goal: Read evaluation results or tamper with output on a shared system.

Attack VectorControl
Read output files0600 file permissions (owner-only)
Read output directories0700 directory permissions
Symlink attack on output pathSymlink write protection (default on)
Overwrite existing filesNo-overwrite protection (default on)

A4: Credential Harvesting

Goal: Use Stave as a vector to exfiltrate credentials.

Attack VectorControl
Read credential env varsStave reads no credential env vars (only NO_COLOR)
Read credential filesStave reads no credential files
Network exfiltrationNo net/http, net/rpc, crypto/tls — architecturally impossible
Subprocess exfiltrationNo os/exec — architecturally impossible

Residual Risks

These risks are acknowledged but not fully mitigated by Stave:

RiskImpactRemediation Guidance
Snapshot sensitivityTerraform exports may contain embedded secretsUse --sanitize when sharing output. Do not include raw secrets in state files passed to Stave.
Umask on shared systemsWeak umask may expose output filesSet umask 077 before running Stave. Write to a private directory.
Provenance requires networkgh attestation verify needs GitHub API accessChecksum + Cosign verification are sufficient for offline environments. Provenance adds defense-in-depth when connectivity is available.
Control tamperingModified controls change evaluation semanticsShip controls from a trusted source. Validate with stave validate before evaluation. Use version control.
Log verbosity-vv may include file paths in logsUse --path-mode=base (default) to show basenames only. Defensive log sanitization strips known sensitive patterns.

Security Tests

The following CI tests enforce the threat model:

TestWhat It Enforces
TestNoBannedImportsInRuntime8 banned packages not in runtime binary
TestNoHTTPSchemaIdentifiersSchema IDs use urn: not http:
TestNoCredentialEnvVarsNo credential environment variable reads
TestOfflineHelpSuffixHelp text documents offline operation

Further Reading