From 978c6ff83fa4bc70275bfbec48da49d80f3c4719 Mon Sep 17 00:00:00 2001 From: David Haywood <28625134+DavidHaywood@users.noreply.github.com> Date: Wed, 2 Sep 2020 00:45:23 +0100 Subject: [PATCH] some experimental code for pcp8728 / pcp8718 [David Haywood] (#7168) * handhelds test code * more experiments * change some terminology for now * some kind of input * looking better * bump up CPU clock * dma isn't as abnormal as thought, use was misunderstood * better palette * only use data for screen for screen * make 'fast read' mode work for the cases we have * some inputs as per test mode --- src/mame/drivers/generalplus_gpl_unknown.cpp | 463 +++++++++++++++++-- 1 file changed, 424 insertions(+), 39 deletions(-) diff --git a/src/mame/drivers/generalplus_gpl_unknown.cpp b/src/mame/drivers/generalplus_gpl_unknown.cpp index 0e45a6c8288..c59c342aa5e 100644 --- a/src/mame/drivers/generalplus_gpl_unknown.cpp +++ b/src/mame/drivers/generalplus_gpl_unknown.cpp @@ -90,7 +90,9 @@ public: m_mainram(*this, "mainram"), m_palette(*this, "palette"), m_screen(*this, "screen"), - m_spirom(*this, "spi") + m_spirom(*this, "spi"), + m_io_p1(*this, "IN0"), + m_io_p2(*this, "IN1") { } void pcp8718(machine_config &config); @@ -101,7 +103,7 @@ private: virtual void machine_start() override; virtual void machine_reset() override; - uint32_t screen_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect); + uint32_t screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); required_device m_maincpu; required_region_ptr m_mainrom; @@ -132,6 +134,32 @@ private: uint16_t unk_780f_r(); void unk_7868_w(uint16_t data); + uint16_t unk_7868_r(); + uint16_t m_7868; + + void bankswitch_707e_w(uint16_t data); + uint16_t bankswitch_707e_r(); + uint16_t m_707e_bank; + + void bankswitch_703a_w(uint16_t data); + uint16_t bankswitch_703a_r(); + uint16_t m_703a_bank; + + void bankedram_7300_w(offs_t offset, uint16_t data); + uint16_t bankedram_7300_r(offs_t offset); + uint16_t m_bankedram_7300[0x400]; + + void bankedram_7400_w(offs_t offset, uint16_t data); + uint16_t bankedram_7400_r(offs_t offset); + uint16_t m_bankedram_7400[0x800]; + + void system_dma_params_channel0_w(offs_t offset, uint16_t data); + uint16_t system_dma_params_channel0_r(offs_t offset); + + uint16_t m_dmaregs[8]; + + void lcd_w(uint16_t data); + void lcd_command_w(uint16_t data); uint16_t spi_misc_control_r(); uint16_t spi_rx_fifo_r(); @@ -139,12 +167,12 @@ private: void spi_control_w(uint16_t data); - void spi_process_tx_data(uint8_t data); uint8_t spi_process_rx(); uint8_t spi_rx(); + uint8_t spi_rx_fast(); - uint8_t m_rx_fifo[4]; // actually 8 bytes? or 8 half-bytes? + uint8_t m_rx_fifo[5]; // actually 8 bytes? or 8 half-bytes? uint32_t m_spiaddress; @@ -162,17 +190,60 @@ private: SPI_STATE_WAITING_HIGH_ADDR_FAST = 8, SPI_STATE_WAITING_MID_ADDR_FAST = 9, SPI_STATE_WAITING_LOW_ADDR_FAST = 10, - SPI_STATE_WAITING_LOW_ADDR_FAST_DUMMY = 11 + SPI_STATE_WAITING_LOW_ADDR_FAST_DUMMY = 11, + SPI_STATE_READING_FAST = 12 + }; spistate m_spistate; + enum lcdstate : const int + { + LCD_STATE_READY = 0, + LCD_STATE_WAITING_FOR_COMMAND = 1, + LCD_STATE_PROCESSING_COMMAND = 2 + }; + + lcdstate m_lcdstate; + int m_lastlcdcommand; + + uint8_t m_displaybuffer[0x40000]; + int m_lcdaddr; + + uint16_t unk_7870_r(); + required_ioport m_io_p1; + required_ioport m_io_p2; }; -uint32_t pcp8718_state::screen_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect) +uint32_t pcp8718_state::screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect) { m_mainram[0x12] |= 0x8000; // some code waits on this, what is it? - m_mainram[0x09] &= 0xfff0; // should be cleared by IRQ? + + for (int x = 8; x < 8 + 4; x++) + { + if (m_mainram[x] > 0) + m_mainram[x] -= 1; + } + + int count = 0; + for (int y = 0; y < 256; y++) + { + uint32_t* dst = &bitmap.pix32(y); + + for (int x = 0; x < 320; x++) + { + // 8-bit values get pumped through a 256 word table in intenral ROM and converted to words, so it's probably raw 16-bit RGB data? + uint16_t dat = m_displaybuffer[(count * 2) + 1] | (m_displaybuffer[(count * 2) + 0] << 8); + + int b = ((dat >> 0) & 0x1f) << 3; + int g = ((dat >> 5) & 0x3f) << 2; + int r = ((dat >> 11) & 0x1f) << 3; + + dst[x] = (r << 16) | (g << 8) | (b << 0); + count++; + } + } + return 0; } @@ -184,6 +255,87 @@ void pcp8718_state::machine_start() } static INPUT_PORTS_START( pcp8718 ) + PORT_START("IN0") + PORT_DIPNAME( 0x0001, 0x0001, "P1:0001" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0001, "0001" ) + PORT_DIPNAME( 0x0002, 0x0002, "P1:0002" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0002, "0002" ) + PORT_DIPNAME( 0x0004, 0x0004, "P1:0004" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0004, "0004" ) + PORT_DIPNAME( 0x0008, 0x0008, "P1:0008" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0008, "0008" ) + PORT_DIPNAME( 0x0010, 0x0010, "P1:0010" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0010, "0010" ) + PORT_DIPNAME( 0x0020, 0x0020, "P1:0020" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0020, "0020" ) + PORT_DIPNAME( 0x0040, 0x0040, "P1:0040" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0040, "0040" ) + PORT_DIPNAME( 0x0080, 0x0080, "P1:0080" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0080, "0080" ) + PORT_DIPNAME( 0x0100, 0x0100, "P1:0100" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0100, "0100" ) + PORT_DIPNAME( 0x0200, 0x0200, "P1:0200" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0200, "0200" ) + PORT_DIPNAME( 0x0400, 0x0400, "P1:0400" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0400, "0400" ) + PORT_DIPNAME( 0x0800, 0x0800, "P1:0800" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0800, "0800" ) + PORT_DIPNAME( 0x1000, 0x1000, "P1:1000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x1000, "1000" ) + PORT_DIPNAME( 0x2000, 0x2000, "P1:2000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x2000, "2000" ) + PORT_DIPNAME( 0x4000, 0x4000, "P1:4000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x4000, "4000" ) + PORT_DIPNAME( 0x8000, 0x8000, "P1:8000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x8000, "8000" ) + + PORT_START("IN1") + PORT_DIPNAME( 0x0001, 0x0001, "P2:0001" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0001, "0001" ) + PORT_DIPNAME( 0x0002, 0x0002, "P2:0002" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0002, "0002" ) + PORT_DIPNAME( 0x0004, 0x0004, "Show Vs in Test Mode" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0004, "0004" ) + PORT_DIPNAME( 0x0008, 0x0008, "P2:0008" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0008, "0008" ) + PORT_DIPNAME( 0x0010, 0x0010, "P2:0010" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x0010, "0010" ) + PORT_BIT( 0x0020, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME("SOUND") + PORT_BIT( 0x0040, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) + PORT_BIT( 0x0080, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) + PORT_BIT( 0x0100, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) + PORT_BIT( 0x0200, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME("A") + PORT_BIT( 0x0400, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME("B") + PORT_BIT( 0x0800, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME("ON/OFF") + PORT_DIPNAME( 0x1000, 0x1000, "P2:1000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x1000, "1000" ) + PORT_DIPNAME( 0x2000, 0x2000, "P2:2000" ) + PORT_DIPSETTING( 0x0000, "0000" ) + PORT_DIPSETTING( 0x2000, "2000" ) + PORT_BIT( 0x4000, IP_ACTIVE_LOW, IPT_START1 ) + PORT_BIT( 0x8000, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) INPUT_PORTS_END uint16_t pcp8718_state::unk_7abf_r() @@ -193,7 +345,7 @@ uint16_t pcp8718_state::unk_7abf_r() uint16_t pcp8718_state::unk_7860_r() { - return machine().rand() & 0x8; + return (machine().rand() & 0x0008) | (m_io_p2->read() & 0xfff7); } @@ -206,20 +358,23 @@ uint16_t pcp8718_state::unk_780f_r() uint16_t pcp8718_state::spi_misc_control_r() { - logerror("%06x: spi_misc_control_r\n", machine().describe_context()); + //logerror("%06x: spi_misc_control_r\n", machine().describe_context()); return 0x0000; } uint16_t pcp8718_state::spi_rx_fifo_r() { - logerror("%06x: spi_rx_fifo_r\n", machine().describe_context()); + if (m_spistate == SPI_STATE_READING_FAST) + return spi_rx_fast(); + + //logerror("%06x: spi_rx_fifo_r\n", machine().describe_context()); return spi_rx(); } void pcp8718_state::spi_process_tx_data(uint8_t data) { - logerror("transmitting %02x\n", data); + //logerror("transmitting %02x\n", data); switch (m_spistate) { @@ -234,6 +389,7 @@ void pcp8718_state::spi_process_tx_data(uint8_t data) { logerror("set to fast read mode (need address) %02x\n", data); m_spistate = SPI_STATE_WAITING_HIGH_ADDR_FAST; + //machine().debug_break(); } else { @@ -245,7 +401,7 @@ void pcp8718_state::spi_process_tx_data(uint8_t data) case SPI_STATE_WAITING_HIGH_ADDR: { m_spiaddress = (m_spiaddress & 0xff00ffff) | data << 16; - logerror("set to high address %02x address is now %08x\n", data, m_spiaddress); + // logerror("set to high address %02x address is now %08x\n", data, m_spiaddress); m_spistate = SPI_STATE_WAITING_MID_ADDR; break; } @@ -253,7 +409,7 @@ void pcp8718_state::spi_process_tx_data(uint8_t data) case SPI_STATE_WAITING_MID_ADDR: { m_spiaddress = (m_spiaddress & 0xffff00ff) | data << 8; - logerror("set to mid address %02x address is now %08x\n", data, m_spiaddress); + // logerror("set to mid address %02x address is now %08x\n", data, m_spiaddress); m_spistate = SPI_STATE_WAITING_LOW_ADDR; break; } @@ -269,7 +425,7 @@ void pcp8718_state::spi_process_tx_data(uint8_t data) case SPI_STATE_READING: { // writes when in read mode clock in data? - logerror("write while in read mode (clock data?)\n", data, m_spiaddress); + // logerror("write while in read mode (clock data?)\n", data, m_spiaddress); break; } @@ -314,7 +470,14 @@ void pcp8718_state::spi_process_tx_data(uint8_t data) case SPI_STATE_WAITING_LOW_ADDR_FAST_DUMMY: { logerror("dummy write %08x\n", data, m_spiaddress); - m_spistate = SPI_STATE_READING; + m_spistate = SPI_STATE_READING_FAST; + break; + } + + case SPI_STATE_READING_FAST: + { + // writes when in read mode clock in data? + // logerror("write while in read mode (clock data?)\n", data, m_spiaddress); break; } @@ -327,6 +490,7 @@ uint8_t pcp8718_state::spi_process_rx() switch (m_spistate) { case SPI_STATE_READING: + case SPI_STATE_READING_FAST: { uint8_t dat = m_spirom[m_spiaddress & 0x3fffff]; @@ -335,7 +499,7 @@ uint8_t pcp8718_state::spi_process_rx() // if (dat == 0x4e) // dat = 0x5e; - logerror("reading SPI %02x from SPI Address %08x (adjusted word offset %08x)\n", dat, m_spiaddress, (m_spiaddress/2)+0x20000); + //logerror("reading SPI %02x from SPI Address %08x (adjusted word offset %08x)\n", dat, m_spiaddress, (m_spiaddress/2)+0x20000); m_spiaddress++; return dat; } @@ -363,11 +527,23 @@ uint8_t pcp8718_state::spi_rx() return ret; } +uint8_t pcp8718_state::spi_rx_fast() +{ + uint8_t ret = m_rx_fifo[0]; + + m_rx_fifo[0] = m_rx_fifo[1]; + m_rx_fifo[1] = m_rx_fifo[2]; + m_rx_fifo[2] = m_rx_fifo[3]; + m_rx_fifo[3] = m_rx_fifo[4]; + m_rx_fifo[4] = spi_process_rx(); + + return ret; +} void pcp8718_state::spi_tx_fifo_w(uint16_t data) { data &= 0x00ff; - logerror("%06x: spi_tx_fifo_w %02x\n", machine().describe_context(), data); + //logerror("%06x: spi_tx_fifo_w %04x\n", machine().describe_context(), data); spi_process_tx_data(data); } @@ -376,15 +552,157 @@ void pcp8718_state::spi_tx_fifo_w(uint16_t data) // it's accessed after each large data transfer, probably to reset the SPI into 'ready for command' state? void pcp8718_state::unk_7868_w(uint16_t data) { - logerror("%06x: unk_7868_w %02x (Port B + SPI reset?)\n", machine().describe_context(), data); + //logerror("%06x: unk_7868_w %04x (Port B + SPI reset?)\n", machine().describe_context(), data); for (int i = 0; i < 4; i++) m_rx_fifo[i] = 0xff; m_spistate = SPI_STATE_READY; - + m_7868 = data; } +uint16_t pcp8718_state::unk_7868_r() +{ + return m_7868; +} + +void pcp8718_state::bankswitch_707e_w(uint16_t data) +{ + logerror("%06x: bankswitch_707e_w %04x\n", machine().describe_context(), data); + m_707e_bank = data; +} + +uint16_t pcp8718_state::bankswitch_707e_r() +{ + return m_707e_bank; +} + + +void pcp8718_state::bankswitch_703a_w(uint16_t data) +{ + logerror("%06x: bankswitch_703a_w %04x\n", machine().describe_context(), data); + m_703a_bank = data; +} + +uint16_t pcp8718_state::bankswitch_703a_r() +{ + return m_703a_bank; +} + +void pcp8718_state::bankedram_7300_w(offs_t offset, uint16_t data) +{ + offset |= (m_703a_bank & 0x000c) << 6; + m_bankedram_7300[offset] = data; +} + +uint16_t pcp8718_state::bankedram_7300_r(offs_t offset) +{ + offset |= (m_703a_bank & 0x000c) << 6; + return m_bankedram_7300[offset]; +} + +void pcp8718_state::bankedram_7400_w(offs_t offset, uint16_t data) +{ + if (m_707e_bank & 1) + { + m_bankedram_7400[offset + 0x400] = data; + } + else + { + m_bankedram_7400[offset] = data; + } +} + +uint16_t pcp8718_state::bankedram_7400_r(offs_t offset) +{ + if (m_707e_bank & 1) + { + return m_bankedram_7400[offset + 0x400]; + } + else + { + return m_bankedram_7400[offset]; + } +} + +void pcp8718_state::system_dma_params_channel0_w(offs_t offset, uint16_t data) +{ + m_dmaregs[offset] = data; + + switch (offset) + { + case 0: + { + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Mode)\n", machine().describe_context(), offset, data); + +#if 1 + + uint16_t mode = m_dmaregs[0]; + uint32_t source = m_dmaregs[1] | (m_dmaregs[4] << 16); + uint32_t dest = m_dmaregs[2] | (m_dmaregs[5] << 16) ; + uint32_t length = m_dmaregs[3] | (m_dmaregs[6] << 16); + + if ((mode != 0x0200) && (mode != 0x4009)) + fatalerror("unknown dma mode write %04x\n", data); + + if (mode == 0x4009) + { + address_space& mem = m_maincpu->space(AS_PROGRAM); + + // source and dest are swapped compared to gpl16250 hookup? probably mode? + for (int i = 0; i < length; i++) + { + uint16_t dat = mem.read_word(source); + mem.write_word(dest, dat); + + dest++; + source++; + } + } +#endif + break; + } + case 1: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Source Low)\n", machine().describe_context(), offset, data); + break; + + case 2: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Dest Low)\n", machine().describe_context(), offset, data); + break; + + case 3: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Length Low)\n", machine().describe_context(), offset, data); + break; + + case 4: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Source High)\n", machine().describe_context(), offset, data); + break; + + case 5: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Dest High)\n", machine().describe_context(), offset, data); + break; + + case 6: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA Length High)\n", machine().describe_context(), offset, data); + break; + + case 7: + logerror("%06x: system_dma_params_channel0_w %01x %04x (DMA unknown)\n", machine().describe_context(), offset, data); + break; + } +} + +uint16_t pcp8718_state::system_dma_params_channel0_r(offs_t offset) +{ + logerror("%06x: system_dma_params_channel0_r %01x\n", machine().describe_context(), offset); + return m_dmaregs[offset]; +} + +uint16_t pcp8718_state::unk_7870_r() +{ + logerror("%06x: unk_7870_r (IO port)\n", machine().describe_context()); + return m_io_p2->read(); +} void pcp8718_state::spi_control_w(uint16_t data) { @@ -397,14 +715,27 @@ void pcp8718_state::map(address_map &map) // (RAM populated by internal ROM?, TODO: check to make sure code copied there isn't from SPI ROM like the GPL16250 bootstrap // does from NAND, it doesn't seem to have a header in the same format at least) map(0x000000, 0x006fff).ram().share("mainram"); - map(0x007000, 0x0077ff).ram(); // might be registers, but the call stubs for RAM calls explicitly use addresses in here for private stack so that previous snippets can be restored? + + // registers at 7xxx are similar to GPL16250, but not identical? (different video system? or just GPL16250 with the video part unused?) + + map(0x00703a, 0x00703a).rw(FUNC(pcp8718_state::bankswitch_703a_r), FUNC(pcp8718_state::bankswitch_703a_w)); + map(0x00707e, 0x00707e).rw(FUNC(pcp8718_state::bankswitch_707e_r), FUNC(pcp8718_state::bankswitch_707e_w)); + + map(0x007100, 0x0071ff).ram(); // rowscroll on gpl16250 + map(0x007300, 0x0073ff).rw(FUNC(pcp8718_state::bankedram_7300_r), FUNC(pcp8718_state::bankedram_7300_w)); // palette on gpl16250 + map(0x007400, 0x0077ff).rw(FUNC(pcp8718_state::bankedram_7400_r), FUNC(pcp8718_state::bankedram_7400_w)); // spriteram on gpl16250 map(0x00780f, 0x00780f).r(FUNC(pcp8718_state::unk_780f_r)); map(0x007860, 0x007860).r(FUNC(pcp8718_state::unk_7860_r)); - map(0x007868, 0x007868).w(FUNC(pcp8718_state::unk_7868_w)); + map(0x007870, 0x007870).r(FUNC(pcp8718_state::unk_7870_r)); // I/O + + map(0x007862, 0x007862).nopw(); + + + map(0x007868, 0x007868).rw(FUNC(pcp8718_state::unk_7868_r), FUNC(pcp8718_state::unk_7868_w)); map(0x007940, 0x007940).w(FUNC(pcp8718_state::spi_control_w)); // 7941 SPI Transmit Status @@ -413,16 +744,62 @@ void pcp8718_state::map(address_map &map) map(0x007944, 0x007944).r(FUNC(pcp8718_state::spi_rx_fifo_r)); map(0x007945, 0x007945).r(FUNC(pcp8718_state::spi_misc_control_r)); + map(0x007a80, 0x007a87).rw(FUNC(pcp8718_state::system_dma_params_channel0_r), FUNC(pcp8718_state::system_dma_params_channel0_w)); + map(0x007abf, 0x007abf).r(FUNC(pcp8718_state::unk_7abf_r)); - // registers at 7xxx are similar to GPL16250, but not identical? (different video system?) - // there are calls to 0x0f000 (internal ROM?) map(0x00f000, 0x00ffff).rom().region("maincpu", 0x00000); + + // external LCD controller + map(0x200000, 0x200000).w(FUNC(pcp8718_state::lcd_command_w)); + map(0x20fc00, 0x20fc00).w(FUNC(pcp8718_state::lcd_w)); } +void pcp8718_state::lcd_command_w(uint16_t data) +{ + data &= 0xff; + switch (m_lcdstate) + { + case LCD_STATE_READY: + case LCD_STATE_PROCESSING_COMMAND: + { + if (data == 0x0000) + { + m_lcdstate = LCD_STATE_WAITING_FOR_COMMAND; + m_lastlcdcommand = 0; + } + break; + } + + case LCD_STATE_WAITING_FOR_COMMAND: + { + m_lastlcdcommand = data; + m_lcdstate = LCD_STATE_PROCESSING_COMMAND; + break; + } + + } +} + +void pcp8718_state::lcd_w(uint16_t data) +{ + data &= 0xff; // definitely looks like 8-bit port as 16-bit values are shifted and rewritten + logerror("%06x: lcd_w %02x\n", machine().describe_context(), data); + + if ((m_lcdstate == LCD_STATE_PROCESSING_COMMAND) && (m_lastlcdcommand == 0x22)) + { + m_displaybuffer[m_lcdaddr] = data; + m_lcdaddr++; + + if (m_lcdaddr >= ((320 * 240) * 2)) + m_lcdaddr = 0; + + //m_lcdaddr &= 0x3ffff; + } +} uint16_t pcp8718_state::simulate_f000_r(offs_t offset) { @@ -434,6 +811,7 @@ uint16_t pcp8718_state::simulate_f000_r(offs_t offset) if ((offset + 0xf000) == (realpc)) { +#if 0 // still simulate this as it uses 'fast read' mode which doesn't work in the SPI handler at the moment if (realpc == 0xf000) { @@ -461,28 +839,28 @@ uint16_t pcp8718_state::simulate_f000_r(offs_t offset) } else if (realpc == 0xf58f) { - logerror("call to 0xf58f - unknown function\n"); + // logerror("call to 0xf58f - unknown function\n"); return m_mainrom[offset]; } else if (realpc == 0xfb26) // done with a call, and also a pc = { - logerror("call to 0xfb26 - unknown function\n"); + // logerror("call to 0xfb26 - unknown function\n"); return m_mainrom[offset]; } else if (realpc == 0xf56f) // done with a pc = { - logerror("call to 0xf56f - unknown function\n"); + // logerror("call to 0xf56f - unknown function\n"); return m_mainrom[offset]; } else { return m_mainrom[offset]; } - +#endif } else { - logerror("simulate_f000_r reading BIOS area (for checksum?) %04x\n", offset); + // logerror("simulate_f000_r reading BIOS area (for checksum?) %04x\n", offset); return m_mainrom[offset]; } } @@ -493,7 +871,7 @@ uint16_t pcp8718_state::ramcall_2060_logger_r() { if (!machine().side_effects_disabled()) { - logerror("call to 0x2060 in RAM (set SPI to read mode, set address, do dummy FIFO reads)\n"); + // logerror("call to 0x2060 in RAM (set SPI to read mode, set address, do dummy FIFO reads)\n"); } return m_mainram[0x2060]; } @@ -502,7 +880,7 @@ uint16_t pcp8718_state::ramcall_2189_logger_r() { if (!machine().side_effects_disabled()) { - logerror("call to 0x2189 in RAM (unknown)\n"); + // logerror("call to 0x2189 in RAM (unknown)\n"); } return m_mainram[0x2189]; } @@ -513,7 +891,7 @@ uint16_t pcp8718_state::ramcall_2829_logger_r() // this in turn calls 28f7 but has restore logic too if (!machine().side_effects_disabled()) { - logerror("call to 0x2829 in RAM (load+call function from SPI address %08x)\n", (m_mainram[0x1e] << 16) | m_mainram[0x1d]); + // logerror("call to 0x2829 in RAM (load+call function from SPI address %08x)\n", (m_mainram[0x1e] << 16) | m_mainram[0x1d]); } return m_mainram[0x2829]; } @@ -525,7 +903,7 @@ uint16_t pcp8718_state::ramcall_287a_logger_r() { if (!machine().side_effects_disabled()) { - logerror("call to 0x287a in RAM (unknown)\n"); + // logerror("call to 0x287a in RAM (unknown)\n"); } return m_mainram[0x287a]; } @@ -535,7 +913,7 @@ uint16_t pcp8718_state::ramcall_28f7_logger_r() if (!machine().side_effects_disabled()) { // no restore logic? - logerror("call to 0x28f7 in RAM (load+GO TO function from SPI address %08x)\n", (m_mainram[0x1e] << 16) | m_mainram[0x1d]); + // logerror("call to 0x28f7 in RAM (load+GO TO function from SPI address %08x)\n", (m_mainram[0x1e] << 16) | m_mainram[0x1d]); } return m_mainram[0x28f7]; } @@ -544,7 +922,7 @@ uint16_t pcp8718_state::ramcall_2079_logger_r() { if (!machine().side_effects_disabled()) { - logerror("call to 0x2079 in RAM (maybe drawing related?)\n"); // called in the 'dummy' loop that doesn't actually draw? and other places? as well as after the actual draw command below in the real loop + // logerror("call to 0x2079 in RAM (maybe drawing related?)\n"); // called in the 'dummy' loop that doesn't actually draw? and other places? as well as after the actual draw command below in the real loop } return m_mainram[0x2079]; } @@ -553,7 +931,7 @@ uint16_t pcp8718_state::ramcall_2434_logger_r() { if (!machine().side_effects_disabled()) { - logerror("call to 0x2434 in RAM (drawing related?)\n"); // [1d] as the tile / sprite number, [1e] as xpos, [1f] as ypos, [20] as 0. [21] as ff in some title drawing calls + // logerror("call to 0x2434 in RAM (drawing related?)\n"); // [1d] as the tile / sprite number, [1e] as xpos, [1f] as ypos, [20] as 0. [21] as ff in some title drawing calls } return m_mainram[0x2434]; } @@ -592,24 +970,31 @@ void pcp8718_state::machine_reset() m_spistate = SPI_STATE_READY; m_spiaddress = 0; + for (int i = 0; i < 0x20000; i++) + m_displaybuffer[i] = i&0xff; + + m_lcdaddr = 0; + + m_lcdstate = LCD_STATE_READY; + m_lastlcdcommand = 0; } void pcp8718_state::pcp8718(machine_config &config) { - UNSP_20(config, m_maincpu, 20000000); // unknown CPU, unsp20 based + UNSP_20(config, m_maincpu, 100000000); // unknown CPU, unsp20 based, must be clocked ~100Mhz, maybe higher (or cycles per instruction needs to be lower for unSP 2.0) m_maincpu->set_addrmap(AS_PROGRAM, &pcp8718_state::map); SCREEN(config, m_screen, SCREEN_TYPE_RASTER); m_screen->set_refresh_hz(60); m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); m_screen->set_size(64*8, 32*8); - m_screen->set_visarea(0*8, 40*8-1, 0*8, 30*8-1); + m_screen->set_visarea(0*8, 320-1, 0*8, 240-1); m_screen->set_screen_update(FUNC(pcp8718_state::screen_update)); - m_screen->set_palette(m_palette); + //m_screen->set_palette(m_palette); - PALETTE(config, m_palette).set_format(palette_device::xBGR_555, 0x200); + PALETTE(config, m_palette).set_format(palette_device::xBGR_555, 0x8000); } // pcp8718 and pcp8728 both contain user data (player name?) and will need to be factory defaulted once they work