fix: refactor to avoid circular dependencies

This commit is contained in:
2026-07-20 23:14:26 +02:00
parent 455585eeb6
commit 605d23f529
20 changed files with 603 additions and 522 deletions
+73 -55
View File
@@ -1,13 +1,31 @@
use strum::IntoEnumIterator;
use crate::common::validator::{validate_ascii_padded, validate_range};
use crate::dsp408::client::constants::{self as client_constants};
use crate::dsp408::protocol::constants as protocol_constants;
use crate::dsp408::protocol::validators;
use crate::common::errors::{MapperError, DecodingError, ValidationError};
use super::{encode_ascii, decode_ascii};
use crate::{
common::{
errors::{
DecodingError,
MapperError,
ValidationError,
},
validator::{
validate_ascii_padded,
validate_range,
},
},
dsp408::{
protocol::{
constants as protocol_constants,
validators,
},
types,
},
};
use crate::dsp408::client::types;
use super::{
constants as mapper_constants,
decode_ascii,
encode_ascii,
};
// ------ CHANNEL ------
@@ -76,12 +94,12 @@ pub fn output_channel_to_raw(channel: types::OutputChannel) -> Result<u8, Mapper
pub fn channel_name_to_raw(name: &str) -> Result<Vec<u8>, MapperError> {
validate_ascii_padded(
name.as_bytes(),
client_constants::CHANNEL_NAME_LENGTH,
client_constants::CHANNEL_NAME_PADDING,
protocol_constants::CHANNEL_NAME_LENGTH,
protocol_constants::CHANNEL_NAME_PADDING,
"Channel name",
)?;
Ok(encode_ascii(name, client_constants::CHANNEL_NAME_LENGTH, client_constants::CHANNEL_NAME_PADDING)?)
Ok(encode_ascii(name, protocol_constants::CHANNEL_NAME_LENGTH, protocol_constants::CHANNEL_NAME_PADDING)?)
}
pub fn raw_to_channel_name(raw_name: &[u8]) -> Result<String, MapperError> {
@@ -95,7 +113,7 @@ pub fn raw_to_channel_name(raw_name: &[u8]) -> Result<String, MapperError> {
pub fn attack_ms_to_raw(value: u16) -> Result<u16, MapperError> {
validate_range(
value,
client_constants::ATTACK_MS_RANGE,
mapper_constants::ATTACK_MS_RANGE,
|| format!("Invalid attack: {:#06x}", value),
)?;
@@ -113,7 +131,7 @@ pub fn raw_to_attack_ms(value: u16) -> Result<u16, MapperError> {
pub fn release_ms_to_raw(value: u16) -> Result<u16, MapperError> {
validate_range(
value,
client_constants::RELEASE_MS_RANGE,
mapper_constants::RELEASE_MS_RANGE,
|| format!("Invalid release: {:#06x}", value),
)?;
@@ -131,7 +149,7 @@ pub fn raw_to_release_ms(value: u16) -> Result<u16, MapperError> {
pub fn hold_ms_to_raw(hold: u16) -> Result<u16, MapperError> {
validate_range(
hold,
client_constants::HOLD_MS_RANGE,
mapper_constants::HOLD_MS_RANGE,
|| format!("Invalid hold: {:#06x}", hold),
)?;
@@ -149,19 +167,19 @@ pub fn raw_to_hold_ms(hold: u16) -> Result<u16, MapperError> {
pub fn gate_threshold_db_to_raw(db: f32) -> Result<u16, MapperError> {
validate_range(
db,
client_constants::GATE_THRESHOLD_DB_RANGE,
mapper_constants::GATE_THRESHOLD_DB_RANGE,
|| format!("Invalid gate threshold: {db}"),
)?;
let db = (db * 2.0).round() / 2.0;
Ok(((db - *client_constants::GATE_THRESHOLD_DB_RANGE.start()) * 2.0).round() as u16)
Ok(((db - *mapper_constants::GATE_THRESHOLD_DB_RANGE.start()) * 2.0).round() as u16)
}
pub fn raw_to_gate_threshold_db(value: u16) -> Result<f32, MapperError> {
validators::validate_raw_gate_threshold(value)?;
Ok(*client_constants::GATE_THRESHOLD_DB_RANGE.start() + value as f32 / 2.0)
Ok(*mapper_constants::GATE_THRESHOLD_DB_RANGE.start() + value as f32 / 2.0)
}
// ------ EQ GAIN ------
@@ -172,8 +190,8 @@ fn eq_gain_raw_steps() -> f32 {
}
fn eq_gain_step_db() -> f32 {
(*client_constants::EQ_GAIN_DB_RANGE.end()
- *client_constants::EQ_GAIN_DB_RANGE.start())
(*mapper_constants::EQ_GAIN_DB_RANGE.end()
- *mapper_constants::EQ_GAIN_DB_RANGE.start())
/ eq_gain_raw_steps()
}
@@ -184,7 +202,7 @@ fn eq_quantize(db: f32) -> f32 {
pub fn eq_gain_db_to_raw(gain: f32) -> Result<u16, MapperError> {
validate_range(
gain,
client_constants::EQ_GAIN_DB_RANGE,
mapper_constants::EQ_GAIN_DB_RANGE,
|| format!("Invalid EQ gain: {gain}"),
)?;
@@ -192,7 +210,7 @@ pub fn eq_gain_db_to_raw(gain: f32) -> Result<u16, MapperError> {
Ok(
*protocol_constants::EQ_GAIN_RAW_RANGE.start()
+ ((gain - *client_constants::EQ_GAIN_DB_RANGE.start())
+ ((gain - *mapper_constants::EQ_GAIN_DB_RANGE.start())
/ eq_gain_step_db())
.round() as u16
)
@@ -202,7 +220,7 @@ pub fn raw_to_eq_gain(value: u16) -> Result<f32, MapperError> {
validators::validate_raw_eq_gain(value)?;
let gain =
*client_constants::EQ_GAIN_DB_RANGE.start()
*mapper_constants::EQ_GAIN_DB_RANGE.start()
+ (value - *protocol_constants::EQ_GAIN_RAW_RANGE.start()) as f32
* eq_gain_step_db();
@@ -246,30 +264,30 @@ pub fn peq_band_to_raw(band: types::PEQBand, channel: types::Channel) -> Result<
// ------ GAIN ------
fn gain_split_raw() -> u16 {
((client_constants::GAIN_SPLIT_DB - client_constants::GAIN_DB_RANGE.start()) / client_constants::GAIN_LOW_STEP_DB).round() as u16
((mapper_constants::GAIN_SPLIT_DB - mapper_constants::GAIN_DB_RANGE.start()) / mapper_constants::GAIN_LOW_STEP_DB).round() as u16
}
fn quantize_gain(db: f32) -> f32 {
if db < client_constants::GAIN_SPLIT_DB {
(db / client_constants::GAIN_LOW_STEP_DB).round() * client_constants::GAIN_LOW_STEP_DB
if db < mapper_constants::GAIN_SPLIT_DB {
(db / mapper_constants::GAIN_LOW_STEP_DB).round() * mapper_constants::GAIN_LOW_STEP_DB
} else {
(db / client_constants::GAIN_HIGH_STEP_DB).round() * client_constants::GAIN_HIGH_STEP_DB
(db / mapper_constants::GAIN_HIGH_STEP_DB).round() * mapper_constants::GAIN_HIGH_STEP_DB
}
}
pub fn gain_db_to_raw(gain: f32) -> Result<u16, MapperError> {
validate_range(
gain,
client_constants::GAIN_DB_RANGE,
mapper_constants::GAIN_DB_RANGE,
|| format!("Invalid channel gain: {gain}"),
)?;
let gain = quantize_gain(gain);
if gain < client_constants::GAIN_SPLIT_DB {
Ok(((gain - client_constants::GAIN_DB_RANGE.start()) / client_constants::GAIN_LOW_STEP_DB).round() as u16)
if gain < mapper_constants::GAIN_SPLIT_DB {
Ok(((gain - mapper_constants::GAIN_DB_RANGE.start()) / mapper_constants::GAIN_LOW_STEP_DB).round() as u16)
} else {
Ok(gain_split_raw() + ((gain - client_constants::GAIN_SPLIT_DB) / client_constants::GAIN_HIGH_STEP_DB).round() as u16)
Ok(gain_split_raw() + ((gain - mapper_constants::GAIN_SPLIT_DB) / mapper_constants::GAIN_HIGH_STEP_DB).round() as u16)
}
}
@@ -277,9 +295,9 @@ pub fn raw_to_gain(raw_gain: u16) -> Result<f32, MapperError> {
validators::validate_raw_gain(raw_gain)?;
if raw_gain < gain_split_raw() {
Ok(client_constants::GAIN_DB_RANGE.start() + raw_gain as f32 * client_constants::GAIN_LOW_STEP_DB)
Ok(mapper_constants::GAIN_DB_RANGE.start() + raw_gain as f32 * mapper_constants::GAIN_LOW_STEP_DB)
} else {
Ok(client_constants::GAIN_SPLIT_DB + (raw_gain - gain_split_raw()) as f32 * client_constants::GAIN_HIGH_STEP_DB)
Ok(mapper_constants::GAIN_SPLIT_DB + (raw_gain - gain_split_raw()) as f32 * mapper_constants::GAIN_HIGH_STEP_DB)
}
}
@@ -289,13 +307,13 @@ pub fn frequency_hz_to_raw(hz: f32) -> Result<u16, MapperError> {
validate_range(
hz,
client_constants::FREQUENCY_HZ_RANGE,
mapper_constants::FREQUENCY_HZ_RANGE,
|| format!("Invalid frequency: {hz}"),
)?;
let device_steps = (protocol_constants::FREQUENCY_RAW_RANGE.end() - protocol_constants::FREQUENCY_RAW_RANGE.start()) as f32;
let raw = ((hz / client_constants::FREQUENCY_HZ_RANGE.start()).ln() / (client_constants::FREQUENCY_HZ_RANGE.end() / client_constants::FREQUENCY_HZ_RANGE.start()).ln()
let raw = ((hz / mapper_constants::FREQUENCY_HZ_RANGE.start()).ln() / (mapper_constants::FREQUENCY_HZ_RANGE.end() / mapper_constants::FREQUENCY_HZ_RANGE.start()).ln()
* device_steps)
.round();
@@ -308,7 +326,7 @@ pub fn raw_to_frequency_hz(value: u16) -> Result<f32, MapperError> {
let device_steps = (protocol_constants::FREQUENCY_RAW_RANGE.end() - protocol_constants::FREQUENCY_RAW_RANGE.start()) as f32;
let normalized = (value - protocol_constants::FREQUENCY_RAW_RANGE.start()) as f32 / device_steps;
Ok(client_constants::FREQUENCY_HZ_RANGE.start() * (client_constants::FREQUENCY_HZ_RANGE.end() / client_constants::FREQUENCY_HZ_RANGE.start()).powf(normalized))
Ok(mapper_constants::FREQUENCY_HZ_RANGE.start() * (mapper_constants::FREQUENCY_HZ_RANGE.end() / mapper_constants::FREQUENCY_HZ_RANGE.start()).powf(normalized))
}
// ------ DISCRETE FREQUENCY ------
@@ -481,13 +499,13 @@ pub fn raw_to_crossover_filter(raw: u8) -> Result<types::CrossoverFilter, Mapper
pub fn peq_q_to_raw(q: f32, filter: types::PEQFilter) -> Result<u8, MapperError> {
validate_range(
q,
client_constants::peq_q_range(filter),
mapper_constants::peq_q_range(filter),
|| format!("Invalid PEQ Q: {q}"),
)?;
let raw_range = (protocol_constants::PEQ_Q_RAW_RANGE.end() - protocol_constants::PEQ_Q_RAW_RANGE.start()) as f32;
Ok(((q / client_constants::PEQ_Q_RANGE.start()).ln() / (client_constants::PEQ_Q_RANGE.end() / client_constants::PEQ_Q_RANGE.start()).ln() * raw_range).round() as u8
Ok(((q / mapper_constants::PEQ_Q_RANGE.start()).ln() / (mapper_constants::PEQ_Q_RANGE.end() / mapper_constants::PEQ_Q_RANGE.start()).ln() * raw_range).round() as u8
+ protocol_constants::PEQ_Q_RAW_RANGE.start())
}
@@ -497,7 +515,7 @@ pub fn raw_to_peq_q(value: u8) -> Result<f32, MapperError> {
let raw_range = (protocol_constants::PEQ_Q_RAW_RANGE.end() - protocol_constants::PEQ_Q_RAW_RANGE.start()) as f32;
let normalized = (value - protocol_constants::PEQ_Q_RAW_RANGE.start()) as f32 / raw_range;
Ok(client_constants::PEQ_Q_RANGE.start() * (client_constants::PEQ_Q_RANGE.end() / client_constants::PEQ_Q_RANGE.start()).powf(normalized))
Ok(mapper_constants::PEQ_Q_RANGE.start() * (mapper_constants::PEQ_Q_RANGE.end() / mapper_constants::PEQ_Q_RANGE.start()).powf(normalized))
}
// ------ FILTER ------
@@ -615,7 +633,7 @@ pub fn raw_to_ratio(value: u16) -> Result<types::Ratio, MapperError> {
pub fn knee_db_to_raw(db: u16) -> Result<u16, MapperError> {
validate_range(
db,
client_constants::KNEE_DB_RANGE,
mapper_constants::KNEE_DB_RANGE,
|| format!("Invalid compressor knee: {db}"),
)?;
@@ -632,18 +650,18 @@ pub fn raw_to_knee_db(value: u16) -> Result<u16, MapperError> {
pub fn threshold_db_to_raw(db: f32) -> Result<u16, MapperError> {
validate_range(
db,
client_constants::THRESHOLD_DB_RANGE,
mapper_constants::THRESHOLD_DB_RANGE,
|| format!("Invalid compressor threshold: {db}"),
)?;
let db = (db * 2.0).round() / 2.0;
Ok(((db - client_constants::THRESHOLD_DB_RANGE.start()) * 2.0).round() as u16)
Ok(((db - mapper_constants::THRESHOLD_DB_RANGE.start()) * 2.0).round() as u16)
}
pub fn raw_to_threshold_db(value: u16) -> Result<f32, MapperError> {
validators::validate_raw_threshold(value)?;
Ok(client_constants::THRESHOLD_DB_RANGE.start() + (value as f32 / 2.0))
Ok(mapper_constants::THRESHOLD_DB_RANGE.start() + (value as f32 / 2.0))
}
// ------ LINK ------
@@ -739,31 +757,31 @@ pub fn raw_to_link_channels(source_raw: u8, destination_mask: u8) -> Result<Vec<
// ------ MATRIX GAIN ------
fn matrix_gain_split_raw() -> u16 {
((client_constants::GAIN_SPLIT_DB - client_constants::MATRIX_GAIN_DB_RANGE.start()) / client_constants::GAIN_LOW_STEP_DB).round() as u16
((mapper_constants::GAIN_SPLIT_DB - mapper_constants::MATRIX_GAIN_DB_RANGE.start()) / mapper_constants::GAIN_LOW_STEP_DB).round() as u16
}
fn quantize_matrix_gain(db: f32) -> f32 {
if db < client_constants::GAIN_SPLIT_DB {
(db / client_constants::GAIN_LOW_STEP_DB).round() * client_constants::GAIN_LOW_STEP_DB
if db < mapper_constants::GAIN_SPLIT_DB {
(db / mapper_constants::GAIN_LOW_STEP_DB).round() * mapper_constants::GAIN_LOW_STEP_DB
} else {
(db / client_constants::GAIN_HIGH_STEP_DB).round() * client_constants::GAIN_HIGH_STEP_DB
(db / mapper_constants::GAIN_HIGH_STEP_DB).round() * mapper_constants::GAIN_HIGH_STEP_DB
}
}
pub fn matrix_gain_db_to_raw(gain: f32) -> Result<u16, MapperError> {
validate_range(
gain,
client_constants::MATRIX_GAIN_DB_RANGE,
mapper_constants::MATRIX_GAIN_DB_RANGE,
|| format!("Invalid matrix gain: {gain}"),
)?;
let gain = quantize_matrix_gain(gain);
if gain < client_constants::GAIN_SPLIT_DB {
Ok(((gain - client_constants::MATRIX_GAIN_DB_RANGE.start()) / client_constants::GAIN_LOW_STEP_DB).round() as u16)
if gain < mapper_constants::GAIN_SPLIT_DB {
Ok(((gain - mapper_constants::MATRIX_GAIN_DB_RANGE.start()) / mapper_constants::GAIN_LOW_STEP_DB).round() as u16)
} else {
Ok(matrix_gain_split_raw()
+ ((gain - client_constants::GAIN_SPLIT_DB) / client_constants::GAIN_HIGH_STEP_DB).round() as u16)
+ ((gain - mapper_constants::GAIN_SPLIT_DB) / mapper_constants::GAIN_HIGH_STEP_DB).round() as u16)
}
}
@@ -771,9 +789,9 @@ pub fn raw_to_matrix_gain(raw_gain: u16) -> Result<f32, MapperError> {
validators::validate_raw_matrix_gain(raw_gain)?;
if raw_gain < matrix_gain_split_raw() {
Ok(client_constants::MATRIX_GAIN_DB_RANGE.start() + raw_gain as f32 * client_constants::GAIN_LOW_STEP_DB)
Ok(mapper_constants::MATRIX_GAIN_DB_RANGE.start() + raw_gain as f32 * mapper_constants::GAIN_LOW_STEP_DB)
} else {
Ok(client_constants::GAIN_SPLIT_DB + (raw_gain - matrix_gain_split_raw()) as f32 * client_constants::GAIN_HIGH_STEP_DB)
Ok(mapper_constants::GAIN_SPLIT_DB + (raw_gain - matrix_gain_split_raw()) as f32 * mapper_constants::GAIN_HIGH_STEP_DB)
}
}
@@ -815,7 +833,7 @@ fn delay_raw_steps() -> f32 {
pub fn delay_to_raw(delay: f32, unit: types::DelayUnit) -> Result<u8, MapperError> {
let (delay_min, delay_max) = client_constants::delay_range(unit);
let (delay_min, delay_max) = mapper_constants::delay_range(unit);
validate_range(
delay,
@@ -832,7 +850,7 @@ pub fn delay_to_raw(delay: f32, unit: types::DelayUnit) -> Result<u8, MapperErro
pub fn raw_to_delay(value: u8, unit: types::DelayUnit) -> Result<f32, MapperError> {
validators::validate_raw_channel_delay(value)?;
let (delay_min, delay_max) = client_constants::delay_range(unit);
let (delay_min, delay_max) = mapper_constants::delay_range(unit);
Ok(delay_min + ((value - protocol_constants::DELAY_RAW_RANGE.start()) as f32 / delay_raw_steps()) * (delay_max - delay_min))
}
@@ -915,7 +933,7 @@ mod tests {
fn channel_name_round_trip() {
let name = "In ABCDE";
let raw = channel_name_to_raw(name).unwrap();
assert_eq!(raw.len(), client_constants::CHANNEL_NAME_LENGTH);
assert_eq!(raw.len(), protocol_constants::CHANNEL_NAME_LENGTH);
let decoded = raw_to_channel_name(&raw).unwrap();
assert_eq!(decoded, name);
}
@@ -923,7 +941,7 @@ mod tests {
#[test]
fn channel_name_padding_is_applied() {
let raw = channel_name_to_raw(" Kick ").unwrap();
assert_eq!(raw.len(), client_constants::CHANNEL_NAME_LENGTH);
assert_eq!(raw.len(), protocol_constants::CHANNEL_NAME_LENGTH);
}
// ------------------------------------------------------------------