use libm::{ceil, pow, sqrt};
pub const LDR_M_CAP: usize = 1000;
pub fn alpha_udr(log_trace_length: usize, log_blowup: usize, max_combo: usize) -> f64 {
let k = (1u64 << log_trace_length) as f64;
let n = (1u64 << (log_trace_length + log_blowup)) as f64;
let rho_plus = (k + max_combo as f64) / n;
(1.0 + rho_plus) * 0.5
}
pub fn alpha_ldr_m(log_blowup: usize, m: usize) -> f64 {
let rho = pow(2.0, -(log_blowup as f64));
(1.0 + 0.5 / m as f64) * sqrt(rho)
}
pub fn gamma_udr(log_trace_length: usize, log_blowup: usize, max_combo: usize) -> f64 {
1.0 - alpha_udr(log_trace_length, log_blowup, max_combo)
}
pub fn gamma_ldr_m(log_blowup: usize, m: usize) -> f64 {
let rho = pow(2.0, -(log_blowup as f64));
1.0 - sqrt(rho) * (1.0 + 0.5 / m as f64)
}
pub const fn list_size_udr() -> f64 {
1.0
}
pub const fn list_size_conjectured() -> f64 {
1.0
}
pub fn list_size_ldr_m(log_blowup: usize, m: usize) -> f64 {
let rho = pow(2.0, -(log_blowup as f64));
(m as f64 + 0.5) / sqrt(rho)
}
pub fn compute_upper_m(trace_length: usize) -> usize {
if trace_length == 0 {
return 0;
}
let h = trace_length as f64;
let ratio = (h + 2.0) / h;
ceil(1.0 / (2.0 * (sqrt(ratio) - 1.0))) as usize
}