feat: Add VEX compact fixture and implement offline verifier for Findings Ledger exports

- Introduced a new VEX compact fixture for testing purposes.
- Implemented `verify_export.py` script to validate Findings Ledger exports, ensuring deterministic ordering and applying redaction manifests.
- Added a lightweight stub `HarnessRunner` for unit tests to validate ledger hashing expectations.
- Documented tasks related to the Mirror Creator.
- Created models for entropy signals and implemented the `EntropyPenaltyCalculator` to compute penalties based on scanner outputs.
- Developed unit tests for `EntropyPenaltyCalculator` to ensure correct penalty calculations and handling of edge cases.
- Added tests for symbol ID normalization in the reachability scanner.
- Enhanced console status service with comprehensive unit tests for connection handling and error recovery.
- Included Cosign tool version 2.6.0 with checksums for various platforms.
This commit is contained in:
StellaOps Bot
2025-12-02 21:08:01 +02:00
parent 6d049905c7
commit 47168fec38
146 changed files with 4329 additions and 549 deletions

View File

@@ -0,0 +1,115 @@
using System.Collections.Generic;
using Microsoft.Extensions.Logging.Abstractions;
using StellaOps.Policy.Engine.Options;
using StellaOps.Policy.Engine.Signals.Entropy;
using Xunit;
using OptionsFactory = Microsoft.Extensions.Options.Options;
namespace StellaOps.Policy.Engine.Tests.Signals;
public sealed class EntropyPenaltyCalculatorTests
{
private readonly EntropyPenaltyCalculator _calculator = new(
OptionsFactory.Create(new PolicyEngineOptions()),
NullLogger<EntropyPenaltyCalculator>.Instance);
[Fact]
public void ComputeFromJson_ComputesPenaltyAndBlock_WhenImageOpaqueHighAndProvenanceUnknown()
{
var summaryJson = """
{
"schema": "stellaops.entropy/layer-summary@1",
"imageOpaqueRatio": 0.18,
"layers": [
{ "digest": "sha256:l1", "opaqueBytes": 2306867, "totalBytes": 10485760, "opaqueRatio": 0.22, "indicators": ["packed", "no-symbols"] },
{ "digest": "sha256:l2", "opaqueBytes": 0, "totalBytes": 1048576, "opaqueRatio": 0.0, "indicators": ["symbols"] }
]
}
""";
var reportJson = """
{
"schema": "stellaops.entropy/report@1",
"files": [
{ "path": "/opt/app/libblob.so", "size": 5242880, "opaqueBytes": 1342177, "opaqueRatio": 0.25, "flags": ["stripped", "section:.UPX0"], "windows": [ { "offset": 0, "length": 4096, "entropy": 7.45 } ] },
{ "path": "/opt/app/ok.bin", "size": 1024, "opaqueBytes": 0, "opaqueRatio": 0.0, "flags": [] }
]
}
""";
var result = _calculator.ComputeFromJson(summaryJson, reportJson, provenanceAttested: false);
Assert.True(result.Blocked);
Assert.False(result.Warned);
Assert.InRange(result.Penalty, 0.099m, 0.101m); // ~0.1 after K=0.5
Assert.Contains("image_opaque_ratio_exceeds_threshold", result.ReasonCodes);
Assert.Contains(result.TopFiles, tf => tf.Path == "/opt/app/libblob.so" && tf.OpaqueRatio == 0.25m);
}
[Fact]
public void Compute_AppliesMitigationAndCap_WhenSymbolsPresentAndProvenanceAttested()
{
var summary = new EntropyLayerSummary
{
ImageOpaqueRatio = 0.9m,
Layers = new List<EntropyLayer>
{
new()
{
Digest = "sha256:layer",
OpaqueBytes = 900,
TotalBytes = 1000,
Indicators = new List<string> { "symbols" }
}
}
};
var report = new EntropyReport
{
Files = new List<EntropyFile>
{
new()
{
Path = "/bin/high.bin",
Size = 1000,
OpaqueBytes = 900,
OpaqueRatio = 0.9m,
Flags = new List<string> { "packed" }
}
}
};
var result = _calculator.Compute(summary, report, provenanceAttested: true);
Assert.False(result.Blocked); // provenance attested suppresses block
Assert.False(result.Capped);
Assert.InRange(result.Penalty, 0.224m, 0.226m); // mitigation reduces below cap and stays under cap
Assert.Contains("symbols_mitigated", result.ReasonCodes);
Assert.DoesNotContain("penalty_capped", result.ReasonCodes);
}
[Fact]
public void Compute_WarnsWhenLayerExceedsThresholdWithoutReport()
{
var summary = new EntropyLayerSummary
{
ImageOpaqueRatio = 0.05m,
Layers = new List<EntropyLayer>
{
new()
{
Digest = "sha256:l1",
OpaqueBytes = 40,
TotalBytes = 100,
Indicators = new List<string> { "packed" }
}
}
};
var result = _calculator.Compute(summary, report: null, provenanceAttested: false);
Assert.False(result.Blocked);
Assert.True(result.Warned);
Assert.Contains("file_opaque_ratio_exceeds_threshold", result.ReasonCodes);
}
}