summaryrefslogtreecommitdiffstatshomepage
path: root/src/devices/machine/spg110.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/devices/machine/spg110.cpp')
-rw-r--r--src/devices/machine/spg110.cpp658
1 files changed, 85 insertions, 573 deletions
diff --git a/src/devices/machine/spg110.cpp b/src/devices/machine/spg110.cpp
index df614deb314..060ae511f0c 100644
--- a/src/devices/machine/spg110.cpp
+++ b/src/devices/machine/spg110.cpp
@@ -17,352 +17,61 @@
DEFINE_DEVICE_TYPE(SPG110, spg110_device, "spg110", "SPG110 System-on-a-Chip")
spg110_device::spg110_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock)
- : device_t(mconfig, type, tag, owner, clock),
- device_memory_interface(mconfig, *this),
- m_space_config("spg110", ENDIANNESS_BIG, 16, 32, 0, address_map_constructor(FUNC(spg110_device::map_video), this)),
- m_cpu(*this, finder_base::DUMMY_TAG),
- m_palette(*this, "palette"),
- m_gfxdecode(*this, "gfxdecode"),
- m_palram(*this, "palram")
+ : device_t(mconfig, type, tag, owner, clock)
+ , m_cpu(*this, finder_base::DUMMY_TAG)
+ , m_screen(*this, finder_base::DUMMY_TAG)
+ , m_spg_io(*this, "spg_io")
+ , m_spg_video(*this, "spg_video")
+ , m_porta_out(*this)
+ , m_portb_out(*this)
+ , m_portc_out(*this)
+ , m_porta_in(*this)
+ , m_portb_in(*this)
+ , m_portc_in(*this)
+ , m_adc_in{{*this}, {*this}}
+ , m_chip_sel(*this)
{
}
-template<spg110_device::flipx_t FlipX>
-void spg110_device::blit(const rectangle &cliprect, uint32_t line, uint32_t xoff, uint32_t yoff, uint32_t attr, uint32_t ctrl, uint32_t bitmap_addr, uint16_t tile)
-{
- address_space &space = m_cpu->space(AS_PROGRAM);
-
- int32_t h = 8 << ((attr & PAGE_TILE_HEIGHT_MASK) >> PAGE_TILE_HEIGHT_SHIFT);
- int32_t w = 8 << ((attr & PAGE_TILE_WIDTH_MASK) >> PAGE_TILE_WIDTH_SHIFT);
-
- uint32_t yflipmask = attr & TILE_Y_FLIP ? h - 1 : 0;
-
- uint32_t nc = ((attr & 0x0003) + 1) << 1;
-
- uint32_t palette_offset = (attr & 0x0f00) >> 4;
-
- palette_offset >>= nc;
- palette_offset <<= nc;
-
- uint32_t bits_per_row = nc * w / 16;
- uint32_t words_per_tile = bits_per_row * h;
- uint32_t m = bitmap_addr + words_per_tile * tile + bits_per_row * (line ^ yflipmask);
- uint32_t bits = 0;
- uint32_t nbits = 0;
- uint32_t y = line;
-
- int yy = (yoff + y) & 0x1ff;
- if (yy >= 0x01c0)
- yy -= 0x0200;
-
- if (yy > 240 || yy < 0)
- return;
-
- int y_index = yy * 320;
-
- for (int32_t x = FlipX ? (w - 1) : 0; FlipX ? x >= 0 : x < w; FlipX ? x-- : x++)
- {
- int xx = xoff + x;
-
- bits <<= nc;
-
- if (nbits < nc)
- {
- uint16_t b = space.read_word(m++ & 0x3fffff);
- //b = (b << 8) | (b >> 8);
- bits |= b << (nc - nbits);
- nbits += 16;
- }
- nbits -= nc;
-
- uint32_t pal = palette_offset + (bits >> 16);
- bits &= 0xffff;
-
- xx &= 0x01ff;
- if (xx >= 0x01c0)
- xx -= 0x0200;
-
- if (xx >= 0 && xx < 320)
- {
- // TODO, this is completely wrong for this palette system
- int pix_index = xx + y_index;
- uint16_t rawpal = m_palram[pal];
- const pen_t *pens = m_palette->pens();
- uint32_t paldata = pens[pal];
-
- if (!(rawpal & 0x8000))
- {
- m_screenbuf[pix_index] = paldata;
- }
- }
- }
-}
-
-void spg110_device::blit_page(const rectangle &cliprect, uint32_t scanline, int depth, uint32_t bitmap_addr, uint16_t *regs)
-{
- uint32_t xscroll = regs[0];
- uint32_t yscroll = regs[1];
- uint32_t attr = regs[2];
- uint32_t ctrl = regs[3];
- uint32_t tilemap = regs[4];
- uint32_t palette_map = regs[5];
- address_space &space2 = this->space(0);
-
- if (!(ctrl & PAGE_ENABLE_MASK))
- {
- return;
- }
-
- if (((attr & PAGE_DEPTH_FLAG_MASK) >> PAGE_DEPTH_FLAG_SHIFT) != depth)
- {
- return;
- }
-
- uint32_t tile_h = 8 << ((attr & PAGE_TILE_HEIGHT_MASK) >> PAGE_TILE_HEIGHT_SHIFT);
- uint32_t tile_w = 8 << ((attr & PAGE_TILE_WIDTH_MASK) >> PAGE_TILE_WIDTH_SHIFT);
-
- uint32_t tile_count_x = 512 / tile_w;
-
- uint32_t bitmap_y = (scanline + yscroll) & 0xff;
- uint32_t y0 = bitmap_y / tile_h;
- uint32_t tile_scanline = bitmap_y % tile_h;
- uint32_t tile_address = tile_count_x * y0;
-
- for (uint32_t x0 = 0; x0 < tile_count_x; x0++, tile_address++)
- {
- uint32_t yy = ((tile_h * y0 - yscroll + 0x10) & 0xff) - 0x10;
- uint32_t xx = (tile_w * x0 - xscroll) & 0x1ff;
- uint16_t tile = (ctrl & PAGE_WALLPAPER_MASK) ? space2.read_word(tilemap*2) : space2.read_word((tilemap + tile_address)*2);
- uint16_t palette = 0;
-
- if (!tile)
- continue;
-
- palette = space2.read_word(palette_map + tile_address / 2);
- if (x0 & 1)
- palette = (palette & 0xff00) >> 8;
- else
- palette = (palette & 0x00ff);
-
-
- bool flip_x = 0;//(tileattr & TILE_X_FLIP);
-
- if (flip_x)
- blit<FlipXOn>(cliprect, tile_scanline, xx, yy, attr, ctrl, bitmap_addr, tile);
- else
- blit<FlipXOff>(cliprect, tile_scanline, xx, yy, attr, ctrl, bitmap_addr, tile);
-
- }
-}
-
-
-/* correct, 4bpp gfxs */
-static const gfx_layout charlayout =
-{
- 8,8,
- RGN_FRAC(1,1),
- 4,
- { STEP4(0,1) },
- { 0*4,1*4,2*4,3*4,4*4,5*4,6*4,7*4 },
- { STEP8(0,4*8) },
- 8*8*4
-};
-
-static const gfx_layout charlayout6 =
-{
- 8,8,
- RGN_FRAC(1,1),
- 6,
- { 0,1,2,3,4,5 },
- { STEP8(0,6) },
- { STEP8(0,6*8) },
- 8*8*6
-};
-
-static const gfx_layout char16layout =
-{
- 16,16,
- RGN_FRAC(1,1),
- 4,
- { STEP4(0,1) },
- { 0*4,1*4,2*4,3*4,4*4,5*4,6*4,7*4, 8*4,9*4,10*4,11*4,12*4,13*4,14*4,15*4 },
- { STEP16(0,4*16) },
- 16*16*4
-};
-
-static const gfx_layout char32layout =
-{
- 32,32,
- RGN_FRAC(1,1),
- 4,
- { STEP4(0,1) },
- { STEP32(0,4) },
- { STEP32(0,4*32) },
- 32*32*4
-};
-
-
-
-static GFXDECODE_START( gfx )
- GFXDECODE_ENTRY( ":maincpu", 0, charlayout, 0, 16 )
- GFXDECODE_ENTRY( ":maincpu", 0, char16layout, 0, 16 )
- GFXDECODE_ENTRY( ":maincpu", 0, char32layout, 0, 16 )
- GFXDECODE_ENTRY( ":maincpu", 0, charlayout6, 0, 16 ) // correct for lots of the tiles inc. startup text
-GFXDECODE_END
-
-
-
-void spg110_device::device_add_mconfig(machine_config &config)
-{
-// PALETTE(config, m_palette).set_format(palette_device::xRGB_555, 0x100);
-// PALETTE(config, m_palette).set_format(palette_device::RGB_565, 0x100);
-// PALETTE(config, m_palette).set_format(palette_device::IRGB_4444, 0x100);
-// PALETTE(config, m_palette).set_format(palette_device::RGBI_4444, 0x100);
-// PALETTE(config, m_palette).set_format(palette_device::xRGB_555, 0x100);
- PALETTE(config, m_palette, palette_device::BLACK, 256);
-
- GFXDECODE(config, m_gfxdecode, m_palette, gfx);
-}
-
-
-device_memory_interface::space_config_vector spg110_device::memory_space_config() const
-{
- return space_config_vector {
- std::make_pair(0, &m_space_config)
- };
-}
spg110_device::spg110_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: spg110_device(mconfig, SPG110, tag, owner, clock)
{
}
-// irq source or similar?
-READ16_MEMBER(spg110_device::spg110_2063_r)
-{
- // checks for bits 0x20 and 0x08 in the IRQ function (all IRQs point to the same place)
- return 0x0008;
-}
-
-WRITE16_MEMBER(spg110_device::spg110_2063_w)
+WRITE_LINE_MEMBER(spg110_device::videoirq_w)
{
- // writes 0x28, probably clears the IRQ / IRQ sources? 0x63 is the same offset for this in spg2xx but bits used seem to be different
- m_cpu->set_state_unsynced(UNSP_IRQ0_LINE, CLEAR_LINE);
+ m_cpu->set_state_unsynced(UNSP_IRQ0_LINE, state);
}
-READ16_MEMBER(spg110_device::datasegment_r)
+void spg110_device::configure_spg_io(spg2xx_io_device* io)
{
- uint16_t val = m_cpu->get_ds();
- return val;
+ io->porta_in().set(FUNC(spg110_device::porta_r));
+ io->portb_in().set(FUNC(spg110_device::portb_r));
+ io->portc_in().set(FUNC(spg110_device::portc_r));
+ io->porta_out().set(FUNC(spg110_device::porta_w));
+ io->portb_out().set(FUNC(spg110_device::portb_w));
+ io->portc_out().set(FUNC(spg110_device::portc_w));
+ io->adc_in<0>().set(FUNC(spg110_device::adc_r<0>));
+ io->adc_in<1>().set(FUNC(spg110_device::adc_r<1>));
+ io->chip_select().set(FUNC(spg110_device::cs_w));
+// io->pal_read_callback().set(FUNC(spg110_device::get_pal_r));
+// io->write_timer_irq_callback().set(FUNC(spg110_device::timerirq_w));
+// io->write_uart_adc_irq_callback().set(FUNC(spg110_device::uartirq_w));
+// io->write_external_irq_callback().set(FUNC(spg110_device::extirq_w));
+// io->write_ffrq_tmr1_irq_callback().set(FUNC(spg110_device::ffreq1_w));
+// io->write_ffrq_tmr2_irq_callback().set(FUNC(spg110_device::ffreq2_w));
}
-WRITE16_MEMBER(spg110_device::datasegment_w)
+void spg110_device::device_add_mconfig(machine_config &config)
{
- m_cpu->set_ds(data & 0x3f);
-}
+ SPG24X_IO(config, m_spg_io, DERIVED_CLOCK(1, 1), m_cpu, m_screen);
+ configure_spg_io(m_spg_io);
-WRITE16_MEMBER(spg110_device::spg110_3221_w)
-{
- /* first write on startup? */
+ SPG110_VIDEO(config, m_spg_video, DERIVED_CLOCK(1, 1), m_cpu, m_screen);
+ m_spg_video->write_video_irq_callback().set(FUNC(spg110_device::videoirq_w));
}
-WRITE16_MEMBER(spg110_device::spg110_3223_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3225_w) { }
-
-
-WRITE16_MEMBER(spg110_device::spg110_201c_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2020_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2042_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2031_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2032_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2033_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2034_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2035_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2036_w) { COMBINE_DATA(&m_2036_scroll); }
-WRITE16_MEMBER(spg110_device::spg110_2039_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2037_w) { }
-WRITE16_MEMBER(spg110_device::spg110_203c_w) { }
-WRITE16_MEMBER(spg110_device::spg110_203d_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2045_w) { }
-
-
-WRITE16_MEMBER(spg110_device::spg110_2028_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2029_w) { }
-
-READ16_MEMBER(spg110_device::spg110_2028_r) { return 0x0000; }
-READ16_MEMBER(spg110_device::spg110_2029_r) { return 0x0000; }
-
-
-WRITE16_MEMBER(spg110_device::spg110_2050_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2051_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2052_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2053_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2054_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2055_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2056_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2057_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2058_w) { }
-WRITE16_MEMBER(spg110_device::spg110_2059_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205a_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205b_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205c_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205d_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205e_w) { }
-WRITE16_MEMBER(spg110_device::spg110_205f_w) { }
-
-WRITE16_MEMBER(spg110_device::dma_unk_2061_w) { COMBINE_DATA(&m_dma_unk_2061); }
-WRITE16_MEMBER(spg110_device::dma_dst_step_w) { COMBINE_DATA(&m_dma_dst_step); }
-WRITE16_MEMBER(spg110_device::dma_unk_2067_w) { COMBINE_DATA(&m_dma_unk_2067); }
-WRITE16_MEMBER(spg110_device::dma_src_step_w) { COMBINE_DATA(&m_dma_src_step); }
-
-WRITE16_MEMBER(spg110_device::dma_dst_w) { COMBINE_DATA(&m_dma_dst); }
-WRITE16_MEMBER(spg110_device::dma_src_w) { COMBINE_DATA(&m_dma_src); }
-
-WRITE16_MEMBER(spg110_device::dma_len_trigger_w)
-{
- int length = data & 0x1fff;
-
- // this is presumably a counter that underflows to 0x1fff, because that's what the wait loop waits for?
- logerror("%s: (trigger len) %04x with values (unk) %04x (dststep) %04x (unk) %04x (src step) %04x | (dst) %04x (src) %04x\n", machine().describe_context(), data, m_dma_unk_2061, m_dma_dst_step, m_dma_unk_2067, m_dma_src_step, m_dma_dst, m_dma_src);
-
- if ((m_dma_unk_2061!=0x0000) || (m_dma_unk_2067 != 0x0000))
- fatalerror("unknown DMA params are not zero!\n");
-
- int source = m_dma_src;
- int dest = m_dma_dst;
-
- for (int i = 0; i < length; i++)
- {
- address_space &mem = m_cpu->space(AS_PROGRAM);
- uint16_t val = mem.read_word(source);
-
- this->space(0).write_word(dest * 2, val, 0xffff);
-
- source+=m_dma_src_step;
- dest+=m_dma_dst_step;
- }
-}
-
-READ16_MEMBER(spg110_device::dma_len_status_r)
-{
- return 0x1fff; // DMA related?
-}
-
-READ16_MEMBER(spg110_device::spg110_2037_r) { return 0x0000; }
-READ16_MEMBER(spg110_device::spg110_2042_r) { return 0x0000; }
-
-WRITE16_MEMBER(spg110_device::spg110_3200_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3201_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3203_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3204_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3206_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3208_w) { }
-WRITE16_MEMBER(spg110_device::spg110_3209_w) { }
-
-READ16_MEMBER(spg110_device::spg110_3201_r) { return 0x0000; }
-READ16_MEMBER(spg110_device::spg110_3225_r) { return 0x0000; }
-READ16_MEMBER(spg110_device::spg110_322c_r) { return 0x0000; }
-
WRITE16_MEMBER(spg110_device::spg110_3100_w) { }
WRITE16_MEMBER(spg110_device::spg110_3101_w) { }
WRITE16_MEMBER(spg110_device::spg110_3102_w) { }
@@ -378,128 +87,60 @@ WRITE16_MEMBER(spg110_device::spg110_310d_w) { }
READ16_MEMBER(spg110_device::spg110_310f_r) { return 0x0000; }
-READ16_MEMBER(spg110_device::tmap0_regs_r) { return tmap0_regs[offset]; }
-READ16_MEMBER(spg110_device::tmap1_regs_r) { return tmap1_regs[offset]; }
-
-void spg110_device::tilemap_write_regs(int which, uint16_t* regs, int regno, uint16_t data)
-{
- switch (regno)
- {
- case 0x0: // Page X scroll
- logerror("video_w: Page %d X Scroll = %04x\n", which, data & 0x01ff);
- regs[regno] = data & 0x01ff;
- break;
-
- case 0x1: // Page Y scroll
- logerror("video_w: Page %d Y Scroll = %04x\n", which, data & 0x00ff);
- regs[regno] = data & 0x00ff;
- break;
-
- case 0x2: // Page Attributes
- // 'depth' (aka z value) can't be depth here as it is on spg2xx, or the scores in attract will be behind the table, it really seems to be per attribute bit instead
-
- logerror("video_w: Page %d Attributes = %04x (Depth:%d, Palette:%d, VSize:%d, HSize:%d, FlipY:%d, FlipX:%d, BPP:%d)\n", which, data
- , (data >> 12) & 3, (data >> 8) & 15, 8 << ((data >> 6) & 3), 8 << ((data >> 4) & 3), BIT(data, 3), BIT(data, 2), 2 * ((data & 3) + 1));
- regs[regno] = data;
- break;
-
- case 0x3: // Page Control
- logerror("video_w: Page %d Control = %04x (Blend:%d, HiColor:%d, RowScroll:%d, Enable:%d, Wallpaper:%d, RegSet:%d, Bitmap:%d)\n", which, data
- , BIT(data, 8), BIT(data, 7), BIT(data, 4), BIT(data, 3), BIT(data, 2), BIT(data, 1), BIT(data, 0));
- regs[regno] = data;
- break;
-
- case 0x4: // Page Tile Address
- logerror("video_w: Page %d Tile Address = %04x\n", which, data);
- regs[regno] = data;
- break;
-
- case 0x5: // Page Attribute Address
- logerror("video_w: Page %d Attribute Address = %04x\n", which, data);
- regs[regno] = data;
- break;
- }
-}
-
-
-WRITE16_MEMBER(spg110_device::tmap0_regs_w)
-{
- tilemap_write_regs(0, tmap0_regs,offset,data);
-}
-
-
-WRITE16_MEMBER(spg110_device::tmap1_regs_w)
-{
- tilemap_write_regs(1, tmap1_regs,offset,data);
-}
-
void spg110_device::map(address_map &map)
{
map(0x000000, 0x000fff).ram();
-
// vregs are at 2000?
- map(0x002010, 0x002015).rw(FUNC(spg110_device::tmap0_regs_r), FUNC(spg110_device::tmap0_regs_w));
- map(0x002016, 0x00201b).rw(FUNC(spg110_device::tmap1_regs_r), FUNC(spg110_device::tmap1_regs_w));
-
- map(0x00201c, 0x00201c).w(FUNC(spg110_device::spg110_201c_w));
+ map(0x002010, 0x002015).rw(m_spg_video, FUNC(spg110_video_device::tmap0_regs_r), FUNC(spg110_video_device::tmap0_regs_w));
+ map(0x002016, 0x00201b).rw(m_spg_video, FUNC(spg110_video_device::tmap1_regs_r), FUNC(spg110_video_device::tmap1_regs_w));
- map(0x002020, 0x002020).w(FUNC(spg110_device::spg110_2020_w));
+#if 1 // more vregs?
+ map(0x00201c, 0x00201c).w(m_spg_video, FUNC(spg110_video_device::spg110_201c_w));
- map(0x002028, 0x002028).rw(FUNC(spg110_device::spg110_2028_r), FUNC(spg110_device::spg110_2028_w));
- map(0x002029, 0x002029).rw(FUNC(spg110_device::spg110_2029_r), FUNC(spg110_device::spg110_2029_w));
+ map(0x002020, 0x002020).w(m_spg_video, FUNC(spg110_video_device::spg110_2020_w));
- map(0x002031, 0x002031).w(FUNC(spg110_device::spg110_2031_w)); // sometimes 14a?
- map(0x002032, 0x002032).w(FUNC(spg110_device::spg110_2032_w)); // always 14a?
- map(0x002033, 0x002033).w(FUNC(spg110_device::spg110_2033_w));
- map(0x002034, 0x002034).w(FUNC(spg110_device::spg110_2034_w));
- map(0x002035, 0x002035).w(FUNC(spg110_device::spg110_2035_w));
- map(0x002036, 0x002036).w(FUNC(spg110_device::spg110_2036_w)); // possible scroll register?
- map(0x002037, 0x002037).rw(FUNC(spg110_device::spg110_2037_r), FUNC(spg110_device::spg110_2037_w));
+ map(0x002028, 0x002028).rw(m_spg_video, FUNC(spg110_video_device::spg110_2028_r), FUNC(spg110_video_device::spg110_2028_w));
+ map(0x002029, 0x002029).rw(m_spg_video, FUNC(spg110_video_device::spg110_2029_r), FUNC(spg110_video_device::spg110_2029_w));
- map(0x002039, 0x002039).w(FUNC(spg110_device::spg110_2039_w));
+ map(0x002031, 0x002031).w(m_spg_video, FUNC(spg110_video_device::spg110_2031_w)); // sometimes 14a?
+ map(0x002032, 0x002032).w(m_spg_video, FUNC(spg110_video_device::spg110_2032_w)); // always 14a?
+ map(0x002033, 0x002033).w(m_spg_video, FUNC(spg110_video_device::spg110_2033_w));
+ map(0x002034, 0x002034).w(m_spg_video, FUNC(spg110_video_device::spg110_2034_w));
+ map(0x002035, 0x002035).w(m_spg_video, FUNC(spg110_video_device::spg110_2035_w));
+ map(0x002036, 0x002036).w(m_spg_video, FUNC(spg110_video_device::spg110_2036_w)); // possible scroll register?
+ map(0x002037, 0x002037).rw(m_spg_video, FUNC(spg110_video_device::spg110_2037_r), FUNC(spg110_video_device::spg110_2037_w));
- map(0x00203c, 0x00203c).w(FUNC(spg110_device::spg110_203c_w));
+ map(0x002039, 0x002039).w(m_spg_video, FUNC(spg110_video_device::spg110_2039_w));
- map(0x00203d, 0x00203d).w(FUNC(spg110_device::spg110_203d_w)); // possible scroll register?
+ map(0x00203c, 0x00203c).w(m_spg_video, FUNC(spg110_video_device::spg110_203c_w));
- map(0x002042, 0x002042).rw(FUNC(spg110_device::spg110_2042_r),FUNC(spg110_device::spg110_2042_w));
+ map(0x00203d, 0x00203d).w(m_spg_video, FUNC(spg110_video_device::spg110_203d_w)); // possible scroll register?
- map(0x002045, 0x002045).w(FUNC(spg110_device::spg110_2045_w));
+ map(0x002042, 0x002042).rw(m_spg_video, FUNC(spg110_video_device::spg110_2042_r),FUNC(spg110_video_device::spg110_2042_w));
- // seems to be 16 entries for.. something?
- map(0x002050, 0x002050).w(FUNC(spg110_device::spg110_2050_w));
- map(0x002051, 0x002051).w(FUNC(spg110_device::spg110_2051_w));
- map(0x002052, 0x002052).w(FUNC(spg110_device::spg110_2052_w));
- map(0x002053, 0x002053).w(FUNC(spg110_device::spg110_2053_w));
- map(0x002054, 0x002054).w(FUNC(spg110_device::spg110_2054_w));
- map(0x002055, 0x002055).w(FUNC(spg110_device::spg110_2055_w));
- map(0x002056, 0x002056).w(FUNC(spg110_device::spg110_2056_w));
- map(0x002057, 0x002057).w(FUNC(spg110_device::spg110_2057_w));
- map(0x002058, 0x002058).w(FUNC(spg110_device::spg110_2058_w));
- map(0x002059, 0x002059).w(FUNC(spg110_device::spg110_2059_w));
- map(0x00205a, 0x00205a).w(FUNC(spg110_device::spg110_205a_w));
- map(0x00205b, 0x00205b).w(FUNC(spg110_device::spg110_205b_w));
- map(0x00205c, 0x00205c).w(FUNC(spg110_device::spg110_205c_w));
- map(0x00205d, 0x00205d).w(FUNC(spg110_device::spg110_205d_w));
- map(0x00205e, 0x00205e).w(FUNC(spg110_device::spg110_205e_w));
- map(0x00205f, 0x00205f).w(FUNC(spg110_device::spg110_205f_w));
+ map(0x002045, 0x002045).w(m_spg_video, FUNC(spg110_video_device::spg110_2045_w));
+#endif
- //map(0x002010, 0x00205f).ram();
+ // seems to be 16 entries for.. something? on jak_capb these seem connected to the palette DMA operations, 0x2050 for 0x8000, 0x2051 for 0x8020, 0x2052 for 0x8040 etc. maybe 1 bit per pen?
+ map(0x002050, 0x00205f).ram().w(m_spg_video, FUNC(spg110_video_device::spg110_205x_w)).share("spg_video:palctrlram");
// everything (dma? and interrupt flag?!)
- map(0x002060, 0x002060).w(FUNC(spg110_device::dma_dst_w));
- map(0x002061, 0x002061).w(FUNC(spg110_device::dma_unk_2061_w));
- map(0x002062, 0x002062).rw(FUNC(spg110_device::dma_len_status_r),FUNC(spg110_device::dma_len_trigger_w));
- map(0x002063, 0x002063).rw(FUNC(spg110_device::spg110_2063_r),FUNC(spg110_device::spg110_2063_w)); // this looks like interrupt stuff and is checked in the irq like an irq source, but why in the middle of what otherwise look like some kind of DMA?
- map(0x002064, 0x002064).w(FUNC(spg110_device::dma_dst_step_w));
- map(0x002066, 0x002066).w(FUNC(spg110_device::dma_src_w));
- map(0x002067, 0x002067).w(FUNC(spg110_device::dma_unk_2067_w));
- map(0x002068, 0x002068).w(FUNC(spg110_device::dma_src_step_w));
-
- map(0x002200, 0x0022ff).ram(); // looks like per-pen brightness or similar? strange because palette isn't memory mapped here
-
- map(0x003000, 0x00307f).ram(); // sound registers? seems to be 8 long entries, only uses up to 0x7f?
+ map(0x002060, 0x002060).w(m_spg_video, FUNC(spg110_video_device::dma_dst_w));
+ map(0x002061, 0x002061).w(m_spg_video, FUNC(spg110_video_device::dma_unk_2061_w));
+ map(0x002062, 0x002062).rw(m_spg_video, FUNC(spg110_video_device::dma_len_status_r),FUNC(spg110_video_device::dma_len_trigger_w));
+ map(0x002063, 0x002063).rw(m_spg_video, FUNC(spg110_video_device::spg110_2063_r),FUNC(spg110_video_device::spg110_2063_w)); // Video IRQ source / ack (3 different things checked here instead of 2 on spg2xx?)
+ map(0x002064, 0x002064).w(m_spg_video, FUNC(spg110_video_device::dma_dst_step_w));
+ map(0x002065, 0x002065).rw(m_spg_video, FUNC(spg110_video_device::dma_manual_r), FUNC(spg110_video_device::dma_manual_w));
+ map(0x002066, 0x002066).w(m_spg_video, FUNC(spg110_video_device::dma_src_w));
+ map(0x002067, 0x002067).w(m_spg_video, FUNC(spg110_video_device::dma_unk_2067_w));
+ map(0x002068, 0x002068).w(m_spg_video, FUNC(spg110_video_device::dma_src_step_w));
+
+ map(0x002100, 0x0021ff).ram(); // jak_spdmo only
+ map(0x002200, 0x0022ff).ram(); // looks like per-pen brightness or similar? strange because palette isn't memory mapped here (maybe rowscroll?)
+
+#if 1 // sound registers? seems to be 8 long entries, only uses up to 0x7f? (register mapping seems similar to spg2xx, maybe with less channels?)
+ map(0x003000, 0x00307f).ram();
map(0x003080, 0x0030ff).ram();
map(0x003100, 0x003100).w(FUNC(spg110_device::spg110_3100_w));
@@ -518,157 +159,28 @@ void spg110_device::map(address_map &map)
map(0x00310d, 0x00310d).w(FUNC(spg110_device::spg110_310d_w));
map(0x00310f, 0x00310f).r(FUNC(spg110_device::spg110_310f_r));
+#endif
// 0032xx looks like it could be the same as 003d00 on spg2xx
- map(0x003200, 0x003200).w(FUNC(spg110_device::spg110_3200_w));
-
- map(0x003201, 0x003201).rw(FUNC(spg110_device::spg110_3201_r),FUNC(spg110_device::spg110_3201_w));
-
- map(0x003203, 0x003203).w(FUNC(spg110_device::spg110_3203_w));
- map(0x003204, 0x003204).w(FUNC(spg110_device::spg110_3204_w));
-
- map(0x003206, 0x003206).w(FUNC(spg110_device::spg110_3206_w));
-
- map(0x003208, 0x003208).w(FUNC(spg110_device::spg110_3208_w));
- map(0x003209, 0x003209).w(FUNC(spg110_device::spg110_3209_w));
-
- map(0x003221, 0x003221).w(FUNC(spg110_device::spg110_3221_w));
- map(0x003223, 0x003223).w(FUNC(spg110_device::spg110_3223_w));
- map(0x003225, 0x003225).rw(FUNC(spg110_device::spg110_3225_r),FUNC(spg110_device::spg110_3225_w));
- map(0x00322c, 0x00322c).r(FUNC(spg110_device::spg110_322c_r));
-
- map(0x00322f, 0x00322f).rw(FUNC(spg110_device::datasegment_r),FUNC(spg110_device::datasegment_w));
+ map(0x003200, 0x00322f).rw(m_spg_io, FUNC(spg2xx_io_device::io_r), FUNC(spg2xx_io_device::io_w));
}
-// this seems to be a different, non-cpu mapped space only accessible via the DMA?
-void spg110_device::map_video(address_map &map)
-{
- // are these addresses hardcoded, or can they move (in which case tilemap system isn't really suitable)
- map(0x00000, 0x03fff).ram(); // 2fff?
-
- map(0x04000, 0x04fff).ram(); // seems to be 3 blocks, almost certainly spritelist
-
-// map(0x08000, 0x081ff).ram().w(m_palette, FUNC(palette_device::write16)).share("palette"); // probably? format unknown tho
- map(0x08000, 0x081ff).ram().share("palram");
-}
-
-
-/*
-TIMER_CALLBACK_MEMBER(spg110_device::test_timer)
-{
- //
-}
-*/
-
-
void spg110_device::device_start()
{
-// m_test_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(spg110_device::test_timer), this));
- save_item(NAME(m_dma_src_step));
- save_item(NAME(m_dma_dst_step));
- save_item(NAME(m_dma_unk_2061));
- save_item(NAME(m_dma_unk_2067));
- save_item(NAME(m_dma_dst));
- save_item(NAME(m_dma_src));
- save_item(NAME(m_bg_scrollx));
- save_item(NAME(m_bg_scrolly));
- save_item(NAME(m_2036_scroll));
-}
-
-void spg110_device::device_reset()
-{
- m_dma_src_step = 0;
- m_dma_dst_step = 0;
- m_dma_unk_2061 = 0;
- m_dma_unk_2067 = 0;
- m_dma_dst = 0;
- m_dma_src = 0;
- m_bg_scrollx = 0;
- m_bg_scrolly = 0;
- m_2036_scroll = 0;
-}
+ m_porta_out.resolve_safe();
+ m_portb_out.resolve_safe();
+ m_portc_out.resolve_safe();
+ m_porta_in.resolve_safe(0);
+ m_portb_in.resolve_safe(0);
+ m_portc_in.resolve_safe(0);
+ m_adc_in[0].resolve_safe(0x0fff);
+ m_adc_in[1].resolve_safe(0x0fff);
+ m_chip_sel.resolve_safe();
-double spg110_device::hue2rgb(double p, double q, double t)
-{
- if (t < 0) t += 1;
- if (t > 1) t -= 1;
- if (t < 1 / 6.0f) return p + (q - p) * 6 * t;
- if (t < 1 / 2.0f) return q;
- if (t < 2 / 3.0f) return p + (q - p) * (2 / 3.0f - t) * 6;
- return p;
}
-uint32_t spg110_device::screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect)
+void spg110_device::device_reset()
{
- // Palette, this is still wrong!
- int offs = 0;
- for (int index = 0;index < 256; index++)
- {
- uint16_t dat = m_palram[offs++];
-
- // llll lsss sshh hhhh
- int l_raw = (dat & 0xf800) >> 11;
- int sl_raw = (dat & 0x07c0) >> 6;
- int h_raw = (dat & 0x003f) >> 0;
-
- double l = (double)l_raw / 31.0f;
- double s = (double)sl_raw / 31.0f;
- double h = (double)h_raw / 47.0f;
-
- double r, g, b;
-
- if (s == 0) {
- r = g = b = l; // greyscale
- } else {
- double q = l < 0.5f ? l * (1 + s) : l + s - l * s;
- double p = 2 * l - q;
- r = hue2rgb(p, q, h + 1/3.0f);
- g = hue2rgb(p, q, h);
- b = hue2rgb(p, q, h - 1/3.0f);
- }
-
- int r_real = r * 255.0f;
- int g_real = g * 255.0f;
- int b_real = b * 255.0f;
-
- m_palette->set_pen_color(index, r_real, g_real, b_real);
- }
-
- memset(&m_screenbuf[320 * cliprect.min_y], 0, 4 * 320 * ((cliprect.max_y - cliprect.min_y) + 1));
-
- const uint32_t page1_addr = 0;//0x40 * m_video_regs[0x20];
- const uint32_t page2_addr = 0;//0x40 * m_video_regs[0x21];
- uint16_t *page1_regs = tmap0_regs;
- uint16_t *page2_regs = tmap1_regs;
-
- for (uint32_t scanline = (uint32_t)cliprect.min_y; scanline <= (uint32_t)cliprect.max_y; scanline++)
- {
- for (int i = 0; i < 4; i++)
- {
- blit_page(cliprect, scanline, i, page2_addr, page2_regs);
- blit_page(cliprect, scanline, i, page1_addr, page1_regs);
- //blit_sprites(cliprect, scanline, i);
- }
- }
-
- for (int y = cliprect.min_y; y <= cliprect.max_y; y++)
- {
- uint32_t *dest = &bitmap.pix32(y, cliprect.min_x);
- uint32_t *src = &m_screenbuf[cliprect.min_x + 320 * y];
- memcpy(dest, src, sizeof(uint32_t) * ((cliprect.max_x - cliprect.min_x) + 1));
- }
-
- return 0;
}
-WRITE_LINE_MEMBER(spg110_device::vblank)
-{
- if (!state)
- {
- m_cpu->set_state_unsynced(UNSP_IRQ0_LINE, ASSERT_LINE);
- // m_test_timer->adjust(attotime::from_usec(100), 0);
- }
-
- return;
-}