From 71de1ddb2e9d77659abc722ca2d327d0c1087dba Mon Sep 17 00:00:00 2001 From: angelosa Date: Tue, 9 May 2023 19:45:37 +0200 Subject: [PATCH] sega/powervr2.cpp: apply portions of PR #7746 to newest code --- src/mame/sega/powervr2.cpp | 53 +++++++++++++++++++++++++++++++++----- src/mame/sega/powervr2.h | 4 +++ 2 files changed, 50 insertions(+), 7 deletions(-) diff --git a/src/mame/sega/powervr2.cpp b/src/mame/sega/powervr2.cpp index 13ca2540a23..3e3b56ba3b5 100644 --- a/src/mame/sega/powervr2.cpp +++ b/src/mame/sega/powervr2.cpp @@ -996,9 +996,33 @@ void powervr2_device::softreset_w(offs_t offset, uint32_t data, uint32_t mem_mas } } -void powervr2_device::startrender_w(address_space &space, uint32_t data) +void powervr2_device::startrender_w(address_space& space, uint32_t data) { + if (m_render_request) + { + int result; + do + { + result = osd_work_item_wait(m_render_request, 1000); + //printf("waiting\n"); + + } while (result == 0); + osd_work_item_release(m_render_request); + } + + m_render_request = osd_work_item_queue(m_work_queue, blit_request_callback, (void*)this, 0); + dc_state *state = machine().driver_data(); + + // hacky end of render delay for Capcom games, otherwise they works at ~1/10 speed + int sanitycount = 1500; + endofrender_timer_isp->adjust(state->m_maincpu->cycles_to_attotime(sanitycount*25 + 2000000)); // hacky end of render delay for Capcom games, otherwise they works at ~1/10 speed +} + + +void powervr2_device::startrender_real_w(address_space &space) +{ + //dc_state *state = machine().driver_data(); auto profile = g_profiler.start(PROFILER_USER1); LOGTACMD("Start render, region=%08x, params=%08x\n", region_base, param_base); @@ -1014,7 +1038,7 @@ void powervr2_device::startrender_w(address_space &space, uint32_t data) grab[a].fbwsof1 = fb_w_sof1; grab[a].fbwsof2 = fb_w_sof2; - rectangle clip(0, 1023, 0, 1023); + rectangle clip(0, 640, 0, 480); // we've got a request to draw, so, draw to the accumulation buffer! // this should really be done for each tile! @@ -1074,16 +1098,26 @@ void powervr2_device::startrender_w(address_space &space, uint32_t data) // vbl-in and expect that it completes after some time that vbl-out kicks in, // in order to have enough time to execute logic stuff in the meantime. // const u64 isp_completion = sanitycount * 25 + 500000; - const u64 isp_completion = sanitycount * 25 + 2000000; - LOGIRQ("[%d] ISP end of render start %d in %d cycles\n", - screen().frame_number(), screen().vpos(), isp_completion - ); - endofrender_timer_isp->adjust(state->m_maincpu->cycles_to_attotime(isp_completion)); + //const u64 isp_completion = sanitycount * 25 + 2000000; + //LOGIRQ("[%d] ISP end of render start %d in %d cycles\n", + // screen().frame_number(), screen().vpos(), isp_completion + //); + //endofrender_timer_isp->adjust(state->m_maincpu->cycles_to_attotime(isp_completion)); break; } } } +void *powervr2_device::blit_request_callback(void *param, int threadid) +{ + powervr2_device *object = reinterpret_cast(param); + + dc_state *state = object->machine().driver_data(); + address_space &space = state->m_maincpu->space(AS_PROGRAM); + + object->startrender_real_w(space); + return nullptr; +} uint32_t powervr2_device::param_base_r() { @@ -4045,6 +4079,9 @@ void powervr2_device::device_start() save_pointer(NAME(tafifo_buff),32); save_item(NAME(scanline)); save_item(NAME(next_y)); + + m_work_queue = nullptr; + m_render_request = nullptr; } void powervr2_device::device_reset() @@ -4082,6 +4119,8 @@ void powervr2_device::device_reset() dc_state *state = machine().driver_data(); dc_texture_ram = state->dc_texture_ram.target(); dc_framebuffer_ram = state->dc_framebuffer_ram.target(); + + m_work_queue = osd_work_queue_alloc(WORK_QUEUE_FLAG_HIGH_FREQ); } /* called by TIMER_ADD_PERIODIC, in driver sections (controlled by SPG, that's a PVR sub-device) */ diff --git a/src/mame/sega/powervr2.h b/src/mame/sega/powervr2.h index a2afbf4c7f9..5adfbd28396 100644 --- a/src/mame/sega/powervr2.h +++ b/src/mame/sega/powervr2.h @@ -197,12 +197,16 @@ public: uint32_t tafifo_buff[32]; int scanline; int next_y; + osd_work_queue *m_work_queue; + osd_work_item *m_render_request; + static void *blit_request_callback(void *param, int threadid); uint32_t id_r(); uint32_t revision_r(); uint32_t softreset_r(); void softreset_w(offs_t offset, uint32_t data, uint32_t mem_mask = ~0); void startrender_w(address_space &space, uint32_t data); + void startrender_real_w(address_space &space); uint32_t param_base_r(); void param_base_w(offs_t offset, uint32_t data, uint32_t mem_mask = ~0); uint32_t region_base_r();