nautechsystems/nautilus_trader · error · anyhow::Error

combined BitMEX broadcaster pool size overflow

Error message

combined BitMEX broadcaster pool size overflow

What it means

Config validation in the BitMEX data client adds submitter_pool_size and canceller_pool_size (each defaulting to 1) and rejects the config when the checked_add overflows usize. This is a defensive guard; the range check to MAX_BROADCASTER_POOL_SIZE that follows normally catches oversized values first.

Source

Thrown at crates/adapters/bitmex/src/config.rs:328

    #[must_use]
    pub fn new() -> Self {
        Self::default()
    }

    /// Validates the individual and combined broadcaster pool sizes.
    ///
    /// # Errors
    ///
    /// Returns an error if either pool is outside `[1, 15]` or their combined size is outside
    /// `[2, 16]`.
    pub(crate) fn validate_broadcaster_pool_sizes(&self) -> anyhow::Result<()> {
        let submitter_pool_size = self.submitter_pool_size.unwrap_or(1);
        let canceller_pool_size = self.canceller_pool_size.unwrap_or(1);
        validate_broadcaster_pool_size(submitter_pool_size, "submitter_pool_size")?;
        validate_broadcaster_pool_size(canceller_pool_size, "canceller_pool_size")?;
        let combined_pool_size = submitter_pool_size
            .checked_add(canceller_pool_size)
            .ok_or_else(|| anyhow::anyhow!("combined BitMEX broadcaster pool size overflow"))?;
        check_in_range_inclusive_usize(
            combined_pool_size,
            2,
            MAX_BROADCASTER_POOL_SIZE,
            "combined_pool_size",
        )?;
        Ok(())
    }

    /// Returns `true` if both API key and secret are available
    /// (either explicitly set or resolvable from environment variables).
    #[must_use]
    pub fn has_api_credentials(&self) -> bool {
        let (key_var, secret_var) = credential_env_vars(self.environment);
        let has_key = self.api_key.is_some() || std::env::var(key_var).is_ok();
        let has_secret = self.api_secret.is_some() || std::env::var(secret_var).is_ok();
        has_key && has_secret
    }

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Set submitter_pool_size and canceller_pool_size to small sane values (e.g. 1-16 each) so their sum stays within MAX_BROADCASTER_POOL_SIZE
  2. Clamp or validate pool sizes at config load time before constructing the client

Example fix

// before
submitter_pool_size: usize::MAX,
canceller_pool_size: usize::MAX,
// after
submitter_pool_size: 1,
canceller_pool_size: 1,
Defensive patterns

Strategy: validation

Validate before calling

fn pool_sizes_ok(sub: usize, cancel: usize, max: usize) -> bool {
    sub.checked_add(cancel).map_or(false, |t| (2..=max).contains(&t))
}

Try / catch

match BitmexDataClientConfig::new(...) {
    Err(e) if e.to_string().contains("combined BitMEX broadcaster pool size overflow") => {
        eprintln!("pool sizes invalid, use small values (1-16): {e}");
    }
    r => r?,
}

Prevention

When it happens

Trigger: Constructing the client (new -> validate_broadcaster_pool_sizes) with submitter_pool_size/canceller_pool_size whose sum exceeds usize::MAX — practically only via usize::MAX values in config.

Common situations: Programmatic config built with usize::MAX placeholders; config deserialization bugs injecting extreme values.

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 nautechsystems/nautilus_trader@18893faf8b (2026-09-08). Data as JSON: /api/errors/5f8e6e9d2c0bd7cf. Report an issue: GitHub.