leave specnext_dma as is
Some checks failed
Rebuild BGFX shaders / rebuild (push) Has been cancelled
CI (Linux) / build-linux (-U_FORTIFY_SOURCE, gcc, gcc, g++, mametiny, tiny) (push) Has been cancelled
CI (Linux) / build-linux (clang, clang, clang++, mame, mame) (push) Has been cancelled
CI (macOS) / build-macos (push) Has been cancelled
CI (Windows) / build-windows (clang, clang, clang++, mametiny, tiny) (push) Has been cancelled
CI (Windows) / build-windows (gcc, gcc, g++, mame, mame) (push) Has been cancelled
Build documentation / build-docs (push) Has been cancelled
XML/JSON validation / validate (push) Has been cancelled
Compile UI translations / build-language (push) Has been cancelled

This commit is contained in:
Andrei Holub 2024-12-31 21:26:07 -05:00
parent dabf077a10
commit 05d0e74e71
5 changed files with 139 additions and 76 deletions

View File

@ -896,59 +896,3 @@ ua858d_device::ua858d_device(const machine_config &mconfig, const char *tag, dev
: z80dma_device(mconfig, UA858D, tag, owner, clock, dma_mode::UA858D)
{
}
DEFINE_DEVICE_TYPE(SPECNEXT_DMA, specnext_dma_device, "specnext_dma", "Spectrum Next DMA")
specnext_dma_device::specnext_dma_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock)
: z80dma_device(mconfig, SPECNEXT_DMA, tag, owner, clock, dma_mode::SPEC_NEXT)
{
}
void specnext_dma_device::do_write()
{
if (m_dma_mode != dma_mode::SPEC_NEXT)
{
z80dma_device::do_write();
}
else
{
if (m_byte_counter)
m_addressB += PORTB_FIXED ? 0 : PORTB_INC ? 1 : -1;
switch (TRANSFER_MODE)
{
case TM_TRANSFER:
do_transfer_write();
break;
case TM_SEARCH:
do_search();
break;
case TM_SEARCH_TRANSFER:
do_transfer_write();
do_search();
break;
default:
logerror("z80dma_do_operation: invalid mode %d!\n", TRANSFER_MODE);
break;
}
m_addressA += PORTA_FIXED ? 0 : PORTA_INC ? 1 : -1;
m_byte_counter++;
if ((m_byte_counter + 1) == m_count)
m_byte_counter++;
}
}
void specnext_dma_device::write(u8 data)
{
if (m_dma_mode == dma_mode::SPEC_NEXT && data == COMMAND_ENABLE_DMA && num_follow() == 0)
{
m_byte_counter = 0;
}
z80dma_device::write(data);
}

View File

@ -51,8 +51,7 @@ public:
enum class dma_mode : u8
{
ZILOG = 0,
UA858D = 1,
SPEC_NEXT = 2
UA858D = 1
};
// construction/destruction
@ -179,20 +178,8 @@ public:
ua858d_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
};
class specnext_dma_device : public z80dma_device
{
public:
specnext_dma_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
virtual void write(u8 data) override;
protected:
virtual void do_write() override;
};
// device type definition
DECLARE_DEVICE_TYPE(Z80DMA, z80dma_device)
DECLARE_DEVICE_TYPE(UA858D, ua858d_device)
DECLARE_DEVICE_TYPE(SPECNEXT_DMA, specnext_dma_device)
#endif // MAME_MACHINE_Z80DMA_H

View File

@ -25,6 +25,7 @@
#include "specnext_copper.h"
#include "specnext_ctc.h"
#include "specnext_divmmc.h"
#include "specnext_dma.h"
#include "specnext_multiface.h"
#include "specnext_layer2.h"
#include "specnext_lores.h"
@ -35,7 +36,6 @@
#include "cpu/z80/z80n.h"
#include "machine/i2cmem.h"
#include "machine/spi_sdcard.h"
#include "machine/z80dma.h"
#include "sound/ay8910.h"
#include "sound/dac.h"
#include "speaker.h"
@ -1146,13 +1146,13 @@ void specnext_state::mmu_x2_w(offs_t bank, u8 data)
u8 specnext_state::dma_r(bool dma_mode)
{
m_dma->set_dma_mode(dma_mode ? z80dma_device::dma_mode::ZILOG : z80dma_device::dma_mode::SPEC_NEXT);
m_dma->dma_mode_w(dma_mode);
return m_dma->read();
}
void specnext_state::dma_w(bool dma_mode, u8 data)
{
m_dma->set_dma_mode(dma_mode ? z80dma_device::dma_mode::ZILOG : z80dma_device::dma_mode::SPEC_NEXT);
m_dma->dma_mode_w(dma_mode);
m_dma->write(data);
}
@ -3035,7 +3035,7 @@ void specnext_state::reset_hard()
m_nr_02_hard_reset = 0;
m_bootrom_en = 1;
m_dma->set_dma_mode(z80dma_device::dma_mode::SPEC_NEXT);
m_dma->dma_mode_w(0);
// nmi_mf = 0;
// nmi_divmmc = 0;
// nmi_expbus = 0;
@ -3162,7 +3162,7 @@ void specnext_state::machine_reset()
m_port_ff_data = 0;
m_divmmc_delayed_check = 0;
m_dma->set_dma_mode(z80dma_device::dma_mode::SPEC_NEXT);
m_dma->dma_mode_w(0);
//z80_retn_seen_28_d = 0;
//im2_dma_delay = 0;
m_pulse_int_n = 1;
@ -3449,7 +3449,7 @@ void specnext_state::tbblue(machine_config &config)
m_maincpu->in_nextreg_cb().set(FUNC(specnext_state::reg_r));
m_maincpu->out_retn_seen_cb().set(FUNC(specnext_state::leave_nmi));
m_maincpu->nomreq_cb().set_nop();
m_maincpu->busack_cb().set(m_dma, FUNC(z80dma_device::bai_w));
m_maincpu->busack_cb().set(m_dma, FUNC(specnext_dma_device::bai_w));
SPECNEXT_CTC(config, m_ctc, 28_MHz_XTAL / 8);
m_ctc->intr_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0);

View File

@ -0,0 +1,101 @@
// license:BSD-3-Clause
// copyright-holders:Andrei I. Holub
/**********************************************************************
Spectrum Next DMA
Spectrum Next DMA operates in two mode: z80dma compatible and
N-mode with Next specific fixes.
z80dma mode is implemented there based on intensive testing of
the device. Potentially any mismatches not related to N-mode
covered here must be moved to the z80dma parent.
**********************************************************************/
#include "emu.h"
#include "specnext_dma.h"
// device type definition
DEFINE_DEVICE_TYPE(SPECNEXT_DMA, specnext_dma_device, "specnext_dma", "Spectrum Next DMA")
// TODO: this stuff is copy/pasted from machine/z80dma.cpp - ideally it wouldn't need to be
#define WR0 REG(0, 0)
#define WR1 REG(1, 0)
#define WR2 REG(2, 0)
#define PORTA_INC (WR1 & 0x10)
#define PORTB_INC (WR2 & 0x10)
#define PORTA_FIXED (((WR1 >> 4) & 0x02) == 0x02)
#define PORTB_FIXED (((WR2 >> 4) & 0x02) == 0x02)
#define TRANSFER_MODE (WR0 & 0x03)
specnext_dma_device::specnext_dma_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock)
: z80dma_device(mconfig, SPECNEXT_DMA, tag, owner, clock, dma_mode::ZILOG)
{
}
void specnext_dma_device::write(u8 data)
{
if (!m_ndma_mode && data == COMMAND_ENABLE_DMA && num_follow() == 0)
{
m_byte_counter = 0;
}
z80dma_device::write(data);
}
void specnext_dma_device::do_write()
{
if (m_ndma_mode)
{
z80dma_device::do_write();
return;
}
// else (zxnDMA)
if (m_byte_counter)
m_addressB += PORTB_FIXED ? 0 : PORTB_INC ? 1 : -1;
switch (TRANSFER_MODE)
{
case TM_TRANSFER:
do_transfer_write();
break;
case TM_SEARCH:
do_search();
break;
case TM_SEARCH_TRANSFER:
do_transfer_write();
do_search();
break;
default:
logerror("z80dma_do_operation: invalid mode %d!\n", TRANSFER_MODE);
break;
}
m_addressA += PORTA_FIXED ? 0 : PORTA_INC ? 1 : -1;
m_byte_counter++;
if ((m_byte_counter + 1) == m_count)
m_byte_counter++;
}
void specnext_dma_device::device_start()
{
z80dma_device::device_start();
save_item(NAME(m_ndma_mode));
}
void specnext_dma_device::device_reset()
{
z80dma_device::device_reset();
m_ndma_mode = 0;
}

View File

@ -0,0 +1,31 @@
// license:BSD-3-Clause
// copyright-holders:Andrei I. Holub
#ifndef MAME_SINCLAIR_SPECNEXT_DMA_H
#define MAME_SINCLAIR_SPECNEXT_DMA_H
#pragma once
#include "machine/z80dma.h"
class specnext_dma_device : public z80dma_device
{
public:
specnext_dma_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
void dma_mode_w(bool dma_mode) { m_ndma_mode = dma_mode; }
virtual void write(u8 data) override;
protected:
virtual void device_start() override ATTR_COLD;
virtual void device_reset() override ATTR_COLD;
virtual void do_write() override;
private:
bool m_ndma_mode; // 0 = zxn dma, 1 = z80 dma
};
DECLARE_DEVICE_TYPE(SPECNEXT_DMA, specnext_dma_device)
#endif // MAME_SINCLAIR_SPECNEXT_DMA_H