Skip to main content

audio_engine_core/
diagnostics.rs

1use serde::Serialize;
2
3const BYTES_PER_MIB_USIZE: usize = 1024 * 1024;
4
5/// Decoded-buffer budget shared by non-Range downloads, playback loads, and
6/// gapless preload.
7pub const ENV_DECODE_MAX_MEMORY_MB: &str = "DECODE_MAX_MEMORY_MB";
8pub const DEFAULT_DECODE_MAX_MEMORY_MB: usize = 2048;
9pub const MIN_DECODE_MAX_MEMORY_MB: usize = 64;
10pub const MAX_DECODE_MAX_MEMORY_MB: usize = 32 * 1024;
11
12/// Resolved decode-buffer memory budget.
13///
14/// Returned by [`decode_memory_budget`]; reports the effective limit and
15/// whether it came from the environment override or the built-in default.
16#[derive(Debug, Clone, Serialize)]
17pub struct DecodeMemoryBudget {
18    /// Effective limit in mebibytes.
19    pub limit_mb: usize,
20    /// Effective limit in bytes (`limit_mb * 1024 * 1024`).
21    pub limit_bytes: usize,
22    /// Origin of the limit: the env var name when overridden, else `"default"`.
23    pub source: &'static str,
24}
25
26/// Resolve the decode-buffer memory budget from the environment.
27///
28/// Reads [`ENV_DECODE_MAX_MEMORY_MB`]; falls back to
29/// [`DEFAULT_DECODE_MAX_MEMORY_MB`] and clamps to
30/// `[MIN_DECODE_MAX_MEMORY_MB, MAX_DECODE_MAX_MEMORY_MB]`.
31pub fn decode_memory_budget() -> DecodeMemoryBudget {
32    let configured = std::env::var(ENV_DECODE_MAX_MEMORY_MB)
33        .ok()
34        .and_then(|value| value.parse::<usize>().ok());
35    let limit_mb = configured
36        .unwrap_or(DEFAULT_DECODE_MAX_MEMORY_MB)
37        .clamp(MIN_DECODE_MAX_MEMORY_MB, MAX_DECODE_MAX_MEMORY_MB);
38
39    DecodeMemoryBudget {
40        limit_mb,
41        limit_bytes: limit_mb * BYTES_PER_MIB_USIZE,
42        source: if configured.is_some() {
43            ENV_DECODE_MAX_MEMORY_MB
44        } else {
45            "default"
46        },
47    }
48}