Files
git.stella-ops.org/docs/airgap/runbooks/import-verify.md
StellaOps Bot e923880694
Some checks failed
AOC Guard CI / aoc-guard (push) Has been cancelled
AOC Guard CI / aoc-verify (push) Has been cancelled
Concelier Attestation Tests / attestation-tests (push) Has been cancelled
Docs CI / lint-and-preview (push) Has been cancelled
Export Center CI / export-ci (push) Has been cancelled
Mirror Thin Bundle Sign & Verify / mirror-sign (push) Has been cancelled
feat: Add DigestUpsertRequest and LockEntity models
- Introduced DigestUpsertRequest for handling digest upsert requests with properties like ChannelId, Recipient, DigestKey, Events, and CollectUntil.
- Created LockEntity to represent a lightweight distributed lock entry with properties such as Id, TenantId, Resource, Owner, ExpiresAt, and CreatedAt.

feat: Implement ILockRepository interface and LockRepository class

- Defined ILockRepository interface with methods for acquiring and releasing locks.
- Implemented LockRepository class with methods to try acquiring a lock and releasing it, using SQL for upsert operations.

feat: Add SurfaceManifestPointer record for manifest pointers

- Introduced SurfaceManifestPointer to represent a minimal pointer to a Surface.FS manifest associated with an image digest.

feat: Create PolicySimulationInputLock and related validation logic

- Added PolicySimulationInputLock record to describe policy simulation inputs and expected digests.
- Implemented validation logic for policy simulation inputs, including checks for digest drift and shadow mode requirements.

test: Add unit tests for ReplayVerificationService and ReplayVerifier

- Created ReplayVerificationServiceTests to validate the behavior of the ReplayVerificationService under various scenarios.
- Developed ReplayVerifierTests to ensure the correctness of the ReplayVerifier logic.

test: Implement PolicySimulationInputLockValidatorTests

- Added tests for PolicySimulationInputLockValidator to verify the validation logic against expected inputs and conditions.

chore: Add cosign key example and signing scripts

- Included a placeholder cosign key example for development purposes.
- Added a script for signing Signals artifacts using cosign with support for both v2 and v3.

chore: Create script for uploading evidence to the evidence locker

- Developed a script to upload evidence to the evidence locker, ensuring required environment variables are set.
2025-12-03 07:51:50 +02:00

2.7 KiB
Raw Blame History

Offline Kit Import Verification Runbook

This runbook supports AIRGAP-MANIFEST-510-010, AIRGAP-REPLAY-510-013, and AIRGAP-VERIFY-510-014. It validates bundles fully offline and enforces replay depth.

Replay depth levels (manifest replayPolicy)

  • hash-only: verify manifest/bundle digests, staleness window, optional signature.
  • full-recompute: hash-only + every chunk hash + AV report hash.
  • policy-freeze: full-recompute + manifest policies must include the sealed policy hash (prevents imports with drifting policy/graph material).

Quick steps

src/AirGap/scripts/verify-kit.sh \
  --manifest offline-kit/manifest.json \
  --bundle offline-kit/bundle.tar.gz \
  --signature offline-kit/manifest.sig --pubkey offline-kit/manifest.pub.pem \
  --av-report offline-kit/reports/av-report.json \
  --receipt offline-kit/receipts/ingress.json \
  --sealed-policy-hash "aa55..." \
  --depth policy-freeze

What the script enforces

  1. Manifest & bundle digests match (hashes.*).
  2. Optional manifest signature is valid (OpenSSL).
  3. Staleness: createdAt must be within stalenessWindowHours of --now (defaults to UTC now).
  4. AV: avScan.status must not be findings; if reportSha256 is present, the provided report hash must match.
  5. Chunks (full-recompute/policy-freeze): every chunks[].path exists relative to the manifest and matches its recorded SHA-256.
  6. Policy-freeze: --sealed-policy-hash must appear in policies[].sha256.
  7. Optional: --expected-graph-sha checks the graph chunk hash; --receipt reuses verify-receipt.sh to bind the receipt to the manifest/bundle hashes.

Exit codes: hash mismatch (3/4), staleness (5), AV issues (68), chunk drift (910), graph mismatch (11), policy drift (1213), bad depth (14).

Controller verify endpoint (server-side guard)

POST /system/airgap/verify (scope airgap:verify) expects VerifyRequest:

{
  "depth": "PolicyFreeze",
  "manifestSha256": "...",
  "bundleSha256": "...",
  "computedManifestSha256": "...", // from offline verifier
  "computedBundleSha256": "...",
  "manifestCreatedAt": "2025-12-02T00:00:00Z",
  "stalenessWindowHours": 168,
  "bundlePolicyHash": "aa55...",
  "sealedPolicyHash": "aa55..." // optional, controller fills from state if omitted
}

The controller applies the same replay rules and returns { "valid": true|false, "reason": "..." }.

References

  • Schema: docs/airgap/manifest.schema.json
  • Samples: docs/airgap/samples/offline-kit-manifest.sample.json, docs/airgap/samples/av-report.sample.json, docs/airgap/samples/receipt.sample.json
  • Scripts: src/AirGap/scripts/verify-kit.sh, src/AirGap/scripts/verify-manifest.sh, src/AirGap/scripts/verify-receipt.sh