summaryrefslogtreecommitdiffstatshomepage
path: root/src
diff options
context:
space:
mode:
author Angelo Salese <angelosa@users.noreply.github.com>2021-10-20 03:28:43 +0200
committer GitHub <noreply@github.com>2021-10-19 21:28:43 -0400
commitb3e20002b716b75887214acc38c00b989942a633 (patch)
tree59d8464937c4cdcd88614fa5d4f35c4f03dd035f /src
parent4e74debb69abecb4f8f2b654040f56f768de9653 (diff)
First pass in improving Amiga SW compatibility (#8722)
* amiga.cpp: connect missing DSKINDEX signal from FDC to CIA-B ICR bit 4 * amigafdc.cpp: workaround live_counter > 8 to reset, makes abreed to boot to gameplay * 8364_paula.cpp: fix output channel of irq delegation, and throw one when a DMA reaches the end of a stream. Fixes asparmgp/gpmaster BGMs at very least * mos6526.cpp: guard against resetting IRQs when none is chained * makes timer B polling reads to actually work in barb2paln4, fixing booting * amigafdc.cpp: start adding logmacros * amigafdc.cpp: fix DMAON readback, giving logica2 diag BIOS the chance to print extensive floppy test info * 8364_paula.cpp: avoid reading audio DMA buffers outside the allocated ranges, fixes sound buzzing/aliasing bug * alg.cpp: standardize title metadatas * amigaocs_flop.xml: QA, consistent XML titles, consistent ids of virus plagued disks (additional field plus mark these as baddump) * amigaocs_flop.xml: mark the failures on mount and bulk test with ATK * 8364_paula.cpp: fix DMA reload behaviour (fixes BGMs in Ocean games), add live logging, misc * amiga.cpp: ignore bit 0 with BPLxMOD writes, fixes hpoker/hpokera GFXs * amigaocs_flop.xml: misc QA notes
Diffstat (limited to 'src')
-rw-r--r--src/devices/machine/8364_paula.cpp125
-rw-r--r--src/devices/machine/8364_paula.h7
-rw-r--r--src/devices/machine/amigafdc.cpp64
-rw-r--r--src/devices/machine/mos6526.cpp5
-rw-r--r--src/mame/drivers/alg.cpp64
-rw-r--r--src/mame/drivers/amiga.cpp16
-rw-r--r--src/mame/includes/amiga.h2
-rw-r--r--src/mame/machine/amiga.cpp16
8 files changed, 223 insertions, 76 deletions
diff --git a/src/devices/machine/8364_paula.cpp b/src/devices/machine/8364_paula.cpp
index 6869ffb3395..83c4f033661 100644
--- a/src/devices/machine/8364_paula.cpp
+++ b/src/devices/machine/8364_paula.cpp
@@ -2,22 +2,36 @@
// copyright-holders: Aaron Giles, Dirk Best
/***************************************************************************
- Commodore 8364 "Paula"
+ MOS Technology 8364 "Paula"
+
+ TODO:
+ - Inherit FDC, serial and irq controller to here;
+ - Move Agnus "location" logic from here;
+ - low-pass filter;
+ - convert volume values to non-linear dB scale (cfr. )
+ - Verify ADKCON modulation;
+ - Verify manual mode;
+ - When a DMA stop occurs, is the correlated channel playback stopped
+ at the end of the current cycle or as soon as possible like current
+ implementation?
***************************************************************************/
#include "emu.h"
#include "8364_paula.h"
+#define LIVE_AUDIO_VIEW 0
+
//#define VERBOSE 1
#include "logmacro.h"
+#include <cstring>
//**************************************************************************
// DEVICE DEFINITIONS
//**************************************************************************
-DEFINE_DEVICE_TYPE(PAULA_8364, paula_8364_device, "paula_8364", "8364 Paula")
+DEFINE_DEVICE_TYPE(PAULA_8364, paula_8364_device, "paula_8364", "MOS 8364 \"Paula\"")
//*************************************************************************
@@ -51,9 +65,6 @@ void paula_8364_device::device_start()
for (int i = 0; i < 4; i++)
{
m_channel[i].index = i;
- m_channel[i].curticks = 0;
- m_channel[i].manualmode = false;
- m_channel[i].curlocation = 0;
m_channel[i].irq_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(paula_8364_device::signal_irq), this));
}
@@ -61,6 +72,24 @@ void paula_8364_device::device_start()
m_stream = stream_alloc(0, 4, clock() / CLOCK_DIVIDER);
}
+void paula_8364_device::device_reset()
+{
+ m_dmacon = 0;
+ m_adkcon = 0;
+ for (auto &chan : m_channel)
+ {
+ chan.loc = 0;
+ chan.len = 0;
+ chan.per = 0;
+ chan.vol = 0;
+ chan.curticks = 0;
+ chan.manualmode = false;
+ chan.curlocation = 0;
+ chan.curlength = 0;
+ chan.dma_enabled = false;
+ }
+}
+
//-------------------------------------------------
// update - stream updater
//-------------------------------------------------
@@ -99,6 +128,18 @@ void paula_8364_device::reg_w(offs_t offset, uint16_t data)
case REG_DMACON:
m_stream->update();
m_dmacon = (data & 0x8000) ? (m_dmacon | (data & 0x021f)) : (m_dmacon & ~(data & 0x021f)); // only bits 15, 9 and 5 to 0
+ // update the DMA latches on each channel and reload if fresh
+ // This holds true particularly for Ocean games (bchvolly, lostpatr, pang) and waylildr:
+ // they sets a DMA length for a channel then enable DMA then resets that length to 1
+ // after a short delay loop.
+ for (int channum = 0; channum < 4; channum++)
+ {
+ audio_channel *chan = &m_channel[channum];
+ if (!chan->dma_enabled && ((m_dmacon >> channum) & 1))
+ dma_reload(chan, true);
+
+ chan->dma_enabled = BIT(m_dmacon, channum);
+ }
break;
case REG_ADKCON:
@@ -106,7 +147,7 @@ void paula_8364_device::reg_w(offs_t offset, uint16_t data)
m_adkcon = (data & 0x8000) ? (m_adkcon | (data & 0x7fff)) : (m_adkcon & ~(data & 0x7fff));
break;
- // to be moved
+ // FIXME: location belongs to Agnus
case REG_AUD0LCL: m_channel[CHAN_0].loc = (m_channel[CHAN_0].loc & 0xffff0000) | ((data & 0xfffe) << 0); break; // 15-bit
case REG_AUD0LCH: m_channel[CHAN_0].loc = (m_channel[CHAN_0].loc & 0x0000ffff) | ((data & 0x001f) << 16); break; // 3-bit on ocs, 5-bit ecs
case REG_AUD1LCL: m_channel[CHAN_1].loc = (m_channel[CHAN_1].loc & 0xffff0000) | ((data & 0xfffe) << 0); break; // 15-bit
@@ -119,19 +160,19 @@ void paula_8364_device::reg_w(offs_t offset, uint16_t data)
// audio data
case REG_AUD0LEN: m_channel[CHAN_0].len = data; break;
case REG_AUD0PER: m_channel[CHAN_0].per = data; break;
- case REG_AUD0VOL: m_channel[CHAN_0].vol = data; break;
+ case REG_AUD0VOL: m_channel[CHAN_0].vol = data & 0x7f; break;
case REG_AUD0DAT: m_channel[CHAN_0].dat = data; m_channel[CHAN_0].manualmode = true; break;
case REG_AUD1LEN: m_channel[CHAN_1].len = data; break;
case REG_AUD1PER: m_channel[CHAN_1].per = data; break;
- case REG_AUD1VOL: m_channel[CHAN_1].vol = data; break;
+ case REG_AUD1VOL: m_channel[CHAN_1].vol = data & 0x7f; break;
case REG_AUD1DAT: m_channel[CHAN_1].dat = data; m_channel[CHAN_1].manualmode = true; break;
case REG_AUD2LEN: m_channel[CHAN_2].len = data; break;
case REG_AUD2PER: m_channel[CHAN_2].per = data; break;
- case REG_AUD2VOL: m_channel[CHAN_2].vol = data; break;
+ case REG_AUD2VOL: m_channel[CHAN_2].vol = data & 0x7f; break;
case REG_AUD2DAT: m_channel[CHAN_2].dat = data; m_channel[CHAN_2].manualmode = true; break;
case REG_AUD3LEN: m_channel[CHAN_3].len = data; break;
case REG_AUD3PER: m_channel[CHAN_3].per = data; break;
- case REG_AUD3VOL: m_channel[CHAN_3].vol = data; break;
+ case REG_AUD3VOL: m_channel[CHAN_3].vol = data & 0x7f; break;
case REG_AUD3DAT: m_channel[CHAN_3].dat = data; m_channel[CHAN_3].manualmode = true; break;
}
}
@@ -142,20 +183,51 @@ void paula_8364_device::reg_w(offs_t offset, uint16_t data)
TIMER_CALLBACK_MEMBER( paula_8364_device::signal_irq )
{
- m_int_w(param);
+ m_int_w(param, 1);
}
//-------------------------------------------------
// dma_reload
//-------------------------------------------------
-void paula_8364_device::dma_reload(audio_channel *chan)
+void paula_8364_device::dma_reload(audio_channel *chan, bool startup)
{
chan->curlocation = chan->loc;
+ // TODO: how to treat length == 0?
chan->curlength = chan->len;
- chan->irq_timer->adjust(attotime::from_hz(15750), chan->index); // clock() / 227
+ // TODO: on startup=false irq should be delayed two cycles
+ if (startup)
+ chan->irq_timer->adjust(attotime::from_hz(15750), chan->index); // clock() / 227
+ else
+ signal_irq(nullptr, chan->index);
- LOG("dma_reload(%d): offs=%05X len=%04X\n", chan->index, chan->curlocation, chan->curlength);
+ LOG("dma_reload(%d): offs=%06X len=%04X\n", chan->index, chan->curlocation, chan->curlength);
+}
+
+std::string paula_8364_device::print_audio_state()
+{
+ std::ostringstream outbuffer;
+
+ util::stream_format(outbuffer, "DMACON: %04x (%d) ADKCON %04x\n", m_dmacon, BIT(m_dmacon, 9), m_adkcon);
+ for (auto &chan : m_channel)
+ {
+ util::stream_format(outbuffer, "%d (%d) (%d%d) REGS: %06x %04x %03x %02x %d LIVE: %06x %04x %d\n"
+ , chan.index
+ , BIT(m_dmacon, chan.index)
+ , BIT(m_adkcon, chan.index+4)
+ , BIT(m_adkcon, chan.index)
+ , chan.loc
+ , chan.len
+ , chan.per
+ , chan.vol
+ , chan.manualmode
+ , chan.curlocation
+ , chan.curlength
+ , chan.dma_enabled
+ );
+ }
+
+ return outbuffer.str();
}
//-------------------------------------------------
@@ -182,15 +254,8 @@ void paula_8364_device::sound_stream_update(sound_stream &stream, std::vector<re
int samples = outputs[0].samples() * CLOCK_DIVIDER;
- // update the DMA states on each channel and reload if fresh
- for (channum = 0; channum < 4; channum++)
- {
- audio_channel *chan = &m_channel[channum];
- if (!chan->dma_enabled && ((m_dmacon >> channum) & 1))
- dma_reload(chan);
-
- chan->dma_enabled = BIT(m_dmacon, channum);
- }
+ if (LIVE_AUDIO_VIEW)
+ popmessage(print_audio_state());
// loop until done
while (samples > 0)
@@ -219,6 +284,7 @@ void paula_8364_device::sound_stream_update(sound_stream &stream, std::vector<re
int i;
// normalize the volume value
+ // FIXME: definitely not linear
volume = (volume & 0x40) ? 64 : (volume & 0x3f);
volume *= 4;
@@ -268,9 +334,18 @@ void paula_8364_device::sound_stream_update(sound_stream &stream, std::vector<re
if (chan->curlength != 0)
chan->curlength--;
- // if we run out of data, reload the dma
+ // if we run out of data, reload the dma and signal an IRQ,
+ // gpmaster/asparmgp definitely expects this
+ // (uses channel 3 as a sequencer, changing the start address on the fly)
if (chan->curlength == 0)
- dma_reload(chan);
+ {
+ dma_reload(chan, false);
+ // reload the data pointer, otherwise aliasing / buzzing outside the given buffer will be heard
+ // For example: Xenon 2 sets up location=0x63298 length=0x20
+ // for silencing channels on-the-fly without relying on irqs.
+ // Without this the location will read at 0x632d8 (data=0x7a7d), causing annoying buzzing.
+ chan->dat = m_mem_r(chan->curlocation);
+ }
}
// latch the next byte of the sample
diff --git a/src/devices/machine/8364_paula.h b/src/devices/machine/8364_paula.h
index 9fa7a6ebf38..0596cd6d4a1 100644
--- a/src/devices/machine/8364_paula.h
+++ b/src/devices/machine/8364_paula.h
@@ -66,6 +66,7 @@ public:
protected:
// device-level overrides
virtual void device_start() override;
+ virtual void device_reset() override;
// sound stream update overrides
virtual void sound_stream_update(sound_stream &stream, std::vector<read_stream_view> const &inputs, std::vector<write_stream_view> &outputs) override;
@@ -133,11 +134,11 @@ private:
uint16_t dat;
};
- void dma_reload(audio_channel *chan);
+ void dma_reload(audio_channel *chan, bool startup);
// callbacks
devcb_read16 m_mem_r;
- devcb_write_line m_int_w;
+ devcb_write8 m_int_w;
// internal state
uint16_t m_dmacon;
@@ -147,6 +148,8 @@ private:
sound_stream *m_stream;
TIMER_CALLBACK_MEMBER( signal_irq );
+
+ std::string print_audio_state();
};
// device type definition
diff --git a/src/devices/machine/amigafdc.cpp b/src/devices/machine/amigafdc.cpp
index 4452af43493..ad83a268039 100644
--- a/src/devices/machine/amigafdc.cpp
+++ b/src/devices/machine/amigafdc.cpp
@@ -12,6 +12,18 @@
#include "formats/ipf_dsk.h"
#include "amigafdc.h"
+#define LOG_WARN (1U << 1) // Show warnings
+#define LOG_DMA (1U << 2) // Show DMA setups
+#define LOG_SYNC (1U << 3) // Show sync block setups
+
+#define VERBOSE (LOG_WARN | LOG_DMA | LOG_SYNC)
+
+#include "logmacro.h"
+
+#define LOGWARN(...) LOGMASKED(LOG_WARN, __VA_ARGS__)
+#define LOGDMA(...) LOGMASKED(LOG_DMA, __VA_ARGS__)
+#define LOGSYNC(...) LOGMASKED(LOG_SYNC, __VA_ARGS__)
+
DEFINE_DEVICE_TYPE(AMIGA_FDC, amiga_fdc_device, "amiga_fdc", "Amiga FDC")
void amiga_fdc_device::floppy_formats(format_registration &fr)
@@ -210,7 +222,12 @@ void amiga_fdc_device::live_run(const attotime &limit)
}
if(cur_live.bit_counter > 8)
- fatalerror("amiga_fdc_device::live_run - cur_live.bit_counter > 8\n");
+ {
+ // CHECKME: abreed, ghoulsvf Ghouls'n Goblins and lastnin2 at very least throws this
+ // is it a side effect of something else not happening at the right time or the assumption is right?
+ cur_live.bit_counter = 0;
+ LOGWARN("%s: live_run - cur_live.bit_counter > 8\n", machine().describe_context());
+ }
if(cur_live.bit_counter == 8) {
live_delay(RUNNING_SYNCPOINT);
@@ -233,7 +250,10 @@ void amiga_fdc_device::live_run(const attotime &limit)
return;
cur_live.bit_counter++;
if(cur_live.bit_counter > 8)
- fatalerror("amiga_fdc_device::live_run - cur_live.bit_counter > 8\n");
+ {
+ cur_live.bit_counter = 0;
+ LOGWARN("%s: live_run - cur_live.bit_counter > 8\n", machine().describe_context());
+ }
if(cur_live.bit_counter == 8) {
live_delay(RUNNING_SYNCPOINT);
@@ -247,6 +267,14 @@ void amiga_fdc_device::live_run(const attotime &limit)
if(!(dskbyt & 0x2000)) {
if(cur_live.shift_reg == dsksync) {
if(adkcon & 0x0400) {
+ // FIXME: exact dsksync behaviour
+ // - Some games currently writes two dsksync to the buffer (marked as "[FDC] dsksync"),
+ // removing one will make most of them happy.
+ // This is reported as 0-lower cylinder good and everything else as bad in the ATK suite;
+ // - Some games trashes memory, mostly the ones with "[FDC] dsksync bootblock":
+ // they attempt to load the tracks in AmigaDOS in the same way that's done by the
+ // Kickstart to check if the disk is bootable.
+ // This is reported as 0-upper cylinder bad in the ATK suite;
if(dma_state == DMA_WAIT_START) {
cur_live.bit_counter = 0;
@@ -257,16 +285,22 @@ void amiga_fdc_device::live_run(const attotime &limit)
cur_live.bit_counter = 0;
dma_value = dma_read();
- } else
+ } else {
+ LOGSYNC("%s: DSKSYNC on %06x %d\n", this->tag(), dskpt, dma_state);
dma_write(dsksync);
+ }
} else if(dma_state != DMA_IDLE) {
+ LOGSYNC("%s: DSKSYNC on %06x %d\n", this->tag(), dskpt, dma_state);
dma_write(dsksync);
cur_live.bit_counter = 0;
} else if(cur_live.bit_counter != 8)
cur_live.bit_counter = 0;
}
+ //else
+ // LOGSYNC("%s: no DSKSYNC\n", this->tag());
+
dskbyt |= 0x1000;
m_write_dsksyn(1);
} else
@@ -332,6 +366,11 @@ void amiga_fdc_device::dma_check()
bool was_writing = dskbyt & 0x2000;
dskbyt &= 0x9fff;
if(dma_enabled()) {
+ LOGDMA("%s: DMA start dskpt=%08x dsklen=%04x dir=%s adkcon=%04x dsksync=%04x\n",
+ machine().describe_context(),
+ dskpt, dsklen & 0x3fff, BIT(dsklen, 14) ? "RAM->disk" : "disk->RAM", adkcon, dsksync
+ );
+
if(dma_state == IDLE) {
dma_state = adkcon & 0x0400 ? DMA_WAIT_START : DMA_RUNNING_BYTE_0;
if(dma_state == DMA_RUNNING_BYTE_0) {
@@ -344,7 +383,6 @@ void amiga_fdc_device::dma_check()
}
}
} else {
- dskbyt |= 0x4000;
if(dsklen & 0x4000)
dskbyt |= 0x2000;
}
@@ -355,7 +393,6 @@ void amiga_fdc_device::dma_check()
cur_live.pll.stop_writing(floppy, cur_live.tm);
if(!was_writing && (dskbyt & 0x2000))
cur_live.pll.start_writing(cur_live.tm);
-
}
void amiga_fdc_device::adkcon_set(uint16_t data)
@@ -409,6 +446,7 @@ uint16_t amiga_fdc_device::dskptl_r()
void amiga_fdc_device::dsksync_w(uint16_t data)
{
live_sync();
+ LOGSYNC("%s: DSKSYNC %04x\n", machine().describe_context(), data);
dsksync = data;
live_run();
}
@@ -416,6 +454,7 @@ void amiga_fdc_device::dsksync_w(uint16_t data)
void amiga_fdc_device::dmacon_set(uint16_t data)
{
live_sync();
+ LOGDMA("%s: DMACON set DSKEN %d DMAEN %d (%04x)\n", machine().describe_context(), BIT(data, 4), BIT(data, 9), data);
dmacon = data;
dma_check();
live_run();
@@ -423,8 +462,15 @@ void amiga_fdc_device::dmacon_set(uint16_t data)
uint16_t amiga_fdc_device::dskbytr_r()
{
- uint16_t res = dskbyt;
- dskbyt &= 0x7fff;
+ uint16_t res = (dskbyt & ~0x4000);
+ // check if DMA is on
+ // logica2 diagnostic BIOS floppy test requires this
+ bool dmaon = (dma_state != DMA_IDLE) && ((dmacon & 0x0210) == 0x0210);
+ res |= dmaon << 14;
+
+ // reset DSKBYT ready on read
+ if (!machine().side_effects_disabled())
+ dskbyt &= 0x7fff;
return res;
}
@@ -454,6 +500,7 @@ void amiga_fdc_device::ciaaprb_w(uint8_t data)
live_sync();
+ // FIXME: several sources claims that multiple drive selects is really possible
if(!(data & 0x08))
floppy = floppy_devices[0];
else if(!(data & 0x10))
@@ -494,7 +541,8 @@ uint8_t amiga_fdc_device::ciaapra_r()
{
uint8_t ret = 0x3c;
if(floppy) {
- //if(!floppy->ready_r()) fixit: seems to not work well with multiple disk drives
+ // FIXME: seems to not work well with multiple disk drives
+ //if(!floppy->ready_r())
ret &= ~0x20;
if(!floppy->trk00_r())
ret &= ~0x10;
diff --git a/src/devices/machine/mos6526.cpp b/src/devices/machine/mos6526.cpp
index e1f40b109c1..55368e33e86 100644
--- a/src/devices/machine/mos6526.cpp
+++ b/src/devices/machine/mos6526.cpp
@@ -902,7 +902,10 @@ uint8_t mos6526_device::read(offs_t offset)
case ICR:
data = (m_ir1 << 7) | m_icr;
- if (machine().side_effects_disabled())
+ // Do not reset irqs unless one is effectively issued.
+ // cfr. amigaocs_flop.xml barb2paln4 that polls for Timer B status
+ // until it expires at PC=7821c and other places.
+ if (machine().side_effects_disabled() || !m_icr)
return data;
m_icr_read = true;
diff --git a/src/mame/drivers/alg.cpp b/src/mame/drivers/alg.cpp
index d6cf201c7d0..860a6fadbfb 100644
--- a/src/mame/drivers/alg.cpp
+++ b/src/mame/drivers/alg.cpp
@@ -7,6 +7,13 @@
Amiga 500 + Sony laserdisc player LDP-1450
(LDP-3300P for Zorton Brothers, LDP-1500 for Marbella Vice)
+ TODO:
+ - Implement LD comms (thru Amiga SERDAT / SERDATR ports);
+ - Why it enables FDC DMA like at all?
+ Is the board really capable of reading floppies for some reason?
+ - Picmatic games may really belong to a different driver,
+ just sharing the Amiga base state;
+
Games Supported:
Mad Dog McCree [3 versions]
@@ -913,49 +920,52 @@ GAME( 199?, alg_bios, 0, alg_r1, alg, alg_state, init_ntsc,
// Rev. A board
// PAL R1
-GAME( 1990, maddoga, maddog, alg_r1, alg, alg_state, init_palr1, ROT0, "American Laser Games", "Mad Dog McCree v1C board rev.A", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1990, maddoga, maddog, alg_r1, alg, alg_state, init_palr1, ROT0, "American Laser Games", "Mad Dog McCree (v1C board rev.A)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// PAL R3
-GAME( 1991, wsjr, alg_bios, alg_r1, alg, alg_state, init_palr3, ROT0, "American Laser Games", "Who Shot Johnny Rock? v1.6", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1991, wsjr_15, wsjr, alg_r1, alg, alg_state, init_palr3, ROT0, "American Laser Games", "Who Shot Johnny Rock? v1.5", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1991, wsjr, alg_bios, alg_r1, alg, alg_state, init_palr3, ROT0, "American Laser Games", "Who Shot Johnny Rock? (v1.6)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1991, wsjr_15, wsjr, alg_r1, alg, alg_state, init_palr3, ROT0, "American Laser Games", "Who Shot Johnny Rock? (v1.5)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// Rev. B board
// PAL R6
-GAME( 1990, maddog, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog McCree v2.03 board rev.B", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1990, maddog_202, maddog, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog McCree v2.02 board rev.B", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1990, maddog, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog McCree (v2.03 board rev.B)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1990, maddog_202, maddog, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog McCree (v2.02 board rev.B)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// Works OK but uses right player (2) controls only for trigger and holster
-GAME( 1992, maddog2, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold v2.04", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, maddog2_202, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold v2.02", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, maddog2_110, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold v1.10", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, maddog2_100, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold v1.00", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, maddog2, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold (v2.04)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, maddog2_202, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold (v2.02)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, maddog2_110, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold (v1.10)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, maddog2_100, maddog2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Mad Dog II: The Lost Gold (v1.00)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// Works ok but uses right player (2) controls only for trigger and holster
-GAME( 1992, spacepir, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Space Pirates v2.2", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, spacepir_14, spacepir, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Space Pirates v1.4", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, spacepir, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Space Pirates (v2.2)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, spacepir_14, spacepir, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Space Pirates (v1.4)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, gallgall, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Gallagher's Gallery v2.2", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1992, gallgall_21, gallgall, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Gallagher's Gallery v2.1", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, gallgall, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Gallagher's Gallery (v2.2)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1992, gallgall_21, gallgall, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Gallagher's Gallery (v2.1)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// All good, but no holster
-GAME( 1993, crimepat, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol v1.51", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1993, crimepat_14, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol v1.4", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1993, crimepat_12, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol v1.2", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1993, crimepat_10, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol v1.0", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-
-GAME( 1993, crimep2, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol 2: Drug Wars v1.3", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1993, crimep2_11, crimep2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol 2: Drug Wars v1.1", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1994, lastbh, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "The Last Bounty Hunter v1.01", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1994, lastbh_006, lastbh, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "The Last Bounty Hunter v0.06", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1995, fastdraw, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT90, "American Laser Games", "Fast Draw Showdown v1.31", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1995, fastdraw_130, fastdraw, alg_r2, alg_2p, alg_state, init_palr6, ROT90, "American Laser Games", "Fast Draw Showdown v1.30", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1993, crimepat, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol (v1.51)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1993, crimepat_14, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol (v1.4)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1993, crimepat_12, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol (v1.2)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1993, crimepat_10, crimepat, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol (v1.0)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+
+GAME( 1993, crimep2, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol 2: Drug Wars (v1.3)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1993, crimep2_11, crimep2, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "Crime Patrol 2: Drug Wars (v1.1)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1994, lastbh, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "The Last Bounty Hunter (v1.01)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1994, lastbh_006, lastbh, alg_r2, alg_2p, alg_state, init_palr6, ROT0, "American Laser Games", "The Last Bounty Hunter (v0.06)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1995, fastdraw, alg_bios, alg_r2, alg_2p, alg_state, init_palr6, ROT90, "American Laser Games", "Fast Draw Showdown (v1.31)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1995, fastdraw_130, fastdraw, alg_r2, alg_2p, alg_state, init_palr6, ROT90, "American Laser Games", "Fast Draw Showdown (v1.30)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// Works OK but uses right player (2) controls only for trigger and holster
// NOVA games on ALG hardware with own address scramble
-GAME( 1995, aplatoon, alg_bios, alg_r2, alg, alg_state, init_aplatoon, ROT0, "Nova?", "Platoon V.3.1 US", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1995, aplatoon, alg_bios, alg_r2, alg, alg_state, init_aplatoon, ROT0, "Nova?", "Platoon (V.3.1 US)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// Picmatic games NTSC or PAL (50 or 100Hz) TV standard, own ROM board
-GAME( 1993, zortonbr_100, zortonbr, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Zorton Brothers v1.00 (Los Justicieros)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
-GAME( 1994, zortonbr, alg_bios, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Zorton Brothers v1.01 (Los Justicieros)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+// CHECKME: Zorton Brothers is the English title while Los Justicieros is the Spanish one?
+// Eventually confirm if they shares same roms with different LD side depending on language,
+// or perhaps the title "Zorton Brothers" is the only one for Arcade LD, while "Los Justicieros" is the later PC release?
+GAME( 1993, zortonbr_100, zortonbr, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Zorton Brothers / Los Justicieros (v1.00)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+GAME( 1994, zortonbr, alg_bios, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Zorton Brothers / Los Justicieros (v1.01)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
GAME( 1994, marvice, alg_bios, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Marbella Vice", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
GAME( 1994, marvice100hz, alg_bios, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Marbella Vice (100Hz display)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
GAME( 1995, tierras100hz, alg_bios, picmatic, alg, alg_state, init_pal, ROT0, "Picmatic", "Tierras Salvajes (100Hz display)", MACHINE_NOT_WORKING | MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
diff --git a/src/mame/drivers/amiga.cpp b/src/mame/drivers/amiga.cpp
index 200e47f7baf..d17eaba1440 100644
--- a/src/mame/drivers/amiga.cpp
+++ b/src/mame/drivers/amiga.cpp
@@ -1607,6 +1607,7 @@ void amiga_state::amiga_base(machine_config &config)
// floppy drives
AMIGA_FDC(config, m_fdc, amiga_state::CLK_7M_PAL);
+ m_fdc->index_callback().set(m_cia_1, FUNC(mos8520_device::flag_w));
m_fdc->read_dma_callback().set(FUNC(amiga_state::chip_ram_r));
m_fdc->write_dma_callback().set(FUNC(amiga_state::chip_ram_w));
m_fdc->dskblk_callback().set(FUNC(amiga_state::fdc_dskblk_w));
@@ -1864,7 +1865,7 @@ void a3000_state::a3000(machine_config &config)
// real-time clock
RP5C01(config, "rtc", XTAL(32'768));
- // todo: zorro3 slots, super dmac, scsi
+ // TODO: zorro3 slots, super dmac, scsi
// software
SOFTWARE_LIST(config, "a3000_list").set_original("amiga_a3000");
@@ -1949,7 +1950,7 @@ void a600_state::a600(machine_config &config)
ata_interface_device &ata(ATA_INTERFACE(config, "ata").options(ata_devices, "hdd", nullptr, false));
ata.irq_handler().set("gayle", FUNC(gayle_device::ide_interrupt_w));
- // todo: pcmcia
+ // TODO: pcmcia
// software
SOFTWARE_LIST(config, "ecs_list").set_original("amigaecs_flop");
@@ -2008,7 +2009,7 @@ void a1200_state::a1200(machine_config &config)
subdevice<amiga_keyboard_bus_device>("kbd").set_default_option("a1200_us");
#endif
- // todo: pcmcia
+ // TODO: pcmcia
// software
SOFTWARE_LIST(config, "aga_list").set_original("amigaaga_flop");
@@ -2059,7 +2060,7 @@ void a4000_state::a4000(machine_config &config)
ata_interface_device &ata(ATA_INTERFACE(config, "ata").options(ata_devices, "hdd", nullptr, false));
ata.irq_handler().set(FUNC(a4000_state::ide_interrupt_w));
- // todo: zorro3
+ // TODO: zorro3
// software
SOFTWARE_LIST(config, "aga_list").set_original("amigaaga_flop");
@@ -2088,7 +2089,7 @@ void a4000_state::a400030(machine_config &config)
m_maincpu->set_addrmap(AS_PROGRAM, &a4000_state::a400030_mem);
m_maincpu->set_cpu_space(AS_PROGRAM);
- // todo: ide
+ // TODO: ide
}
void a4000_state::a400030n(machine_config &config)
@@ -2163,7 +2164,7 @@ void a4000_state::a4000t(machine_config &config)
m_maincpu->set_addrmap(AS_PROGRAM, &a4000_state::a4000t_mem);
m_maincpu->set_cpu_space(AS_PROGRAM);
- // todo: ide, zorro3, scsi, super dmac
+ // TODO: ide, zorro3, scsi, super dmac
}
void a4000_state::a4000tn(machine_config &config)
@@ -2422,7 +2423,8 @@ ROM_END
ROM_START( cd32 )
ROM_REGION32_BE(0x100000, "kickstart", 0)
-// ROM_LOAD16_WORD("391640-03.u6a", 0x000000, 0x100000, CRC(a4fbc94a) SHA1(816ce6c5077875850c7d43452230a9ba3a2902db)) // todo: this is the real dump
+ // TODO: this is the real dump
+// ROM_LOAD16_WORD("391640-03.u6a", 0x000000, 0x100000, CRC(a4fbc94a) SHA1(816ce6c5077875850c7d43452230a9ba3a2902db))
ROM_LOAD16_WORD("391640-03.u6a", 0x000000, 0x100000, CRC(d3837ae4) SHA1(06807db3181637455f4d46582d9972afec8956d9))
ROM_END
diff --git a/src/mame/includes/amiga.h b/src/mame/includes/amiga.h
index 1b5f389d04a..68f27a5110a 100644
--- a/src/mame/includes/amiga.h
+++ b/src/mame/includes/amiga.h
@@ -458,7 +458,7 @@ public:
uint16_t custom_chip_r(offs_t offset);
void custom_chip_w(offs_t offset, uint16_t data);
- DECLARE_WRITE_LINE_MEMBER( paula_int_w );
+ void paula_int_w(offs_t channel, u8 state);
uint16_t rom_mirror_r(offs_t offset, uint16_t mem_mask = ~0);
uint32_t rom_mirror32_r(offs_t offset, uint32_t mem_mask = ~0);
diff --git a/src/mame/machine/amiga.cpp b/src/mame/machine/amiga.cpp
index 95842dc8c94..62da9267548 100644
--- a/src/mame/machine/amiga.cpp
+++ b/src/mame/machine/amiga.cpp
@@ -202,7 +202,7 @@ WRITE_LINE_MEMBER(amiga_state::fdc_dskblk_w)
WRITE_LINE_MEMBER(amiga_state::fdc_dsksyn_w)
{
- set_interrupt(INTENA_SETCLR | INTENA_DSKSYN);
+ set_interrupt((state ? INTENA_SETCLR : 0) | INTENA_DSKSYN);
}
WRITE_LINE_MEMBER( amiga_state::kbreset_w )
@@ -387,9 +387,9 @@ TIMER_CALLBACK_MEMBER( amiga_state::amiga_irq_proc )
m_irq_timer->reset();
}
-WRITE_LINE_MEMBER( amiga_state::paula_int_w )
+void amiga_state::paula_int_w (offs_t channel, u8 state)
{
- set_interrupt(INTENA_SETCLR | (0x80 << state));
+ set_interrupt(INTENA_SETCLR | (0x80 << channel));
}
@@ -922,7 +922,7 @@ TIMER_CALLBACK_MEMBER( amiga_state::amiga_blitter_proc )
CUSTOM_REG(REG_DMACON) &= ~0x4000;
// signal an interrupt
- set_interrupt(0x8000 | INTENA_BLIT);
+ set_interrupt(INTENA_SETCLR | INTENA_BLIT);
/* reset the blitter timer */
m_blitter_timer->reset();
@@ -1443,7 +1443,6 @@ void amiga_state::custom_chip_w(offs_t offset, uint16_t data)
data = (data & INTENA_SETCLR) ? (CUSTOM_REG(offset) | (data & 0x7fff)) : (CUSTOM_REG(offset) & ~(data & 0x7fff));
CUSTOM_REG(offset) = data;
-
if (temp & INTENA_SETCLR)
// if we're enabling irq's, delay a bit
m_irq_timer->adjust(m_maincpu->cycles_to_attotime(AMIGA_IRQ_DELAY_CYCLES));
@@ -1497,6 +1496,13 @@ void amiga_state::custom_chip_w(offs_t offset, uint16_t data)
CUSTOM_REG(offset) = data;
break;
+ case REG_BPL1MOD: case REG_BPL2MOD:
+ // bit 0 is implicitly ignored on writes,
+ // and wouldn't otherwise make sense with 68k inability of word reading with odd addresses.
+ // hpoker/hpokera would otherwise draw misaligned bottom GFX area without this (writes 0x27)
+ data &= ~1;
+ break;
+
case REG_COLOR00: case REG_COLOR01: case REG_COLOR02: case REG_COLOR03:
case REG_COLOR04: case REG_COLOR05: case REG_COLOR06: case REG_COLOR07:
case REG_COLOR08: case REG_COLOR09: case REG_COLOR10: case REG_COLOR11: