Files
git.stella-ops.org/docs/modules/attestor/fix-chain-predicate.md
master 7f7eb8b228 Complete batch 012 (golden set diff) and 013 (advisory chat), fix build errors
Sprints completed:
- SPRINT_20260110_012_* (golden set diff layer - 10 sprints)
- SPRINT_20260110_013_* (advisory chat - 4 sprints)

Build fixes applied:
- Fix namespace conflicts with Microsoft.Extensions.Options.Options.Create
- Fix VexDecisionReachabilityIntegrationTests API drift (major rewrite)
- Fix VexSchemaValidationTests FluentAssertions method name
- Fix FixChainGateIntegrationTests ambiguous type references
- Fix AdvisoryAI test files required properties and namespace aliases
- Add stub types for CveMappingController (ICveSymbolMappingService)
- Fix VerdictBuilderService static context issue

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-11 10:09:07 +02:00

341 lines
8.8 KiB
Markdown

# FixChain Attestation Predicate
> **Sprint:** SPRINT_20260110_012_005_ATTESTOR
> **Predicate Type:** `https://stella-ops.org/predicates/fix-chain/v1`
> **Last Updated:** 10-Jan-2026
## Overview
The FixChain predicate provides cryptographically verifiable proof that a patch eliminates a vulnerable code path. It bridges the gap between vulnerability disclosure and fix verification by encoding evidence from binary analysis into a DSSE-signed attestation.
## Why FixChain?
| Current State | With FixChain |
|---------------|---------------|
| Trust vendor claims | Verify with evidence chain |
| No attestable fix evidence | DSSE-signed fix proofs |
| Version-based assumptions | Binary signature comparison |
| No air-gap verification | Offline-verifiable bundles |
## Predicate Schema
```json
{
"$id": "https://stella-ops.org/schemas/predicates/fix-chain/v1",
"type": "object",
"required": [
"cveId", "component", "goldenSetRef", "vulnerableBinary",
"patchedBinary", "sbomRef", "signatureDiff", "reachability",
"verdict", "analyzer", "analyzedAt"
],
"properties": {
"cveId": {
"description": "CVE or GHSA identifier",
"pattern": "^CVE-\\d{4}-\\d{4,}$|^GHSA-[a-z0-9]{4}-[a-z0-9]{4}-[a-z0-9]{4}$"
},
"component": {
"description": "Component being verified"
},
"goldenSetRef": {
"description": "Content-addressed reference to golden set definition"
},
"vulnerableBinary": {
"description": "Pre-patch binary identity (SHA-256, architecture)"
},
"patchedBinary": {
"description": "Post-patch binary identity (SHA-256, architecture, PURL)"
},
"sbomRef": {
"description": "Reference to SBOM containing the component"
},
"signatureDiff": {
"description": "Summary of signature differences"
},
"reachability": {
"description": "Reachability analysis outcome"
},
"verdict": {
"description": "Final fix determination",
"properties": {
"status": { "enum": ["fixed", "partial", "not_fixed", "inconclusive"] },
"confidence": { "type": "number", "minimum": 0, "maximum": 1 },
"rationale": { "type": "array", "items": { "type": "string" } }
}
},
"analyzer": {
"description": "Analyzer metadata for reproducibility"
},
"analyzedAt": {
"description": "ISO 8601 timestamp"
}
}
}
```
## Evidence Chain
The FixChain attestation encodes evidence from multiple analysis stages:
```
Golden Set Definition (CVE signature)
|
v
+------------------+ +------------------+
| Vulnerable Binary| --> | Patch Diff Engine|
+------------------+ +------------------+
| |
v v
+------------------+ +------------------+
| Patched Binary | --> | Signature Diff |
+------------------+ +------------------+
|
v
+------------------+
| Reachability |
| Analysis |
+------------------+
|
v
+------------------+
| FixChain |
| Attestation |
+------------------+
```
## Verdict Calculation
The verdict is calculated based on multiple factors:
### Status Values
| Status | Description | Conditions |
|--------|-------------|------------|
| `fixed` | Vulnerability fully addressed | High confidence (>=80%), all paths eliminated |
| `partial` | Vulnerability partially addressed | Medium confidence (50-80%), some paths remain |
| `not_fixed` | Vulnerability still present | Diff shows no fix, paths unchanged |
| `inconclusive` | Cannot determine | Low confidence, insufficient evidence |
### Confidence Scoring
```
Confidence = Base + FunctionBonus + EdgeBonus + PathBonus
Base = Diff.Confidence (from analysis)
FunctionBonus:
- +0.1 per vulnerable function removed
- +0.05 per vulnerable function modified
EdgeBonus:
- +0.05 per vulnerable edge eliminated
PathBonus:
- +0.3 if all paths eliminated
- +0.1 if paths reduced by >50%
```
### Rationale Generation
The rationale array explains the verdict:
```json
{
"rationale": [
"3 vulnerable function(s) removed",
"5 vulnerable edge(s) eliminated",
"All paths to vulnerable sink eliminated"
]
}
```
## Example Attestation
```json
{
"_type": "https://in-toto.io/Statement/v1",
"subject": [{
"name": "pkg:deb/debian/openssl@3.1.0",
"digest": {
"sha256": "abc123..."
}
}],
"predicateType": "https://stella-ops.org/predicates/fix-chain/v1",
"predicate": {
"cveId": "CVE-2024-0727",
"component": "openssl",
"goldenSetRef": {
"digest": "sha256:def456..."
},
"vulnerableBinary": {
"sha256": "111111...",
"architecture": "x86_64"
},
"patchedBinary": {
"sha256": "222222...",
"architecture": "x86_64",
"purl": "pkg:deb/debian/openssl@3.1.0"
},
"sbomRef": {
"digest": "sha256:789abc..."
},
"signatureDiff": {
"vulnerableFunctionsRemoved": 1,
"vulnerableFunctionsModified": 2,
"vulnerableEdgesEliminated": 5,
"sanitizersInserted": 0,
"details": ["Function X509_VERIFY_PARAM_set_flags rewritten"]
},
"reachability": {
"prePathCount": 3,
"postPathCount": 0,
"eliminated": true,
"reason": "All 3 path(s) to vulnerable sink eliminated"
},
"verdict": {
"status": "fixed",
"confidence": 0.95,
"rationale": [
"1 vulnerable function(s) removed",
"5 vulnerable edge(s) eliminated",
"All paths to vulnerable sink eliminated"
]
},
"analyzer": {
"name": "StellaOps.BinaryIndex",
"version": "1.0.0",
"sourceDigest": "sha256:analyzerxyz..."
},
"analyzedAt": "2026-01-10T12:00:00Z"
}
}
```
## CLI Usage
### Create FixChain Attestation
```bash
stella attest fixchain \
--sbom sbom.cdx.json \
--diff diff-result.json \
--golden golden-set.yaml \
--out fixchain.dsse.json \
--arch x86_64 \
--purl "pkg:deb/debian/openssl@3.1.0"
```
### Verify FixChain Attestation
```bash
stella attest fixchain-verify \
--attestation fixchain.dsse.json \
--format summary
```
Output:
```
[OK] FixChain attestation is valid
CVE: CVE-2024-0727
Component: openssl
Verdict: fixed (95%)
Analyzed: 2026-01-10T12:00:00Z
```
### JSON Output
```bash
stella attest fixchain-verify \
--attestation fixchain.dsse.json \
--format json
```
## API Integration
### Service Registration
```csharp
services.AddFixChainAttestation(opts =>
{
opts.AnalyzerName = "MyAnalyzer";
opts.AnalyzerVersion = "1.0.0";
opts.FixedConfidenceThreshold = 0.80m;
});
```
### Creating Attestation
```csharp
var request = new FixChainBuildRequest
{
CveId = "CVE-2024-0727",
Component = "openssl",
GoldenSetDigest = goldenSetDigest,
SbomDigest = sbomDigest,
VulnerableBinary = new BinaryIdentity { ... },
PatchedBinary = new BinaryIdentity { ... },
ComponentPurl = "pkg:deb/debian/openssl@3.1.0",
DiffResult = diffResult
};
var result = await attestationService.CreateAsync(request);
// result.EnvelopeJson - DSSE envelope
// result.ContentDigest - SHA-256 of statement
// result.Predicate - Parsed predicate
```
### Verifying Attestation
```csharp
var result = await attestationService.VerifyAsync(envelopeJson);
if (result.IsValid)
{
var verdict = result.Predicate!.Verdict;
Console.WriteLine($"Status: {verdict.Status}");
Console.WriteLine($"Confidence: {verdict.Confidence:P0}");
}
```
## Air-Gap Verification
FixChain attestations support offline verification:
1. **Bundle Export**: Export attestation with all referenced artifacts
2. **Signature Verification**: Verify DSSE signature with bundled public key
3. **Content Validation**: Validate predicate structure and content
4. **Optional Rekor Proof**: Include offline Rekor inclusion proof
```bash
# Export bundle for air-gap
stella attest bundle export \
--attestation fixchain.dsse.json \
--include-artifacts \
--out fixchain-bundle.tar.gz
# Verify in air-gap
stella attest bundle verify \
--bundle fixchain-bundle.tar.gz \
--offline
```
## Related Documents
- [Golden Set Schema](../binary-index/golden-set-schema.md)
- [SBOM Extension Fields](../binary-index/sbom-extensions.md)
- [Proof Chain Specification](./proof-chain-specification.md)
- [DSSE Roundtrip Verification](./dsse-roundtrip-verification.md)
## Configuration
```yaml
Attestor:
Predicates:
FixChain:
Enabled: true
AnalyzerName: "StellaOps.BinaryIndex"
AnalyzerVersion: "1.0.0"
FixedConfidenceThreshold: 0.80
PartialConfidenceThreshold: 0.50
PublishToRekor: true
Archive: true
```