git-slop 0.16.4

A deterministic repository token-defragmenter for humans and AI agents.
Documentation
use anyhow::{Context, Result, bail};
use serde::Deserialize;

pub const CANONICAL_ADVISOR_MODEL: &str = "openai/gpt-oss-safeguard-20b";
pub const MINIMUM_MODEL_SIZE_BYTES: u64 = 13_793_441_254;
pub const MINIMUM_ESTIMATED_PEAK_MEMORY_BYTES: u64 = 16 * 1024 * 1024 * 1024;
pub const MINIMUM_PHYSICAL_MEMORY_BYTES: u64 = 24 * 1024 * 1024 * 1024;
pub const MINIMUM_AVAILABLE_MEMORY_RESERVE_BYTES: u64 = 8 * 1024 * 1024 * 1024;
pub const MAXIMUM_INITIAL_SWAP_USED_BYTES: u64 = 256 * 1024 * 1024;
pub const MAXIMUM_SWAP_GROWTH_BYTES: u64 = 256 * 1024 * 1024;
pub const ADVISOR_DECISION_RECORD: &str = "docs/benchmarks/safeguard-v1-m2-air-decision.md";

#[derive(Debug, Clone, Deserialize)]
#[serde(deny_unknown_fields)]
pub struct AdvisorReleaseGate {
    pub schema_version: u64,
    pub recommendation: String,
    pub public_inference_enabled: bool,
    pub canonical_model: String,
    pub minimum_model_size_bytes: u64,
    pub minimum_estimated_peak_memory_bytes: u64,
    pub minimum_physical_memory_bytes: u64,
    pub minimum_available_memory_reserve_bytes: u64,
    pub maximum_initial_swap_used_bytes: u64,
    pub maximum_swap_growth_bytes: u64,
    pub decision_record: String,
}

fn validate_release_gate(gate: &AdvisorReleaseGate) -> Result<()> {
    if gate.schema_version != 1 {
        bail!(
            "embedded advisor release gate uses unsupported schema {}",
            gate.schema_version
        );
    }
    if !matches!(gate.recommendation.as_str(), "ship" | "adjust" | "defer") {
        bail!(
            "embedded advisor release gate has invalid recommendation {:?}",
            gate.recommendation
        );
    }
    if gate.public_inference_enabled && gate.recommendation != "ship" {
        bail!(
            "embedded advisor release gate cannot enable public inference without a ship recommendation"
        );
    }
    if gate.canonical_model != CANONICAL_ADVISOR_MODEL
        || gate.minimum_model_size_bytes < MINIMUM_MODEL_SIZE_BYTES
        || gate.minimum_estimated_peak_memory_bytes < MINIMUM_ESTIMATED_PEAK_MEMORY_BYTES
        || gate.minimum_estimated_peak_memory_bytes < gate.minimum_model_size_bytes
        || gate.minimum_physical_memory_bytes < MINIMUM_PHYSICAL_MEMORY_BYTES
        || gate.minimum_available_memory_reserve_bytes < MINIMUM_AVAILABLE_MEMORY_RESERVE_BYTES
        || gate.maximum_initial_swap_used_bytes > MAXIMUM_INITIAL_SWAP_USED_BYTES
        || gate.maximum_swap_growth_bytes > MAXIMUM_SWAP_GROWTH_BYTES
    {
        bail!("embedded advisor release gate weakens the fixed V1 resource safety floor");
    }
    if gate.decision_record != ADVISOR_DECISION_RECORD {
        bail!("embedded advisor release gate must reference the canonical V1 decision record");
    }
    Ok(())
}

pub fn release_gate() -> Result<AdvisorReleaseGate> {
    let gate: AdvisorReleaseGate =
        serde_json::from_slice(include_bytes!("../../benchmarks/advisor/release-gate.json"))
            .context("embedded advisor release gate is invalid")?;
    validate_release_gate(&gate)?;
    Ok(gate)
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn checked_in_gate_fails_closed() {
        let gate = release_gate().expect("release gate");
        assert_eq!(gate.recommendation, "defer");
        assert!(!gate.public_inference_enabled);
        assert!(gate.minimum_physical_memory_bytes >= 24 * 1024 * 1024 * 1024);
    }

    #[test]
    fn embedded_gate_cannot_weaken_runtime_safety_floors() {
        let mut gate = release_gate().expect("release gate");
        gate.minimum_available_memory_reserve_bytes = 4 * 1024 * 1024 * 1024;
        assert!(validate_release_gate(&gate).is_err());

        let mut gate = release_gate().expect("release gate");
        gate.maximum_initial_swap_used_bytes = MAXIMUM_INITIAL_SWAP_USED_BYTES + 1;
        assert!(validate_release_gate(&gate).is_err());
    }
}