1use super::envelope::State as EnvState;
7use super::sampler::{Sampler, SamplingMethod};
8use super::synth::Synth;
9use super::ChipModel;
10
11pub mod reg {
12 pub const FREQLO1: u8 = 0x00;
13 pub const FREQHI1: u8 = 0x01;
14 pub const PWLO1: u8 = 0x02;
15 pub const PWHI1: u8 = 0x03;
16 pub const CR1: u8 = 0x04;
17 pub const AD1: u8 = 0x05;
18 pub const SR1: u8 = 0x06;
19 pub const FREQLO2: u8 = 0x07;
20 pub const FREQHI2: u8 = 0x08;
21 pub const PWLO2: u8 = 0x09;
22 pub const PWHI2: u8 = 0x0a;
23 pub const CR2: u8 = 0x0b;
24 pub const AD2: u8 = 0x0c;
25 pub const SR2: u8 = 0x0d;
26 pub const FREQLO3: u8 = 0x0e;
27 pub const FREQHI3: u8 = 0x0f;
28 pub const PWLO3: u8 = 0x10;
29 pub const PWHI3: u8 = 0x11;
30 pub const CR3: u8 = 0x12;
31 pub const AD3: u8 = 0x13;
32 pub const SR3: u8 = 0x14;
33 pub const FCLO: u8 = 0x15;
34 pub const FCHI: u8 = 0x16;
35 pub const RESFILT: u8 = 0x17;
36 pub const MODVOL: u8 = 0x18;
37 pub const POTX: u8 = 0x19;
38 pub const POTY: u8 = 0x1a;
39 pub const OSC3: u8 = 0x1b;
40 pub const ENV3: u8 = 0x1c;
41}
42
43#[derive(Debug)]
44pub struct State {
45 pub sid_register: [u8; 32],
47 pub bus_value: u8,
48 pub bus_value_ttl: u32,
49 pub ext_in: i32,
50 pub accumulator: [u32; 3],
52 pub shift_register: [u32; 3],
53 pub envelope_state: [u8; 3],
55 pub envelope_counter: [u8; 3],
56 pub exponential_counter: [u8; 3],
57 pub exponential_counter_period: [u8; 3],
58 pub hold_zero: [u8; 3],
59 pub rate_counter: [u16; 3],
60 pub rate_counter_period: [u16; 3],
61}
62
63#[derive(Clone)]
64pub struct Sid {
65 sampler: Sampler,
67 bus_value: u8,
69 bus_value_ttl: u32,
70}
71
72impl Sid {
73 pub fn new(chip_model: ChipModel) -> Self {
74 let synth = Synth::new(chip_model);
75 let mut sid = Sid {
76 sampler: Sampler::new(synth),
77 bus_value: 0,
78 bus_value_ttl: 0,
79 };
80 sid.set_sampling_parameters(SamplingMethod::Fast, 985_248, 44100);
81 sid
82 }
83
84 pub fn set_sampling_parameters(
85 &mut self,
86 method: SamplingMethod,
87 clock_freq: u32,
88 sample_freq: u32,
89 ) {
90 self.sampler.set_parameters(method, clock_freq, sample_freq);
91 }
92
93 pub fn clock(&mut self) {
94 if self.bus_value_ttl > 0 {
96 self.bus_value_ttl -= 1;
97 if self.bus_value_ttl == 0 {
98 self.bus_value = 0;
99 }
100 }
101 self.sampler.synth.clock();
103 }
104
105 pub fn clock_delta(&mut self, delta: u32) {
106 if self.bus_value_ttl >= delta {
108 self.bus_value_ttl -= delta;
109 } else {
110 self.bus_value_ttl = 0;
111 }
112 if self.bus_value_ttl == 0 {
113 self.bus_value = 0;
114 }
115 self.sampler.synth.clock_delta(delta);
117 }
118
119 pub fn enable_external_filter(&mut self, enabled: bool) {
120 self.sampler.synth.ext_filter.set_enabled(enabled);
121 }
122
123 pub fn enable_filter(&mut self, enabled: bool) {
124 self.sampler.synth.filter.set_enabled(enabled);
125 }
126
127 pub fn input(&mut self, sample: i32) {
128 self.sampler.synth.ext_in = (sample << 4) * 3;
131 }
132
133 pub fn output(&self) -> i16 {
134 self.sampler.synth.output()
135 }
136
137 pub fn reset(&mut self) {
138 self.sampler.reset();
139 self.bus_value = 0;
140 self.bus_value_ttl = 0;
141 }
142
143 pub fn sample(&mut self, delta: u32, buffer: &mut [i16], interleave: usize) -> (usize, u32) {
160 self.sampler.clock(delta, buffer, interleave)
161 }
162
163 pub fn read(&self, reg: u8) -> u8 {
166 self.sampler.synth.read(reg, self.bus_value)
167 }
168
169 pub fn write(&mut self, reg: u8, value: u8) {
170 self.bus_value = value;
171 self.bus_value_ttl = 0x2000;
172 self.sampler.synth.write(reg, value);
173 }
174
175 pub fn read_state(&self) -> State {
178 let mut state = State {
179 sid_register: [0; 32],
180 bus_value: 0,
181 bus_value_ttl: 0,
182 ext_in: 0,
183 accumulator: [0; 3],
184 shift_register: [0; 3],
185 envelope_state: [0; 3],
186 envelope_counter: [0; 3],
187 exponential_counter: [0; 3],
188 exponential_counter_period: [0; 3],
189 hold_zero: [0; 3],
190 rate_counter: [0; 3],
191 rate_counter_period: [0; 3],
192 };
193 for i in 0..3 {
194 let j = i * 7;
195 let wave = &self.sampler.synth.voices[i].wave;
196 let envelope = &self.sampler.synth.voices[i].envelope;
197 state.sid_register[j] = wave.get_frequency_lo();
198 state.sid_register[j + 1] = wave.get_frequency_hi();
199 state.sid_register[j + 2] = wave.get_pulse_width_lo();
200 state.sid_register[j + 3] = wave.get_pulse_width_hi();
201 state.sid_register[j + 4] = wave.get_control() | envelope.get_control();
202 state.sid_register[j + 5] = envelope.get_attack_decay();
203 state.sid_register[j + 6] = envelope.get_sustain_release();
204 }
205 let filter = &self.sampler.synth.filter;
206 state.sid_register[0x15] = filter.get_fc_lo();
207 state.sid_register[0x16] = filter.get_fc_hi();
208 state.sid_register[0x17] = filter.get_res_filt();
209 state.sid_register[0x18] = filter.get_mode_vol();
210 for i in 0x19..0x1d {
211 state.sid_register[i] = self.read(i as u8);
212 }
213 for i in 0x1d..0x20 {
214 state.sid_register[i] = 0;
215 }
216 state.bus_value = self.bus_value;
217 state.bus_value_ttl = self.bus_value_ttl;
218 state.ext_in = self.sampler.synth.ext_in;
219 for i in 0..3 {
220 let wave = &self.sampler.synth.voices[i].wave;
221 let envelope = &self.sampler.synth.voices[i].envelope;
222 state.accumulator[i] = wave.get_acc();
223 state.shift_register[i] = wave.get_shift();
224 state.envelope_state[i] = envelope.state as u8;
225 state.envelope_counter[i] = envelope.envelope_counter;
226 state.exponential_counter[i] = envelope.exponential_counter;
227 state.exponential_counter_period[i] = envelope.exponential_counter_period;
228 state.hold_zero[i] = if envelope.hold_zero { 1 } else { 0 };
229 state.rate_counter[i] = envelope.rate_counter;
230 state.rate_counter_period[i] = envelope.rate_counter_period;
231 }
232 state
233 }
234
235 pub fn write_state(&mut self, state: &State) {
236 for i in 0..0x19 {
237 self.write(i, state.sid_register[i as usize]);
238 }
239 self.bus_value = state.bus_value;
240 self.bus_value_ttl = state.bus_value_ttl;
241 self.sampler.synth.ext_in = state.ext_in;
242 for i in 0..3 {
243 let envelope = &mut self.sampler.synth.voices[i].envelope;
244 self.sampler.synth.voices[i].wave.acc = state.accumulator[i];
245 self.sampler.synth.voices[i].wave.shift = state.shift_register[i];
246 envelope.state = match state.envelope_state[i] {
247 0 => EnvState::Attack,
248 1 => EnvState::DecaySustain,
249 2 => EnvState::Release,
250 _ => panic!("invalid envelope state"),
251 };
252 envelope.envelope_counter = state.envelope_counter[i];
253 envelope.exponential_counter = state.exponential_counter[i];
254 envelope.exponential_counter_period = state.exponential_counter_period[i];
255 envelope.hold_zero = state.hold_zero[i] != 0;
256 envelope.rate_counter = state.rate_counter[i];
257 envelope.rate_counter_period = state.rate_counter_period[i];
258 }
259 }
260}