tur-rs 0.9.2

A relentless, high-concurrency download manager built for speed and efficiency. Tur uses dynamic work-stealing and aligned storage to saturate your bandwidth while maintaining a minuscule memory footprint. Inspired by the legends, built for the modern Rust ecosystem.
Documentation
use super::*;

#[derive(Debug, Clone, Copy)]
pub struct ScalerConfig {
    pub min_connections: usize,
    pub max_connections: usize,
    pub heartbeat_ms: u64,
}

impl Default for ScalerConfig {
    fn default() -> Self {
        Self {
            min_connections: 1,
            max_connections: 16,
            heartbeat_ms: 2000,
        }
    }
}

pub struct TokenBucket {
    pub quota_bytes_per_sec: Cell<u64>,
    pub tokens: Cell<i64>,
    pub refill_interval_ms: Cell<u64>,
}

impl TokenBucket {
    pub fn new() -> Self {
        Self {
            quota_bytes_per_sec: Cell::new(0),
            tokens: Cell::new(0),
            refill_interval_ms: Cell::new(100),
        }
    }

    pub fn refill(&self, interval_ms: u64) {
        let quota = self.quota_bytes_per_sec.get();
        if quota == 0 {
            self.tokens.set(i64::MAX / 2);
            return;
        }
        let add = (quota * interval_ms / 1000) as i64;
        let cap = (quota * 2) as i64;
        self.tokens.set((self.tokens.get() + add).min(cap));
    }

    pub fn consume(&self, bytes: usize) -> bool {
        let quota = self.quota_bytes_per_sec.get();
        if quota == 0 {
            return true;
        }
        let remaining = self.tokens.get() - bytes as i64;
        self.tokens.set(remaining);
        remaining >= 0
    }
}

#[derive(Clone, Copy, PartialEq, Debug)]
pub enum ScalerAction {
    Grow,
    Shrink,
    Hold,
}

#[derive(Clone, Copy, PartialEq, Eq, Debug, Serialize, Deserialize)]
pub enum ProtocolFamily {
    Http1,
    Http2,
    Http3,
    Other,
}

impl Default for ProtocolFamily {
    fn default() -> Self {
        Self::Other
    }
}

impl ProtocolFamily {
    pub(super) fn as_str(self) -> &'static str {
        match self {
            Self::Http1 => "http1",
            Self::Http2 => "http2",
            Self::Http3 => "http3",
            Self::Other => "other",
        }
    }
}

pub(crate) struct Scaler {
    pub ewma_throughput: Cell<f64>,
    pub peak_efficiency: Cell<f64>,
    pub throughput_before_add: Cell<f64>,
    pub n_active: Cell<usize>,
    pub last_action: Cell<ScalerAction>,
    pub slow_start_remaining: Cell<u32>,
    pub config: Rc<RefCell<ScalerConfig>>,
    pub sample_ring: RefCell<[f64; 10]>,
    pub sample_head: Cell<usize>,
    pub sample_count: Cell<usize>,
    pub alpha: Cell<f64>,
    pub cv: Cell<f64>,
    pub ewma_rtt_ms: Cell<f64>,
    pub ewma_handshake_ms: Cell<f64>,
    pub reused_count: Cell<u64>,
    pub total_request_count: Cell<u64>,
    pub reuse_rate: Cell<f64>,
    pub last_reuse_reset: Cell<Instant>,
    pub effective_add_threshold: Cell<f64>,
    pub reused_rtt_samples: Cell<u64>,
    pub skip_growth_sample: Cell<bool>,
    pub reuse_health_low: Cell<bool>,
    pub last_add_was_stream: Cell<bool>,
    pub h2_stream_count: Cell<usize>,
    pub h2_stream_saturated: Cell<bool>,
    pub(super) last_protocol: Cell<ProtocolFamily>,
}

impl Scaler {
    pub fn from_config_handle(config: Rc<RefCell<ScalerConfig>>) -> Rc<Self> {
        Rc::new(Self {
            ewma_throughput: Cell::new(0.0),
            peak_efficiency: Cell::new(0.0),
            throughput_before_add: Cell::new(0.0),
            n_active: Cell::new(1),
            last_action: Cell::new(ScalerAction::Hold),
            slow_start_remaining: Cell::new(3),
            config,
            sample_ring: RefCell::new([0.0; 10]),
            sample_head: Cell::new(0),
            sample_count: Cell::new(0),
            alpha: Cell::new(0.3),
            cv: Cell::new(0.0),
            ewma_rtt_ms: Cell::new(200.0),
            ewma_handshake_ms: Cell::new(50.0),
            reused_count: Cell::new(0),
            total_request_count: Cell::new(0),
            reuse_rate: Cell::new(1.0),
            last_reuse_reset: Cell::new(Instant::now()),
            effective_add_threshold: Cell::new(0.05),
            reused_rtt_samples: Cell::new(0),
            skip_growth_sample: Cell::new(false),
            reuse_health_low: Cell::new(false),
            last_add_was_stream: Cell::new(false),
            h2_stream_count: Cell::new(0),
            h2_stream_saturated: Cell::new(false),
            last_protocol: Cell::new(ProtocolFamily::Other),
        })
    }
}