Skip to main content

Container Escape Scenario Modeler — enumerate container security posture and model escape paths

Project description

Cepheus

Container escape scenario modeler. A POSIX shell enumerator captures a container's security posture; a Python engine matches that posture against 65 known escape techniques, builds scored single- and multi-step attack chains, and reports prioritized findings. It runs as a CLI, a CI gate, a Kubernetes admission webhook, and a cluster fleet scanner, and ships an offline SARIF viewer for the results.

Cepheus SARIF Explorer

How it works

Two components, one pipeline:

  1. Enumerator — a dependency-free POSIX shell script. It runs inside a container (busybox sh, dash, or bash; works in distroless/scratch when a shell is present) and dumps the security posture to JSON: capabilities, mounts and filesystem types, kernel version, cgroup version, seccomp mode, AppArmor/SELinux profiles, namespace isolation, network and cloud-metadata reachability, socket access, K8s service-account tokens, secret-pattern environment variables, and writable sensitive paths.
  2. Analysis engine — ingests the posture, matches it against the technique database, builds attack chains (single-technique escapes plus natural two-step pairings such as info-disclosure → escalation), scores each chain by a composite of reliability, stealth, and confidence, and renders the result in the format you ask for.
  3. Live confirmation — a static match is a hypothesis, not a finding. When a live container is available (scan -c or analyze -c), Cepheus runs each technique's non-destructive verifier inside it and reports only the escapes it can actually confirm by default. This is the precision-first default that keeps a report from becoming a wall of theoretical matches.

Chains are ranked highest-score-first. Missing posture data falls back to a low confidence rather than dropping the technique, so a partial enumeration still produces signal. Each chain carries a confirmation verdict — CONFIRMED (the verifier demonstrated the primitive), POTENTIAL (matched but not yet confirmed), or UNVERIFIABLE (no automated probe exists, e.g. a kernel CVE) — so a reader never mistakes a hypothesis for a demonstrated escape.

Install

Pick the form that fits where you're running Cepheus. Full details in docs/INSTALL.md.

# Container (CI-friendly, no Python required)
docker run --rm -v /var/run/docker.sock:/var/run/docker.sock \
  ghcr.io/su1ph3r/cepheus:latest ci nginx:latest --max-severity critical

# Single binary (Linux/macOS/Windows, no Python required)
curl -L -o cepheus \
  https://github.com/Su1ph3r/Cepheus/releases/latest/download/cepheus-linux-amd64
chmod +x cepheus && ./cepheus --version

# Homebrew (macOS + Linux)
brew tap su1ph3r/cepheus https://github.com/Su1ph3r/Cepheus
brew install cepheus

# Scoop (Windows)
scoop install https://raw.githubusercontent.com/Su1ph3r/Cepheus/main/scoop/cepheus.json

# pip (existing Python env) — the PyPI distribution is `cepheus-engine`;
# the bare name `cepheus` on PyPI is held by an unrelated 2018 package.
# The installed CLI is still `cepheus` and `import cepheus` still works.
pip install cepheus-engine

# Source (contributors)
git clone https://github.com/su1ph3r/Cepheus.git && cd Cepheus
pip install -e '.[dev,html,llm]'

Quick start

# One shot against a live container: enumerate + analyze + live-confirm,
# reporting only the escapes Cepheus can actually demonstrate
cepheus scan --container-id mycontainer

# Capture posture from a running container, then analyze it (offline)
cepheus enumerate --container-id mycontainer -o posture.json
cepheus analyze posture.json

# Analyze a captured posture but live-confirm against the running container
cepheus analyze posture.json --container-id mycontainer

# Or enumerate an image directly (spins up an ephemeral container)
cepheus enumerate --image nginx:1.27-alpine -o posture.json

# One shot: enumerate + analyze + gate, straight from an image
cepheus ci nginx:1.27-alpine --max-severity critical

Commands

Command Purpose
scan Enumerate + analyze + live-confirm a running container in one shot; reports only confirmed escapes by default.
analyze Analyze a posture JSON and report escape chains; pass --container-id to live-confirm.
ci Enumerate + analyze + gate a build; emits SARIF for Code Scanning.
verify Run non-destructive probes against a live container to confirm matched techniques.
enumerate Capture posture JSON from a running container or an image.
diff Compare two postures and report what changed.
fleet scan / fleet diff Scan every pod in a cluster; track posture drift over time.
admission-server Run as a Kubernetes ValidatingAdmissionWebhook.
techniques Browse the technique database.
update Check for (and optionally apply) a newer release.
notify Send a one-off alert through a configured channel.
# analyze with severity filtering and alternate output formats
cepheus analyze posture.json --min-severity high
cepheus analyze posture.json --format json   -o report.json
cepheus analyze posture.json --format sarif  -o report.sarif
cepheus analyze posture.json --format mitre  -o layer.json
cepheus analyze posture.json --format html   -o report.html

# compare before/after hardening
cepheus diff before.json after.json
cepheus diff before.json after.json --format json -o delta.json

# browse techniques
cepheus techniques --category capability
cepheus techniques --search sys_admin
cepheus techniques --severity critical

Output formats

scan, analyze, ci, and verify render to terminal tables, JSON, or SARIF 2.1.0; analyze and scan additionally emit HTML reports and MITRE ATT&CK Navigator layers. The terminal and JSON/SARIF output carry each chain's confirmation verdict when a live confirmation pass has run. SARIF is the default for ci because GitHub Code Scanning ingests it directly.

Every SARIF finding carries the data a reviewer needs to triage it without re-running the tool: severity, the affected component(s) (the container plus the subsystems the chain abuses — capabilities, host mounts, kernel, runtime), the impact (the consequence an attacker achieves), a recommendation (including the container-runtime flag that closes the primitive), the reliability/stealth/confidence sub-scores, and the compliance crosswalk. The stable output contract is documented in docs/API.md.

SARIF viewer

A self-contained, offline viewer for Cepheus SARIF reports lives in web/. Open web/index.html in any browser and drop a report — no server, no network, no data leaves the page. The left pane is a severity-sorted findings table; selecting a finding shows its chain graph and the full detail panel. Light and dark themes are included.

SARIF Explorer — light theme

CI integration

cepheus ci enumerates an image (or reads a pre-captured posture), analyzes it, and exits non-zero when the gate trips. Exit codes are stable: 0 pass, 1 gate tripped, 2 usage/IO error.

# fail the build on critical chains; upload SARIF to GitHub Code Scanning
cepheus ci my-app:${GITHUB_SHA} --max-severity critical -f sarif -o cepheus.sarif

# regression-only gate — fail only when NEW chains appear vs. a baseline
cepheus ci my-app:${GITHUB_SHA} --baseline baseline.sarif --fail-on-new -f sarif -o out.sarif

A dedicated GitHub Action wraps this for one-line use:

- uses: Su1ph3r/cepheus-action@v1.1.1
  with:
    image: my-app:${{ github.sha }}
    max-severity: critical

The action installs cepheus-engine, runs cepheus ci, writes SARIF, and uploads it to Code Scanning. Its source lives in cepheus-action/ and is mirrored to the standalone Su1ph3r/cepheus-action repo on each release. See docs/CI.md for the full workflow.

Kubernetes admission webhook

cepheus admission-server runs as a ValidatingAdmissionWebhook: it converts each incoming PodSpec into a synthetic posture, runs the same analysis pipeline, and allows or denies the pod against the configured gate. It supports per-pod policy labels (cepheus.io/policy: enforce|warn|skip), optional mutual TLS so only the kube-apiserver can reach /validate, fail-open vs. fail-closed behavior, optional Node kernel-version lookup for kernel-CVE gating, and Slack / PagerDuty / generic-webhook deny notifications.

Install with the Helm chart at charts/cepheus-admission/ (cert-manager or a self-signed one-shot Job for TLS). Deployment guide: docs/ADMISSION.md.

Fleet operations

# scan every running pod in the current cluster, then track drift
cepheus fleet scan -o fleet-before.json
cepheus fleet scan --namespace prod --selector "tier=backend" -o fleet-after.json
cepheus fleet diff fleet-before.json fleet-after.json --fail-on-regression

fleet scan shells out to kubectl, so it uses your current kubeconfig/context unless --kubeconfig / --context override them. fleet diff --fail-on-regression exits non-zero only when a pod gains chains or raises its score, so a clean rollout doesn't break CI.

Live verification

A static posture match reports what could be exploitable. Live verification confirms it: for each matched technique with a probe, Cepheus runs a non-destructive check inside the live container and classifies the outcome as CONFIRMED, NOT_CONFIRMED, NO_VERIFIER, or ERROR.

The fastest path is scan, which folds confirmation into the default flow and surfaces only confirmed escapes:

# enumerate + analyze + confirm; report only what is actually exploitable
cepheus scan --container-id mycontainer

# include unproven (potential / unverifiable) matches too
cepheus scan --container-id mycontainer --show-potential

# confirm a previously captured posture against its live container
cepheus analyze posture.json --container-id mycontainer

Each surviving chain is tagged CONFIRMED, POTENTIAL, or UNVERIFIABLE. By default only CONFIRMED chains are shown; refuted matches (the verifier rejected them) are dropped entirely. Some CVE probes only prove a precondition (a GPU device is present, a build socket is reachable) rather than the version-specific bug — a pass on those is reported as POTENTIAL, not CONFIRMED, so a fully patched host is never flagged as a confirmed escape.

The lower-level verify command runs the probes against an existing analysis without the confirmed-only gating:

cepheus verify --container-id mycontainer
cepheus verify --container-id mycontainer --all-critical -f sarif -o verify.sarif

Probes are read-only or use the open-then-close idiom that triggers the kernel's permission check without writing. The verifier never exploits.

Compliance crosswalk

Techniques carry CIS Kubernetes Benchmark, NIST SP 800-190, and PCI DSS v4 control references where they apply. The mappings surface in the SARIF rule properties, the HTML report, and the web viewer. Absence of a mapping means "not yet enumerated," never "no control applies."

Technique coverage

75 techniques across 6 categories:

  • Capability-based (13): SYS_ADMIN, SYS_MODULE, SYS_PTRACE, SYS_BOOT, SYSLOG, PERFMON, DAC_READ_SEARCH, DAC_OVERRIDE, NET_ADMIN, SYS_RAWIO, BPF probe_write_user, and more.
  • Mount-based (18): docker.sock, podman/containerd/CRI-O sockets, core_pattern, modprobe, /sys/kernel/uevent_helper, sysrq, sysfs, host path mounts, cgroup fs, /dev, shared /dev/shm, /proc/self/fd, device-mapper, /proc/sys/vm.
  • Kernel CVE-based (18): CVE-2022-0185, CVE-2022-0847 (DirtyPipe), CVE-2024-1086, CVE-2024-21626 (Leaky Vessels), CVE-2025-21756, the CVE-2024-23651/23652/23653 BuildKit set, and more.
  • Runtime / orchestrator (16): K8s service account, kubelet API, etcd, Docker API, containerd-shim, shared host PID namespace, runc CVE-2019-5736, cloud metadata SSRF, NVIDIA Container Toolkit CVEs (CVE-2024-0132/0133, CVE-2025-23266), ingress-nginx CVE-2025-1974.
  • Combinatorial (6): multi-prerequisite escapes plus dynamic two-step chain building.
  • Information disclosure (4): env-var secrets, cloud metadata credentials, K8s secret mounts, Docker env inspection.

Scoring

composite = (reliability × 0.40 + stealth × 0.25 + confidence × 0.35) × length_penalty

Multi-step chains take a per-step length penalty so a single reliable escape outranks a longer speculative one. Sandbox runtimes (gVisor, Kata) discount the score. All weights are configurable.

Configuration

CEPHEUS_MIN_CONFIDENCE=0.3              # minimum confidence threshold
CEPHEUS_MAX_CHAIN_LENGTH=3              # maximum chain step count
CEPHEUS_WEIGHT_RELIABILITY=0.40        # scoring weight: reliability
CEPHEUS_WEIGHT_STEALTH=0.25            # scoring weight: stealth
CEPHEUS_WEIGHT_CONFIDENCE=0.35        # scoring weight: confidence
CEPHEUS_CHAIN_LENGTH_PENALTY=0.15      # per-step penalty
CEPHEUS_KERNEL_ONLY_MAX_CONFIDENCE=0.5 # cap on kernel-version-only matches
CEPHEUS_DISTRO_KERNEL_MAX_CONFIDENCE=0.2 # further cap on backport-maintained distro kernels
CEPHEUS_LLM_MODEL=anthropic/claude-sonnet-4-20250514
CEPHEUS_LLM_API_KEY=sk-...             # API key for LLM enrichment

LLM enrichment (optional)

With the llm extra installed and --llm passed, Cepheus adds novel combination analysis, contextual remediation, and an executive summary via LiteLLM. It degrades gracefully: if the extra is missing or no key is configured, the report still renders and the missing enrichment is reported rather than failing silently.

Documentation

Testing

pip install -e '.[dev,html]'
pytest
pytest --cov=cepheus --cov-report=term

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

cepheus_engine-1.1.1.tar.gz (621.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

cepheus_engine-1.1.1-py3-none-any.whl (169.8 kB view details)

Uploaded Python 3

File details

Details for the file cepheus_engine-1.1.1.tar.gz.

File metadata

  • Download URL: cepheus_engine-1.1.1.tar.gz
  • Upload date:
  • Size: 621.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.13

File hashes

Hashes for cepheus_engine-1.1.1.tar.gz
Algorithm Hash digest
SHA256 9deb8505e4e856758a2a6573f27dda3ee491259e2067664c4440ae356c1ebbe3
MD5 aca60af6cbdf38fc8fe7045c2dd15caf
BLAKE2b-256 2d085b6b72978e0d2cbe8438803128e50c3838ca83c79131fe0d4aea89e3fc3f

See more details on using hashes here.

File details

Details for the file cepheus_engine-1.1.1-py3-none-any.whl.

File metadata

  • Download URL: cepheus_engine-1.1.1-py3-none-any.whl
  • Upload date:
  • Size: 169.8 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.13

File hashes

Hashes for cepheus_engine-1.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 9ec780e31af4cfc51595e7bec2a43fbc6df169f91fac5d86cfe8427a4223803b
MD5 885dcaa462cf95cf9e00cf76ef6a1385
BLAKE2b-256 dbdef136072b652ad608ab2b477be03c6868be6abe0a2065a6b70246629b51fa

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page