1 // license:BSD-3-Clause 2 // copyright-holders:Ryan Holtz 3 /***************************************************************************** 4 5 SunPlus SPG2xx-series SoC peripheral emulation (Audio) 6 7 **********************************************************************/ 8 9 #ifndef MAME_MACHINE_SPG2XX_AUDIO_H 10 #define MAME_MACHINE_SPG2XX_AUDIO_H 11 12 #pragma once 13 14 #include "sound/okiadpcm.h" 15 #include "cpu/unsp/unsp.h" 16 17 class spg2xx_audio_device : public device_t, public device_sound_interface 18 { 19 public: 20 spg2xx_audio_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); 21 spg2xx_audio_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); 22 space_read_callback()23 auto space_read_callback() { return m_space_read_cb.bind(); } write_irq_callback()24 auto write_irq_callback() { return m_irq_cb.bind(); } channel_irq_callback()25 auto channel_irq_callback() { return m_ch_irq_cb.bind(); } 26 27 uint16_t audio_r(offs_t offset); 28 virtual void audio_w(offs_t offset, uint16_t data); 29 uint16_t audio_ctrl_r(offs_t offset); 30 void audio_ctrl_w(offs_t offset, uint16_t data); 31 uint16_t audio_phase_r(offs_t offset); 32 void audio_phase_w(offs_t offset, uint16_t data); 33 34 protected: 35 // sound stream update overrides 36 virtual void sound_stream_update(sound_stream &stream, std::vector<read_stream_view> const &inputs, std::vector<write_stream_view> &outputs) override; 37 38 void audio_beat_tick(); 39 void audio_rampdown_tick(const uint32_t channel); 40 bool audio_envelope_tick(const uint32_t channel); 41 inline uint32_t get_rampdown_frame_count(const uint32_t channel); 42 inline uint32_t get_envclk_frame_count(const uint32_t channel); 43 44 // Audio getters get_channel_enable(const offs_t channel)45 bool get_channel_enable(const offs_t channel) const { return m_audio_ctrl_regs[AUDIO_CHANNEL_ENABLE] & (1 << channel); } get_channel_status(const offs_t channel)46 bool get_channel_status(const offs_t channel) const { return m_audio_ctrl_regs[AUDIO_CHANNEL_STATUS] & (1 << channel); } get_manual_envelope_enable(const offs_t channel)47 bool get_manual_envelope_enable(const offs_t channel) const { return m_audio_ctrl_regs[AUDIO_CHANNEL_ENV_MODE] & (1 << channel); } get_auto_envelope_enable(const offs_t channel)48 bool get_auto_envelope_enable(const offs_t channel) const { return !get_manual_envelope_enable(channel); } 49 uint32_t get_envelope_clock(const offs_t channel) const; get_vol_sel()50 uint16_t get_vol_sel() const { return (m_audio_ctrl_regs[AUDIO_CONTROL] & AUDIO_CONTROL_VOLSEL_MASK) >> AUDIO_CONTROL_VOLSEL_SHIFT; } 51 52 // Audio Mode getters get_wave_addr_high(const offs_t channel)53 uint16_t get_wave_addr_high(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_MODE] & AUDIO_WADDR_HIGH_MASK; } get_loop_addr_high(const offs_t channel)54 uint16_t get_loop_addr_high(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_MODE] & AUDIO_LADDR_HIGH_MASK) >> AUDIO_LADDR_HIGH_SHIFT; } get_tone_mode(const offs_t channel)55 uint16_t get_tone_mode(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_MODE] & AUDIO_TONE_MODE_MASK) >> AUDIO_TONE_MODE_SHIFT; } get_16bit_bit(const offs_t channel)56 virtual uint16_t get_16bit_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_MODE] & AUDIO_16M_MASK) ? 1 : 0; } get_adpcm_bit(const offs_t channel)57 virtual uint16_t get_adpcm_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_MODE] & AUDIO_ADPCM_MASK) ? 1 : 0; } 58 59 // Audio Pan getters get_volume(const offs_t channel)60 uint16_t get_volume(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_PAN_VOL] & AUDIO_VOLUME_MASK; } get_pan(const offs_t channel)61 uint16_t get_pan(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_PAN_VOL] & AUDIO_PAN_MASK) >> AUDIO_PAN_SHIFT; } 62 63 // Audio Envelope0 Data getters get_envelope_inc(const offs_t channel)64 uint16_t get_envelope_inc(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_ENVELOPE0] & AUDIO_ENVELOPE_INC_MASK; } get_envelope_sign_bit(const offs_t channel)65 uint16_t get_envelope_sign_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE0] & AUDIO_ENVELOPE_SIGN_MASK) ? 1 : 0; } get_envelope_target(const offs_t channel)66 uint16_t get_envelope_target(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE0] & AUDIO_ENVELOPE_TARGET_MASK) >> AUDIO_ENVELOPE_TARGET_SHIFT; } get_repeat_period_bit(const offs_t channel)67 uint16_t get_repeat_period_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE0] & AUDIO_ENVELOPE_REPEAT_PERIOD_MASK) ? 1 : 0; } 68 69 // Audio Envelope Data getters get_edd(const offs_t channel)70 uint16_t get_edd(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA] & AUDIO_EDD_MASK; } get_envelope_count(const offs_t channel)71 uint16_t get_envelope_count(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA] & AUDIO_ENVELOPE_COUNT_MASK) >> AUDIO_ENVELOPE_COUNT_SHIFT; } set_edd(const offs_t channel,uint8_t edd)72 void set_edd(const offs_t channel, uint8_t edd) { m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA] = (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA] & ~AUDIO_EDD_MASK) | edd; } set_envelope_count(const offs_t channel,uint16_t count)73 void set_envelope_count(const offs_t channel, uint16_t count) { m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA] = get_edd(channel) | (count << AUDIO_ENVELOPE_COUNT_SHIFT); } 74 75 // Audio Envelope1 Data getters get_envelope_load(const offs_t channel)76 uint16_t get_envelope_load(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_ENVELOPE1] & AUDIO_ENVELOPE_LOAD_MASK; } get_envelope_repeat_bit(const offs_t channel)77 uint16_t get_envelope_repeat_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE1] & AUDIO_ENVELOPE_RPT_MASK) ? 1 : 0; } get_envelope_repeat_count(const offs_t channel)78 uint16_t get_envelope_repeat_count(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE1] & AUDIO_ENVELOPE_RPCNT_MASK) >> AUDIO_ENVELOPE_RPCNT_SHIFT; } set_envelope_repeat_count(const offs_t channel,const uint16_t count)79 inline void set_envelope_repeat_count(const offs_t channel, const uint16_t count) { m_audio_regs[(channel << 4) | AUDIO_ENVELOPE1] = (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE1] & ~AUDIO_ENVELOPE_RPCNT_MASK) | ((count << AUDIO_ENVELOPE_RPCNT_SHIFT) & AUDIO_ENVELOPE_RPCNT_MASK); } 80 81 // Audio Envelope Address getters get_envelope_addr_high(const offs_t channel)82 uint16_t get_envelope_addr_high(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_ADDR_HIGH] & AUDIO_EADDR_HIGH_MASK; } get_audio_irq_enable_bit(const offs_t channel)83 uint16_t get_audio_irq_enable_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_ADDR_HIGH] & AUDIO_IRQ_EN_MASK) ? 1 : 0; } get_audio_irq_addr(const offs_t channel)84 uint16_t get_audio_irq_addr(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_ADDR_HIGH] & AUDIO_IRQ_ADDR_MASK) >> AUDIO_IRQ_ADDR_SHIFT; } 85 86 // Audio Envelope Loop getters get_envelope_eaoffset(const offs_t channel)87 uint16_t get_envelope_eaoffset(const offs_t channel) const { return m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_LOOP_CTRL] & AUDIO_EAOFFSET_MASK; } get_rampdown_offset(const offs_t channel)88 uint16_t get_rampdown_offset(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_LOOP_CTRL] & AUDIO_RAMPDOWN_OFFSET_MASK) >> AUDIO_RAMPDOWN_OFFSET_SHIFT; } set_envelope_eaoffset(const offs_t channel,uint16_t eaoffset)89 void set_envelope_eaoffset(const offs_t channel, uint16_t eaoffset) { m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_LOOP_CTRL] = (m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_LOOP_CTRL] & ~AUDIO_RAMPDOWN_OFFSET_MASK) | (eaoffset & AUDIO_EAOFFSET_MASK); } 90 91 // Audio ADPCM getters get_point_number(const offs_t channel)92 uint16_t get_point_number(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ADPCM_SEL] & AUDIO_POINT_NUMBER_MASK) >> AUDIO_POINT_NUMBER_SHIFT; } get_adpcm36_bit(const offs_t channel)93 uint16_t get_adpcm36_bit(const offs_t channel) const { return (m_audio_regs[(channel << 4) | AUDIO_ADPCM_SEL] & AUDIO_ADPCM36_MASK) ? 1 : 0; } 94 95 // Audio high-word getters get_phase_high(const offs_t channel)96 uint16_t get_phase_high(const offs_t channel) const { return m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_HIGH] & AUDIO_PHASE_HIGH_MASK; } get_phase_accum_high(const offs_t channel)97 uint16_t get_phase_accum_high(const offs_t channel) const { return m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_ACCUM_HIGH] & AUDIO_PHASE_ACCUM_HIGH_MASK; } get_target_phase_high(const offs_t channel)98 uint16_t get_target_phase_high(const offs_t channel) const { return m_audio_phase_regs[(channel << 4) | AUDIO_TARGET_PHASE_HIGH] & AUDIO_TARGET_PHASE_HIGH_MASK; } get_rampdown_clock(const offs_t channel)99 uint16_t get_rampdown_clock(const offs_t channel) const { return m_audio_phase_regs[(channel << 4) | AUDIO_RAMP_DOWN_CLOCK] & AUDIO_RAMP_DOWN_CLOCK_MASK; } 100 101 // Audio ADPCM getters get_phase_offset(const offs_t channel)102 uint16_t get_phase_offset(const offs_t channel) const { return m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_CTRL] & AUDIO_PHASE_OFFSET_MASK; } get_phase_sign_bit(const offs_t channel)103 uint16_t get_phase_sign_bit(const offs_t channel) const { return (m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_CTRL] & AUDIO_PHASE_SIGN_MASK) >> AUDIO_PHASE_SIGN_SHIFT; } get_phase_time_step(const offs_t channel)104 uint16_t get_phase_time_step(const offs_t channel) const { return (m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_CTRL] & AUDIO_PHASE_TIME_STEP_MASK) >> AUDIO_PHASE_TIME_STEP_SHIFT; } 105 106 // Audio combined getters get_phase(const offs_t channel)107 virtual uint32_t get_phase(const offs_t channel) const { return ((uint32_t)get_phase_high(channel) << 16) | m_audio_phase_regs[(channel << 4) | AUDIO_PHASE]; } get_phase_accum(const offs_t channel)108 uint32_t get_phase_accum(const offs_t channel) const { return ((uint32_t)get_phase_accum_high(channel) << 16) | m_audio_phase_regs[(channel << 4) | AUDIO_PHASE_ACCUM]; } get_target_phase(const offs_t channel)109 uint32_t get_target_phase(const offs_t channel) const { return ((uint32_t)get_target_phase_high(channel) << 16) | m_audio_phase_regs[(channel << 4) | AUDIO_TARGET_PHASE]; } 110 get_wave_addr(const offs_t channel)111 uint32_t get_wave_addr(const offs_t channel) const { return ((uint32_t)get_wave_addr_high(channel) << 16) | m_audio_regs[(channel << 4) | AUDIO_WAVE_ADDR]; } get_loop_addr(const offs_t channel)112 uint32_t get_loop_addr(const offs_t channel) const { return ((uint32_t)get_loop_addr_high(channel) << 16) | m_audio_regs[(channel << 4) | AUDIO_LOOP_ADDR]; } get_envelope_addr(const offs_t channel)113 uint32_t get_envelope_addr(const offs_t channel) const { return ((uint32_t)get_envelope_addr_high(channel) << 16) | m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_ADDR]; } 114 115 enum // at audio write offset 0x000 in spg2xx 116 { 117 AUDIO_WAVE_ADDR = 0x000, 118 119 AUDIO_MODE = 0x001, 120 AUDIO_WADDR_HIGH_MASK = 0x003f, 121 AUDIO_LADDR_HIGH_MASK = 0x0fc0, 122 AUDIO_LADDR_HIGH_SHIFT = 6, 123 AUDIO_TONE_MODE_MASK = 0x3000, 124 AUDIO_TONE_MODE_SHIFT = 12, 125 AUDIO_TONE_MODE_SW = 0, 126 AUDIO_TONE_MODE_HW_ONESHOT = 1, 127 AUDIO_TONE_MODE_HW_LOOP = 2, 128 AUDIO_16M_MASK = 0x4000, 129 AUDIO_ADPCM_MASK = 0x8000, 130 131 AUDIO_LOOP_ADDR = 0x002, 132 133 AUDIO_PAN_VOL = 0x003, 134 AUDIO_PAN_VOL_MASK = 0x7f7f, 135 AUDIO_VOLUME_MASK = 0x007f, 136 AUDIO_PAN_MASK = 0x7f00, 137 AUDIO_PAN_SHIFT = 8, 138 139 AUDIO_ENVELOPE0 = 0x004, 140 AUDIO_ENVELOPE_INC_MASK = 0x007f, 141 AUDIO_ENVELOPE_SIGN_MASK = 0x0080, 142 AUDIO_ENVELOPE_TARGET_MASK = 0x7f00, 143 AUDIO_ENVELOPE_TARGET_SHIFT = 8, 144 AUDIO_ENVELOPE_REPEAT_PERIOD_MASK = 0x8000, 145 146 AUDIO_ENVELOPE_DATA = 0x005, 147 AUDIO_ENVELOPE_DATA_MASK = 0xff7f, 148 AUDIO_EDD_MASK = 0x007f, 149 AUDIO_ENVELOPE_COUNT_MASK = 0xff00, 150 AUDIO_ENVELOPE_COUNT_SHIFT = 8, 151 152 AUDIO_ENVELOPE1 = 0x006, 153 AUDIO_ENVELOPE_LOAD_MASK = 0x00ff, 154 AUDIO_ENVELOPE_RPT_MASK = 0x0100, 155 AUDIO_ENVELOPE_RPCNT_MASK = 0xfe00, 156 AUDIO_ENVELOPE_RPCNT_SHIFT = 9, 157 158 AUDIO_ENVELOPE_ADDR_HIGH = 0x007, 159 AUDIO_EADDR_HIGH_MASK = 0x003f, 160 AUDIO_IRQ_EN_MASK = 0x0040, 161 AUDIO_IRQ_ADDR_MASK = 0xff80, 162 AUDIO_IRQ_ADDR_SHIFT = 7, 163 164 AUDIO_ENVELOPE_ADDR = 0x008, 165 AUDIO_WAVE_DATA_PREV = 0x009, 166 167 AUDIO_ENVELOPE_LOOP_CTRL = 0x00a, 168 AUDIO_EAOFFSET_MASK = 0x01ff, 169 AUDIO_RAMPDOWN_OFFSET_MASK = 0xfe00, 170 AUDIO_RAMPDOWN_OFFSET_SHIFT = 9, 171 172 AUDIO_WAVE_DATA = 0x00b, 173 174 AUDIO_ADPCM_SEL = 0x00d, 175 AUDIO_ADPCM_SEL_MASK = 0xfe00, 176 AUDIO_POINT_NUMBER_MASK = 0x7e00, 177 AUDIO_POINT_NUMBER_SHIFT = 9, 178 AUDIO_ADPCM36_MASK = 0x8000, 179 }; 180 181 enum // at audio write offset 0x200 in spg2xx 182 { 183 AUDIO_PHASE_HIGH = 0x000, 184 AUDIO_PHASE_HIGH_MASK = 0x0007, 185 186 AUDIO_PHASE_ACCUM_HIGH = 0x001, 187 AUDIO_PHASE_ACCUM_HIGH_MASK = 0x0007, 188 189 AUDIO_TARGET_PHASE_HIGH = 0x002, 190 AUDIO_TARGET_PHASE_HIGH_MASK= 0x0007, 191 192 AUDIO_RAMP_DOWN_CLOCK = 0x003, 193 AUDIO_RAMP_DOWN_CLOCK_MASK = 0x0007, 194 195 AUDIO_PHASE = 0x004, 196 AUDIO_PHASE_ACCUM = 0x005, 197 AUDIO_TARGET_PHASE = 0x006, 198 199 AUDIO_PHASE_CTRL = 0x007, 200 AUDIO_PHASE_OFFSET_MASK = 0x0fff, 201 AUDIO_PHASE_SIGN_MASK = 0x1000, 202 AUDIO_PHASE_SIGN_SHIFT = 12, 203 AUDIO_PHASE_TIME_STEP_MASK = 0xe000, 204 AUDIO_PHASE_TIME_STEP_SHIFT = 13, 205 206 AUDIO_CHAN_OFFSET_MASK = 0xf0f, 207 }; 208 209 enum // at audio write offset 0x400 in spg2xx 210 { 211 212 AUDIO_CHANNEL_ENABLE = 0x000, 213 AUDIO_CHANNEL_ENABLE_MASK = 0xffff, 214 215 AUDIO_MAIN_VOLUME = 0x001, 216 AUDIO_MAIN_VOLUME_MASK = 0x007f, 217 218 AUDIO_CHANNEL_FIQ_ENABLE = 0x002, 219 AUDIO_CHANNEL_FIQ_ENABLE_MASK = 0xffff, 220 221 AUDIO_CHANNEL_FIQ_STATUS = 0x003, 222 AUDIO_CHANNEL_FIQ_STATUS_MASK = 0xffff, 223 224 AUDIO_BEAT_BASE_COUNT = 0x004, 225 AUDIO_BEAT_BASE_COUNT_MASK = 0x07ff, 226 227 AUDIO_BEAT_COUNT = 0x005, 228 AUDIO_BEAT_COUNT_MASK = 0x3fff, 229 AUDIO_BIS_MASK = 0x4000, 230 AUDIO_BIE_MASK = 0x8000, 231 232 AUDIO_ENVCLK0 = 0x006, 233 234 AUDIO_ENVCLK0_HIGH = 0x007, 235 AUDIO_ENVCLK0_HIGH_MASK = 0xffff, 236 237 AUDIO_ENVCLK1 = 0x008, 238 239 AUDIO_ENVCLK1_HIGH = 0x009, 240 AUDIO_ENVCLK1_HIGH_MASK = 0xffff, 241 242 AUDIO_ENV_RAMP_DOWN = 0x00a, 243 AUDIO_ENV_RAMP_DOWN_MASK = 0xffff, 244 245 AUDIO_CHANNEL_STOP = 0x00b, 246 AUDIO_CHANNEL_STOP_MASK = 0xffff, 247 248 AUDIO_CHANNEL_ZERO_CROSS = 0x00c, 249 AUDIO_CHANNEL_ZERO_CROSS_MASK = 0xffff, 250 251 AUDIO_CONTROL = 0x00d, 252 AUDIO_CONTROL_MASK = 0x9fe8, 253 AUDIO_CONTROL_SATURATE_MASK = 0x8000, 254 AUDIO_CONTROL_SOFTCH_MASK = 0x1000, 255 AUDIO_CONTROL_COMPEN_MASK = 0x0800, 256 AUDIO_CONTROL_NOHIGH_MASK = 0x0400, 257 AUDIO_CONTROL_NOINT_MASK = 0x0200, 258 AUDIO_CONTROL_EQEN_MASK = 0x0100, 259 AUDIO_CONTROL_VOLSEL_MASK = 0x00c0, 260 AUDIO_CONTROL_VOLSEL_SHIFT = 6, 261 AUDIO_CONTROL_FOF_MASK = 0x0020, 262 AUDIO_CONTROL_INIT_MASK = 0x0008, 263 264 AUDIO_COMPRESS_CTRL = 0x00e, 265 AUDIO_COMPRESS_CTRL_PEAK_MASK = 0x8000, 266 AUDIO_COMPRESS_CTRL_THRESHOLD_MASK = 0x7f00, 267 AUDIO_COMPRESS_CTRL_THRESHOLD_SHIFT = 8, 268 AUDIO_COMPRESS_CTRL_ATTSCALE_MASK = 0x00c0, 269 AUDIO_COMPRESS_CTRL_ATTSCALE_SHIFT = 6, 270 AUDIO_COMPRESS_CTRL_RELSCALE_MASK = 0x0030, 271 AUDIO_COMPRESS_CTRL_RELSCALE_SHIFT = 4, 272 AUDIO_COMPRESS_CTRL_DISZC_MASK = 0x0008, 273 AUDIO_COMPRESS_CTRL_RATIO_MASK = 0x0007, 274 275 AUDIO_CHANNEL_STATUS = 0x00f, 276 AUDIO_CHANNEL_STATUS_MASK = 0xffff, 277 278 AUDIO_WAVE_IN_L = 0x010, 279 280 AUDIO_WAVE_IN_R = 0x011, 281 AUDIO_SOFTIRQ_MASK = 0x8000, 282 AUDIO_SOFTIRQ_EN_MASK = 0x4000, 283 AUDIO_SOFT_PHASE_HIGH_MASK = 0x0070, 284 AUDIO_SOFT_PHASE_HIGH_SHIFT = 4, 285 AUDIO_FIFO_IRQ_THRESHOLD_MASK = 0x000f, 286 287 AUDIO_WAVE_OUT_L = 0x012, 288 AUDIO_WAVE_OUT_R = 0x013, 289 290 AUDIO_CHANNEL_REPEAT = 0x014, 291 AUDIO_CHANNEL_REPEAT_MASK = 0xffff, 292 293 AUDIO_CHANNEL_ENV_MODE = 0x015, 294 AUDIO_CHANNEL_ENV_MODE_MASK = 0xffff, 295 296 AUDIO_CHANNEL_TONE_RELEASE = 0x016, 297 AUDIO_CHANNEL_TONE_RELEASE_MASK = 0xffff, 298 299 AUDIO_CHANNEL_ENV_IRQ = 0x017, 300 AUDIO_CHANNEL_ENV_IRQ_MASK = 0xffff, 301 302 AUDIO_CHANNEL_PITCH_BEND = 0x018, 303 AUDIO_CHANNEL_PITCH_BEND_MASK = 0xffff, 304 305 AUDIO_SOFT_PHASE = 0x019, 306 307 AUDIO_ATTACK_RELEASE = 0x01a, 308 AUDIO_RELEASE_TIME_MASK = 0x00ff, 309 AUDIO_ATTACK_TIME_MASK = 0xff00, 310 AUDIO_ATTACK_TIME_SHIFT = 8, 311 312 AUDIO_EQ_CUTOFF10 = 0x01b, 313 AUDIO_EQ_CUTOFF10_MASK = 0x7f7f, 314 315 AUDIO_EQ_CUTOFF32 = 0x01c, 316 AUDIO_EQ_CUTOFF32_MASK = 0x7f7f, 317 318 AUDIO_EQ_GAIN10 = 0x01d, 319 AUDIO_EQ_GAIN10_MASK = 0x7f7f, 320 321 AUDIO_EQ_GAIN32 = 0x01e, 322 AUDIO_EQ_GAIN32_MASK = 0x7f7f 323 }; 324 325 struct adpcm36_state 326 { 327 uint16_t m_remaining; 328 uint16_t m_header; 329 int16_t m_prevsamp[2]; 330 }; 331 332 static const device_timer_id TIMER_BEAT = 3; 333 static const device_timer_id TIMER_IRQ = 4; 334 335 void check_irqs(const uint16_t changed); 336 337 virtual void device_start() override; 338 virtual void device_reset() override; 339 virtual void device_stop() override; 340 virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override; 341 342 uint16_t read_space(offs_t offset); 343 344 void stop_channel(const uint32_t channel); 345 bool advance_channel(const uint32_t channel); 346 bool fetch_sample(const uint32_t channel); 347 void loop_channel(const uint32_t channel); 348 uint16_t decode_adpcm36_nybble(const uint32_t channel, const uint8_t data); 349 void read_adpcm36_header(const uint32_t channel); 350 351 bool m_debug_samples; 352 bool m_debug_rates; 353 354 uint16_t m_audio_regs[0x200]; 355 uint16_t m_audio_phase_regs[0x200]; 356 uint16_t m_audio_ctrl_regs[0x400]; 357 uint8_t m_sample_shift[16]; 358 uint32_t m_sample_count[16]; 359 uint32_t m_sample_addr[16]; 360 double m_channel_rate[16]; 361 double m_channel_rate_accum[16]; 362 uint32_t m_rampdown_frame[16]; 363 uint32_t m_envclk_frame[16]; 364 uint32_t m_envelope_addr[16]; 365 int m_channel_debug; 366 uint16_t m_audio_curr_beat_base_count; 367 368 emu_timer *m_audio_beat; 369 emu_timer *m_channel_irq[16]; 370 371 sound_stream *m_stream; 372 oki_adpcm_state m_adpcm[16]; 373 adpcm36_state m_adpcm36_state[16]; 374 375 static const uint32_t s_rampdown_frame_counts[8]; 376 static const uint32_t s_envclk_frame_counts[16]; 377 378 private: 379 devcb_read16 m_space_read_cb; 380 devcb_write_line m_irq_cb; 381 devcb_write_line m_ch_irq_cb; 382 }; 383 384 class spg110_audio_device : public spg2xx_audio_device 385 { 386 public: 387 spg110_audio_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); 388 389 virtual void audio_w(offs_t offset, uint16_t data) override; 390 391 // these either come from somewhere else on spg110 or are hardcoded get_16bit_bit(const offs_t channel)392 virtual uint16_t get_16bit_bit(const offs_t channel) const override { return 1; } get_adpcm_bit(const offs_t channel)393 virtual uint16_t get_adpcm_bit(const offs_t channel) const override { return 0; } 394 get_phase(const offs_t channel)395 virtual uint32_t get_phase(const offs_t channel) const override { return m_audio_regs[(channel << 4) | 0xe]; } 396 }; 397 398 class sunplus_gcm394_audio_device : public spg2xx_audio_device 399 { 400 public: 401 sunplus_gcm394_audio_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); 402 403 uint16_t control_r(offs_t offset); 404 void control_w(offs_t offset, uint16_t data); 405 406 virtual void device_start() override; 407 408 private: 409 uint16_t control_group16_r(uint8_t group, uint8_t offset); 410 void control_group16_w(uint8_t group, uint8_t offset, uint16_t data); 411 412 uint16_t m_control[2][0x20]; 413 }; 414 415 DECLARE_DEVICE_TYPE(SPG2XX_AUDIO, spg2xx_audio_device) 416 DECLARE_DEVICE_TYPE(SPG110_AUDIO, spg110_audio_device) 417 DECLARE_DEVICE_TYPE(SUNPLUS_GCM394_AUDIO, sunplus_gcm394_audio_device) 418 419 #endif // MAME_MACHINE_SPG2XX_AUDIO_H 420