summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
author Angelo Salese <angelosa@users.noreply.github.com>2011-07-11 15:06:19 +0000
committer Angelo Salese <angelosa@users.noreply.github.com>2011-07-11 15:06:19 +0000
commitfecff8f38706ab7c5ad080b00df683cd5990d06f (patch)
tree23f4747ed3ba25f2ea26d0b5a4681498bfe54065
parentc59f40791634fb8bc32a5f09c58f952e40d48cc1 (diff)
Preliminary work for ATV Track, in order to get the second SH-4 into
business [Samuele Zannoli] Added support for dma transfers between the processor and external devices in SH-4 CPU core [Samuele Zannoli] Modified naomibd device so that it allocates the memory for the gdrom data on startup based on a parameter that specifies the size in megabytes. [Samuele Zannoli] Added two new commands to the unidasm utility [Samuele Zannoli] -skip <n> allows to skip the first <n> bytes from the file -count <n> specifiest that only <n> bytes from the file must be disassembled
-rw-r--r--src/emu/cpu/sh4/sh4.h14
-rw-r--r--src/emu/cpu/sh4/sh4comn.c235
-rw-r--r--src/emu/cpu/sh4/sh4comn.h7
-rw-r--r--src/emu/cpu/sh4/sh4regs.h44
-rw-r--r--src/mame/drivers/atvtrack.c301
-rw-r--r--src/mame/drivers/chihiro.c2
-rw-r--r--src/mame/drivers/naomi.c2
-rw-r--r--src/mame/drivers/triforce.c2
-rw-r--r--src/mame/includes/naomibd.h14
-rw-r--r--src/mame/machine/naomibd.c19
-rw-r--r--src/tools/unidasm.c35
11 files changed, 620 insertions, 55 deletions
diff --git a/src/emu/cpu/sh4/sh4.h b/src/emu/cpu/sh4/sh4.h
index 54879eee05a..d5b211bc511 100644
--- a/src/emu/cpu/sh4/sh4.h
+++ b/src/emu/cpu/sh4/sh4.h
@@ -57,9 +57,10 @@ enum
{
SH4_IOPORT_16=8*0,
SH4_IOPORT_4=8*1,
+ SH4_IOPORT_DMA=8*2,
// future use
- SH4_IOPORT_SCI=8*2,
- SH4_IOPORT_SCIF=8*3
+ SH4_IOPORT_SCI=8*3,
+ SH4_IOPORT_SCIF=8*4
};
struct sh4_config
@@ -76,6 +77,14 @@ struct sh4_config
int clock;
};
+struct sh4_device_dma
+{
+ UINT32 length;
+ UINT32 size;
+ void *buffer;
+ int channel;
+};
+
struct sh4_ddt_dma
{
UINT32 source;
@@ -99,6 +108,7 @@ READ32_HANDLER( sh4_internal_r );
void sh4_set_frt_input(device_t *device, int state);
void sh4_set_irln_input(device_t *device, int value);
void sh4_set_ftcsr_callback(device_t *device, sh4_ftcsr_callback callback);
+int sh4_dma_data(device_t *device, struct sh4_device_dma *s);
void sh4_dma_ddt(device_t *device, struct sh4_ddt_dma *s);
/***************************************************************************
diff --git a/src/emu/cpu/sh4/sh4comn.c b/src/emu/cpu/sh4/sh4comn.c
index 6097ece9251..0ddf9e4297b 100644
--- a/src/emu/cpu/sh4/sh4comn.c
+++ b/src/emu/cpu/sh4/sh4comn.c
@@ -404,26 +404,26 @@ static TIMER_CALLBACK( sh4_dmac_callback )
{
case 0:
sh4->m[DMATCR0] = 0;
- sh4->m[CHCR0] |= 2;
- if (sh4->m[CHCR0] & 4)
+ sh4->m[CHCR0] |= CHCR_TE;
+ if (sh4->m[CHCR0] & CHCR_IE)
sh4_exception_request(sh4, SH4_INTC_DMTE0);
break;
case 1:
sh4->m[DMATCR1] = 0;
- sh4->m[CHCR1] |= 2;
- if (sh4->m[CHCR1] & 4)
+ sh4->m[CHCR1] |= CHCR_TE;
+ if (sh4->m[CHCR1] & CHCR_IE)
sh4_exception_request(sh4, SH4_INTC_DMTE1);
break;
case 2:
sh4->m[DMATCR2] = 0;
- sh4->m[CHCR2] |= 2;
- if (sh4->m[CHCR2] & 4)
+ sh4->m[CHCR2] |= CHCR_TE;
+ if (sh4->m[CHCR2] & CHCR_IE)
sh4_exception_request(sh4, SH4_INTC_DMTE2);
break;
case 3:
sh4->m[DMATCR3] = 0;
- sh4->m[CHCR3] |= 2;
- if (sh4->m[CHCR3] & 4)
+ sh4->m[CHCR3] |= CHCR_TE;
+ if (sh4->m[CHCR3] & CHCR_IE)
sh4_exception_request(sh4, SH4_INTC_DMTE3);
break;
}
@@ -434,9 +434,9 @@ static int sh4_dma_transfer(sh4_state *sh4, int channel, int timermode, UINT32 c
int incs, incd, size;
UINT32 src, dst, count;
- incd = (chcr >> 14) & 3;
- incs = (chcr >> 12) & 3;
- size = dmasize[(chcr >> 4) & 7];
+ incd = (chcr & CHCR_DM) >> 14;
+ incs = (chcr & CHCR_SM) >> 12;
+ size = dmasize[(chcr & CHCR_TS) >> 4];
if(incd == 3 || incs == 3)
{
logerror("SH4: DMA: bad increment values (%d, %d, %d, %04x)\n", incd, incs, size, chcr);
@@ -450,12 +450,12 @@ static int sh4_dma_transfer(sh4_state *sh4, int channel, int timermode, UINT32 c
LOG(("SH4: DMA %d start %x, %x, %x, %04x, %d, %d, %d\n", channel, src, dst, count, chcr, incs, incd, size));
- if (timermode == 1)
+ if (timermode == 1) // timer actvated after a time based on the number of words to transfer
{
sh4->dma_timer_active[channel] = 1;
sh4->dma_timer[channel]->adjust(sh4->device->cycles_to_attotime(2*count+1), channel);
}
- else if (timermode == 2)
+ else if (timermode == 2) // timer activated immediately
{
sh4->dma_timer_active[channel] = 1;
sh4->dma_timer[channel]->adjust(attotime::zero, channel);
@@ -556,9 +556,50 @@ static int sh4_dma_transfer(sh4_state *sh4, int channel, int timermode, UINT32 c
return 1;
}
+static int sh4_dma_transfer_device(sh4_state *sh4, int channel, UINT32 chcr, UINT32 *sar, UINT32 *dar, UINT32 *dmatcr)
+{
+ int incs, incd, size, mod;
+ UINT32 src, dst, count;
+
+ incd = (chcr & CHCR_DM) >> 14;
+ incs = (chcr & CHCR_SM) >> 12;
+ size = dmasize[(chcr & CHCR_TS) >> 4];
+ mod = ((chcr & CHCR_RS) >> 8);
+ if (incd == 3 || incs == 3)
+ {
+ logerror("SH4: DMA: bad increment values (%d, %d, %d, %04x)\n", incd, incs, size, chcr);
+ return 0;
+ }
+ src = *sar;
+ dst = *dar;
+ count = *dmatcr;
+ if (!count)
+ count = 0x1000000;
+
+ LOG(("SH4: DMA %d start device<->memory %x, %x, %x, %04x, %d, %d, %d\n", channel, src, dst, count, chcr, incs, incd, size));
+
+ sh4->dma_timer_active[channel] = 1;
+
+ src &= AM;
+ dst &= AM;
+
+ // remember parameters
+ sh4->dma_source[channel]=src;
+ sh4->dma_destination[channel]=dst;
+ sh4->dma_count[channel]=count;
+ sh4->dma_wordsize[channel]=size;
+ sh4->dma_source_increment[channel]=incs;
+ sh4->dma_destination_increment[channel]=incd;
+ sh4->dma_mode[channel]=mod;
+
+ // inform device its ready to transfer
+ sh4->io->write_dword(SH4_IOPORT_DMA, channel | (mod << 16));
+ return 1;
+}
+
static void sh4_dmac_check(sh4_state *sh4, int channel)
{
-UINT32 dmatcr,chcr,sar,dar;
+UINT32 dmatcr, chcr, sar, dar;
switch (channel)
{
@@ -589,12 +630,17 @@ UINT32 dmatcr,chcr,sar,dar;
default:
return;
}
- if (chcr & sh4->m[DMAOR] & 1)
+ if (chcr & sh4->m[DMAOR] & DMAOR_DME)
{
- if ((((chcr >> 8) & 15) < 4) || (((chcr >> 8) & 15) > 6))
+ if ((((chcr & CHCR_RS) >> 8) < 2) || (((chcr & CHCR_RS) >> 8) > 6))
return;
- if (!sh4->dma_timer_active[channel] && !(chcr & 2) && !(sh4->m[DMAOR] & 6))
- sh4_dma_transfer(sh4, channel, 1, chcr, &sar, &dar, &dmatcr);
+ if (!sh4->dma_timer_active[channel] && !(chcr & CHCR_TE) && !(sh4->m[DMAOR] & (DMAOR_AE | DMAOR_NMIF)))
+ {
+ if (((chcr & CHCR_RS) >> 8) > 3)
+ sh4_dma_transfer(sh4, channel, 1, chcr, &sar, &dar, &dmatcr);
+ else if ((sh4->m[DMAOR] & DMAOR_DDT) == 0)
+ sh4_dma_transfer_device(sh4, channel, chcr, &sar, &dar, &dmatcr); // tell device we are ready to transfer
+ }
}
else
{
@@ -607,11 +653,11 @@ UINT32 dmatcr,chcr,sar,dar;
}
}
-static void sh4_dmac_nmi(sh4_state *sh4) // manage dma when nmi
+static void sh4_dmac_nmi(sh4_state *sh4) // manage dma when nmi gets asserted
{
int s;
- sh4->m[DMAOR] |= 2; // nmif = 1
+ sh4->m[DMAOR] |= DMAOR_NMIF;
for (s = 0;s < 4;s++)
{
if (sh4->dma_timer_active[s])
@@ -638,7 +684,7 @@ WRITE32_HANDLER( sh4_internal_w )
switch( offset )
{
case MMUCR: // MMU Control
- if (data & 1)
+ if (data & MMUCR_AT)
{
printf("SH4 MMU Enabled\n");
printf("If you're seeing this, but running something other than a Naomi GD-ROM game then chances are it won't work\n");
@@ -880,10 +926,10 @@ WRITE32_HANDLER( sh4_internal_w )
sh4_dmac_check(sh4, 3);
break;
case DMAOR:
- if ((sh4->m[DMAOR] & 4) && (~old & 4))
- sh4->m[DMAOR] &= ~4;
- if ((sh4->m[DMAOR] & 2) && (~old & 2))
- sh4->m[DMAOR] &= ~2;
+ if ((sh4->m[DMAOR] & DMAOR_AE) && (~old & DMAOR_AE))
+ sh4->m[DMAOR] &= ~DMAOR_AE;
+ if ((sh4->m[DMAOR] & DMAOR_NMIF) && (~old & DMAOR_NMIF))
+ sh4->m[DMAOR] &= ~DMAOR_NMIF;
sh4_dmac_check(sh4, 0);
sh4_dmac_check(sh4, 1);
sh4_dmac_check(sh4, 2);
@@ -953,7 +999,10 @@ READ32_HANDLER( sh4_internal_r )
switch( offset )
{
case VERSION:
- return 0x040205c1; // this is what a real SH7750 in a Dreamcast returns - the later Naomi BIOSes check and care!
+ return PVR_SH7091; // 0x040205c1, this is what a real SH7091 in a Dreamcast returns - the later Naomi BIOSes check and care!
+ break;
+ case PRR:
+ return 0;
break;
case IPRD:
return 0x00000000; // SH7750 ignores writes here and always returns zero
@@ -1197,6 +1246,140 @@ void sh4_common_init(device_t *device)
sh4->m = auto_alloc_array(device->machine(), UINT32, 16384);
}
+// called by drivers to transfer data in a cpu<->device dma. 'device' must be a SH4 cpu
+int sh4_dma_data(device_t *device, struct sh4_device_dma *s)
+{
+ UINT32 pos, len, siz;
+ int channel = s->channel;
+ void *data = s->buffer;
+
+ sh4_state *sh4 = get_safe_token(device);
+
+ if (!sh4->dma_timer_active[channel])
+ return 0;
+
+ if (sh4->dma_mode[channel] == 2)
+ {
+ // device receives data
+ len = sh4->dma_count[channel];
+ if (s->length < len)
+ len = s->length;
+ siz = sh4->dma_wordsize[channel];
+ for (pos = 0;pos < len;pos++) {
+ switch (siz)
+ {
+ case 8:
+ if (sh4->dma_source_increment[channel] == 2)
+ sh4->dma_source[channel] -= 8;
+ *(UINT64 *)data = sh4->program->read_qword(sh4->dma_source[channel] & ~7);
+ if (sh4->dma_source_increment[channel] == 1)
+ sh4->dma_source[channel] += 8;
+ break;
+ case 1:
+ if (sh4->dma_source_increment[channel] == 2)
+ sh4->dma_source[channel]--;
+ *(UINT8 *)data = sh4->program->read_byte(sh4->dma_source[channel]);
+ if (sh4->dma_source_increment[channel] == 1)
+ sh4->dma_source[channel]++;
+ break;
+ case 2:
+ if (sh4->dma_source_increment[channel] == 2)
+ sh4->dma_source[channel] -= 2;
+ *(UINT16 *)data = sh4->program->read_word(sh4->dma_source[channel] & ~1);
+ if (sh4->dma_source_increment[channel] == 1)
+ sh4->dma_source[channel] += 2;
+ break;
+ case 4:
+ if (sh4->dma_source_increment[channel] == 2)
+ sh4->dma_source[channel] -= 4;
+ *(UINT32 *)data = sh4->program->read_dword(sh4->dma_source[channel] & ~3);
+ if (sh4->dma_source_increment[channel] == 1)
+ sh4->dma_source[channel] += 4;
+ break;
+ case 32:
+ if (sh4->dma_source_increment[channel] == 2)
+ sh4->dma_source[channel] -= 32;
+ *(UINT64 *)data = sh4->program->read_qword(sh4->dma_source[channel] & ~31);
+ *((UINT64 *)data+1) = sh4->program->read_qword((sh4->dma_source[channel] & ~31)+8);
+ *((UINT64 *)data+2) = sh4->program->read_qword((sh4->dma_source[channel] & ~31)+16);
+ *((UINT64 *)data+3) = sh4->program->read_qword((sh4->dma_source[channel] & ~31)+24);
+ if (sh4->dma_source_increment[channel] == 1)
+ sh4->dma_source[channel] += 32;
+ break;
+ }
+ sh4->dma_count[channel]--;
+ }
+ if (sh4->dma_count[channel] == 0) // all data transferred ?
+ {
+ sh4->dma_timer[channel]->adjust(attotime::zero, channel);
+ return 2;
+ }
+ return 1;
+ }
+ else if (sh4->dma_mode[channel] == 3)
+ {
+ // device sends data
+ len = sh4->dma_count[channel];
+ if (s->length < len)
+ len = s->length;
+ siz = sh4->dma_wordsize[channel];
+ for (pos = 0;pos < len;pos++) {
+ switch (siz)
+ {
+ case 8:
+ if (sh4->dma_destination_increment[channel] == 2)
+ sh4->dma_destination[channel]-=8;
+ sh4->program->write_qword(sh4->dma_destination[channel] & ~7, *(UINT64 *)data);
+ if (sh4->dma_destination_increment[channel] == 1)
+ sh4->dma_destination[channel]+=8;
+ break;
+ case 1:
+ if (sh4->dma_destination_increment[channel] == 2)
+ sh4->dma_destination[channel]--;
+ sh4->program->write_byte(sh4->dma_destination[channel], *(UINT8 *)data);
+ if (sh4->dma_destination_increment[channel] == 1)
+ sh4->dma_destination[channel]++;
+ break;
+ case 2:
+ if (sh4->dma_destination_increment[channel] == 2)
+ sh4->dma_destination[channel]-=2;
+ sh4->program->write_word(sh4->dma_destination[channel] & ~1, *(UINT16 *)data);
+ if (sh4->dma_destination_increment[channel] == 1)
+ sh4->dma_destination[channel]+=2;
+ break;
+ case 4:
+ if (sh4->dma_destination_increment[channel] == 2)
+ sh4->dma_destination[channel]-=4;
+ sh4->program->write_dword(sh4->dma_destination[channel] & ~3, *(UINT32 *)data);
+ if (sh4->dma_destination_increment[channel] == 1)
+ sh4->dma_destination[channel]+=4;
+ break;
+ case 32:
+ if (sh4->dma_destination_increment[channel] == 2)
+ sh4->dma_destination[channel]-=32;
+ sh4->program->write_qword(sh4->dma_destination[channel] & ~31, *(UINT64 *)data);
+ sh4->program->write_qword((sh4->dma_destination[channel] & ~31)+8, *((UINT64 *)data+1));
+ sh4->program->write_qword((sh4->dma_destination[channel] & ~31)+16, *((UINT64 *)data+2));
+ sh4->program->write_qword((sh4->dma_destination[channel] & ~31)+24, *((UINT64 *)data+3));
+ if (sh4->dma_destination_increment[channel] == 1)
+ sh4->dma_destination[channel]+=32;
+ break;
+ }
+ sh4->dma_count[channel]--;
+ }
+
+ if (sh4->dma_count[channel] == 0) // all data transferred ?
+ {
+ sh4->dma_timer[channel]->adjust(attotime::zero, channel);
+ return 2;
+ }
+ return 1;
+ }
+ else
+ return 0;
+}
+
+// called by drivers to transfer data in a DDT dma. 'device' must be a SH4 cpu
void sh4_dma_ddt(device_t *device, struct sh4_ddt_dma *s)
{
sh4_state *sh4 = get_safe_token(device);
diff --git a/src/emu/cpu/sh4/sh4comn.h b/src/emu/cpu/sh4/sh4comn.h
index ef589829c4c..ab08e9ffd1b 100644
--- a/src/emu/cpu/sh4/sh4comn.h
+++ b/src/emu/cpu/sh4/sh4comn.h
@@ -94,6 +94,13 @@ typedef struct
emu_timer *timer[3];
UINT32 refresh_timer_base;
int dma_timer_active[4];
+ UINT32 dma_source[4];
+ UINT32 dma_destination[4];
+ UINT32 dma_count[4];
+ int dma_wordsize[4];
+ int dma_source_increment[4];
+ int dma_destination_increment[4];
+ int dma_mode[4];
int sh4_icount;
int is_slave;
diff --git a/src/emu/cpu/sh4/sh4regs.h b/src/emu/cpu/sh4/sh4regs.h
index b8c2233e3f9..e6c1aaa80c6 100644
--- a/src/emu/cpu/sh4/sh4regs.h
+++ b/src/emu/cpu/sh4/sh4regs.h
@@ -19,6 +19,7 @@
#define PTEA 0x200D /* FF000034 */
#define QACR0 0x200E /* FF000038 */
#define QACR1 0x200F /* FF00003C */
+#define PRR 0x2011 /* FF000044 */
#define BARA 0x2400 /* FF200000 */
#define BAMRA 0x2401 /* FF200004 */
#define BBRA 0x2402 /* FF200008 */
@@ -157,4 +158,47 @@
#define SDINT 0x3E05 /* FFF00014 */
#define SIZEREGS 15878
+/* bit definitions */
+#define CHCR_SSA 0xe0000000
+#define CHCR_STC 0x10000000
+#define CHCR_DSA 0x0e000000
+#define CHCR_DTC 0x01000000
+#define CHCR_DS 0x00080000
+#define CHCR_RL 0x00040000
+#define CHCR_AM 0x00020000
+#define CHCR_AL 0x00010000
+#define CHCR_DM 0x0000c000
+#define CHCR_SM 0x00003000
+#define CHCR_RS 0x00000f00
+#define CHCR_TM 0x00000080
+#define CHCR_TS 0x00000070
+#define CHCR_IE 0x00000004
+#define CHCR_TE 0x00000002
+#define CHCR_DE 0x00000001
+
+#define DMAOR_DDT 0x8000
+#define DMAOR_PR 0x0300
+#define DMAOR_COD 0x0010
+#define DMAOR_AE 0x0004
+#define DMAOR_NMIF 0x0002
+#define DMAOR_DME 0x0001
+
+#define MMUCR_LRUI 0xfc000000
+#define MMUCR_URB 0x00fc0000
+#define MMUCR_URC 0x0000fc00
+#define MMUCR_SQMD 0x00000200
+#define MMUCR_SV 0x00000100
+#define MMUCR_TI 0x00000004
+#define MMUCR_AT 0x00000001
+
+/* constants */
+#define PVR_SH7091 0x040205c1
+#define PVR_SH7750 0x04020500 // from TN-SH7-361B/E
+#define PVR_SH7750S 0x04020600
+#define PVR_SH7750R 0x04050000
+#define PRR_SH7750R 0x00000100
+#define PVR_SH7751 0x04110000
+#define PVR_SH7751R 0x04050000
+#define PRR_SH7751R 0x00000110
+
#endif /* __SH4REGS_H__ */
diff --git a/src/mame/drivers/atvtrack.c b/src/mame/drivers/atvtrack.c
index 70decf11f3e..e8729ff0680 100644
--- a/src/mame/drivers/atvtrack.c
+++ b/src/mame/drivers/atvtrack.c
@@ -50,15 +50,21 @@ Notes:
L4955 - ST Microelectronics L4955 low-power, quad channel, 8-bit buffered voltage output DAC and amplifier
7LB176 - Texas Instruments 7LB176 Differential Bus Tranceiver (SOIC8)
385-1 - National LM385 Adjustable Micropower Voltage Reference Diode (SOIC8)
- CN1 - Multi-pin connector for filter board (input power & controls connectors etc)
- DB9 - Video output connector (for twin monitors)
+ CN1 - Multi-pin connector for filter board (input, video, power & controls connectors etc)
+ DB9 - Probably used for cabinet linking
SW3 - Push button switch
*/
#include "emu.h"
#include "cpu/sh4/sh4.h"
+#include "debugger.h"
+const memory_region *nandregion;
+int nandcommand[4], nandoffset[4], nandaddressstep, nandaddress[4];
+UINT32 area1_data[4];
+
+//#define SPECIALMODE 1 // Alternate code path
class atvtrack_state : public driver_device
{
@@ -68,6 +74,232 @@ public:
};
+static void logbinary(UINT32 data,int high=31,int low=0)
+{
+ UINT32 s;
+ int z;
+
+ s=1 << high;
+ for (z = high;z >= low;z--) {
+ if (data & s)
+ logerror("1");
+ else
+ logerror("0");
+ s=s >> 1;
+ }
+}
+
+static inline UINT32 decode64_32(offs_t offset64, UINT64 data, UINT64 mem_mask, offs_t &offset32)
+{
+ if (ACCESSING_BITS_0_31) {
+ offset32 = offset64 << 1;
+ return (UINT32)data;
+ }
+ if (ACCESSING_BITS_32_63) {
+ offset32 = (offset64 << 1)+1;
+ return (UINT32)(data >> 32);
+ }
+ logerror("Wrong word size in external access\n");
+ //debugger_break(NULL);
+ return 0;
+}
+
+static READ64_HANDLER( area1_r )
+{
+ UINT32 addr;
+
+ addr = 0;
+ decode64_32(offset, 0, mem_mask, addr);
+ if (addr == (0x00020000-0x00020000)/4)
+ return -1;
+ else if (addr == (0x00020004-0x00020000)/4)
+ return -1;
+ return -1;
+}
+
+static WRITE64_HANDLER( area1_w )
+{
+ UINT32 addr, dat, old;
+
+ addr = 0;
+ dat = decode64_32(offset, data, mem_mask, addr);
+ old = area1_data[addr];
+ area1_data[addr] = dat;
+ if (addr == (0x00020000-0x00020000)/4) {
+ if (data & 4) {
+ device_execute_interface *exec = dynamic_cast<device_execute_interface *>(space->machine().device("subcpu"));
+ exec->set_input_line(INPUT_LINE_RESET, CLEAR_LINE);
+ }
+ }
+ logerror("Write %08x at %08x ",dat, 0x20000+addr*4+0);
+ logbinary(dat);
+ logerror("\n");
+}
+
+static READ64_HANDLER( area2_r )
+{
+ UINT32 addr, dat;
+ int c;
+
+ addr = 0;
+ dat = decode64_32(offset, 0, mem_mask, addr);
+ if (addr == 0) {
+ dat = 0;
+ for (c = 3;c >= 0;c--) {
+ if (nandcommand[c] <= 0x50) {
+ addr = nandaddress[c]+nandoffset[c];
+ dat = (dat << 8) | nandregion->u8(addr+c);
+ nandoffset[c] += 4;
+ } else
+ dat = (dat << 8) | 0xc0;
+ }
+ return dat;
+ } else
+ ;
+ return 0;
+}
+
+static WRITE64_HANDLER( area2_w )
+{
+ UINT32 addr, dat;
+
+ addr = 0;
+ dat = decode64_32(offset, data, mem_mask, addr);
+ if (addr == 0)
+ ;
+ else
+ ;
+}
+
+static READ64_HANDLER( area3_r )
+{
+ UINT32 addr, dat;
+
+ addr = 0;
+ dat = decode64_32(offset, 0, mem_mask, addr);
+ if (addr == 0)
+ ;
+ else
+ ;
+ return 0;
+}
+
+static WRITE64_HANDLER( area3_w )
+{
+ UINT32 addr, dat;
+ int c;
+
+ addr = 0;
+ dat = decode64_32(offset, data, mem_mask, addr);
+ if (addr == 0) {
+ for (c = 0;c < 4;c++) {
+ nandcommand[c] = data & 0xff;
+ if (nandcommand[c] == 0x00) {
+ nandoffset[c] = 0;
+ } else if (nandcommand[c] == 0x01) {
+ nandoffset[c] = 256*4;
+ } else if (nandcommand[c] == 0x50) {
+ nandoffset[c] = 512*4;
+ } else if (nandcommand[c] == 0x90) {
+ } else if (nandcommand[c] == 0xff) {
+ } else if (nandcommand[c] == 0x80) {
+ } else if (nandcommand[c] == 0x60) {
+ } else if (nandcommand[c] == 0x70) {
+ } else if (nandcommand[c] == 0x10) {
+ } else if (nandcommand[c] == 0xd0) {
+ } else {
+ nandcommand[c] = 0xff;
+ }
+ data=data >> 8;
+ }
+ nandaddressstep = 0;
+ } else
+ ;
+}
+
+static READ64_HANDLER( area4_r )
+{
+ UINT32 addr, dat;
+
+ addr = 0;
+ dat = decode64_32(offset, 0, mem_mask, addr);
+ if (addr == 0)
+ ;
+ else
+ ;
+ return 0;
+}
+
+static WRITE64_HANDLER( area4_w )
+{
+ UINT32 addr, dat;
+ int c;
+
+ addr = 0;
+ dat = decode64_32(offset, data, mem_mask, addr);
+ if (addr == 0) {
+ for (c = 0;c < 4;c++) {
+ if (nandaddressstep == 0) {
+ nandaddress[c] = (data & 0xff)*4;
+ } else if (nandaddressstep == 1) {
+ nandaddress[c] = nandaddress[c]+(data & 0xff)*0x840;
+ } else if (nandaddressstep == 2) {
+ nandaddress[c] = nandaddress[c]+(data & 0xff)*0x84000;
+ }
+ data = data >> 8;
+ }
+ nandaddressstep++;
+ } else
+ ;
+}
+
+static READ64_HANDLER( ioport_r )
+{
+ if (offset == SH4_IOPORT_16/8) {
+ // much simplified way
+ if (strcmp(space->device().tag(), "maincpu") == 0)
+#ifndef SPECIALMODE
+ return -1; // normal
+#else
+ return 0; // testing
+#endif
+ else
+ return 0; // unknown
+ }
+ return 0;
+}
+
+static WRITE64_HANDLER( ioport_w )
+{
+#ifdef SPECIALMODE
+ UINT64 d;
+ static int cnt=0;
+ sh4_device_dma dm;
+#endif
+
+ if (offset == SH4_IOPORT_16/8) {
+ logerror("SH4 16bit i/o port write ");
+ logbinary((UINT32)data,15,0);
+ logerror("\n");
+ }
+#ifdef SPECIALMODE
+ if (offset == SH4_IOPORT_DMA/8) {
+ dm.buffer = &d;
+ dm.channel = data & 0xffff;
+ dm.length = 1;
+ dm.size = 4;
+ if (cnt == 0)
+ d=0x12340153;
+ else
+ d=0x11223344;
+ if (cnt == 0)
+ sh4_dma_data(space->cpu,&dm);
+ else
+ sh4_dma_data(space->cpu,&dm);
+ cnt++;
+ }
+#endif
+}
VIDEO_START(atvtrack)
{
@@ -78,11 +310,57 @@ SCREEN_UPDATE(atvtrack)
return 0;
}
-static ADDRESS_MAP_START( atvtrack_map, AS_PROGRAM, 64 )
- AM_RANGE(0x00000000, 0x001fffff) AM_ROM AM_REGION("maincpu", 0)
+static MACHINE_START(atvtrack)
+{
+ UINT8 *src, *dst;
+ address_space *as;
+
+ nandaddressstep = 0;
+ nandregion = machine.region("maincpu");
+ as = machine.device("maincpu")->memory().space(AS_PROGRAM);
+ dst = (UINT8 *)(as->get_write_ptr(0x0c7f0000));
+ src = nandregion->base()+0x10;
+ // copy 0x10000 bytes from region "maincpu" offset 0x10 to 0x0c7f0000
+ memcpy(dst, src, 0x10000);
+}
+
+static MACHINE_RESET(atvtrack)
+{
+ address_space *as;
+
+ // Probably just after reset the cpu executes some bootsrtap routine from a memory inside the fpga.
+ // The routine initializes the cpu, copies the boot program from the flash memories into the cpu sdram
+ // and finally executes it.
+ // Here there is the setup of the cpu, the boot program is copied in machine_start
+ as = machine.device("maincpu")->memory().space(AS_PROGRAM);
+ // set cpu PC register to 0x0c7f0000
+ cpu_set_reg(machine.device("maincpu"), STATE_GENPC, 0x0c7f0000);
+ // set BCR2 to 1
+ sh4_internal_w(as, 0x3001, 1, 0xffffffff);
+ device_execute_interface *exec = dynamic_cast<device_execute_interface *>(machine.device("subcpu"));
+ exec->set_input_line(INPUT_LINE_RESET, ASSERT_LINE);
+}
+
+static ADDRESS_MAP_START( atvtrack_main_map, AS_PROGRAM, 64 )
+ AM_RANGE(0x00000000, 0x000003ff) AM_RAM AM_SHARE("sharedmem")
+ AM_RANGE(0x00020000, 0x00020007) AM_READWRITE(area1_r, area1_w)
+ AM_RANGE(0x14000000, 0x14000007) AM_READWRITE(area2_r, area2_w) // data
+ AM_RANGE(0x14100000, 0x14100007) AM_READWRITE(area3_r, area3_w) // command
+ AM_RANGE(0x14200000, 0x14200007) AM_READWRITE(area4_r, area4_w) // address
+ AM_RANGE(0x0c000000, 0x0cffffff) AM_RAM
+ADDRESS_MAP_END
+
+static ADDRESS_MAP_START( atvtrack_main_port, AS_IO, 64 )
+ AM_RANGE(0x00, 0x1f) AM_READWRITE(ioport_r, ioport_w)
+ADDRESS_MAP_END
+
+static ADDRESS_MAP_START( atvtrack_sub_map, AS_PROGRAM, 64 )
+ AM_RANGE(0x00000000, 0x000003ff) AM_RAM AM_SHARE("sharedmem")
+ AM_RANGE(0x0c000000, 0x0cffffff) AM_RAM
ADDRESS_MAP_END
-static ADDRESS_MAP_START( atvtrack_port, AS_IO, 64 )
+static ADDRESS_MAP_START( atvtrack_sub_port, AS_IO, 64 )
+ /*AM_RANGE(0x00, 0x1f) AM_READWRITE(ioport_r, ioport_w) */
ADDRESS_MAP_END
@@ -98,14 +376,13 @@ static MACHINE_CONFIG_START( atvtrack, atvtrack_state )
/* basic machine hardware */
MCFG_CPU_ADD("maincpu", SH4, ATV_CPU_CLOCK)
MCFG_CPU_CONFIG(sh4cpu_config)
- MCFG_CPU_PROGRAM_MAP(atvtrack_map)
- MCFG_CPU_IO_MAP(atvtrack_port)
+ MCFG_CPU_PROGRAM_MAP(atvtrack_main_map)
+ MCFG_CPU_IO_MAP(atvtrack_main_port)
MCFG_CPU_ADD("subcpu", SH4, ATV_CPU_CLOCK)
MCFG_CPU_CONFIG(sh4cpu_config)
- MCFG_CPU_PROGRAM_MAP(atvtrack_map)
- MCFG_CPU_IO_MAP(atvtrack_port)
- MCFG_DEVICE_DISABLE()
+ MCFG_CPU_PROGRAM_MAP(atvtrack_sub_map)
+ MCFG_CPU_IO_MAP(atvtrack_sub_port)
/* video hardware */
MCFG_SCREEN_ADD("screen", RASTER)
@@ -118,6 +395,8 @@ static MACHINE_CONFIG_START( atvtrack, atvtrack_state )
MCFG_PALETTE_LENGTH(0x1000)
+ MCFG_MACHINE_RESET(atvtrack)
+ MCFG_MACHINE_START(atvtrack)
MCFG_VIDEO_START(atvtrack)
MACHINE_CONFIG_END
@@ -129,7 +408,7 @@ ROM_START( atvtrack )
ROM_LOAD32_BYTE("19.bin", 0x0000003, 0x1080000, CRC(9fc5c579) SHA1(8829329ef229564952aea2108ef1750dc226cbac) )
ROM_REGION( 0x20000, "eeprom", ROMREGION_ERASEFF)
- ROM_LOAD("epc1pc8.ic23", 0x0000000, 0x1ff01, CRC(752444c7) SHA1(c77e8fcfcbe15b53eda25553763bdac45f0ef7df) ) // contains a large amount of data, maybe used for some form of protection
+ ROM_LOAD("epc1pc8.ic23", 0x0000000, 0x1ff01, CRC(752444c7) SHA1(c77e8fcfcbe15b53eda25553763bdac45f0ef7df) ) // contains configuration data for the fpga, maybe used for some form of protection
ROM_END
ROM_START( atvtracka )
diff --git a/src/mame/drivers/chihiro.c b/src/mame/drivers/chihiro.c
index 0722120bf3a..3c17a9cc015 100644
--- a/src/mame/drivers/chihiro.c
+++ b/src/mame/drivers/chihiro.c
@@ -661,7 +661,7 @@ static MACHINE_CONFIG_START( chihiro_base, driver_device )
MACHINE_CONFIG_END
static MACHINE_CONFIG_DERIVED( chihirogd, chihiro_base )
- MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", "user1", "picreturn")
+ MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", NULL, 512, "picreturn")
MACHINE_CONFIG_END
#define ROM_LOAD16_WORD_SWAP_BIOS(bios,name,offset,length,hash) \
diff --git a/src/mame/drivers/naomi.c b/src/mame/drivers/naomi.c
index 4bb404af9d8..b59a3595e80 100644
--- a/src/mame/drivers/naomi.c
+++ b/src/mame/drivers/naomi.c
@@ -2545,7 +2545,7 @@ static MACHINE_CONFIG_DERIVED( naomigd, naomi_base )
MCFG_SEGA_837_13551_DEVICE_ADD("837_13551", "mie", "TILT", "P1", "P2", "A0", "A1", "A2", "A3", "A4", "A5", "A6", "A7", "OUTPUT")
MCFG_EEPROM_93C46_8BIT_ADD("mie_eeprom")
- MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", "user1", "picreturn")
+ MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", NULL, 512, "picreturn")
MCFG_X76F100_ADD("naomibd_eeprom")
MACHINE_CONFIG_END
diff --git a/src/mame/drivers/triforce.c b/src/mame/drivers/triforce.c
index 22b57eb525c..db59d487b3e 100644
--- a/src/mame/drivers/triforce.c
+++ b/src/mame/drivers/triforce.c
@@ -443,7 +443,7 @@ static MACHINE_CONFIG_START( triforce_base, driver_device )
MACHINE_CONFIG_END
static MACHINE_CONFIG_DERIVED( triforcegd, triforce_base )
- MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", "user1", "picreturn")
+ MCFG_NAOMI_DIMM_BOARD_ADD("rom_board", "gdrom", NULL, 256, "picreturn")
MACHINE_CONFIG_END
#define ROM_LOAD16_WORD_SWAP_BIOS(bios,name,offset,length,hash) \
diff --git a/src/mame/includes/naomibd.h b/src/mame/includes/naomibd.h
index dcfc20389c5..3ad71fc2d00 100644
--- a/src/mame/includes/naomibd.h
+++ b/src/mame/includes/naomibd.h
@@ -26,16 +26,17 @@ enum
TYPE DEFINITIONS
***************************************************************************/
-typedef void (*naomibd_interrupt_func)(device_t *device, int state);
+typedef void (*naomibd_signal_func)(device_t *device, int signal, int state);
typedef struct _naomibd_config naomibd_config;
struct _naomibd_config
{
int type;
+ int size;
const char * regiontag;
const char * gdromregiontag;
const char * picregiontag;
- naomibd_interrupt_func interrupt;
+ naomibd_signal_func signal;
};
@@ -56,10 +57,11 @@ struct _naomibd_config
MCFG_NAOMIBD_ADD(_tag, AW_ROM_BOARD) \
MCFG_NAOMIBD_REGION(_region)
-#define MCFG_NAOMI_DIMM_BOARD_ADD(_tag, _gdrom, _region, _pic) \
+#define MCFG_NAOMI_DIMM_BOARD_ADD(_tag, _gdrom, _callback, _sizemb, _pic) \
MCFG_NAOMIBD_ADD(_tag, DIMM_BOARD) \
- MCFG_NAOMIBD_REGION(_region) \
+ MCFG_DEVICE_CONFIG_DATAPTR(naomibd_config, signal, _callback) \
MCFG_NAOMIBD_GDROM_REGION(_gdrom) \
+ MCFG_NAOMIBD_SIZE(_sizemb) \
MCFG_NAOMIBD_PIC_REGION(_pic)
#define MCFG_NAOMIBD_REGION(_region) \
@@ -71,6 +73,9 @@ struct _naomibd_config
#define MCFG_NAOMIBD_PIC_REGION(_region) \
MCFG_DEVICE_CONFIG_DATAPTR(naomibd_config, picregiontag, _region)
+#define MCFG_NAOMIBD_SIZE(_sizemb) \
+ MCFG_DEVICE_CONFIG_DATA32(naomibd_config, size, _sizemb)
+
#define MCFG_NAOMIBD_MODIFY(_tag) \
MCFG_DEVICE_MODIFY(_tag)
@@ -84,7 +89,6 @@ struct _naomibd_config
FUNCTION PROTOTYPES
***************************************************************************/
-int naomibd_interrupt_callback(device_t *device, naomibd_interrupt_func callback);
int naomibd_get_type(device_t *device);
void *naomibd_get_memory(device_t *device, UINT32 length);
offs_t naomibd_get_dmaoffset(device_t *device);
diff --git a/src/mame/machine/naomibd.c b/src/mame/machine/naomibd.c
index f87ee50455d..6cdf1ad5f14 100644
--- a/src/mame/machine/naomibd.c
+++ b/src/mame/machine/naomibd.c
@@ -238,7 +238,9 @@ struct _naomibd_state
UINT8 * memory;
chd_file * gdromchd;
+ cdrom_file * gdrom;
UINT8 * picdata;
+ UINT32 size; /* size of installed dimm memory */
UINT32 rom_offset, rom_offset_flags, dma_count;
UINT32 dma_offset, dma_offset_flags;
UINT32 prot_offset, prot_key;
@@ -351,11 +353,14 @@ INLINE naomibd_state *get_safe_token(device_t *device)
*
*************************************/
-int naomibd_interrupt_callback(device_t *device, naomibd_interrupt_func callback)
+// send interrupt to host system
+void output_interrupt(naomibd_state *st, int state)
{
- naomibd_config *config = (naomibd_config *)downcast<const legacy_device_base *>(device)->inline_config();
- config->interrupt = callback;
- return 0;
+ naomibd_config *config = (naomibd_config *)downcast<const legacy_device_base *>(st->device)->inline_config();
+
+ /* send out an interrupt */
+ if (config->signal != NULL)
+ (*config->signal)(st->device, 0, state); // 0: this signal is an interrupt
}
int naomibd_get_type(device_t *device)
@@ -1438,6 +1443,8 @@ static void load_rom_gdrom(running_machine& machine, naomibd_state *v)
}
if (start != 0)
{
+ // check for size
+ assert(size <= v->size);
// read encrypted data into memory
ptr = v->memory;
sectors = (size+2047)/2048;
@@ -2093,7 +2100,9 @@ static DEVICE_START( naomibd )
break;
case DIMM_BOARD:
- v->memory = (UINT8 *)auto_alloc_array_clear(device->machine(), UINT8, 0x40000000/4); // 0x40000000 is needed for some Chihiro sets, Naomi should be less, we should pass as device param
+ assert((config->size >= 256) && !(config->size & 255)); // size multiple of 256 megabytes ?
+ v->size = config->size << 20;
+ v->memory = (UINT8 *)auto_alloc_array_clear(device->machine(), UINT8, v->size); // 0x40000000 is needed for some Chihiro sets, Naomi should be less
v->gdromchd = get_disk_handle(device->machine(), config->gdromregiontag);
v->picdata = (UINT8 *)device->machine().region(config->picregiontag)->base();
if (v->memory != NULL && v->gdromchd != NULL && v->picdata != NULL)
diff --git a/src/tools/unidasm.c b/src/tools/unidasm.c
index d48591d5ebc..b56a668c5ff 100644
--- a/src/tools/unidasm.c
+++ b/src/tools/unidasm.c
@@ -83,6 +83,8 @@ struct _options
UINT8 flipped;
int mode;
const dasm_table_entry *dasm;
+ UINT32 skip;
+ UINT32 count;
};
@@ -356,6 +358,8 @@ static int parse_options(int argc, char *argv[], options *opts)
int pending_base = FALSE;
int pending_arch = FALSE;
int pending_mode = FALSE;
+ int pending_skip = FALSE;
+ int pending_count = FALSE;
int curarch;
int numrows;
int arg;
@@ -370,7 +374,7 @@ static int parse_options(int argc, char *argv[], options *opts)
// is it a switch?
if (curarg[0] == '-')
{
- if (pending_base || pending_arch || pending_mode)
+ if (pending_base || pending_arch || pending_mode || pending_skip || pending_count)
goto usage;
if (tolower((UINT8)curarg[1]) == 'a')
@@ -383,6 +387,10 @@ static int parse_options(int argc, char *argv[], options *opts)
opts->lower = TRUE;
else if (tolower((UINT8)curarg[1]) == 'm')
pending_mode = TRUE;
+ else if (tolower((UINT8)curarg[1]) == 's')
+ pending_skip = TRUE;
+ else if (tolower((UINT8)curarg[1]) == 'c')
+ pending_count = TRUE;
else if (tolower((UINT8)curarg[1]) == 'n')
opts->norawbytes = TRUE;
else if (tolower((UINT8)curarg[1]) == 'u')
@@ -426,6 +434,22 @@ static int parse_options(int argc, char *argv[], options *opts)
pending_arch = FALSE;
}
+ // skip bytes
+ else if (pending_skip)
+ {
+ if (sscanf(curarg, "%d", &opts->skip) != 1)
+ goto usage;
+ pending_skip = FALSE;
+ }
+
+ // size
+ else if (pending_count)
+ {
+ if (sscanf(curarg, "%d", &opts->count) != 1)
+ goto usage;
+ pending_count = FALSE;
+ }
+
// filename
else if (opts->filename == NULL)
opts->filename = curarg;
@@ -436,7 +460,7 @@ static int parse_options(int argc, char *argv[], options *opts)
}
// if we have a dangling option, error
- if (pending_base || pending_arch || pending_mode)
+ if (pending_base || pending_arch || pending_mode || pending_skip || pending_count)
goto usage;
// if no file or no architecture, fail
@@ -447,6 +471,7 @@ static int parse_options(int argc, char *argv[], options *opts)
usage:
printf("Usage: %s <filename> -arch <architecture> [-basepc <pc>] \n", argv[0]);
printf(" [-mode <n>] [-norawbytes] [-flipped] [-upper] [-lower]\n");
+ printf(" [-skip <n>] [-count <n>]\n");
printf("\n");
printf("Supported architectures:");
numrows = (ARRAY_LENGTH(dasm_table) + 6) / 7;
@@ -504,10 +529,14 @@ int main(int argc, char *argv[])
// run it
try
{
+ if (length > opts.skip)
+ length = length - opts.skip;
+ if ((length > opts.count) && (opts.count != 0))
+ length = opts.count;
curpc = opts.basepc;
for (curbyte = 0; curbyte < length; curbyte += numbytes)
{
- UINT8 *oprom = (UINT8 *)data + curbyte;
+ UINT8 *oprom = (UINT8 *)data + opts.skip + curbyte;
char buffer[1024];
UINT32 pcdelta;
int numchunks;