tests fixes and some product advisories tunes ups
This commit is contained in:
11
demos/binary-micro-witness/CHECKSUMS.sha256
Normal file
11
demos/binary-micro-witness/CHECKSUMS.sha256
Normal file
@@ -0,0 +1,11 @@
|
||||
# Binary Micro-Witness Golden Demo - SHA-256 Checksums
|
||||
# Generated: 2026-01-28
|
||||
# Sprint: SPRINT_0128_001_BinaryIndex_binary_micro_witness
|
||||
#
|
||||
# Verify with: sha256sum -c CHECKSUMS.sha256
|
||||
|
||||
526283cf498cded25032a2fd1bbf2896ede05e32545bec1ccd38b787ba6ef0d1 *witnesses/libcurl-cve-2023-38545.json
|
||||
87d7b026b37523abd29d917c22b9ffa0c3e7a3ddcf8db8990eb4d6b9cb35ed91 *witnesses/openssl-cve-2024-0567.json
|
||||
59ab7b9c5bc01af9f81af8801c90c7123f5d4c503e8bad1be3a3a71c847eebbf *verify.ps1
|
||||
5e7140744f6421cf6cbf8d707706d8b0fbe7bbb6c43604be38ec088cd19e21a0 *verify.sh
|
||||
b5538232fdc8936f6a4529254b29d70014f76830c84aa4d977db3c1152c6e5b0 *README.md
|
||||
114
demos/binary-micro-witness/README.md
Normal file
114
demos/binary-micro-witness/README.md
Normal file
@@ -0,0 +1,114 @@
|
||||
# Binary Micro-Witness Golden Demo
|
||||
|
||||
This bundle demonstrates binary-level patch verification using StellaOps micro-witnesses.
|
||||
|
||||
## Overview
|
||||
|
||||
Binary micro-witnesses provide cryptographic proof that a specific binary contains (or doesn't contain) a security fix. This enables auditors and procurement teams to verify patch status without source code access.
|
||||
|
||||
## Contents
|
||||
|
||||
```
|
||||
binary-micro-witness/
|
||||
├── README.md # This file
|
||||
├── witnesses/
|
||||
│ ├── openssl-cve-2024-0567.json # Sample witness for OpenSSL CVE
|
||||
│ └── libcurl-cve-2023-38545.json # Sample witness for curl CVE
|
||||
├── verify.ps1 # PowerShell verification script
|
||||
├── verify.sh # Bash verification script
|
||||
└── CHECKSUMS.sha256 # Deterministic checksums for all files
|
||||
```
|
||||
|
||||
## Quick Start
|
||||
|
||||
### Windows (PowerShell)
|
||||
```powershell
|
||||
.\verify.ps1 -WitnessPath witnesses\openssl-cve-2024-0567.json
|
||||
```
|
||||
|
||||
### Linux/macOS (Bash)
|
||||
```bash
|
||||
chmod +x verify.sh
|
||||
./verify.sh witnesses/openssl-cve-2024-0567.json
|
||||
```
|
||||
|
||||
## Threat Model & Scope
|
||||
|
||||
### What Micro-Witnesses Prove
|
||||
- A specific binary (identified by SHA-256) was analyzed
|
||||
- The analysis compared function-level signatures against known vulnerable/patched versions
|
||||
- A confidence score indicates how certain the verdict is
|
||||
|
||||
### What Micro-Witnesses Do NOT Prove
|
||||
- That the binary came from a trusted source (that's what SBOM + attestations are for)
|
||||
- That the analysis is 100% accurate (confidence scores indicate uncertainty)
|
||||
- That other vulnerabilities don't exist (only the specified CVE is verified)
|
||||
|
||||
### Limitations
|
||||
- Function-level matching can be affected by heavy compiler optimizations
|
||||
- Inlined functions may not be detected
|
||||
- Obfuscated binaries may yield "inconclusive" verdicts
|
||||
|
||||
## Offline Verification
|
||||
|
||||
This bundle is designed for air-gapped environments:
|
||||
1. No network access required
|
||||
2. All verification logic is self-contained
|
||||
3. Checksums allow integrity verification
|
||||
|
||||
## Predicate Schema
|
||||
|
||||
Witnesses follow the `https://stellaops.dev/predicates/binary-micro-witness@v1` schema:
|
||||
|
||||
```json
|
||||
{
|
||||
"schemaVersion": "1.0.0",
|
||||
"binary": {
|
||||
"digest": "sha256:...",
|
||||
"filename": "libssl.so.3",
|
||||
"arch": "linux-amd64"
|
||||
},
|
||||
"cve": {
|
||||
"id": "CVE-2024-0567",
|
||||
"advisory": "https://..."
|
||||
},
|
||||
"verdict": "patched|vulnerable|inconclusive",
|
||||
"confidence": 0.95,
|
||||
"evidence": [
|
||||
{
|
||||
"function": "SSL_CTX_new",
|
||||
"state": "patched",
|
||||
"score": 0.97,
|
||||
"method": "semantic_ksg"
|
||||
}
|
||||
],
|
||||
"tooling": {
|
||||
"binaryIndexVersion": "2.1.0",
|
||||
"lifter": "b2r2",
|
||||
"matchAlgorithm": "semantic_ksg"
|
||||
},
|
||||
"computedAt": "2026-01-28T12:00:00Z"
|
||||
}
|
||||
```
|
||||
|
||||
## Reproduction
|
||||
|
||||
To regenerate witnesses using the StellaOps CLI:
|
||||
|
||||
```bash
|
||||
# Generate a witness
|
||||
stella witness generate /path/to/libssl.so.3 --cve CVE-2024-0567 --output witness.json
|
||||
|
||||
# Verify a witness
|
||||
stella witness verify witness.json --offline
|
||||
|
||||
# Create an air-gapped bundle
|
||||
stella witness bundle witness.json --output ./bundle
|
||||
```
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Demo Version**: 1.0.0
|
||||
- **Schema Version**: binary-micro-witness@v1
|
||||
- **Generated**: 2026-01-28
|
||||
- **Sprint**: SPRINT_0128_001_BinaryIndex_binary_micro_witness
|
||||
204
demos/binary-micro-witness/verify.ps1
Normal file
204
demos/binary-micro-witness/verify.ps1
Normal file
@@ -0,0 +1,204 @@
|
||||
# Binary Micro-Witness Verification Script
|
||||
# Sprint: SPRINT_0128_001_BinaryIndex_binary_micro_witness
|
||||
# Usage: .\verify.ps1 [-WitnessPath <path>] [-VerboseOutput]
|
||||
|
||||
[CmdletBinding()]
|
||||
param(
|
||||
[Parameter(Position=0)]
|
||||
[string]$WitnessPath,
|
||||
|
||||
[switch]$All,
|
||||
[switch]$VerboseOutput
|
||||
)
|
||||
|
||||
$ErrorActionPreference = "Stop"
|
||||
$Script:PassCount = 0
|
||||
$Script:FailCount = 0
|
||||
|
||||
function Write-Status {
|
||||
param([string]$Status, [string]$Message, [string]$Color = "White")
|
||||
$symbol = switch ($Status) {
|
||||
"PASS" { "[OK]"; $Color = "Green" }
|
||||
"FAIL" { "[FAIL]"; $Color = "Red" }
|
||||
"SKIP" { "[SKIP]"; $Color = "Yellow" }
|
||||
"INFO" { "[INFO]"; $Color = "Cyan" }
|
||||
default { "[-]" }
|
||||
}
|
||||
Write-Host "$symbol " -ForegroundColor $Color -NoNewline
|
||||
Write-Host $Message
|
||||
}
|
||||
|
||||
function Verify-Witness {
|
||||
param([string]$Path)
|
||||
|
||||
Write-Host "`n=== Verifying: $Path ===" -ForegroundColor Cyan
|
||||
|
||||
if (-not (Test-Path $Path)) {
|
||||
Write-Status "FAIL" "Witness file not found: $Path"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
|
||||
try {
|
||||
$witness = Get-Content $Path -Raw | ConvertFrom-Json
|
||||
} catch {
|
||||
Write-Status "FAIL" "Failed to parse witness JSON: $_"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
|
||||
# Handle both standalone predicate and in-toto statement formats
|
||||
$predicate = if ($witness.predicate) { $witness.predicate } else { $witness }
|
||||
|
||||
# Verify required fields
|
||||
$requiredFields = @("schemaVersion", "binary", "cve", "verdict", "confidence", "tooling", "computedAt")
|
||||
$missingFields = @()
|
||||
foreach ($field in $requiredFields) {
|
||||
if (-not $predicate.$field) {
|
||||
$missingFields += $field
|
||||
}
|
||||
}
|
||||
|
||||
if ($missingFields.Count -gt 0) {
|
||||
Write-Status "FAIL" "Missing required fields: $($missingFields -join ', ')"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
Write-Status "PASS" "All required fields present"
|
||||
|
||||
# Display witness details
|
||||
Write-Host "`nWitness Details:" -ForegroundColor White
|
||||
Write-Host " Binary Digest: $($predicate.binary.digest)"
|
||||
Write-Host " Binary File: $($predicate.binary.filename)"
|
||||
Write-Host " CVE: $($predicate.cve.id)"
|
||||
Write-Host " Verdict: $($predicate.verdict)"
|
||||
Write-Host " Confidence: $([math]::Round($predicate.confidence * 100, 1))%"
|
||||
Write-Host " Computed At: $($predicate.computedAt)"
|
||||
|
||||
# Verify schema version
|
||||
if ($predicate.schemaVersion -eq "1.0.0") {
|
||||
Write-Status "PASS" "Schema version: $($predicate.schemaVersion)"
|
||||
} else {
|
||||
Write-Status "SKIP" "Unknown schema version: $($predicate.schemaVersion)"
|
||||
}
|
||||
|
||||
# Verify binary digest format
|
||||
if ($predicate.binary.digest -match "^sha256:[a-fA-F0-9]{64}$") {
|
||||
Write-Status "PASS" "Binary digest format valid"
|
||||
} else {
|
||||
Write-Status "FAIL" "Invalid binary digest format"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
|
||||
# Verify CVE ID format
|
||||
if ($predicate.cve.id -match "^CVE-\d{4}-\d{4,}$") {
|
||||
Write-Status "PASS" "CVE ID format valid"
|
||||
} else {
|
||||
Write-Status "SKIP" "Non-standard vulnerability ID: $($predicate.cve.id)"
|
||||
}
|
||||
|
||||
# Verify verdict
|
||||
$validVerdicts = @("patched", "vulnerable", "inconclusive", "partial")
|
||||
if ($predicate.verdict -in $validVerdicts) {
|
||||
$verdictColor = switch ($predicate.verdict) {
|
||||
"patched" { "Green" }
|
||||
"vulnerable" { "Red" }
|
||||
"inconclusive" { "Yellow" }
|
||||
"partial" { "Yellow" }
|
||||
}
|
||||
Write-Status "PASS" "Verdict: $($predicate.verdict)" -Color $verdictColor
|
||||
} else {
|
||||
Write-Status "FAIL" "Invalid verdict: $($predicate.verdict)"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
|
||||
# Verify confidence range
|
||||
if ($predicate.confidence -ge 0 -and $predicate.confidence -le 1) {
|
||||
Write-Status "PASS" "Confidence in valid range"
|
||||
} else {
|
||||
Write-Status "FAIL" "Confidence out of range: $($predicate.confidence)"
|
||||
$Script:FailCount++
|
||||
return
|
||||
}
|
||||
|
||||
# Check evidence
|
||||
if ($predicate.evidence -and $predicate.evidence.Count -gt 0) {
|
||||
Write-Status "PASS" "Evidence present: $($predicate.evidence.Count) function(s)"
|
||||
if ($VerboseOutput) {
|
||||
Write-Host "`nFunction Evidence:" -ForegroundColor White
|
||||
foreach ($ev in $predicate.evidence) {
|
||||
$stateColor = switch ($ev.state) {
|
||||
"patched" { "Green" }
|
||||
"vulnerable" { "Red" }
|
||||
"modified" { "Yellow" }
|
||||
"unchanged" { "Gray" }
|
||||
default { "White" }
|
||||
}
|
||||
Write-Host " - $($ev.function): " -NoNewline
|
||||
Write-Host "$($ev.state)" -ForegroundColor $stateColor -NoNewline
|
||||
Write-Host " (score: $([math]::Round($ev.score * 100, 1))%, method: $($ev.method))"
|
||||
}
|
||||
}
|
||||
} else {
|
||||
Write-Status "SKIP" "No function-level evidence provided"
|
||||
}
|
||||
|
||||
# Check tooling
|
||||
Write-Status "INFO" "Tooling: BinaryIndex $($predicate.tooling.binaryIndexVersion), Lifter: $($predicate.tooling.lifter)"
|
||||
|
||||
# TODO: Signature verification (not yet implemented)
|
||||
Write-Status "SKIP" "Signature verification (not yet implemented)"
|
||||
|
||||
# TODO: Rekor proof verification (not yet implemented)
|
||||
Write-Status "SKIP" "Rekor inclusion proof (not yet implemented)"
|
||||
|
||||
$Script:PassCount++
|
||||
Write-Host "`nResult: " -NoNewline
|
||||
Write-Host "VERIFIED" -ForegroundColor Green
|
||||
}
|
||||
|
||||
# Main
|
||||
Write-Host "Binary Micro-Witness Verification" -ForegroundColor Cyan
|
||||
Write-Host "==================================" -ForegroundColor Cyan
|
||||
Write-Host "Sprint: SPRINT_0128_001_BinaryIndex_binary_micro_witness"
|
||||
Write-Host ""
|
||||
|
||||
if ($All) {
|
||||
$witnessDir = Join-Path $PSScriptRoot "witnesses"
|
||||
$witnesses = Get-ChildItem -Path $witnessDir -Filter "*.json" -ErrorAction SilentlyContinue
|
||||
|
||||
if ($witnesses.Count -eq 0) {
|
||||
Write-Host "No witness files found in $witnessDir" -ForegroundColor Yellow
|
||||
exit 1
|
||||
}
|
||||
|
||||
foreach ($w in $witnesses) {
|
||||
Verify-Witness -Path $w.FullName
|
||||
}
|
||||
} elseif ($WitnessPath) {
|
||||
Verify-Witness -Path $WitnessPath
|
||||
} else {
|
||||
# Default: verify all witnesses
|
||||
$witnessDir = Join-Path $PSScriptRoot "witnesses"
|
||||
$witnesses = Get-ChildItem -Path $witnessDir -Filter "*.json" -ErrorAction SilentlyContinue
|
||||
|
||||
if ($witnesses.Count -eq 0) {
|
||||
Write-Host "Usage: .\verify.ps1 [-WitnessPath <path>] [-All] [-Verbose]" -ForegroundColor Yellow
|
||||
Write-Host ""
|
||||
Write-Host "Examples:"
|
||||
Write-Host " .\verify.ps1 witnesses\openssl-cve-2024-0567.json"
|
||||
Write-Host " .\verify.ps1 -All -Verbose"
|
||||
exit 1
|
||||
}
|
||||
|
||||
foreach ($w in $witnesses) {
|
||||
Verify-Witness -Path $w.FullName
|
||||
}
|
||||
}
|
||||
|
||||
Write-Host "`n==================================" -ForegroundColor Cyan
|
||||
Write-Host "Summary: $Script:PassCount passed, $Script:FailCount failed" -ForegroundColor $(if ($Script:FailCount -eq 0) { "Green" } else { "Red" })
|
||||
|
||||
exit $Script:FailCount
|
||||
238
demos/binary-micro-witness/verify.sh
Normal file
238
demos/binary-micro-witness/verify.sh
Normal file
@@ -0,0 +1,238 @@
|
||||
#!/bin/bash
|
||||
# Binary Micro-Witness Verification Script
|
||||
# Sprint: SPRINT_0128_001_BinaryIndex_binary_micro_witness
|
||||
# Usage: ./verify.sh [witness-path] [-a|--all] [-v|--verbose]
|
||||
|
||||
set -e
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
WITNESS_DIR="$SCRIPT_DIR/witnesses"
|
||||
PASS_COUNT=0
|
||||
FAIL_COUNT=0
|
||||
VERBOSE=false
|
||||
|
||||
# Colors
|
||||
RED='\033[0;31m'
|
||||
GREEN='\033[0;32m'
|
||||
YELLOW='\033[1;33m'
|
||||
CYAN='\033[0;36m'
|
||||
NC='\033[0m' # No Color
|
||||
|
||||
print_status() {
|
||||
local status="$1"
|
||||
local message="$2"
|
||||
|
||||
case "$status" in
|
||||
PASS) echo -e "${GREEN}[OK]${NC} $message" ;;
|
||||
FAIL) echo -e "${RED}[FAIL]${NC} $message" ;;
|
||||
SKIP) echo -e "${YELLOW}[SKIP]${NC} $message" ;;
|
||||
INFO) echo -e "${CYAN}[INFO]${NC} $message" ;;
|
||||
*) echo "[-] $message" ;;
|
||||
esac
|
||||
}
|
||||
|
||||
verify_witness() {
|
||||
local witness_path="$1"
|
||||
|
||||
echo ""
|
||||
echo -e "${CYAN}=== Verifying: $witness_path ===${NC}"
|
||||
|
||||
if [ ! -f "$witness_path" ]; then
|
||||
print_status "FAIL" "Witness file not found: $witness_path"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
fi
|
||||
|
||||
# Check if jq is available
|
||||
if ! command -v jq &> /dev/null; then
|
||||
echo -e "${YELLOW}Warning: jq not installed. Basic verification only.${NC}"
|
||||
echo "Install jq for full verification: apt install jq / brew install jq"
|
||||
|
||||
# Basic JSON validity check
|
||||
if python3 -c "import json; json.load(open('$witness_path'))" 2>/dev/null || \
|
||||
python -c "import json; json.load(open('$witness_path'))" 2>/dev/null; then
|
||||
print_status "PASS" "Valid JSON"
|
||||
else
|
||||
print_status "FAIL" "Invalid JSON"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
fi
|
||||
((PASS_COUNT++))
|
||||
return
|
||||
fi
|
||||
|
||||
# Parse with jq - handle both standalone predicate and in-toto statement
|
||||
local predicate
|
||||
if jq -e '.predicate' "$witness_path" > /dev/null 2>&1; then
|
||||
predicate=$(jq '.predicate' "$witness_path")
|
||||
else
|
||||
predicate=$(jq '.' "$witness_path")
|
||||
fi
|
||||
|
||||
# Extract fields
|
||||
local schema_version=$(echo "$predicate" | jq -r '.schemaVersion // empty')
|
||||
local binary_digest=$(echo "$predicate" | jq -r '.binary.digest // empty')
|
||||
local binary_filename=$(echo "$predicate" | jq -r '.binary.filename // empty')
|
||||
local cve_id=$(echo "$predicate" | jq -r '.cve.id // empty')
|
||||
local verdict=$(echo "$predicate" | jq -r '.verdict // empty')
|
||||
local confidence=$(echo "$predicate" | jq -r '.confidence // empty')
|
||||
local computed_at=$(echo "$predicate" | jq -r '.computedAt // empty')
|
||||
local evidence_count=$(echo "$predicate" | jq -r '.evidence | length // 0')
|
||||
local binary_index_version=$(echo "$predicate" | jq -r '.tooling.binaryIndexVersion // empty')
|
||||
local lifter=$(echo "$predicate" | jq -r '.tooling.lifter // empty')
|
||||
|
||||
# Verify required fields
|
||||
local missing_fields=""
|
||||
[ -z "$schema_version" ] && missing_fields="$missing_fields schemaVersion"
|
||||
[ -z "$binary_digest" ] && missing_fields="$missing_fields binary.digest"
|
||||
[ -z "$cve_id" ] && missing_fields="$missing_fields cve.id"
|
||||
[ -z "$verdict" ] && missing_fields="$missing_fields verdict"
|
||||
[ -z "$confidence" ] && missing_fields="$missing_fields confidence"
|
||||
[ -z "$computed_at" ] && missing_fields="$missing_fields computedAt"
|
||||
|
||||
if [ -n "$missing_fields" ]; then
|
||||
print_status "FAIL" "Missing required fields:$missing_fields"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
fi
|
||||
print_status "PASS" "All required fields present"
|
||||
|
||||
# Display witness details
|
||||
echo ""
|
||||
echo "Witness Details:"
|
||||
echo " Binary Digest: $binary_digest"
|
||||
echo " Binary File: $binary_filename"
|
||||
echo " CVE: $cve_id"
|
||||
echo " Verdict: $verdict"
|
||||
echo " Confidence: $(echo "$confidence * 100" | bc)%"
|
||||
echo " Computed At: $computed_at"
|
||||
|
||||
# Verify schema version
|
||||
if [ "$schema_version" = "1.0.0" ]; then
|
||||
print_status "PASS" "Schema version: $schema_version"
|
||||
else
|
||||
print_status "SKIP" "Unknown schema version: $schema_version"
|
||||
fi
|
||||
|
||||
# Verify binary digest format
|
||||
if [[ "$binary_digest" =~ ^sha256:[a-fA-F0-9]{64}$ ]]; then
|
||||
print_status "PASS" "Binary digest format valid"
|
||||
else
|
||||
print_status "FAIL" "Invalid binary digest format"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
fi
|
||||
|
||||
# Verify CVE ID format
|
||||
if [[ "$cve_id" =~ ^CVE-[0-9]{4}-[0-9]{4,}$ ]]; then
|
||||
print_status "PASS" "CVE ID format valid"
|
||||
else
|
||||
print_status "SKIP" "Non-standard vulnerability ID: $cve_id"
|
||||
fi
|
||||
|
||||
# Verify verdict
|
||||
case "$verdict" in
|
||||
patched|vulnerable|inconclusive|partial)
|
||||
print_status "PASS" "Verdict: $verdict"
|
||||
;;
|
||||
*)
|
||||
print_status "FAIL" "Invalid verdict: $verdict"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
;;
|
||||
esac
|
||||
|
||||
# Verify confidence range
|
||||
if (( $(echo "$confidence >= 0 && $confidence <= 1" | bc -l) )); then
|
||||
print_status "PASS" "Confidence in valid range"
|
||||
else
|
||||
print_status "FAIL" "Confidence out of range: $confidence"
|
||||
((FAIL_COUNT++))
|
||||
return
|
||||
fi
|
||||
|
||||
# Check evidence
|
||||
if [ "$evidence_count" -gt 0 ]; then
|
||||
print_status "PASS" "Evidence present: $evidence_count function(s)"
|
||||
|
||||
if [ "$VERBOSE" = true ]; then
|
||||
echo ""
|
||||
echo "Function Evidence:"
|
||||
echo "$predicate" | jq -r '.evidence[] | " - \(.function): \(.state) (score: \(.score * 100 | floor)%, method: \(.method))"'
|
||||
fi
|
||||
else
|
||||
print_status "SKIP" "No function-level evidence provided"
|
||||
fi
|
||||
|
||||
# Check tooling
|
||||
print_status "INFO" "Tooling: BinaryIndex $binary_index_version, Lifter: $lifter"
|
||||
|
||||
# TODO: Signature verification
|
||||
print_status "SKIP" "Signature verification (not yet implemented)"
|
||||
|
||||
# TODO: Rekor proof verification
|
||||
print_status "SKIP" "Rekor inclusion proof (not yet implemented)"
|
||||
|
||||
((PASS_COUNT++))
|
||||
echo ""
|
||||
echo -e "Result: ${GREEN}VERIFIED${NC}"
|
||||
}
|
||||
|
||||
# Parse arguments
|
||||
WITNESS_PATH=""
|
||||
VERIFY_ALL=false
|
||||
|
||||
while [[ $# -gt 0 ]]; do
|
||||
case $1 in
|
||||
-a|--all)
|
||||
VERIFY_ALL=true
|
||||
shift
|
||||
;;
|
||||
-v|--verbose)
|
||||
VERBOSE=true
|
||||
shift
|
||||
;;
|
||||
-h|--help)
|
||||
echo "Usage: $0 [witness-path] [-a|--all] [-v|--verbose]"
|
||||
echo ""
|
||||
echo "Examples:"
|
||||
echo " $0 witnesses/openssl-cve-2024-0567.json"
|
||||
echo " $0 --all --verbose"
|
||||
exit 0
|
||||
;;
|
||||
*)
|
||||
WITNESS_PATH="$1"
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
# Main
|
||||
echo -e "${CYAN}Binary Micro-Witness Verification${NC}"
|
||||
echo -e "${CYAN}==================================${NC}"
|
||||
echo "Sprint: SPRINT_0128_001_BinaryIndex_binary_micro_witness"
|
||||
|
||||
if [ -n "$WITNESS_PATH" ]; then
|
||||
verify_witness "$WITNESS_PATH"
|
||||
elif [ "$VERIFY_ALL" = true ] || [ -d "$WITNESS_DIR" ]; then
|
||||
for witness in "$WITNESS_DIR"/*.json; do
|
||||
[ -f "$witness" ] && verify_witness "$witness"
|
||||
done
|
||||
else
|
||||
echo "Usage: $0 [witness-path] [-a|--all] [-v|--verbose]"
|
||||
echo ""
|
||||
echo "Examples:"
|
||||
echo " $0 witnesses/openssl-cve-2024-0567.json"
|
||||
echo " $0 --all --verbose"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo ""
|
||||
echo -e "${CYAN}==================================${NC}"
|
||||
if [ $FAIL_COUNT -eq 0 ]; then
|
||||
echo -e "Summary: ${GREEN}$PASS_COUNT passed${NC}, $FAIL_COUNT failed"
|
||||
else
|
||||
echo -e "Summary: $PASS_COUNT passed, ${RED}$FAIL_COUNT failed${NC}"
|
||||
fi
|
||||
|
||||
exit $FAIL_COUNT
|
||||
@@ -0,0 +1,45 @@
|
||||
{
|
||||
"schemaVersion": "1.0.0",
|
||||
"binary": {
|
||||
"digest": "sha256:b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3",
|
||||
"purl": "pkg:deb/debian/curl@8.4.0-2",
|
||||
"arch": "linux-amd64",
|
||||
"filename": "libcurl.so.4"
|
||||
},
|
||||
"cve": {
|
||||
"id": "CVE-2023-38545",
|
||||
"advisory": "https://curl.se/docs/CVE-2023-38545.html",
|
||||
"patchCommit": "fb4415d8aee6c1"
|
||||
},
|
||||
"verdict": "patched",
|
||||
"confidence": 0.91,
|
||||
"evidence": [
|
||||
{
|
||||
"function": "socks5_resolve_local",
|
||||
"state": "patched",
|
||||
"score": 0.95,
|
||||
"method": "semantic_ksg",
|
||||
"hash": "sha256:1234abcd"
|
||||
},
|
||||
{
|
||||
"function": "Curl_SOCKS5",
|
||||
"state": "patched",
|
||||
"score": 0.88,
|
||||
"method": "cfg_structural",
|
||||
"hash": "sha256:5678efgh"
|
||||
},
|
||||
{
|
||||
"function": "socks_state",
|
||||
"state": "modified",
|
||||
"score": 0.85,
|
||||
"method": "semantic_ksg"
|
||||
}
|
||||
],
|
||||
"tooling": {
|
||||
"binaryIndexVersion": "2.1.0",
|
||||
"lifter": "b2r2",
|
||||
"matchAlgorithm": "semantic_ksg",
|
||||
"normalizationRecipe": "stella-norm-v3"
|
||||
},
|
||||
"computedAt": "2026-01-28T12:00:00.000Z"
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
{
|
||||
"schemaVersion": "1.0.0",
|
||||
"binary": {
|
||||
"digest": "sha256:a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2",
|
||||
"purl": "pkg:deb/debian/openssl@3.0.11-1~deb12u2",
|
||||
"arch": "linux-amd64",
|
||||
"filename": "libssl.so.3"
|
||||
},
|
||||
"cve": {
|
||||
"id": "CVE-2024-0567",
|
||||
"advisory": "https://www.openssl.org/news/secadv/20240125.txt"
|
||||
},
|
||||
"verdict": "patched",
|
||||
"confidence": 0.94,
|
||||
"evidence": [
|
||||
{
|
||||
"function": "PKCS12_parse",
|
||||
"state": "patched",
|
||||
"score": 0.97,
|
||||
"method": "semantic_ksg",
|
||||
"hash": "sha256:f1e2d3c4"
|
||||
},
|
||||
{
|
||||
"function": "PKCS12_verify_mac",
|
||||
"state": "patched",
|
||||
"score": 0.92,
|
||||
"method": "semantic_ksg",
|
||||
"hash": "sha256:a9b8c7d6"
|
||||
},
|
||||
{
|
||||
"function": "SSL_CTX_new",
|
||||
"state": "unchanged",
|
||||
"score": 1.0,
|
||||
"method": "byte_exact"
|
||||
}
|
||||
],
|
||||
"deltaSigDigest": "sha256:deadbeef1234567890abcdef1234567890abcdef1234567890abcdef12345678",
|
||||
"sbomRef": {
|
||||
"sbomDigest": "sha256:cafe1234567890abcdef1234567890abcdef1234567890abcdef1234567890ab",
|
||||
"purl": "pkg:deb/debian/openssl@3.0.11-1~deb12u2"
|
||||
},
|
||||
"tooling": {
|
||||
"binaryIndexVersion": "2.1.0",
|
||||
"lifter": "b2r2",
|
||||
"matchAlgorithm": "semantic_ksg",
|
||||
"normalizationRecipe": "stella-norm-v3"
|
||||
},
|
||||
"computedAt": "2026-01-28T12:00:00.000Z"
|
||||
}
|
||||
Reference in New Issue
Block a user