clockworklabs/SpacetimeDB · warning

Timestamp with i64 microseconds since Unix epoch overflows S

Error message

Timestamp with i64 microseconds since Unix epoch overflows SystemTime

What it means

`Timestamp::to_system_time` adds the (positive, post-epoch) micros to `SystemTime::UNIX_EPOCH` via `checked_add(...).expect(...)`. On mainstream platforms SystemTime spans at least i64 seconds, so an i64-micros Timestamp fits easily; the panic is only reachable on exotic platforms whose clock range is narrower than Timestamp's (~±292 years).

Source

Thrown at crates/sats/src/timestamp.rs:94

                .as_micros()
                .try_into()
                .expect("Duration since Unix epoch overflows i64 microseconds"),
        )
    }

    /// Convert `self` into a [`SystemTime`] which refers to approximately the same point in time.
    ///
    /// This conversion may lose precision, as [`SystemTime`]'s prevision varies depending on platform.
    /// E.g. Unix targets have microsecond precision, but Windows only 100-microsecond precision.
    ///
    /// This conversion may panic if `self` is out of bounds for [`SystemTime`].
    /// We are not aware of any platforms for which [`SystemTime`] offers a smaller range than [`Timestamp`],
    /// but such a platform may exist.
    pub fn to_system_time(self) -> SystemTime {
        match self.to_duration_since_unix_epoch() {
            Ok(positive) => SystemTime::UNIX_EPOCH
                .checked_add(positive)
                .expect("Timestamp with i64 microseconds since Unix epoch overflows SystemTime"),
            Err(negative) => SystemTime::UNIX_EPOCH
                .checked_sub(negative)
                .expect("Timestamp with i64 microseconds before Unix epoch overflows SystemTime"),
        }
    }

    /// Convert a [`SystemTime`] into a [`Timestamp`] which refers to approximately the same point in time.
    ///
    /// This conversion may panic if `system_time` is out of bounds for [`Duration`].
    /// [`SystemTime`]'s range is larger than [`Timestamp`] on both Unix and Windows targets,
    /// so times in the far past or far future may panic.
    /// [`Timestamp`]'s range is approximately 292 years before and after the Unix epoch.
    pub fn from_system_time(system_time: SystemTime) -> Self {
        let duration = system_time
            .duration_since(SystemTime::UNIX_EPOCH)
            .expect("SystemTime predates the Unix epoch");
        Self::from_duration_since_unix_epoch(duration)
    }

View on GitHub (pinned to 524b4487d9)

Solutions

  1. Prefer staying in Timestamp arithmetic; only convert to SystemTime at the final boundary (file times, HTTP dates) where values are sane.
  2. Clamp or validate Timestamp values against the target platform's clock range before converting.
  3. For fuzzed/extreme inputs, range-check to_micros() against your platform's bounds first.

Example fix

// before
let st = ts.to_system_time(); // panics on platforms with narrow clock range

// after: keep arithmetic in Timestamp; convert only known-sane values
let st = if ts.to_micros().abs() < sane_bound { ts.to_system_time() } else { fallback_time() };
Defensive patterns

Strategy: validation

Validate before calling

// Only convert known-sane timestamps; keep arithmetic in Timestamp elsewhere
let sane = ts.to_micros().abs() < 86_400_000_000i64 * 366 * 400; // ~400 years
if sane { let st = ts.to_system_time(); }

Prevention

When it happens

Trigger: Converting an extreme far-future Timestamp (near i64 micros max, year ~294,247) to SystemTime on a platform with a limited clock representation — not on Linux/macOS/Windows where the range is far larger.

Common situations: Cross-compiling to a niche RTOS/wasm target with a restricted SystemTime; feeding maxed-out timestamps from fuzzing into to_system_time.

Related errors


AI-assisted analysis of clockworklabs/SpacetimeDB@524b4487d9 (2026-08-16). Data as JSON: /api/errors/4e6d555663135fb9. Report an issue: GitHub.