sinclair/tsconf.cpp,pentevo.cpp: various fixes (#11221)

* sinclair/tsconf.cpp: Added Covox. fixed DMA blitting, fixed Kempston/beta conflict, and added TurboSound mod.
* sinclair/pentevo.cpp: Added TurboSound mod.
This commit is contained in:
holub 2023-05-18 09:17:28 -04:00 committed by GitHub
parent 0d2d63b724
commit d14961c7b7
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
7 changed files with 117 additions and 26 deletions

View file

@ -15,6 +15,7 @@ NOTES:
#include "bus/ata/atapicdr.h"
#include "bus/ata/idehd.h"
#include "sound/ay8910.h"
#define LOG_MEM (1U << 1)
#define LOG_VIDEO (1U << 2)

View file

@ -9,7 +9,6 @@
#include "beta_m.h"
#include "bus/ata/ataintf.h"
#include "bus/centronics/ctronics.h"
#include "sound/ay8910.h"
class atm_state : public spectrum_128_state
{

View file

@ -37,6 +37,8 @@ TODO:
#include "machine/pckeybrd.h"
#include "machine/spi_sdcard.h"
#include "machine/timer.h"
#include "sound/ay8910.h"
#include "speaker.h"
#define LOG_MEM (1U << 1)
#define LOG_VIDEO (1U << 2)
@ -63,6 +65,8 @@ public:
, m_sdcard(*this, "sdcard")
, m_keyboard(*this, "pc_keyboard")
, m_io_mouse(*this, "mouse_input%u", 1U)
, m_ay(*this, "ay%u", 0U)
, m_mod_ay(*this, "MOD_AY")
{ }
void pentevo(machine_config &config);
@ -86,6 +90,7 @@ private:
u8 pentevo_port_1nbd_r(offs_t offset);
void pentevo_port_1nbd_w(offs_t offset, u8 data);
void ay_address_w(u8 data);
void spi_port_77_w(offs_t offset, u8 data);
u8 spi_port_57_r(offs_t offset);
void spi_port_57_w(offs_t offset, u8 data);
@ -119,6 +124,10 @@ private:
required_device<spi_sdcard_sdhc_device> m_sdcard;
required_device<at_keyboard_device> m_keyboard;
required_ioport_array<3> m_io_mouse;
required_device_array<ym2149_device, 2> m_ay;
u8 m_ay_selected;
required_ioport m_mod_ay;
u8 m_port_bf_data;
u8 m_port_eff7_data;
@ -338,6 +347,14 @@ void pentevo_state::pentevo_port_1nbd_w(offs_t offset, u8 data)
m_beta_drive_virtual = data & 0x0f;
}
void pentevo_state::ay_address_w(u8 data)
{
if ((m_mod_ay->read() == 1) && ((data & 0xfe) == 0xfe))
m_ay_selected = data & 1;
else
m_ay[m_ay_selected]->address_w(data);
}
INTERRUPT_GEN_MEMBER(pentevo_state::pentevo_interrupt)
{
// 17989=80*224+69 z80(3.5Hz) clocks between INT and screen paper begins. Screen clock is 7Hz.
@ -584,8 +601,9 @@ void pentevo_state::pentevo_io(address_map &map)
map(0x00be, 0x00be).select(0xff00).lw8(NAME([this](offs_t offset) { m_nmi_active_flip_countdown = 2; }));
// AY
map(0x8000, 0x8000).mirror(0x3ffd).w("ay8912", FUNC(ay8910_device::data_w));
map(0xc000, 0xc000).mirror(0x3ffd).rw("ay8912", FUNC(ay8910_device::data_r), FUNC(ay8910_device::address_w));
map(0x8000, 0x8000).mirror(0x3ffd).lw8(NAME([this](u8 data) { return m_ay[m_ay_selected]->data_w(data); }));
map(0xc000, 0xc000).mirror(0x3ffd).lr8(NAME([this]() { return m_ay[m_ay_selected]->data_r(); }))
.w(FUNC(pentevo_state::ay_address_w));
// HDD: NEMO
map(0x0010, 0x0010).select(0xffe0).lrw8(NAME([this](offs_t offset) { return nemo_ata_r(offset >> 5); })
@ -681,6 +699,7 @@ void pentevo_state::machine_start()
save_item(NAME(m_nmi_active_flip_countdown));
save_item(NAME(m_zctl_di));
save_item(NAME(m_zctl_cs));
save_item(NAME(m_ay_selected));
init_mem_write();
}
@ -699,6 +718,7 @@ void pentevo_state::machine_reset()
m_gluk_ext = 0xff;
m_zctl_cs = 1;
m_zctl_di = 0xff;
m_ay_selected = 0;
m_keyboard->write(0xff);
while (m_keyboard->read() != 0) { /* invalidate buffer */ }
@ -725,6 +745,10 @@ INPUT_PORTS_START( pentevo )
PORT_BIT(0x02, IP_ACTIVE_LOW, IPT_BUTTON5) PORT_NAME("Right mouse button") PORT_CODE(MOUSECODE_BUTTON2)
PORT_BIT(0x04, IP_ACTIVE_LOW, IPT_BUTTON6) PORT_NAME("Middle mouse button") PORT_CODE(MOUSECODE_BUTTON3)
PORT_START("MOD_AY")
PORT_CONFNAME(0x01, 0x00, "AY MOD")
PORT_CONFSETTING(0x00, "Single")
PORT_CONFSETTING(0x01, "TurboSound")
INPUT_PORTS_END
void pentevo_state::pentevo(machine_config &config)
@ -743,6 +767,21 @@ void pentevo_state::pentevo(machine_config &config)
SPI_SDCARD(config, m_sdcard, 0);
m_sdcard->spi_miso_callback().set(FUNC(pentevo_state::spi_miso_w));
SPEAKER(config, "lspeaker").front_left();
SPEAKER(config, "rspeaker").front_right();
config.device_remove("ay8912");
YM2149(config, m_ay[0], 14_MHz_XTAL / 8)
.add_route(0, "lspeaker", 0.50)
.add_route(1, "lspeaker", 0.25)
.add_route(1, "rspeaker", 0.25)
.add_route(2, "rspeaker", 0.50);
YM2149(config, m_ay[1], 14_MHz_XTAL / 8)
.add_route(0, "lspeaker", 0.50)
.add_route(1, "lspeaker", 0.25)
.add_route(1, "rspeaker", 0.25)
.add_route(2, "rspeaker", 0.50);
AT_KEYB(config, m_keyboard, pc_keyboard_device::KEYBOARD_TYPE::AT, 3);
zxbus_device &zxbus(ZXBUS(config, "zxbus", 0));

View file

@ -93,7 +93,7 @@ void tsconf_state::tsconf_io(address_map &map)
{
map.unmap_value_high();
map(0x0000, 0x0000).mirror(0x7ffd).w(FUNC(tsconf_state::tsconf_port_7ffd_w));
map(0x001f, 0x001f).mirror(0xff00).rw(m_beta, FUNC(beta_disk_device::status_r), FUNC(beta_disk_device::command_w));
map(0x001f, 0x001f).mirror(0xff00).r(FUNC(tsconf_state::tsconf_port_xx1f_r)).w(m_beta, FUNC(beta_disk_device::command_w));
map(0x003f, 0x003f).mirror(0xff00).rw(m_beta, FUNC(beta_disk_device::track_r), FUNC(beta_disk_device::track_w));
map(0x0057, 0x0057).mirror(0xff00).rw(FUNC(tsconf_state::tsconf_port_57_zctr_r), FUNC(tsconf_state::tsconf_port_57_zctr_w)); // spi config
map(0x0077, 0x0077).mirror(0xff00).rw(FUNC(tsconf_state::tsconf_port_77_zctr_r), FUNC(tsconf_state::tsconf_port_77_zctr_w)); // spi data
@ -102,13 +102,15 @@ void tsconf_state::tsconf_io(address_map &map)
map(0x00fe, 0x00fe).select(0xff00).rw(FUNC(tsconf_state::spectrum_ula_r), FUNC(tsconf_state::tsconf_ula_w));
map(0x00ff, 0x00ff).mirror(0xff00).rw(m_beta, FUNC(beta_disk_device::state_r), FUNC(beta_disk_device::param_w));
map(0x00af, 0x00af).select(0xff00).rw(FUNC(tsconf_state::tsconf_port_xxaf_r), FUNC(tsconf_state::tsconf_port_xxaf_w));
map(0x8ff7, 0x8ff7).select(0x7000).w(FUNC(tsconf_state::tsconf_port_f7_w)); // 3:bff7 5:dff7 6:eff7
map(0xbff7, 0xbff7).r(FUNC(tsconf_state::tsconf_port_f7_r));
map(0xfadf, 0xfadf).lr8(NAME([this]() { return 0x80 | (m_io_mouse[2]->read() & 0x07); }));
map(0xfbdf, 0xfbdf).lr8(NAME([this]() { return m_io_mouse[0]->read(); }));
map(0xffdf, 0xffdf).lr8(NAME([this]() { return ~m_io_mouse[1]->read(); }));
map(0x8000, 0x8000).mirror(0x3ffd).w("ay8912", FUNC(ay8910_device::data_w));
map(0xc000, 0xc000).mirror(0x3ffd).rw("ay8912", FUNC(ay8910_device::data_r), FUNC(ay8910_device::address_w));
map(0x8ff7, 0x8ff7).select(0x7000).w(FUNC(tsconf_state::tsconf_port_f7_w)); // 3:bff7 5:dff7 6:eff7
map(0xbff7, 0xbff7).r(FUNC(tsconf_state::tsconf_port_f7_r));
map(0x00fb, 0x00fb).mirror(0xff00).w("cent_data_out", FUNC(output_latch_device::write));
map(0x8000, 0x8000).mirror(0x3ffd).lw8(NAME([this](u8 data) { return m_ay[m_ay_selected]->data_w(data); }));
map(0xc000, 0xc000).mirror(0x3ffd).lr8(NAME([this]() { return m_ay[m_ay_selected]->data_r(); }))
.w(FUNC(tsconf_state::tsconf_ay_address_w));
}
void tsconf_state::tsconf_switch(address_map &map)
@ -236,6 +238,7 @@ void tsconf_state::machine_reset()
m_zctl_cs = 1;
m_zctl_di = 0xff;
m_ay_selected = 0;
tsconf_update_bank0();
tsconf_update_video_mode();
@ -258,6 +261,10 @@ INPUT_PORTS_START( tsconf )
PORT_BIT(0x02, IP_ACTIVE_LOW, IPT_BUTTON5) PORT_NAME("Right mouse button") PORT_CODE(MOUSECODE_BUTTON2)
PORT_BIT(0x04, IP_ACTIVE_LOW, IPT_BUTTON6) PORT_NAME("Middle mouse button") PORT_CODE(MOUSECODE_BUTTON3)
PORT_START("MOD_AY")
PORT_CONFNAME(0x01, 0x00, "AY MOD")
PORT_CONFSETTING(0x00, "Single")
PORT_CONFSETTING(0x01, "TurboSound")
INPUT_PORTS_END
void tsconf_state::tsconf(machine_config &config)
@ -299,11 +306,21 @@ void tsconf_state::tsconf(machine_config &config)
SPEAKER(config, "lspeaker").front_left();
SPEAKER(config, "rspeaker").front_right();
YM2149(config.replace(), "ay8912", 14_MHz_XTAL / 8)
config.device_remove("ay8912");
YM2149(config, m_ay[0], 14_MHz_XTAL / 8)
.add_route(0, "lspeaker", 0.50)
.add_route(1, "lspeaker", 0.25)
.add_route(1, "rspeaker", 0.25)
.add_route(2, "rspeaker", 0.50);
YM2149(config, m_ay[1], 14_MHz_XTAL / 8)
.add_route(0, "lspeaker", 0.50)
.add_route(1, "lspeaker", 0.25)
.add_route(1, "rspeaker", 0.25)
.add_route(2, "rspeaker", 0.50);
CENTRONICS(config, m_centronics, centronics_devices, "covox");
output_latch_device &cent_data_out(OUTPUT_LATCH(config, "cent_data_out"));
m_centronics->set_output_latch(cent_data_out);
PALETTE(config, "palette", FUNC(tsconf_state::tsconf_palette), 256);
m_screen->set_raw(14_MHz_XTAL / 2, 448, with_hblank(0), 448, 320, with_vblank(0), 320);

View file

@ -16,9 +16,10 @@
#include "tsconfdma.h"
#include "beta_m.h"
#include "bus/centronics/ctronics.h"
#include "machine/pckeybrd.h"
#include "machine/spi_sdcard.h"
#include "sound/ay8910.h"
#include "tilemap.h"
@ -26,18 +27,21 @@ class tsconf_state : public spectrum_128_state
{
public:
tsconf_state(const machine_config &mconfig, device_type type, const char *tag)
: spectrum_128_state(mconfig, type, tag),
m_bank0_rom(*this, "bank0_rom"),
m_keyboard(*this, "pc_keyboard"),
m_io_mouse(*this, "mouse_input%u", 1U),
m_beta(*this, BETA_DISK_TAG),
m_dma(*this, "dma"),
m_sdcard(*this, "sdcard"),
m_glukrs(*this, "glukrs"),
m_palette(*this, "palette"),
m_gfxdecode(*this, "gfxdecode"),
m_cram(*this, "cram"),
m_sfile(*this, "sfile")
: spectrum_128_state(mconfig, type, tag)
, m_bank0_rom(*this, "bank0_rom")
, m_keyboard(*this, "pc_keyboard")
, m_io_mouse(*this, "mouse_input%u", 1U)
, m_beta(*this, BETA_DISK_TAG)
, m_dma(*this, "dma")
, m_sdcard(*this, "sdcard")
, m_glukrs(*this, "glukrs")
, m_palette(*this, "palette")
, m_gfxdecode(*this, "gfxdecode")
, m_cram(*this, "cram")
, m_sfile(*this, "sfile")
, m_centronics(*this, "centronics")
, m_ay(*this, "ay%u", 0U)
, m_mod_ay(*this, "MOD_AY")
{
}
@ -155,6 +159,7 @@ private:
void tsconf_palette(palette_device &palette) const;
void tsconf_update_video_mode();
u8 tsconf_port_xx1f_r(offs_t offset);
void tsconf_port_7ffd_w(u8 data);
void tsconf_ula_w(offs_t offset, u8 data);
u8 tsconf_port_xxaf_r(offs_t reg);
@ -166,6 +171,7 @@ private:
void tsconf_spi_miso_w(u8 data);
u8 tsconf_port_f7_r(offs_t offset);
void tsconf_port_f7_w(offs_t offset, u8 data);
void tsconf_ay_address_w(u8 data);
void tsconf_update_bank0();
u8 beta_neutral_r(offs_t offset);
@ -213,6 +219,11 @@ private:
tilemap_t *m_ts_tilemap[3]{};
required_device<ram_device> m_cram;
required_device<ram_device> m_sfile;
required_device<centronics_device> m_centronics;
required_device_array<ym2149_device, 2> m_ay;
u8 m_ay_selected;
required_ioport m_mod_ay;
};
/*----------- defined in drivers/tsconf.c -----------*/

View file

@ -368,12 +368,12 @@ void tsconf_state::ram_page_write(u8 page, offs_t offset, u8 data)
u16 tsconf_state::ram_read16(offs_t offset)
{
return ((m_ram->read(offset & 0xfffffffe)) << 8) | m_ram->read(offset | 1);
return ((m_ram->read(offset & ~offs_t(1))) << 8) | m_ram->read(offset | 1);
}
void tsconf_state::ram_write16(offs_t offset, u16 data)
{
ram_page_write(0, offset & 0xfffffffe, data >> 8);
ram_page_write(0, offset & ~offs_t(1), data >> 8);
ram_page_write(0, offset | 1, data & 0xff);
}
@ -404,6 +404,12 @@ void tsconf_state::sfile_write16(offs_t offset, u16 data)
m_sfile->write(dest | 1, data & 0xff);
};
u8 tsconf_state::tsconf_port_xx1f_r(offs_t offset) {
return m_beta->started() && m_beta->is_active()
? m_beta->status_r()
: 0x00; // TODO kempston read
}
void tsconf_state::tsconf_port_7ffd_w(u8 data)
{
// LOCK? BIT(data, 5);
@ -745,6 +751,14 @@ void tsconf_state::tsconf_spi_miso_w(u8 data)
m_zctl_di |= data;
}
void tsconf_state::tsconf_ay_address_w(u8 data)
{
if ((m_mod_ay->read() == 1) && ((data & 0xfe) == 0xfe))
m_ay_selected = data & 1;
else
m_ay[m_ay_selected]->address_w(data);
}
IRQ_CALLBACK_MEMBER(tsconf_state::irq_vector)
{
u8 vector = 0xff;

View file

@ -156,10 +156,20 @@ void tsconfdma_device::start_tx(u8 dev, bool s_align, bool d_align, bool align_o
for (u16 len = 0; len <= m_block_len; len++)
{
u16 d_val = m_in_mreq_cb(d_addr);
if (d_val != 0)
u16 s_val = m_in_mreq_cb(s_addr);
if (align_opt)
{
m_out_mreq_cb(d_addr, m_in_mreq_cb(s_addr));
d_val = (d_val & 0xff00) | (((s_val & 0x00ff) ? s_val : d_val) & 0x00ff);
d_val = (d_val & 0x00ff) | (((s_val & 0xff00) ? s_val : d_val) & 0xff00);
}
else
{
d_val = (d_val & 0xfff0) | (((s_val & 0x000f) ? s_val : d_val) & 0x000f);
d_val = (d_val & 0xff0f) | (((s_val & 0x00f0) ? s_val : d_val) & 0x00f0);
d_val = (d_val & 0xf0ff) | (((s_val & 0x0f00) ? s_val : d_val) & 0x0f00);
d_val = (d_val & 0x0fff) | (((s_val & 0xf000) ? s_val : d_val) & 0xf000);
}
m_out_mreq_cb(d_addr, d_val);
s_addr += 2;
d_addr += 2;
}