From f97679a76281e0eac0581d50ac665c7b013e6cc4 Mon Sep 17 00:00:00 2001 From: MooglyGuy Date: Fri, 5 Jul 2019 21:52:40 +0200 Subject: -midtunit: Add MIDTUNIT_LOG_PNG define, to log unscaled 32bpp PNGs of all DMA draw calls. [Ryan Holtz] --- src/mame/video/midtunit.cpp | 170 ++++++++++++++++++++++++++++++++++++++++++++ src/mame/video/midtunit.h | 7 ++ 2 files changed, 177 insertions(+) diff --git a/src/mame/video/midtunit.cpp b/src/mame/video/midtunit.cpp index 303e374f5fe..20dc6b836d3 100644 --- a/src/mame/video/midtunit.cpp +++ b/src/mame/video/midtunit.cpp @@ -12,6 +12,8 @@ #include "midtunit.ipp" #include "screen.h" #include "midtview.ipp" +#include "emuopts.h" // Used by MIDTUNIT_LOG_PNG +#include "png.h" // Used by MIDTUNIT_LOG_PNG DEFINE_DEVICE_TYPE(MIDTUNIT_VIDEO, midtunit_video_device, "tunitvid", "Midway T-Unit Video") DEFINE_DEVICE_TYPE(MIDWUNIT_VIDEO, midwunit_video_device, "wunitvid", "Midway W-Unit Video") @@ -65,6 +67,9 @@ void midtunit_video_device::device_start() #if DEBUG_MIDTUNIT_BLITTER m_debug_videoram = std::make_unique(0x100000/2); #endif +#if MIDTUNIT_LOG_PNG + m_logged_rom = std::make_unique(0x4000000); +#endif m_dma_timer = timer_alloc(TIMER_DMA); @@ -682,6 +687,17 @@ WRITE16_MEMBER(midtunit_video_device::midtunit_dma_w) m_dma_state.endskip = m_dma_register[DMA_LRSKIP]; } +#if MIDTUNIT_LOG_PNG + if (command & 0x80) + { + log_bitmap(command, bpp ? bpp : 8, true); + } + else + { + log_bitmap(command, bpp ? bpp : 8, false); + } +#endif + /* then draw */ if (m_dma_state.xstep == 0x100 && m_dma_state.ystep == 0x100) { @@ -741,3 +757,157 @@ TMS340X0_SCANLINE_IND16_CB_MEMBER(midxunit_video_device::scanline_update) for (int x = params->heblnk; x < params->hsblnk; x++) dest[x] = src[fulladdr++ & 0x1ff] & 0x7fff; } + +#if MIDTUNIT_LOG_PNG +void midtunit_video_device::log_bitmap(int command, int bpp, bool Skip) +{ + const uint32_t raw_offset = m_dma_register[DMA_OFFSETLO] | (m_dma_register[DMA_OFFSETHI] << 16); + if (m_logged_rom[raw_offset >> 6] & (1ULL << (raw_offset & 0x3f))) + return; + + int Zero = PIXEL_SKIP; + int NonZero = PIXEL_SKIP; + switch (command & 0xf) + { + case 1: Zero = PIXEL_COPY; NonZero = PIXEL_SKIP; break; + case 2: Zero = PIXEL_SKIP; NonZero = PIXEL_COPY; break; + case 3: Zero = PIXEL_COPY; NonZero = PIXEL_COPY; break; + case 4: Zero = PIXEL_COLOR; NonZero = PIXEL_SKIP; break; + case 5: Zero = PIXEL_COLOR; NonZero = PIXEL_SKIP; break; + case 6: Zero = PIXEL_COLOR; NonZero = PIXEL_COPY; break; + case 7: Zero = PIXEL_COLOR; NonZero = PIXEL_COPY; break; + case 8: Zero = PIXEL_SKIP; NonZero = PIXEL_COLOR; break; + case 9: Zero = PIXEL_COPY; NonZero = PIXEL_COLOR; break; + case 10: Zero = PIXEL_SKIP; NonZero = PIXEL_COLOR; break; + case 11: Zero = PIXEL_COPY; NonZero = PIXEL_COLOR; break; + case 12: Zero = PIXEL_COLOR; NonZero = PIXEL_COLOR; break; + case 13: Zero = PIXEL_COLOR; NonZero = PIXEL_COLOR; break; + case 14: Zero = PIXEL_COLOR; NonZero = PIXEL_COLOR; break; + case 15: Zero = PIXEL_COLOR; NonZero = PIXEL_COLOR; break; + default: return; + } + + emu_file file(machine().options().snapshot_directory(), OPEN_FLAG_WRITE | OPEN_FLAG_CREATE | OPEN_FLAG_CREATE_PATHS); + + char name_buf[256]; + snprintf(name_buf, 255, "0x%08x.png", raw_offset); + auto const filerr = file.open(name_buf); + if (filerr != osd_file::error::NONE) + { + return; + } + + m_logged_rom[raw_offset >> 6] |= 1ULL << (raw_offset & 0x3f); + + m_log_bitmap.allocate(m_dma_state.width, m_dma_state.height); + m_log_bitmap.fill(0); + + uint8_t *base = m_dma_state.gfxrom; + uint32_t offset = m_dma_state.offset; + uint16_t pal = m_dma_state.palette; + uint16_t color = pal | m_dma_state.color; + int mask = (1 << bpp) - 1; + + /* loop over the height */ + for (int y = 0; y < m_dma_state.height; y++) + { + int startskip = m_dma_state.startskip; + int endskip = m_dma_state.endskip; + int width = m_dma_state.width; + int ix = 0; + int tx; + uint32_t o = offset; + int pre, post; + + /* handle skipping */ + if (Skip) + { + uint8_t value = EXTRACTGEN(0xff); + o += 8; + + /* adjust for preskip */ + pre = (value & 0x0f) << m_dma_state.preskip; + tx = pre; + ix += tx; + + /* adjust for postskip */ + post = ((value >> 4) & 0x0f) << m_dma_state.postskip; + width -= post; + endskip -= post; + } + + /* handle start skip */ + if (ix < startskip) + { + tx = (startskip - ix); + ix += tx; + o += tx * bpp; + } + + /* handle end skip */ + if (width > m_dma_state.width - m_dma_state.endskip) + width = m_dma_state.width - m_dma_state.endskip; + + bitmap_rgb32::pixel_t *d = &m_log_bitmap.pix(y, ix); + + /* determine destination pointer */ + + /* loop until we draw the entire width */ + while (ix < width) + { + /* special case similar handling of zero/non-zero */ + if (Zero == NonZero) + { + if (Zero == PIXEL_COLOR) + *d = m_palette->palette()->entry_list_raw()[color]; + else if (Zero == PIXEL_COPY) + *d = m_palette->palette()->entry_list_raw()[(EXTRACTGEN(mask)) | pal]; + } + + /* otherwise, read the pixel and look */ + else + { + int pixel = (EXTRACTGEN(mask)); + + /* non-zero pixel case */ + if (pixel) + { + if (NonZero == PIXEL_COLOR) + *d = m_palette->palette()->entry_list_raw()[color]; + else if (NonZero == PIXEL_COPY) + *d = m_palette->palette()->entry_list_raw()[pixel | pal]; + } + + /* zero pixel case */ + else + { + if (Zero == PIXEL_COLOR) + *d = m_palette->palette()->entry_list_raw()[color]; + else if (Zero == PIXEL_COPY) + *d = m_palette->palette()->entry_list_raw()[pal]; + } + } + + /* advance to the next pixel */ + ix++; + d++; + o += bpp; + } + + /* advance to the next row */ + width = m_dma_state.width; + if (Skip) + { + offset += 8; + width -= pre + post; + if (width > 0) offset += width * bpp; + } + else + { + offset += width * bpp; + } + } + + png_write_bitmap(file, nullptr, m_log_bitmap, 0, nullptr); +} +#endif \ No newline at end of file diff --git a/src/mame/video/midtunit.h b/src/mame/video/midtunit.h index baba3687f2e..2a09b64d80f 100644 --- a/src/mame/video/midtunit.h +++ b/src/mame/video/midtunit.h @@ -17,6 +17,7 @@ #include "emupal.h" #define DEBUG_MIDTUNIT_BLITTER (0) +#define MIDTUNIT_LOG_PNG (0) class midtunit_video_device : public device_t { @@ -165,6 +166,12 @@ protected: int32_t m_debug_dma_mode; int32_t m_debug_dma_command; #endif +#if MIDTUNIT_LOG_PNG + std::unique_ptr m_logged_rom; + bitmap_argb32 m_log_bitmap; + + void log_bitmap(int command, int bpp, bool skip); +#endif }; class midwunit_video_device : public midtunit_video_device -- cgit v1.2.3