-spg2xx_audio: Hooked up channel FIQ. [Ryan Holtz]

This commit is contained in:
mooglyguy 2020-02-07 20:01:27 +01:00
parent 6a63b36249
commit dd6b5e332b
5 changed files with 70 additions and 13 deletions

View File

@ -458,7 +458,7 @@ inline void unsp_device::execute_fxxx_110_group(uint16_t op)
// MULS 1 1 1 1* r r r 1* 1 0*s s s r r r (1* = sign bit, 1* = sign bit 0* = upper size bit)
// MULS ss with upper size bit not set
unimplemented_opcode(op);
//unimplemented_opcode(op);
//return;
}
@ -472,7 +472,7 @@ inline void unsp_device::execute_fxxx_111_group(uint16_t op)
// MULS 1 1 1 1* r r r 1* 1 1*s s s r r r (1* = sign bit, 1* = sign bit 1* = upper size bit)
// MULS ss with upper size bit set.
unimplemented_opcode(op);
//unimplemented_opcode(op);
//return;
}

View File

@ -126,6 +126,11 @@ WRITE_LINE_MEMBER(spg2xx_device::audioirq_w)
set_state_unsynced(UNSP_IRQ4_LINE, state);
}
WRITE_LINE_MEMBER(spg2xx_device::audiochirq_w)
{
set_state_unsynced(UNSP_FIQ_LINE, state);
}
WRITE_LINE_MEMBER(spg2xx_device::extirq_w)
{
set_state_unsynced(UNSP_IRQ5_LINE, state);
@ -176,6 +181,7 @@ void spg24x_device::device_add_mconfig(machine_config &config)
{
SPG2XX_AUDIO(config, m_spg_audio, DERIVED_CLOCK(1, 1));
m_spg_audio->write_irq_callback().set(FUNC(spg24x_device::audioirq_w));
m_spg_audio->channel_irq_callback().set(FUNC(spg24x_device::audiochirq_w));
m_spg_audio->space_read_callback().set(FUNC(spg24x_device::space_r));
m_spg_audio->add_route(0, *this, 1.0, AUTO_ALLOC_INPUT, 0);
@ -196,6 +202,7 @@ void spg28x_device::device_add_mconfig(machine_config &config)
{
SPG2XX_AUDIO(config, m_spg_audio, DERIVED_CLOCK(1, 1));
m_spg_audio->write_irq_callback().set(FUNC(spg28x_device::audioirq_w));
m_spg_audio->channel_irq_callback().set(FUNC(spg28x_device::audiochirq_w));
m_spg_audio->space_read_callback().set(FUNC(spg28x_device::space_r));
m_spg_audio->add_route(0, *this, 1.0, AUTO_ALLOC_INPUT, 0);

View File

@ -81,6 +81,7 @@ protected:
DECLARE_WRITE8_MEMBER(fiq_vector_w);
DECLARE_WRITE_LINE_MEMBER(videoirq_w);
DECLARE_WRITE_LINE_MEMBER(audioirq_w);
DECLARE_WRITE_LINE_MEMBER(audiochirq_w);
DECLARE_WRITE_LINE_MEMBER(timerirq_w);
DECLARE_WRITE_LINE_MEMBER(uartirq_w);
DECLARE_WRITE_LINE_MEMBER(extirq_w);

View File

@ -10,7 +10,7 @@
or at least not per-channel)
SPG110 Beat interrupt frequency might be different too, seems to
trigger an FIQ, but music is very slow in jak_spdmo
trigger an IRQ, but music is very slow in jak_spdmo
GCM394 has 32 channels, and potentially a different register layout
it looks close but might be different enough to split off
@ -48,6 +48,7 @@ spg2xx_audio_device::spg2xx_audio_device(const machine_config &mconfig, device_t
, device_sound_interface(mconfig, *this)
, m_space_read_cb(*this)
, m_irq_cb(*this)
, m_ch_irq_cb(*this)
{
}
@ -99,10 +100,14 @@ void spg2xx_audio_device::device_start()
{
save_item(NAME(m_adpcm[i].m_signal), i);
save_item(NAME(m_adpcm[i].m_step), i);
m_channel_irq[i] = timer_alloc(TIMER_IRQ + i);
m_channel_irq[i]->adjust(attotime::never);
}
m_space_read_cb.resolve_safe(0);
m_irq_cb.resolve();
m_ch_irq_cb.resolve();
}
void spg2xx_audio_device::device_reset()
@ -128,11 +133,27 @@ void spg2xx_audio_device::device_reset()
m_audio_ctrl_regs[AUDIO_CHANNEL_ENV_MODE] = 0x3f;
m_audio_beat->adjust(attotime::from_ticks(4, 281250), 0, attotime::from_ticks(4, 281250));
for (int i = 0; i < 16; i++)
{
m_channel_irq[i]->adjust(attotime::never);
}
}
void spg2xx_audio_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
{
if (id >= TIMER_IRQ && id < (TIMER_IRQ + 16))
{
const uint32_t bit = id - TIMER_IRQ;
if (!BIT(m_audio_ctrl_regs[AUDIO_CHANNEL_FIQ_STATUS], bit))
{
m_audio_ctrl_regs[AUDIO_CHANNEL_FIQ_STATUS] |= (1 << (id - TIMER_IRQ));
m_ch_irq_cb(1);
}
return;
}
switch (id)
{
case TIMER_BEAT:
@ -437,8 +458,17 @@ WRITE16_MEMBER(spg2xx_audio_device::audio_ctrl_w)
{
if (!(m_audio_ctrl_regs[AUDIO_CHANNEL_STATUS] & mask))
{
LOGMASKED(LOG_SPU_WRITES, "Enabling channel %d\n", channel_bit);
LOGMASKED(LOG_SPU_WRITES, "Enabling channel %d, rate %f\n", channel_bit, m_channel_rate[channel_bit]);
m_audio_ctrl_regs[offset] |= mask;
if (BIT(m_audio_ctrl_regs[AUDIO_CHANNEL_FIQ_ENABLE], channel_bit))
{
m_channel_irq[channel_bit]->adjust(attotime::from_hz(m_channel_rate[channel_bit]), 0, attotime::from_hz(m_channel_rate[channel_bit]));
}
else
{
m_channel_irq[channel_bit]->adjust(attotime::never);
}
if (!(m_audio_ctrl_regs[AUDIO_CHANNEL_STOP] & mask))
{
LOGMASKED(LOG_SPU_WRITES, "Stop not set, starting playback on channel %d, mask %04x\n", channel_bit, mask);
@ -476,7 +506,12 @@ WRITE16_MEMBER(spg2xx_audio_device::audio_ctrl_w)
case AUDIO_CHANNEL_FIQ_STATUS:
LOGMASKED(LOG_SPU_WRITES, "audio_ctrl_w: Channel FIQ Acknowledge: %04x\n", data);
//machine().debug_break();
m_audio_ctrl_regs[offset] &= ~(data & AUDIO_CHANNEL_FIQ_STATUS_MASK);
if (!m_audio_ctrl_regs[offset])
{
m_ch_irq_cb(0);
}
break;
case AUDIO_BEAT_BASE_COUNT:
@ -882,22 +917,30 @@ void spg2xx_audio_device::sound_stream_update(sound_stream &stream, stream_sampl
const uint16_t mask = (1 << channel);
if (m_audio_ctrl_regs[AUDIO_ENV_RAMP_DOWN] & mask)
{
if (m_rampdown_frame[channel] > 0)
{
m_rampdown_frame[channel]--;
}
if (m_rampdown_frame[channel] == 0)
{
LOGMASKED(LOG_RAMPDOWN, "Ticking rampdown for channel %d\n", channel);
audio_rampdown_tick(channel);
}
m_rampdown_frame[channel]--;
}
else if (!(m_audio_ctrl_regs[AUDIO_CHANNEL_ENV_MODE] & mask))
{
if (m_envclk_frame[channel] > 0)
{
m_envclk_frame[channel]--;
}
if (m_envclk_frame[channel] == 0)
{
LOGMASKED(LOG_ENVELOPES, "Ticking envelope for channel %d\n", channel);
audio_envelope_tick(channel);
m_envclk_frame[channel] = get_envclk_frame_count(channel);
}
m_envclk_frame[channel]--;
}
}
}
@ -922,12 +965,12 @@ void spg2xx_audio_device::sound_stream_update(sound_stream &stream, stream_sampl
inline void spg2xx_audio_device::stop_channel(const uint32_t channel)
{
// TODO: IRQs
m_audio_ctrl_regs[AUDIO_CHANNEL_ENABLE] &= ~(1 << channel);
m_audio_ctrl_regs[AUDIO_CHANNEL_STATUS] &= ~(1 << channel);
m_audio_regs[(channel << 4) | AUDIO_MODE] &= ~AUDIO_ADPCM_MASK;
m_audio_ctrl_regs[AUDIO_CHANNEL_TONE_RELEASE] &= ~(1 << channel);
m_audio_ctrl_regs[AUDIO_ENV_RAMP_DOWN] &= ~(1 << channel);
m_channel_irq[channel]->adjust(attotime::never);
}
bool spg2xx_audio_device::advance_channel(const uint32_t channel)
@ -1110,6 +1153,7 @@ void spg2xx_audio_device::audio_beat_tick()
m_audio_curr_beat_base_count = m_audio_ctrl_regs[AUDIO_BEAT_BASE_COUNT];
uint16_t beat_count = m_audio_ctrl_regs[AUDIO_BEAT_COUNT] & AUDIO_BEAT_COUNT_MASK;
if (beat_count > 0)
{
beat_count--;
@ -1198,6 +1242,12 @@ bool spg2xx_audio_device::audio_envelope_tick(const uint32_t channel)
const uint16_t curr_edd = get_edd(channel);
LOGMASKED(LOG_ENVELOPES, "envelope %d tick, count is %04x, curr edd is %04x\n", channel, new_count, curr_edd);
bool edd_changed = false;
if (new_count > 0)
{
new_count--;
set_envelope_count(channel, new_count);
}
if (new_count == 0)
{
const uint16_t target = get_envelope_target(channel);
@ -1276,11 +1326,6 @@ bool spg2xx_audio_device::audio_envelope_tick(const uint32_t channel)
edd_changed = true;
LOGMASKED(LOG_ENVELOPES, "Setting channel %d edd to %04x, register is %04x\n", channel, new_edd, m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA]);
}
else
{
new_count--;
set_envelope_count(channel, new_count);
}
LOGMASKED(LOG_ENVELOPES, "envelope %d post-tick, count is now %04x, register is %04x\n", channel, new_count, m_audio_regs[(channel << 4) | AUDIO_ENVELOPE_DATA]);
return edd_changed;
}

View File

@ -22,6 +22,7 @@ public:
auto space_read_callback() { return m_space_read_cb.bind(); }
auto write_irq_callback() { return m_irq_cb.bind(); }
auto channel_irq_callback() { return m_ch_irq_cb.bind(); }
DECLARE_READ16_MEMBER(audio_r);
virtual DECLARE_WRITE16_MEMBER(audio_w);
@ -322,6 +323,8 @@ protected:
};
static const device_timer_id TIMER_BEAT = 3;
static const device_timer_id TIMER_IRQ = 4;
void check_irqs(const uint16_t changed);
virtual void device_start() override;
@ -354,6 +357,7 @@ protected:
uint16_t m_audio_curr_beat_base_count;
emu_timer *m_audio_beat;
emu_timer *m_channel_irq[16];
sound_stream *m_stream;
oki_adpcm_state m_adpcm[16];
@ -364,7 +368,7 @@ protected:
private:
devcb_read16 m_space_read_cb;
devcb_write_line m_irq_cb;
devcb_write_line m_ch_irq_cb;
};
class spg110_audio_device : public spg2xx_audio_device