summaryrefslogtreecommitdiffstatshomepage
path: root/src/mame/drivers/vii.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/mame/drivers/vii.cpp')
-rw-r--r--src/mame/drivers/vii.cpp1323
1 files changed, 701 insertions, 622 deletions
diff --git a/src/mame/drivers/vii.cpp b/src/mame/drivers/vii.cpp
index 0e870df1a55..963ddf6e506 100644
--- a/src/mame/drivers/vii.cpp
+++ b/src/mame/drivers/vii.cpp
@@ -27,6 +27,7 @@
Known u'nSP-Based Systems:
+ D - SPG240 - Radica Skateboarder (Sunplus QL8041C die)
ND - SPG243 - Some form of Leapfrog "edutainment" system
ND - SPG243 - Star Wars: Clone Wars
ND - SPG243 - Toy Story
@@ -101,25 +102,22 @@ Detailed list of bugs:
#define TILE_X_FLIP 0x0004
#define TILE_Y_FLIP 0x0008
-class vii_state : public driver_device
+class spg2xx_game_state : public driver_device
{
public:
- vii_state(const machine_config &mconfig, device_type type, const char *tag)
+ spg2xx_game_state(const machine_config &mconfig, device_type type, const char *tag)
: driver_device(mconfig, type, tag),
m_maincpu(*this, "maincpu"),
- m_cart(*this, "cartslot"),
m_p_ram(*this, "p_ram"),
m_p_rowscroll(*this, "p_rowscroll"),
m_p_palette(*this, "p_palette"),
m_p_spriteram(*this, "p_spriteram"),
- m_bank(*this, "cart"),
- m_bios_rom(*this, "bios"),
m_io_p1(*this, "P1"),
- m_io_p2(*this, "P2")
+ m_io_p2(*this, "P2"),
+ m_io_p3(*this, "P3"),
+ m_bank(*this, "cart")
{ }
- required_device<cpu_device> m_maincpu;
- optional_device<generic_slot_device> m_cart;
DECLARE_READ16_MEMBER(video_r);
DECLARE_WRITE16_MEMBER(video_w);
DECLARE_READ16_MEMBER(audio_r);
@@ -127,104 +125,132 @@ public:
DECLARE_READ16_MEMBER(io_r);
DECLARE_WRITE16_MEMBER(io_w);
DECLARE_READ16_MEMBER(rom_r);
- required_shared_ptr<uint16_t> m_p_ram;
- required_shared_ptr<uint16_t> m_p_rowscroll;
- required_shared_ptr<uint16_t> m_p_palette;
- required_shared_ptr<uint16_t> m_p_spriteram;
- required_memory_bank m_bank;
+
+ DECLARE_DRIVER_INIT(walle);
+ DECLARE_DRIVER_INIT(batman);
+ DECLARE_DRIVER_INIT(wirels60);
+ DECLARE_DRIVER_INIT(rad_skat);
+
+ uint32_t screen_update_vii(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect);
+
+ INTERRUPT_GEN_MEMBER(vii_vblank);
+
+ TIMER_CALLBACK_MEMBER(tmb1_tick);
+ TIMER_CALLBACK_MEMBER(tmb2_tick);
+
+ void spg2xx_base(machine_config &config);
+ void spg2xx_basep(machine_config &config);
+ void batman(machine_config &config);
+protected:
+ virtual void machine_start() override;
+ virtual void machine_reset() override;
+ virtual void video_start() override;
+
+ void switch_bank(uint32_t bank);
+ uint32_t m_centered_coordinates; // this must be a vreg?
+ void test_centered(uint8_t *ROM);
+
+ typedef delegate<uint16_t(uint16_t, int)> vii_io_rw_delegate;
+ vii_io_rw_delegate m_vii_io_rw;
+private:
+
+ uint16_t do_spg240_rad_skat_io(uint16_t what, int index);
+ uint16_t do_spg243_batman_io(uint16_t what, int index);
+ uint16_t do_spg243_wireless60_io(uint16_t what, int index);
uint32_t m_current_bank;
uint16_t m_video_regs[0x100];
- uint32_t m_centered_coordinates;
- void test_centered(uint8_t *ROM);
struct
{
uint8_t r, g, b;
}
- m_screenram[320*240];
+ m_screenram[320 * 240];
uint16_t m_io_regs[0x200];
uint16_t m_uart_rx_count;
uint8_t m_controller_input[8];
uint8_t m_w60_controller_input;
- uint32_t m_spg243_mode;
emu_timer *m_tmb1;
emu_timer *m_tmb2;
void do_dma(uint32_t len);
void do_gpio(uint32_t offset);
- void switch_bank(uint32_t bank);
void do_i2c();
void spg_do_dma(uint32_t len);
- DECLARE_DRIVER_INIT(vsmile);
- DECLARE_DRIVER_INIT(walle);
- DECLARE_DRIVER_INIT(vii);
- DECLARE_DRIVER_INIT(batman);
- DECLARE_DRIVER_INIT(wirels60);
- virtual void machine_start() override;
- virtual void machine_reset() override;
- virtual void video_start() override;
- uint32_t screen_update_vii(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect);
- INTERRUPT_GEN_MEMBER(vii_vblank);
- TIMER_CALLBACK_MEMBER(tmb1_tick);
- TIMER_CALLBACK_MEMBER(tmb2_tick);
- DECLARE_DEVICE_IMAGE_LOAD_MEMBER(vii_cart);
- DECLARE_DEVICE_IMAGE_LOAD_MEMBER(vsmile_cart);
-
- void vii(machine_config &config);
- void vsmile(machine_config &config);
- void wirels60(machine_config &config);
- void batman(machine_config &config);
-protected:
- optional_memory_region m_bios_rom;
- required_ioport m_io_p1;
- optional_ioport m_io_p2;
-
- memory_region *m_cart_rom;
void blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t xoff, uint32_t yoff, uint32_t attr, uint32_t ctrl, uint32_t bitmap_addr, uint16_t tile);
void blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t bitmap_addr, uint16_t *regs);
void blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t base_addr);
void blit_sprites(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth);
- inline void verboselog(int n_level, const char *s_fmt, ...) ATTR_PRINTF(3,4);
+ inline void verboselog(int n_level, const char *s_fmt, ...) ATTR_PRINTF(3, 4);
inline uint8_t expand_rgb5_to_rgb8(uint8_t val);
inline uint8_t mix_channel(uint8_t a, uint8_t b);
void mix_pixel(uint32_t offset, uint16_t rgb);
void set_pixel(uint32_t offset, uint16_t rgb);
+
+ // devices
+
+ required_device<cpu_device> m_maincpu;
+ required_shared_ptr<uint16_t> m_p_ram;
+ required_shared_ptr<uint16_t> m_p_rowscroll;
+ required_shared_ptr<uint16_t> m_p_palette;
+ required_shared_ptr<uint16_t> m_p_spriteram;
+ required_ioport m_io_p1;
+ optional_ioport m_io_p2;
+ optional_ioport m_io_p3;
+protected:
+ required_memory_bank m_bank;
};
-enum
+
+class spg2xx_cart_state : public spg2xx_game_state
{
- SPG243_VII = 0,
- SPG243_BATMAN,
- SPG243_VSMILE,
- SPG243_WIRELESS60,
+public:
+ spg2xx_cart_state(const machine_config &mconfig, device_type type, const char *tag)
+ : spg2xx_game_state(mconfig, type, tag),
+ m_cart(*this, "cartslot")
+ { }
- SPG243_MODEL_COUNT
-};
+ DECLARE_DRIVER_INIT(vii);
+ DECLARE_DRIVER_INIT(vsmile);
+
+ uint16_t do_spg243_vsmile_io(uint16_t what, int index);
+ uint16_t do_spg243_vii_io(uint16_t what, int index);
+
+ DECLARE_DEVICE_IMAGE_LOAD_MEMBER(vii_cart);
+ DECLARE_DEVICE_IMAGE_LOAD_MEMBER(vsmile_cart);
+
+ void vii(machine_config &config);
+ void vsmile(machine_config &config);
+protected:
+ virtual void machine_start() override;
+
+private:
+ optional_device<generic_slot_device> m_cart;
+ memory_region *m_cart_rom;
+};
#define VII_CTLR_IRQ_ENABLE m_io_regs[0x21]
#define VII_VIDEO_IRQ_ENABLE m_video_regs[0x62]
#define VII_VIDEO_IRQ_STATUS m_video_regs[0x63]
-
#define VERBOSE_LEVEL (3)
#define ENABLE_VERBOSE_LOG (1)
-inline void vii_state::verboselog(int n_level, const char *s_fmt, ...)
+inline void spg2xx_game_state::verboselog(int n_level, const char *s_fmt, ...)
{
#if ENABLE_VERBOSE_LOG
- if( VERBOSE_LEVEL >= n_level )
+ if (VERBOSE_LEVEL >= n_level)
{
va_list v;
- char buf[ 32768 ];
- va_start( v, s_fmt );
- vsprintf( buf, s_fmt, v );
- va_end( v );
+ char buf[32768];
+ va_start(v, s_fmt);
+ vsprintf(buf, s_fmt, v);
+ va_end(v);
}
#endif
}
@@ -233,38 +259,38 @@ inline void vii_state::verboselog(int n_level, const char *s_fmt, ...)
* Video Hardware *
*************************/
-void vii_state::video_start()
+void spg2xx_game_state::video_start()
{
}
-inline uint8_t vii_state::expand_rgb5_to_rgb8(uint8_t val)
+inline uint8_t spg2xx_game_state::expand_rgb5_to_rgb8(uint8_t val)
{
uint8_t temp = val & 0x1f;
return (temp << 3) | (temp >> 2);
}
// Perform a lerp between a and b
-inline uint8_t vii_state::mix_channel(uint8_t a, uint8_t b)
+inline uint8_t spg2xx_game_state::mix_channel(uint8_t a, uint8_t b)
{
uint8_t alpha = m_video_regs[0x1c] & 0x00ff;
return ((64 - alpha) * a + alpha * b) / 64;
}
-void vii_state::mix_pixel(uint32_t offset, uint16_t rgb)
+void spg2xx_game_state::mix_pixel(uint32_t offset, uint16_t rgb)
{
m_screenram[offset].r = mix_channel(m_screenram[offset].r, expand_rgb5_to_rgb8(rgb >> 10));
m_screenram[offset].g = mix_channel(m_screenram[offset].g, expand_rgb5_to_rgb8(rgb >> 5));
m_screenram[offset].b = mix_channel(m_screenram[offset].b, expand_rgb5_to_rgb8(rgb));
}
-void vii_state::set_pixel(uint32_t offset, uint16_t rgb)
+void spg2xx_game_state::set_pixel(uint32_t offset, uint16_t rgb)
{
m_screenram[offset].r = expand_rgb5_to_rgb8(rgb >> 10);
m_screenram[offset].g = expand_rgb5_to_rgb8(rgb >> 5);
m_screenram[offset].b = expand_rgb5_to_rgb8(rgb);
}
-void vii_state::blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t xoff, uint32_t yoff, uint32_t attr, uint32_t ctrl, uint32_t bitmap_addr, uint16_t tile)
+void spg2xx_game_state::blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t xoff, uint32_t yoff, uint32_t attr, uint32_t ctrl, uint32_t bitmap_addr, uint16_t tile)
{
address_space &space = m_maincpu->space(AS_PROGRAM);
@@ -280,23 +306,23 @@ void vii_state::blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t x
palette_offset >>= nc;
palette_offset <<= nc;
- uint32_t m = bitmap_addr + nc*w*h/16*tile;
+ uint32_t m = bitmap_addr + nc * w*h / 16 * tile;
uint32_t bits = 0;
uint32_t nbits = 0;
uint32_t x, y;
- for(y = 0; y < h; y++)
+ for (y = 0; y < h; y++)
{
uint32_t yy = (yoff + (y ^ yflipmask)) & 0x1ff;
- for(x = 0; x < w; x++)
+ for (x = 0; x < w; x++)
{
uint32_t xx = (xoff + (x ^ xflipmask)) & 0x1ff;
uint32_t pal;
bits <<= nc;
- if(nbits < nc)
+ if (nbits < nc)
{
uint16_t b = space.read_word(m++ & 0x3fffff);
b = (b << 8) | (b >> 8);
@@ -308,23 +334,23 @@ void vii_state::blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t x
pal = palette_offset | (bits >> 16);
bits &= 0xffff;
- if((ctrl & 0x0010) && yy < 240)
+ if ((ctrl & 0x0010) && yy < 240)
{
xx = (xx - (int16_t)m_p_rowscroll[yy]) & 0x01ff;
}
- if(xx < 320 && yy < 240)
+ if (xx < 320 && yy < 240)
{
uint16_t rgb = m_p_palette[pal];
- if(!(rgb & 0x8000))
+ if (!(rgb & 0x8000))
{
if (attr & 0x4000)
{
- mix_pixel(xx + 320*yy, rgb);
+ mix_pixel(xx + 320 * yy, rgb);
}
else
{
- set_pixel(xx + 320*yy, rgb);
+ set_pixel(xx + 320 * yy, rgb);
}
}
}
@@ -332,7 +358,7 @@ void vii_state::blit(bitmap_rgb32 &bitmap, const rectangle &cliprect, uint32_t x
}
}
-void vii_state::blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t bitmap_addr, uint16_t *regs)
+void spg2xx_game_state::blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t bitmap_addr, uint16_t *regs)
{
uint32_t x0, y0;
uint32_t xscroll = regs[0];
@@ -344,12 +370,12 @@ void vii_state::blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int d
uint32_t h, w, hn, wn;
address_space &space = m_maincpu->space(AS_PROGRAM);
- if(!(ctrl & PAGE_ENABLE_MASK))
+ if (!(ctrl & PAGE_ENABLE_MASK))
{
return;
}
- if(((attr & PAGE_DEPTH_FLAG_MASK) >> PAGE_DEPTH_FLAG_SHIFT) != depth)
+ if (((attr & PAGE_DEPTH_FLAG_MASK) >> PAGE_DEPTH_FLAG_SHIFT) != depth)
{
return;
}
@@ -360,21 +386,21 @@ void vii_state::blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int d
hn = 256 / h;
wn = 512 / w;
- for(y0 = 0; y0 < hn; y0++)
+ for (y0 = 0; y0 < hn; y0++)
{
- for(x0 = 0; x0 < wn; x0++)
+ for (x0 = 0; x0 < wn; x0++)
{
uint16_t tile = space.read_word(tilemap + x0 + wn * y0);
uint16_t palette = 0;
uint32_t xx, yy;
- if(!tile)
+ if (!tile)
{
continue;
}
palette = space.read_word(palette_map + (x0 + wn * y0) / 2);
- if(x0 & 1)
+ if (x0 & 1)
{
palette >>= 8;
}
@@ -401,7 +427,7 @@ void vii_state::blit_page(bitmap_rgb32 &bitmap, const rectangle &cliprect, int d
}
}
-void vii_state::blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t base_addr)
+void spg2xx_game_state::blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth, uint32_t base_addr)
{
address_space &space = m_maincpu->space(AS_PROGRAM);
uint16_t tile, attr;
@@ -414,17 +440,17 @@ void vii_state::blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int
y = space.read_word(base_addr + 2);
attr = space.read_word(base_addr + 3);
- if(!tile)
+ if (!tile)
{
return;
}
- if(((attr & PAGE_DEPTH_FLAG_MASK) >> PAGE_DEPTH_FLAG_SHIFT) != depth)
+ if (((attr & PAGE_DEPTH_FLAG_MASK) >> PAGE_DEPTH_FLAG_SHIFT) != depth)
{
return;
}
- if(m_centered_coordinates)
+ if (m_centered_coordinates)
{
x = 160 + x;
y = 120 - y;
@@ -432,8 +458,8 @@ void vii_state::blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int
h = 8 << ((attr & PAGE_TILE_HEIGHT_MASK) >> PAGE_TILE_HEIGHT_SHIFT);
w = 8 << ((attr & PAGE_TILE_WIDTH_MASK) >> PAGE_TILE_WIDTH_SHIFT);
- x -= (w/2);
- y -= (h/2) - 8;
+ x -= (w / 2);
+ y -= (h / 2) - 8;
}
x &= 0x01ff;
@@ -442,7 +468,7 @@ void vii_state::blit_sprite(bitmap_rgb32 &bitmap, const rectangle &cliprect, int
blit(bitmap, cliprect, x, y, attr, 0, bitmap_addr, tile);
}
-void vii_state::blit_sprites(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth)
+void spg2xx_game_state::blit_sprites(bitmap_rgb32 &bitmap, const rectangle &cliprect, int depth)
{
uint32_t n;
@@ -451,16 +477,16 @@ void vii_state::blit_sprites(bitmap_rgb32 &bitmap, const rectangle &cliprect, in
return;
}
- for(n = 0; n < 256; n++)
+ for (n = 0; n < 256; n++)
{
//if(space.read_word(0x2c00 + 4*n)
{
- blit_sprite(bitmap, cliprect, depth, 0x2c00 + 4*n);
+ blit_sprite(bitmap, cliprect, depth, 0x2c00 + 4 * n);
}
}
}
-uint32_t vii_state::screen_update_vii(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect)
+uint32_t spg2xx_game_state::screen_update_vii(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect)
{
int i, x, y;
@@ -468,18 +494,18 @@ uint32_t vii_state::screen_update_vii(screen_device &screen, bitmap_rgb32 &bitma
memset(m_screenram, 0, sizeof(m_screenram));
- for(i = 0; i < 4; i++)
+ for (i = 0; i < 4; i++)
{
blit_page(bitmap, cliprect, i, 0x40 * m_video_regs[0x20], m_video_regs + 0x10);
blit_page(bitmap, cliprect, i, 0x40 * m_video_regs[0x21], m_video_regs + 0x16);
blit_sprites(bitmap, cliprect, i);
}
- for(y = 0; y < 240; y++)
+ for (y = 0; y < 240; y++)
{
- for(x = 0; x < 320; x++)
+ for (x = 0; x < 320; x++)
{
- bitmap.pix32(y, x) = (m_screenram[x + 320*y].r << 16) | (m_screenram[x + 320*y].g << 8) | m_screenram[x + 320*y].b;
+ bitmap.pix32(y, x) = (m_screenram[x + 320 * y].r << 16) | (m_screenram[x + 320 * y].g << 8) | m_screenram[x + 320 * y].b;
}
}
@@ -490,117 +516,117 @@ uint32_t vii_state::screen_update_vii(screen_device &screen, bitmap_rgb32 &bitma
* Machine Hardware *
*************************/
-void vii_state::do_dma(uint32_t len)
+void spg2xx_game_state::do_dma(uint32_t len)
{
address_space &mem = m_maincpu->space(AS_PROGRAM);
uint32_t src = m_video_regs[0x70];
uint32_t dst = m_video_regs[0x71] + 0x2c00;
uint32_t j;
- for(j = 0; j < len; j++)
+ for (j = 0; j < len; j++)
{
- mem.write_word(dst+j, mem.read_word(src+j));
+ mem.write_word(dst + j, mem.read_word(src + j));
}
m_video_regs[0x72] = 0;
m_video_regs[0x63] |= 4;
}
-READ16_MEMBER( vii_state::video_r )
+READ16_MEMBER(spg2xx_game_state::video_r)
{
- switch(offset)
+ switch (offset)
{
- case 0x62: // Video IRQ Enable
- verboselog(0, "video_r: Video IRQ Enable: %04x\n", VII_VIDEO_IRQ_ENABLE);
- return VII_VIDEO_IRQ_ENABLE;
+ case 0x62: // Video IRQ Enable
+ verboselog(0, "video_r: Video IRQ Enable: %04x\n", VII_VIDEO_IRQ_ENABLE);
+ return VII_VIDEO_IRQ_ENABLE;
- case 0x63: // Video IRQ Status
- verboselog(0, "video_r: Video IRQ Status: %04x\n", VII_VIDEO_IRQ_STATUS);
- return VII_VIDEO_IRQ_STATUS;
+ case 0x63: // Video IRQ Status
+ verboselog(0, "video_r: Video IRQ Status: %04x\n", VII_VIDEO_IRQ_STATUS);
+ return VII_VIDEO_IRQ_STATUS;
- default:
- verboselog(0, "video_r: Unknown register %04x = %04x\n", 0x2800 + offset, m_video_regs[offset]);
- break;
+ default:
+ verboselog(0, "video_r: Unknown register %04x = %04x\n", 0x2800 + offset, m_video_regs[offset]);
+ break;
}
return m_video_regs[offset];
}
-WRITE16_MEMBER( vii_state::video_w )
+WRITE16_MEMBER(spg2xx_game_state::video_w)
{
- switch(offset)
+ switch (offset)
{
- case 0x10: case 0x16: // page 1,2 X scroll
- data &= 0x01ff;
- COMBINE_DATA(&m_video_regs[offset]);
- break;
-
- case 0x11: case 0x17: // page 1,2 Y scroll
- data &= 0x00ff;
- COMBINE_DATA(&m_video_regs[offset]);
- break;
- case 0x36: // IRQ pos V
- case 0x37: // IRQ pos H
- data &= 0x01ff;
- COMBINE_DATA(&m_video_regs[offset]);
- break;
- case 0x62: // Video IRQ Enable
- verboselog(0, "video_w: Video IRQ Enable = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&VII_VIDEO_IRQ_ENABLE);
- break;
-
- case 0x63: // Video IRQ Acknowledge
- verboselog(0, "video_w: Video IRQ Acknowledge = %04x (%04x)\n", data, mem_mask);
- VII_VIDEO_IRQ_STATUS &= ~data;
- if(!VII_VIDEO_IRQ_STATUS)
- {
- m_maincpu->set_input_line(UNSP_IRQ0_LINE, CLEAR_LINE);
- }
- break;
-
- case 0x70: // Video DMA Source
- verboselog(0, "video_w: Video DMA Source = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_video_regs[offset]);
- break;
-
- case 0x71: // Video DMA Dest
- verboselog(0, "video_w: Video DMA Dest = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_video_regs[offset]);
- break;
-
- case 0x72: // Video DMA Length
- verboselog(0, "video_w: Video DMA Length = %04x (%04x)\n", data, mem_mask);
- do_dma(data);
- break;
-
- default:
- verboselog(0, "video_w: Unknown register %04x = %04x (%04x)\n", 0x2800 + offset, data, mem_mask);
- COMBINE_DATA(&m_video_regs[offset]);
- break;
+ case 0x10: case 0x16: // page 1,2 X scroll
+ data &= 0x01ff;
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
+
+ case 0x11: case 0x17: // page 1,2 Y scroll
+ data &= 0x00ff;
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
+ case 0x36: // IRQ pos V
+ case 0x37: // IRQ pos H
+ data &= 0x01ff;
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
+ case 0x62: // Video IRQ Enable
+ verboselog(0, "video_w: Video IRQ Enable = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&VII_VIDEO_IRQ_ENABLE);
+ break;
+
+ case 0x63: // Video IRQ Acknowledge
+ verboselog(0, "video_w: Video IRQ Acknowledge = %04x (%04x)\n", data, mem_mask);
+ VII_VIDEO_IRQ_STATUS &= ~data;
+ if (!VII_VIDEO_IRQ_STATUS)
+ {
+ m_maincpu->set_input_line(UNSP_IRQ0_LINE, CLEAR_LINE);
+ }
+ break;
+
+ case 0x70: // Video DMA Source
+ verboselog(0, "video_w: Video DMA Source = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
+
+ case 0x71: // Video DMA Dest
+ verboselog(0, "video_w: Video DMA Dest = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
+
+ case 0x72: // Video DMA Length
+ verboselog(0, "video_w: Video DMA Length = %04x (%04x)\n", data, mem_mask);
+ do_dma(data);
+ break;
+
+ default:
+ verboselog(0, "video_w: Unknown register %04x = %04x (%04x)\n", 0x2800 + offset, data, mem_mask);
+ COMBINE_DATA(&m_video_regs[offset]);
+ break;
}
}
-READ16_MEMBER( vii_state::audio_r )
+READ16_MEMBER(spg2xx_game_state::audio_r)
{
- switch(offset)
+ switch (offset)
{
- default:
- verboselog(4, "audio_r: Unknown register %04x\n", 0x3000 + offset);
- break;
+ default:
+ verboselog(4, "audio_r: Unknown register %04x\n", 0x3000 + offset);
+ break;
}
return 0;
}
-WRITE16_MEMBER( vii_state::audio_w )
+WRITE16_MEMBER(spg2xx_game_state::audio_w)
{
- switch(offset)
+ switch (offset)
{
- default:
- verboselog(4, "audio_w: Unknown register %04x = %04x (%04x)\n", 0x3000 + offset, data, mem_mask);
- break;
+ default:
+ verboselog(4, "audio_w: Unknown register %04x = %04x (%04x)\n", 0x3000 + offset, data, mem_mask);
+ break;
}
}
-void vii_state::switch_bank(uint32_t bank)
+void spg2xx_game_state::switch_bank(uint32_t bank)
{
if (bank != m_current_bank)
{
@@ -609,90 +635,123 @@ void vii_state::switch_bank(uint32_t bank)
}
}
-void vii_state::do_gpio(uint32_t offset)
+uint16_t spg2xx_cart_state::do_spg243_vii_io(uint16_t what, int index)
{
- uint32_t index = (offset - 1) / 5;
- uint16_t buffer = m_io_regs[5*index + 2];
- uint16_t dir = m_io_regs[5*index + 3];
- uint16_t attr = m_io_regs[5*index + 4];
- uint16_t special= m_io_regs[5*index + 5];
-
- uint16_t push = dir;
- uint16_t pull = (~dir) & (~attr);
- uint16_t what = (buffer & (push | pull));
- what ^= (dir & ~attr);
- what &= ~special;
+ if (index == 1)
+ {
+ uint32_t bank = ((what & 0x80) >> 7) | ((what & 0x20) >> 4);
+ switch_bank(bank);
+ }
+ return what;
+}
- if (m_spg243_mode == SPG243_VII)
+uint16_t spg2xx_cart_state::do_spg243_vsmile_io(uint16_t what, int index)
+{
+ // TODO: find out how vsmile accesses these GPIO regs!
+ return what;
+}
+
+uint16_t spg2xx_game_state::do_spg243_batman_io(uint16_t what, int index)
+{
+ if (index == 0)
{
- if(index == 1)
- {
- uint32_t bank = ((what & 0x80) >> 7) | ((what & 0x20) >> 4);
- switch_bank(bank);
- }
+ uint16_t temp = m_io_p1->read();
+ what |= (temp & 0x0001) ? 0x8000 : 0;
+ what |= (temp & 0x0002) ? 0x4000 : 0;
+ what |= (temp & 0x0004) ? 0x2000 : 0;
+ what |= (temp & 0x0008) ? 0x1000 : 0;
+ what |= (temp & 0x0010) ? 0x0800 : 0;
+ what |= (temp & 0x0020) ? 0x0400 : 0;
+ what |= (temp & 0x0040) ? 0x0200 : 0;
+ what |= (temp & 0x0080) ? 0x0100 : 0;
}
- else if (m_spg243_mode == SPG243_BATMAN)
+
+ if (index == 2)
{
- if(index == 0)
- {
- uint16_t temp = m_io_p1->read();
- what |= (temp & 0x0001) ? 0x8000 : 0;
- what |= (temp & 0x0002) ? 0x4000 : 0;
- what |= (temp & 0x0004) ? 0x2000 : 0;
- what |= (temp & 0x0008) ? 0x1000 : 0;
- what |= (temp & 0x0010) ? 0x0800 : 0;
- what |= (temp & 0x0020) ? 0x0400 : 0;
- what |= (temp & 0x0040) ? 0x0200 : 0;
- what |= (temp & 0x0080) ? 0x0100 : 0;
- }
+ // TODO: what is here?
+ }
- if(index == 2)
- {
- }
+ return what;
+}
+
+uint16_t spg2xx_game_state::do_spg240_rad_skat_io(uint16_t what, int index)
+{
+ // have not checked for outputs yet.
+
+ if (index == 0)
+ {
+ what = m_io_p1->read();
}
- else if (m_spg243_mode == SPG243_VSMILE)
+ else if (index == 1)
{
- // TODO: find out how vsmile accesses these GPIO regs!
+ what = m_io_p2->read();
}
- else if (m_spg243_mode == SPG243_WIRELESS60)
+ else if (index == 2)
{
- if(index == 0)
- {
- switch(what & 0x300)
- {
- case 0x300:
- m_w60_controller_input = -1;
- break;
-
- case 0x200:
- m_w60_controller_input++;
- break;
-
- default:
- uint16_t temp1 = m_io_p1->read();
- uint16_t temp2 = m_io_p2->read();
- uint16_t temp3 = 1 << m_w60_controller_input;
- if (temp1 & temp3) what ^= 0x400;
- if (temp2 & temp3) what ^= 0x800;
- break;
- }
- }
+ what = m_io_p3->read();
+ }
+ return what;
+}
- if(index == 1)
+uint16_t spg2xx_game_state::do_spg243_wireless60_io(uint16_t what, int index)
+{
+ if (index == 0)
+ {
+ switch (what & 0x300)
{
- uint32_t bank = (what & 7);
- switch_bank(bank);
+ case 0x300:
+ m_w60_controller_input = -1;
+ break;
+
+ case 0x200:
+ m_w60_controller_input++;
+ break;
+
+ default:
+ uint16_t temp1 = m_io_p1->read();
+ uint16_t temp2 = m_io_p2->read();
+ uint16_t temp3 = 1 << m_w60_controller_input;
+ if (temp1 & temp3) what ^= 0x400;
+ if (temp2 & temp3) what ^= 0x800;
+ break;
}
}
- m_io_regs[5*index + 1] = what;
+ if (index == 1)
+ {
+ uint32_t bank = (what & 7);
+ switch_bank(bank);
+ }
+
+ return what;
}
-void vii_state::do_i2c()
+
+void spg2xx_game_state::do_gpio(uint32_t offset)
{
+ uint32_t index = (offset - 1) / 5;
+ uint16_t buffer = m_io_regs[5 * index + 2];
+ uint16_t dir = m_io_regs[5 * index + 3];
+ uint16_t attr = m_io_regs[5 * index + 4];
+ uint16_t special = m_io_regs[5 * index + 5];
+
+ uint16_t push = dir;
+ uint16_t pull = (~dir) & (~attr);
+ uint16_t what = (buffer & (push | pull));
+ what ^= (dir & ~attr);
+ what &= ~special;
+
+ if (!m_vii_io_rw.isnull())
+ what = m_vii_io_rw(what, index);
+
+ m_io_regs[5 * index + 1] = what;
}
-void vii_state::spg_do_dma(uint32_t len)
+void spg2xx_game_state::do_i2c()
+{
+}
+
+void spg2xx_game_state::spg_do_dma(uint32_t len)
{
address_space &mem = m_maincpu->space(AS_PROGRAM);
@@ -700,225 +759,230 @@ void vii_state::spg_do_dma(uint32_t len)
uint32_t dst = m_io_regs[0x103] & 0x3fff;
uint32_t j;
- for(j = 0; j < len; j++)
- mem.write_word(dst+j, mem.read_word(src+j));
+ for (j = 0; j < len; j++)
+ mem.write_word(dst + j, mem.read_word(src + j));
m_io_regs[0x102] = 0;
}
-READ16_MEMBER( vii_state::io_r )
+READ16_MEMBER(spg2xx_game_state::io_r)
{
+ logerror("io_r %04x\n", offset);
+
static const char *const gpioregs[] = { "GPIO Data Port", "GPIO Buffer Port", "GPIO Direction Port", "GPIO Attribute Port", "GPIO IRQ/Latch Port" };
static const char gpioports[] = { 'A', 'B', 'C' };
uint16_t val = m_io_regs[offset];
- switch(offset)
+ switch (offset)
{
- case 0x01: case 0x06: case 0x0b: // GPIO Data Port A/B/C
- do_gpio(offset);
- verboselog(3, "io_r: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], m_io_regs[offset], mem_mask);
- val = m_io_regs[offset];
- break;
-
- case 0x02: case 0x03: case 0x04: case 0x05:
- case 0x07: case 0x08: case 0x09: case 0x0a:
- case 0x0c: case 0x0d: case 0x0e: case 0x0f: // Other GPIO regs
- verboselog(3, "io_r: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], m_io_regs[offset], mem_mask);
- break;
-
- case 0x1c: // Random
- val = machine().rand() & 0x00ff;
- verboselog(3, "io_r: Random = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x21: // IRQ Control
- verboselog(3, "io_r: Controller IRQ Control = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x22: // IRQ Status
- verboselog(3, "io_r: Controller IRQ Status = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x2c: case 0x2d: // Timers?
- val = machine().rand() & 0x0000ffff;
- verboselog(3, "io_r: Unknown Timer %d Register = %04x (%04x)\n", offset - 0x2c, val, mem_mask);
- break;
-
- case 0x2f: // Data Segment
- val = m_maincpu->state_int(UNSP_SR) >> 10;
- verboselog(3, "io_r: Data Segment = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x31: // Unknown, UART Status?
- verboselog(3, "io_r: Unknown (UART Status?) = %04x (%04x)\n", 3, mem_mask);
- val = 3;
- break;
-
- case 0x36: // UART RX Data
- val = m_controller_input[m_uart_rx_count];
- m_uart_rx_count = (m_uart_rx_count + 1) % 8;
- verboselog(3, "io_r: UART RX Data = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x59: // I2C Status
- verboselog(3, "io_r: I2C Status = %04x (%04x)\n", val, mem_mask);
- break;
-
- case 0x5e: // I2C Data In
- verboselog(3, "io_r: I2C Data In = %04x (%04x)\n", val, mem_mask);
- break;
-
- default:
- verboselog(3, "io_r: Unknown register %04x\n", 0x3d00 + offset);
- break;
+ case 0x01: case 0x06: case 0x0b: // GPIO Data Port A/B/C
+ do_gpio(offset);
+ verboselog(3, "io_r: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], m_io_regs[offset], mem_mask);
+ val = m_io_regs[offset];
+ break;
+
+ case 0x02: case 0x03: case 0x04: case 0x05:
+ case 0x07: case 0x08: case 0x09: case 0x0a:
+ case 0x0c: case 0x0d: case 0x0e: case 0x0f: // Other GPIO regs
+ verboselog(3, "io_r: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], m_io_regs[offset], mem_mask);
+ break;
+
+ case 0x1c: // Random
+ val = machine().rand() & 0x00ff;
+ verboselog(3, "io_r: Random = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x21: // IRQ Control
+ verboselog(3, "io_r: Controller IRQ Control = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x22: // IRQ Status
+ verboselog(3, "io_r: Controller IRQ Status = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x2b:
+ return 0x0000;
+
+ case 0x2c: case 0x2d: // Timers?
+ val = machine().rand() & 0x0000ffff;
+ verboselog(3, "io_r: Unknown Timer %d Register = %04x (%04x)\n", offset - 0x2c, val, mem_mask);
+ break;
+
+ case 0x2f: // Data Segment
+ val = m_maincpu->state_int(UNSP_SR) >> 10;
+ verboselog(3, "io_r: Data Segment = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x31: // Unknown, UART Status?
+ verboselog(3, "io_r: Unknown (UART Status?) = %04x (%04x)\n", 3, mem_mask);
+ val = 3;
+ break;
+
+ case 0x36: // UART RX Data
+ val = m_controller_input[m_uart_rx_count];
+ m_uart_rx_count = (m_uart_rx_count + 1) % 8;
+ verboselog(3, "io_r: UART RX Data = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x59: // I2C Status
+ verboselog(3, "io_r: I2C Status = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ case 0x5e: // I2C Data In
+ verboselog(3, "io_r: I2C Data In = %04x (%04x)\n", val, mem_mask);
+ break;
+
+ default:
+ verboselog(3, "io_r: Unknown register %04x\n", 0x3d00 + offset);
+ break;
}
return val;
}
-WRITE16_MEMBER( vii_state::io_w )
+WRITE16_MEMBER(spg2xx_game_state::io_w)
{
static const char *const gpioregs[] = { "GPIO Data Port", "GPIO Buffer Port", "GPIO Direction Port", "GPIO Attribute Port", "GPIO IRQ/Latch Port" };
static const char gpioports[3] = { 'A', 'B', 'C' };
uint16_t temp = 0;
- switch(offset)
+ switch (offset)
{
- case 0x00: // GPIO special function select
- verboselog(3, "io_w: GPIO Function Select = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x01: case 0x06: case 0x0b: // GPIO data, port A/B/C
- offset++;
- // Intentional fallthrough
-
- case 0x02: case 0x03: case 0x04: case 0x05: // Port A
- case 0x07: case 0x08: case 0x09: case 0x0a: // Port B
- case 0x0c: case 0x0d: case 0x0e: case 0x0f: // Port C
- verboselog(3, "io_w: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- do_gpio(offset);
- break;
-
- case 0x10: // timebase control
- if ((m_io_regs[offset] & 0x0003) != (data & 0x0003)) {
- uint16_t hz = 8 << (data & 0x0003);
- verboselog(3, "*** TMB1 FREQ set to %dHz\n", hz);
- m_tmb1->adjust(attotime::zero, 0, attotime::from_hz( hz ));
- }
- if ((m_io_regs[offset] & 0x000c) != (data & 0x000c)) {
- uint16_t hz = 128 << ((data & 0x000c) >> 2);
- verboselog(3, "*** TMB2 FREQ set to %dHz\n", hz);
- m_tmb2->adjust(attotime::zero, 0, attotime::from_hz( hz ));
- }
- COMBINE_DATA(&m_io_regs[offset]);
- break;
- case 0x21: // IRQ Enable
- verboselog(3, "io_w: Controller IRQ Control = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&VII_CTLR_IRQ_ENABLE);
- if(!VII_CTLR_IRQ_ENABLE)
- {
- m_maincpu->set_input_line(UNSP_IRQ3_LINE, CLEAR_LINE);
- }
- break;
-
- case 0x22: // IRQ Acknowledge
- verboselog(3, "io_w: Controller IRQ Acknowledge = %04x (%04x)\n", data, mem_mask);
- m_io_regs[0x22] &= ~data;
- if(!m_io_regs[0x22])
- {
- m_maincpu->set_input_line(UNSP_IRQ3_LINE, CLEAR_LINE);
- }
- break;
-
- case 0x2f: // Data Segment
- temp = m_maincpu->state_int(UNSP_SR);
- m_maincpu->set_state_int(UNSP_SR, (temp & 0x03ff) | ((data & 0x3f) << 10));
- verboselog(3, "io_w: Data Segment = %04x (%04x)\n", data, mem_mask);
- break;
-
- case 0x31: // Unknown UART
- verboselog(3, "io_w: Unknown UART = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x32: // UART Reset
- verboselog(3, "io_w: UART Reset\n");
- break;
-
- case 0x33: // UART Baud Rate
- verboselog(3, "io_w: UART Baud Rate = %u\n", 27000000 / 16 / (0x10000 - (m_io_regs[0x34] << 8) - data));
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x35: // UART TX Data
- verboselog(3, "io_w: UART Baud Rate = %u\n", 27000000 / 16 / (0x10000 - (data << 8) - m_io_regs[0x33]));
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5a: // I2C Access Mode
- verboselog(3, "io_w: I2C Access Mode = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5b: // I2C Device Address
- verboselog(3, "io_w: I2C Device Address = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5c: // I2C Sub-Address
- verboselog(3, "io_w: I2C Sub-Address = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5d: // I2C Data Out
- verboselog(3, "io_w: I2C Data Out = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5e: // I2C Data In
- verboselog(3, "io_w: I2C Data In = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x5f: // I2C Controller Mode
- verboselog(3, "io_w: I2C Controller Mode = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x58: // I2C Command
- verboselog(3, "io_w: I2C Command = %04x (%04x)\n", data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- do_i2c();
- break;
-
- case 0x59: // I2C Status / IRQ Acknowledge(?)
- verboselog(3, "io_w: I2C Status / Ack = %04x (%04x)\n", data, mem_mask);
- m_io_regs[offset] &= ~data;
- break;
-
- case 0x100: // DMA Source (L)
- case 0x101: // DMA Source (H)
- case 0x103: // DMA Destination
- COMBINE_DATA(&m_io_regs[offset]);
- break;
-
- case 0x102: // DMA Length
- spg_do_dma(data);
- break;
+ case 0x00: // GPIO special function select
+ verboselog(3, "io_w: GPIO Function Select = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x01: case 0x06: case 0x0b: // GPIO data, port A/B/C
+ offset++;
+ // Intentional fallthrough
+
+ case 0x02: case 0x03: case 0x04: case 0x05: // Port A
+ case 0x07: case 0x08: case 0x09: case 0x0a: // Port B
+ case 0x0c: case 0x0d: case 0x0e: case 0x0f: // Port C
+ verboselog(3, "io_w: %s %c = %04x (%04x)\n", gpioregs[(offset - 1) % 5], gpioports[(offset - 1) / 5], data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ do_gpio(offset);
+ break;
+
+ case 0x10: // timebase control
+ if ((m_io_regs[offset] & 0x0003) != (data & 0x0003)) {
+ uint16_t hz = 8 << (data & 0x0003);
+ verboselog(3, "*** TMB1 FREQ set to %dHz\n", hz);
+ m_tmb1->adjust(attotime::zero, 0, attotime::from_hz(hz));
+ }
+ if ((m_io_regs[offset] & 0x000c) != (data & 0x000c)) {
+ uint16_t hz = 128 << ((data & 0x000c) >> 2);
+ verboselog(3, "*** TMB2 FREQ set to %dHz\n", hz);
+ m_tmb2->adjust(attotime::zero, 0, attotime::from_hz(hz));
+ }
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+ case 0x21: // IRQ Enable
+ verboselog(3, "io_w: Controller IRQ Control = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&VII_CTLR_IRQ_ENABLE);
+ if (!VII_CTLR_IRQ_ENABLE)
+ {
+ m_maincpu->set_input_line(UNSP_IRQ3_LINE, CLEAR_LINE);
+ }
+ break;
- default:
- verboselog(3, "io_w: Unknown register %04x = %04x (%04x)\n", 0x3d00 + offset, data, mem_mask);
- COMBINE_DATA(&m_io_regs[offset]);
- break;
+ case 0x22: // IRQ Acknowledge
+ verboselog(3, "io_w: Controller IRQ Acknowledge = %04x (%04x)\n", data, mem_mask);
+ m_io_regs[0x22] &= ~data;
+ if (!m_io_regs[0x22])
+ {
+ m_maincpu->set_input_line(UNSP_IRQ3_LINE, CLEAR_LINE);
+ }
+ break;
+
+ case 0x2f: // Data Segment
+ temp = m_maincpu->state_int(UNSP_SR);
+ m_maincpu->set_state_int(UNSP_SR, (temp & 0x03ff) | ((data & 0x3f) << 10));
+ verboselog(3, "io_w: Data Segment = %04x (%04x)\n", data, mem_mask);
+ break;
+
+ case 0x31: // Unknown UART
+ verboselog(3, "io_w: Unknown UART = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x32: // UART Reset
+ verboselog(3, "io_w: UART Reset\n");
+ break;
+
+ case 0x33: // UART Baud Rate
+ verboselog(3, "io_w: UART Baud Rate = %u\n", 27000000 / 16 / (0x10000 - (m_io_regs[0x34] << 8) - data));
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x35: // UART TX Data
+ verboselog(3, "io_w: UART Baud Rate = %u\n", 27000000 / 16 / (0x10000 - (data << 8) - m_io_regs[0x33]));
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5a: // I2C Access Mode
+ verboselog(3, "io_w: I2C Access Mode = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5b: // I2C Device Address
+ verboselog(3, "io_w: I2C Device Address = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5c: // I2C Sub-Address
+ verboselog(3, "io_w: I2C Sub-Address = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5d: // I2C Data Out
+ verboselog(3, "io_w: I2C Data Out = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5e: // I2C Data In
+ verboselog(3, "io_w: I2C Data In = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x5f: // I2C Controller Mode
+ verboselog(3, "io_w: I2C Controller Mode = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x58: // I2C Command
+ verboselog(3, "io_w: I2C Command = %04x (%04x)\n", data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ do_i2c();
+ break;
+
+ case 0x59: // I2C Status / IRQ Acknowledge(?)
+ verboselog(3, "io_w: I2C Status / Ack = %04x (%04x)\n", data, mem_mask);
+ m_io_regs[offset] &= ~data;
+ break;
+
+ case 0x100: // DMA Source (L)
+ case 0x101: // DMA Source (H)
+ case 0x103: // DMA Destination
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
+
+ case 0x102: // DMA Length
+ spg_do_dma(data);
+ break;
+
+ default:
+ verboselog(3, "io_w: Unknown register %04x = %04x (%04x)\n", 0x3d00 + offset, data, mem_mask);
+ COMBINE_DATA(&m_io_regs[offset]);
+ break;
}
}
/*
-WRITE16_MEMBER( vii_state::rowscroll_w )
+WRITE16_MEMBER( spg2xx_game_state::rowscroll_w )
{
switch(offset)
{
@@ -928,7 +992,7 @@ WRITE16_MEMBER( vii_state::rowscroll_w )
}
}
-WRITE16_MEMBER( vii_state::spriteram_w )
+WRITE16_MEMBER( spg2xx_game_state::spriteram_w )
{
switch(offset)
{
@@ -939,7 +1003,7 @@ WRITE16_MEMBER( vii_state::spriteram_w )
}
*/
-static ADDRESS_MAP_START( vii_mem, AS_PROGRAM, 16, vii_state )
+static ADDRESS_MAP_START( vii_mem, AS_PROGRAM, 16, spg2xx_game_state )
AM_RANGE( 0x000000, 0x0027ff ) AM_RAM AM_SHARE("p_ram")
AM_RANGE( 0x002800, 0x0028ff ) AM_READWRITE(video_r, video_w)
AM_RANGE( 0x002900, 0x002aff ) AM_RAM AM_SHARE("p_rowscroll")
@@ -952,73 +1016,106 @@ ADDRESS_MAP_END
static INPUT_PORTS_START( vii )
PORT_START("P1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("Button A")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Button B")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("Button C")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("Button D")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("Button A")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Button B")
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("Button C")
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("Button D")
INPUT_PORTS_END
static INPUT_PORTS_START( batman )
PORT_START("P1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Menu")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("B Button")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("X Button")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Menu")
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("B Button")
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("X Button")
INPUT_PORTS_END
static INPUT_PORTS_START( vsmile )
PORT_START("P1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Menu")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("B Button")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("X Button")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("Menu")
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("B Button")
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("X Button")
INPUT_PORTS_END
static INPUT_PORTS_START( walle )
PORT_START("P1")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("B Button")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("B Button")
INPUT_PORTS_END
static INPUT_PORTS_START( wirels60 )
PORT_START("P1")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("B Button")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("Menu")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("Start")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(1) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(1) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(1) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(1) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(1) PORT_NAME("A Button")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(1) PORT_NAME("B Button")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(1) PORT_NAME("Menu")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(1) PORT_NAME("Start")
+
PORT_START("P2")
- PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(2) PORT_NAME("Joypad Up")
- PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2) PORT_NAME("Joypad Down")
- PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2) PORT_NAME("Joypad Left")
- PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2) PORT_NAME("Joypad Right")
- PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(2) PORT_NAME("A Button")
- PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(2) PORT_NAME("B Button")
- PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(2) PORT_NAME("Menu")
- PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(2) PORT_NAME("Start")
+ PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP ) PORT_PLAYER(2) PORT_NAME("Joypad Up")
+ PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2) PORT_NAME("Joypad Down")
+ PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2) PORT_NAME("Joypad Left")
+ PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2) PORT_NAME("Joypad Right")
+ PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_PLAYER(2) PORT_NAME("A Button")
+ PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_PLAYER(2) PORT_NAME("B Button")
+ PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_PLAYER(2) PORT_NAME("Menu")
+ PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_BUTTON4 ) PORT_PLAYER(2) PORT_NAME("Start")
INPUT_PORTS_END
+static INPUT_PORTS_START( rad_skat )
+ PORT_START("P1")
+ PORT_BIT( 0x0001, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME("Full Left")
+ PORT_BIT( 0x0002, IP_ACTIVE_LOW, IPT_BUTTON5 ) PORT_NAME("Full Right")
+ PORT_BIT( 0x0004, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_NAME("Slight Left") // you have to use this for the menus (eg trick lists)
+ PORT_BIT( 0x0008, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_NAME("Slight Right")
+ PORT_BIT( 0x0010, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_NAME("Front")
+ PORT_BIT( 0x0020, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_NAME("Back")
+ PORT_BIT( 0x0040, IP_ACTIVE_LOW, IPT_UNUSED )
+ PORT_BIT( 0x0080, IP_ACTIVE_LOW, IPT_UNUSED )
+ // there only seem to be 3 buttons on the pad part, so presumably all the above are the skateboard, and below are the pad?
+ PORT_BIT( 0x0100, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME("M Button")
+ PORT_BIT( 0x0200, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME("X Button")
+ PORT_BIT( 0x0400, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME("O Button")
+ PORT_BIT( 0xf800, IP_ACTIVE_LOW, IPT_UNUSED )
+
+ PORT_START("P2")
+ PORT_BIT( 0xffff, IP_ACTIVE_LOW, IPT_UNUSED ) // read but unused?
+
+
+ PORT_START("P3") // PAL/NTSC flag
+ PORT_BIT( 0xffff, IP_ACTIVE_LOW, IPT_SPECIAL )
+INPUT_PORTS_END
-void vii_state::test_centered(uint8_t *ROM)
+static INPUT_PORTS_START( rad_skatp )
+ PORT_INCLUDE(rad_skat)
+
+ PORT_MODIFY("P3") // PAL/NTSC flag
+ PORT_BIT( 0xffff, IP_ACTIVE_HIGH, IPT_SPECIAL )
+INPUT_PORTS_END
+
+
+
+void spg2xx_game_state::test_centered(uint8_t *ROM)
{
if (ROM[0x3cd808] == 0x99 &&
ROM[0x3cd809] == 0x99 &&
@@ -1033,46 +1130,33 @@ void vii_state::test_centered(uint8_t *ROM)
}
}
-DEVICE_IMAGE_LOAD_MEMBER( vii_state, vii_cart )
-{
- uint32_t size = m_cart->common_get_size("rom");
-
- if (size < 0x800000)
- {
- image.seterror(IMAGE_ERROR_UNSPECIFIED, "Unsupported cartridge size");
- return image_init_result::FAIL;
- }
-
- m_cart->rom_alloc(size, GENERIC_ROM16_WIDTH, ENDIANNESS_LITTLE);
- m_cart->common_load_rom(m_cart->get_rom_base(), size, "rom");
-
- test_centered(m_cart->get_rom_base());
- return image_init_result::PASS;
-}
-DEVICE_IMAGE_LOAD_MEMBER( vii_state, vsmile_cart )
+TIMER_CALLBACK_MEMBER(spg2xx_game_state::tmb1_tick)
{
- uint32_t size = m_cart->common_get_size("rom");
-
- m_cart->rom_alloc(size, GENERIC_ROM16_WIDTH, ENDIANNESS_LITTLE);
- m_cart->common_load_rom(m_cart->get_rom_base(), size, "rom");
-
- return image_init_result::PASS;
+ m_io_regs[0x22] |= 1;
}
-
-TIMER_CALLBACK_MEMBER(vii_state::tmb1_tick)
+TIMER_CALLBACK_MEMBER(spg2xx_game_state::tmb2_tick)
{
- m_io_regs[0x22] |= 1;
+ m_io_regs[0x22] |= 2;
}
-TIMER_CALLBACK_MEMBER(vii_state::tmb2_tick)
+void spg2xx_cart_state::machine_start()
{
- m_io_regs[0x22] |= 2;
+ spg2xx_game_state::machine_start();
+
+ // if there's a cart, override the standard banking
+ if (m_cart && m_cart->exists())
+ {
+ std::string region_tag;
+ m_cart_rom = memregion(region_tag.assign(m_cart->tag()).append(GENERIC_ROM_REGION_TAG).c_str());
+ m_bank->configure_entries(0, ceilf((float)m_cart_rom->bytes() / 0x800000), m_cart_rom->base(), 0x800000);
+ m_bank->set_entry(0);
+ }
}
-void vii_state::machine_start()
+void spg2xx_game_state::machine_start()
{
memset(m_video_regs, 0, 0x100 * sizeof(uint16_t));
memset(m_io_regs, 0, 0x100 * sizeof(uint16_t));
@@ -1084,44 +1168,28 @@ void vii_state::machine_start()
m_controller_input[7] = 0;
m_w60_controller_input = -1;
- if (m_cart && m_cart->exists())
- {
- std::string region_tag;
- m_cart_rom = memregion(region_tag.assign(m_cart->tag()).append(GENERIC_ROM_REGION_TAG).c_str());
- m_bank->configure_entries(0, ceilf((float)m_cart_rom->bytes()/0x800000), m_cart_rom->base(), 0x800000 );
- m_bank->set_entry(0);
- }
- else if (m_spg243_mode == SPG243_VII || m_spg243_mode == SPG243_WIRELESS60) // Vii bios is banked
- {
- m_bank->configure_entries(0, ceilf((float)m_bios_rom->bytes()/0x800000), m_bios_rom->base(), 0x800000 );
- m_bank->set_entry(0);
- }
- else
- {
- m_bank->configure_entries(0, ceilf((float)memregion("maincpu")->bytes()/0x800000), memregion("maincpu")->base(), 0x800000 );
- m_bank->set_entry(0);
- }
-
m_video_regs[0x36] = 0xffff;
m_video_regs[0x37] = 0xffff;
- m_tmb1 = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(vii_state::tmb1_tick),this));
- m_tmb2 = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(vii_state::tmb2_tick),this));
+ m_tmb1 = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(spg2xx_game_state::tmb1_tick), this));
+ m_tmb2 = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(spg2xx_game_state::tmb2_tick), this));
m_tmb1->reset();
m_tmb2->reset();
+
+ m_bank->configure_entries(0, ceilf((float)memregion("maincpu")->bytes() / 0x800000), memregion("maincpu")->base(), 0x800000);
+ m_bank->set_entry(0);
}
-void vii_state::machine_reset()
+void spg2xx_game_state::machine_reset()
{
}
-INTERRUPT_GEN_MEMBER(vii_state::vii_vblank)
+INTERRUPT_GEN_MEMBER(spg2xx_game_state::vii_vblank)
{
uint32_t x = machine().rand() & 0x3ff;
uint32_t y = machine().rand() & 0x3ff;
uint32_t z = machine().rand() & 0x3ff;
-
m_controller_input[0] = m_io_p1->read();
m_controller_input[1] = (uint8_t)x;
m_controller_input[2] = (uint8_t)y;
@@ -1137,17 +1205,17 @@ INTERRUPT_GEN_MEMBER(vii_state::vii_vblank)
m_uart_rx_count = 0;
VII_VIDEO_IRQ_STATUS = VII_VIDEO_IRQ_ENABLE & 1;
- if(VII_VIDEO_IRQ_STATUS)
+ if (VII_VIDEO_IRQ_STATUS)
{
verboselog(0, "Video IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ0_LINE, ASSERT_LINE);
}
-// {
-// verboselog(0, "audio 1 IRQ\n");
-// m_maincpu->set_input_line(UNSP_IRQ1_LINE, ASSERT_LINE);
-// }
- if(m_io_regs[0x22] & m_io_regs[0x21] & 0x0c00)
+ // {
+ // verboselog(0, "audio 1 IRQ\n");
+ // m_maincpu->set_input_line(UNSP_IRQ1_LINE, ASSERT_LINE);
+ // }
+ if (m_io_regs[0x22] & m_io_regs[0x21] & 0x0c00)
{
verboselog(0, "timerA, timer B IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ2_LINE, ASSERT_LINE);
@@ -1155,205 +1223,216 @@ INTERRUPT_GEN_MEMBER(vii_state::vii_vblank)
//if(m_io_regs[0x22] & m_io_regs[0x21] & 0x2100)
// For now trigger always if any enabled
- if(VII_CTLR_IRQ_ENABLE)
+ if (VII_CTLR_IRQ_ENABLE)
{
verboselog(0, "UART, ADC IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ3_LINE, ASSERT_LINE);
}
-// {
-// verboselog(0, "audio 4 IRQ\n");
-// m_maincpu->set_input_line(UNSP_IRQ4_LINE, ASSERT_LINE);
-// }
+ // {
+ // verboselog(0, "audio 4 IRQ\n");
+ // m_maincpu->set_input_line(UNSP_IRQ4_LINE, ASSERT_LINE);
+ // }
- if(m_io_regs[0x22] & m_io_regs[0x21] & 0x1200)
+ if (m_io_regs[0x22] & m_io_regs[0x21] & 0x1200)
{
verboselog(0, "External IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ5_LINE, ASSERT_LINE);
}
- if(m_io_regs[0x22] & m_io_regs[0x21] & 0x0070)
+ if (m_io_regs[0x22] & m_io_regs[0x21] & 0x0070)
{
verboselog(0, "1024Hz, 2048HZ, 4096HZ IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ6_LINE, ASSERT_LINE);
}
- if(m_io_regs[0x22] & m_io_regs[0x21] & 0x008b)
+ if (m_io_regs[0x22] & m_io_regs[0x21] & 0x008b)
{
verboselog(0, "TMB1, TMB2, 4Hz, key change IRQ\n");
m_maincpu->set_input_line(UNSP_IRQ7_LINE, ASSERT_LINE);
}
+}
+
+
+
+DEVICE_IMAGE_LOAD_MEMBER(spg2xx_cart_state, vii_cart)
+{
+ uint32_t size = m_cart->common_get_size("rom");
+
+ if (size < 0x800000)
+ {
+ image.seterror(IMAGE_ERROR_UNSPECIFIED, "Unsupported cartridge size");
+ return image_init_result::FAIL;
+ }
+
+ m_cart->rom_alloc(size, GENERIC_ROM16_WIDTH, ENDIANNESS_LITTLE);
+ m_cart->common_load_rom(m_cart->get_rom_base(), size, "rom");
+
+ test_centered(m_cart->get_rom_base());
+ return image_init_result::PASS;
}
-MACHINE_CONFIG_START(vii_state::vii)
+DEVICE_IMAGE_LOAD_MEMBER(spg2xx_cart_state, vsmile_cart)
+{
+ uint32_t size = m_cart->common_get_size("rom");
+
+ m_cart->rom_alloc(size, GENERIC_ROM16_WIDTH, ENDIANNESS_LITTLE);
+ m_cart->common_load_rom(m_cart->get_rom_base(), size, "rom");
+ return image_init_result::PASS;
+}
+
+MACHINE_CONFIG_START(spg2xx_game_state::spg2xx_base)
MCFG_CPU_ADD( "maincpu", UNSP, XTAL(27'000'000))
MCFG_CPU_PROGRAM_MAP( vii_mem )
- MCFG_CPU_VBLANK_INT_DRIVER("screen", vii_state, vii_vblank)
-
+ MCFG_CPU_VBLANK_INT_DRIVER("screen", spg2xx_game_state, vii_vblank)
MCFG_SCREEN_ADD( "screen", RASTER )
MCFG_SCREEN_REFRESH_RATE(60)
MCFG_SCREEN_SIZE(320, 240)
MCFG_SCREEN_VISIBLE_AREA(0, 320-1, 0, 240-1)
- MCFG_SCREEN_UPDATE_DRIVER(vii_state, screen_update_vii)
+ MCFG_SCREEN_UPDATE_DRIVER(spg2xx_game_state, screen_update_vii)
MCFG_PALETTE_ADD("palette", 32768)
+MACHINE_CONFIG_END
- MCFG_GENERIC_CARTSLOT_ADD("cartslot", generic_plain_slot, "vii_cart")
- MCFG_GENERIC_WIDTH(GENERIC_ROM16_WIDTH)
- MCFG_GENERIC_LOAD(vii_state, vii_cart)
+MACHINE_CONFIG_DERIVED(spg2xx_game_state::spg2xx_basep, spg2xx_base)
- MCFG_SOFTWARE_LIST_ADD("vii_cart","vii")
+ MCFG_SCREEN_MODIFY( "screen" )
+ MCFG_SCREEN_REFRESH_RATE(50)
MACHINE_CONFIG_END
-MACHINE_CONFIG_START(vii_state::vsmile)
-
- MCFG_CPU_ADD( "maincpu", UNSP, XTAL(27'000'000))
- MCFG_CPU_PROGRAM_MAP( vii_mem )
- MCFG_CPU_VBLANK_INT_DRIVER("screen", vii_state, vii_vblank)
+MACHINE_CONFIG_DERIVED(spg2xx_cart_state::vii, spg2xx_base)
+ MCFG_GENERIC_CARTSLOT_ADD("cartslot", generic_plain_slot, "vii_cart")
+ MCFG_GENERIC_WIDTH(GENERIC_ROM16_WIDTH)
+ MCFG_GENERIC_LOAD(spg2xx_cart_state, vii_cart)
- MCFG_SCREEN_ADD( "screen", RASTER )
- MCFG_SCREEN_REFRESH_RATE(60)
- MCFG_SCREEN_SIZE(320, 240)
- MCFG_SCREEN_VISIBLE_AREA(0, 320-1, 0, 240-1)
- MCFG_SCREEN_UPDATE_DRIVER(vii_state, screen_update_vii)
- MCFG_PALETTE_ADD("palette", 32768)
+ MCFG_SOFTWARE_LIST_ADD("vii_cart","vii")
+MACHINE_CONFIG_END
+MACHINE_CONFIG_DERIVED(spg2xx_cart_state::vsmile, spg2xx_base)
MCFG_GENERIC_CARTSLOT_ADD("cartslot", generic_plain_slot, "vsmile_cart")
MCFG_GENERIC_WIDTH(GENERIC_ROM16_WIDTH)
- MCFG_GENERIC_LOAD(vii_state, vsmile_cart)
+ MCFG_GENERIC_LOAD(spg2xx_cart_state, vsmile_cart)
MCFG_SOFTWARE_LIST_ADD("cart_list","vsmile_cart")
MACHINE_CONFIG_END
-MACHINE_CONFIG_START(vii_state::batman)
-
- MCFG_CPU_ADD( "maincpu", UNSP, XTAL(27'000'000))
- MCFG_CPU_PROGRAM_MAP( vii_mem )
- MCFG_CPU_VBLANK_INT_DRIVER("screen", vii_state, vii_vblank)
-
-
+MACHINE_CONFIG_DERIVED(spg2xx_game_state::batman, spg2xx_base)
MCFG_I2CMEM_ADD("i2cmem")
MCFG_I2CMEM_DATA_SIZE(0x200)
-
- MCFG_SCREEN_ADD( "screen", RASTER )
- MCFG_SCREEN_REFRESH_RATE(60)
- MCFG_SCREEN_SIZE(320, 240)
- MCFG_SCREEN_VISIBLE_AREA(0, 320-1, 0, 240-1)
- MCFG_SCREEN_UPDATE_DRIVER(vii_state, screen_update_vii)
- MCFG_PALETTE_ADD("palette", 32768)
MACHINE_CONFIG_END
-MACHINE_CONFIG_START(vii_state::wirels60)
-
- MCFG_CPU_ADD( "maincpu", UNSP, XTAL(27'000'000))
- MCFG_CPU_PROGRAM_MAP( vii_mem )
- MCFG_CPU_VBLANK_INT_DRIVER("screen", vii_state, vii_vblank)
-
- MCFG_SCREEN_ADD( "screen", RASTER )
- MCFG_SCREEN_REFRESH_RATE(60)
- MCFG_SCREEN_SIZE(320, 240)
- MCFG_SCREEN_VISIBLE_AREA(0, 320-1, 0, 240-1)
- MCFG_SCREEN_UPDATE_DRIVER(vii_state, screen_update_vii)
- MCFG_PALETTE_ADD("palette", 32768)
-MACHINE_CONFIG_END
+DRIVER_INIT_MEMBER(spg2xx_cart_state, vii)
+{
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_cart_state::do_spg243_vii_io, this);
+ m_centered_coordinates = 1;
+}
-DRIVER_INIT_MEMBER(vii_state,vii)
+DRIVER_INIT_MEMBER(spg2xx_cart_state, vsmile)
{
- m_spg243_mode = SPG243_VII;
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_cart_state::do_spg243_vsmile_io, this);
m_centered_coordinates = 1;
}
-DRIVER_INIT_MEMBER(vii_state,batman)
+DRIVER_INIT_MEMBER(spg2xx_game_state, batman)
{
- m_spg243_mode = SPG243_BATMAN;
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_game_state::do_spg243_batman_io, this);
m_centered_coordinates = 1;
}
-DRIVER_INIT_MEMBER(vii_state,vsmile)
+DRIVER_INIT_MEMBER(spg2xx_game_state, rad_skat)
{
- m_spg243_mode = SPG243_VSMILE;
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_game_state::do_spg240_rad_skat_io, this);
m_centered_coordinates = 1;
}
-DRIVER_INIT_MEMBER(vii_state,walle)
+DRIVER_INIT_MEMBER(spg2xx_game_state, walle)
{
- m_spg243_mode = SPG243_BATMAN;
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_game_state::do_spg243_batman_io, this);
m_centered_coordinates = 0;
}
-DRIVER_INIT_MEMBER(vii_state,wirels60)
+DRIVER_INIT_MEMBER(spg2xx_game_state, wirels60)
{
- m_spg243_mode = SPG243_WIRELESS60;
+ m_vii_io_rw = vii_io_rw_delegate(&spg2xx_game_state::do_spg243_wireless60_io, this);
m_centered_coordinates = 1;
}
ROM_START( vii )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
-
- ROM_REGION( 0x2000000, "bios", 0 )
- ROM_LOAD( "vii.bin", 0x0000, 0x2000000, CRC(04627639) SHA1(f883a92d31b53c9a5b0cdb112d07cd793c95fc43))
+ ROM_REGION( 0x2000000, "maincpu", ROMREGION_ERASEFF )
+ ROM_LOAD16_WORD_SWAP( "vii.bin", 0x0000, 0x2000000, CRC(04627639) SHA1(f883a92d31b53c9a5b0cdb112d07cd793c95fc43))
ROM_END
ROM_START( batmantv )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD16_WORD_SWAP( "batman.bin", 0x000000, 0x400000, CRC(46f848e5) SHA1(5875d57bb3fe0cac5d20e626e4f82a0e5f9bb94c) )
ROM_END
ROM_START( vsmile )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD( "vsmilebios.bin", 0x000000, 0x200000, CRC(11f1b416) SHA1(11f77c4973d29c962567390e41879c86a759c93b) )
ROM_END
ROM_START( vsmileg )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD16_WORD_SWAP( "bios german.bin", 0x000000, 0x200000, CRC(205c5296) SHA1(7fbcf761b5885c8b1524607aabaf364b4559c8cc) )
ROM_END
ROM_START( vsmilef )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD16_WORD_SWAP( "sysrom_france", 0x000000, 0x200000, CRC(0cd0bdf5) SHA1(5c8d1eada1b6b545555b8d2b09325d7127681af8) )
ROM_END
ROM_START( vsmileb )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD( "vbabybios.bin", 0x000000, 0x800000, CRC(ddc7f845) SHA1(2c17d0f54200070176d03d44a40c7923636e596a) )
ROM_END
ROM_START( walle )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
ROM_LOAD16_WORD_SWAP( "walle.bin", 0x000000, 0x400000, BAD_DUMP CRC(bd554cba) SHA1(6cd06a036ab12e7b0e1fd8003db873b0bb783868) )
// Alternate dump, we need to decide which one is correct.
//ROM_LOAD16_WORD_SWAP( "walle.bin", 0x000000, 0x400000, CRC(6bc90b16) SHA1(184d72de059057aae7800da510fcf05ed1da9ec9))
ROM_END
ROM_START( zone60 )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
-
- ROM_REGION( 0x4000000, "bios", 0 )
- ROM_LOAD( "zone60.bin", 0x0000, 0x4000000, CRC(4cb637d1) SHA1(1f97cbdb4299ac0fbafc2a3aa592066cb0727066))
+ ROM_REGION( 0x4000000, "maincpu", ROMREGION_ERASEFF )
+ ROM_LOAD16_WORD_SWAP( "zone60.bin", 0x0000, 0x4000000, CRC(4cb637d1) SHA1(1f97cbdb4299ac0fbafc2a3aa592066cb0727066))
ROM_END
ROM_START( wirels60 )
- ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF ) /* dummy region for u'nSP */
+ ROM_REGION( 0x4000000, "maincpu", ROMREGION_ERASEFF )
+ ROM_LOAD16_WORD_SWAP( "wirels60.bin", 0x0000, 0x4000000, CRC(b4df8b28) SHA1(00e3da542e4bc14baf4724ad436f66d4c0f65c84))
+ROM_END
+
+ROM_START( rad_skat )
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
+ ROM_LOAD16_WORD_SWAP( "skateboarder.bin", 0x000000, 0x400000, CRC(08b9ab91) SHA1(6665edc4740804956136c68065890925a144626b) )
+ROM_END
- ROM_REGION( 0x4000000, "bios", 0 )
- ROM_LOAD( "wirels60.bin", 0x0000, 0x4000000, CRC(b4df8b28) SHA1(00e3da542e4bc14baf4724ad436f66d4c0f65c84))
+ROM_START( rad_skatp ) // rom was dumped from the NTSC version, but region comes from an io port, so ROM is probably the same
+ ROM_REGION( 0x800000, "maincpu", ROMREGION_ERASEFF )
+ ROM_LOAD16_WORD_SWAP( "skateboarder.bin", 0x000000, 0x400000, CRC(08b9ab91) SHA1(6665edc4740804956136c68065890925a144626b) )
ROM_END
-// YEAR NAME PARENT COMPAT MACHINE INPUT STATE INIT COMPANY FULLNAME FLAGS
+// YEAR NAME PARENT COMPAT MACHINE INPUT STATE INIT COMPANY FULLNAME FLAGS
// VTech systems
-CONS( 2005, vsmile, 0, 0, vsmile, vsmile, vii_state, vsmile, "VTech", "V.Smile (US)", MACHINE_NO_SOUND | MACHINE_NOT_WORKING )
-CONS( 2005, vsmileg, vsmile, 0, vsmile, vsmile, vii_state, vsmile, "VTech", "V.Smile (Germany)", MACHINE_NO_SOUND | MACHINE_NOT_WORKING )
-CONS( 2005, vsmilef, vsmile, 0, vsmile, vsmile, vii_state, vsmile, "VTech", "V.Smile (France)", MACHINE_NO_SOUND | MACHINE_NOT_WORKING )
-CONS( 2005, vsmileb, 0, 0, vsmile, vsmile, vii_state, vsmile, "VTech", "V.Smile Baby (US)", MACHINE_NO_SOUND | MACHINE_NOT_WORKING )
+CONS( 2005, vsmile, 0, 0, vsmile, vsmile, spg2xx_cart_state, vsmile, "VTech", "V.Smile (US)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NOT_WORKING )
+CONS( 2005, vsmileg, vsmile, 0, vsmile, vsmile, spg2xx_cart_state, vsmile, "VTech", "V.Smile (Germany)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NOT_WORKING )
+CONS( 2005, vsmilef, vsmile, 0, vsmile, vsmile, spg2xx_cart_state, vsmile, "VTech", "V.Smile (France)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NOT_WORKING )
+CONS( 2005, vsmileb, 0, 0, vsmile, vsmile, spg2xx_cart_state, vsmile, "VTech", "V.Smile Baby (US)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NOT_WORKING )
// Jungle Soft TV games
-CONS( 2007, vii, 0, 0, vii, vii, vii_state, vii, "Jungle Soft / KenSingTon / Chintendo / Siatronics", "Vii", MACHINE_NO_SOUND | MACHINE_NOT_WORKING ) // some games run, others crash
-CONS( 2010, zone60, 0, 0, wirels60, wirels60, vii_state, wirels60, "Jungle Soft / Ultimate Products (HK) Ltd", "Zone 60", MACHINE_NO_SOUND )
-CONS( 2010, wirels60, 0, 0, wirels60, wirels60, vii_state, wirels60, "Jungle Soft / Kids Station Toys Inc", "Wireless 60", MACHINE_NO_SOUND )
+CONS( 2007, vii, 0, 0, vii, vii, spg2xx_cart_state, vii, "Jungle Soft / KenSingTon / Chintendo / Siatronics", "Vii", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS | MACHINE_NOT_WORKING ) // some games run, others crash
+
+CONS( 2010, zone60, 0, 0, spg2xx_base, wirels60, spg2xx_game_state, wirels60, "Jungle Soft / Ultimate Products (HK) Ltd", "Zone 60", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+CONS( 2010, wirels60, 0, 0, spg2xx_base, wirels60, spg2xx_game_state, wirels60, "Jungle Soft / Kids Station Toys Inc", "Wireless 60", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
// JAKKS Pacific Inc TV games
-CONS( 2004, batmantv, 0, 0, batman, batman, vii_state, batman, "JAKKS Pacific Inc / HotGen Ltd", "The Batman", MACHINE_NO_SOUND )
-CONS( 2008, walle, 0, 0, batman, walle, vii_state, walle, "JAKKS Pacific Inc", "Wall-E", MACHINE_NO_SOUND )
+CONS( 2004, batmantv, 0, 0, batman, batman, spg2xx_game_state, batman, "JAKKS Pacific Inc / HotGen Ltd", "The Batman", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+CONS( 2008, walle, 0, 0, batman, walle, spg2xx_game_state, walle, "JAKKS Pacific Inc", "Wall-E", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+
+// Radica TV games
+CONS( 2006, rad_skat, 0, 0, spg2xx_base, rad_skat, spg2xx_game_state, rad_skat, "Radica", "Play TV Skateboarder (NTSC)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )
+CONS( 2006, rad_skatp, rad_skat,0, spg2xx_basep,rad_skatp,spg2xx_game_state, rad_skat, "Radica", "Connectv Skateboarder (PAL)", MACHINE_NO_SOUND | MACHINE_IMPERFECT_GRAPHICS )