libnyanpasu/clash-nyanpasu · error

runtime revision space exhausted

Error message

runtime revision space exhausted

What it means

`RuntimeRevisionAllocator::allocate` increments an internal counter and returns `RuntimeRevision`; when the counter is at `u64::MAX` (checked_add overflows), allocation fails with this error. It protects the monotonic revision contract used for snapshot ordering.

Solutions

  1. Fix the runaway loop that allocates revisions without bound (profile the repeated update path)
  2. Replace the allocator instance (reset the counter) if the process is truly long-lived and revisions are no longer compared across restarts
  3. Widen the revision type or switch to a UUID/epoch-based scheme if u64 exhaustion is a real requirement

Example fix

// before
for _ in 0..u64::MAX { allocator.allocate()?; } // exhausts revision space
// after
let rev = allocator.allocate()?; // allocate once per actual runtime-config commit
Defensive patterns

Strategy: try-catch

Try / catch

match allocator.allocate() {
    Ok(rev) => rev,
    Err(e) if e.to_string().contains("revision space exhausted") => {
        // recreate the allocator or abort the loop; log the runaway-update condition
        eprintln!("revision allocator exhausted: {e}");
        return;
    }
    Err(e) => return Err(e),
}

Prevention

When it happens

Trigger: Calling `allocate` after the process has allocated `u64::MAX` revisions — practically only possible via an allocation loop that runs ~1.8e19 times, or a test that wraps the counter (e.g. `runtime_revision_allocator_is_monotonic`).

Common situations: Only in theory: an unbounded runtime-config update loop running for years, or a test that pre-seeds the allocator near the maximum to exercise overflow handling.

Understand the failure class

Background: "value must be between 0 and 1" / "out of range" / "must not be negative" errors: fixing range-validation failures across open-source libraries — this error's family across 42 libraries.

Related errors


AI-assisted analysis of libnyanpasu/clash-nyanpasu@f7dbce2997 (2026-09-08). Data as JSON: /api/errors/8fbfa581d35f350b. Report an issue: GitHub.

Appendix: source

Thrown at backend/tauri/src/client/runtime.rs:44

impl RuntimeRevision {
    pub fn get(self) -> u64 {
        self.0
    }
}

pub(crate) struct RuntimeRevisionAllocator(u64);

impl RuntimeRevisionAllocator {
    pub(crate) fn new() -> Self {
        Self(0)
    }

    pub(crate) fn allocate(&mut self) -> anyhow::Result<RuntimeRevision> {
        self.0 = self
            .0
            .checked_add(1)
            .ok_or_else(|| anyhow::anyhow!("runtime revision space exhausted"))?;
        Ok(RuntimeRevision(self.0))
    }
}

#[derive(Debug, Clone)]
pub(crate) struct RuntimeSnapshotData {
    pub config: Mapping,
    pub exists_keys: Vec<String>,
    pub postprocessing_output: PostProcessingOutput,
    pub(crate) inspection: Arc<super::runtime_inspection::RuntimeInspectionData>,
}

#[derive(Debug, Clone)]
pub struct RuntimeSnapshot {
    pub(crate) inspection_id: String,
    pub revision: RuntimeRevision,
    pub target_core: ClashCore,
    pub product_sha256: [u8; 32],

View on GitHub (pinned to f7dbce2997)