From d2adc5c81195dae7a162e738f4a446b031c49173 Mon Sep 17 00:00:00 2001 From: narzoul Date: Sun, 16 Jul 2017 20:35:31 +0200 Subject: [PATCH] Fixed incorrect primary update schedule when updates are disabled/enabled --- DDrawCompat/DDraw/RealPrimarySurface.cpp | 52 +++++++++++++++--------- 1 file changed, 32 insertions(+), 20 deletions(-) diff --git a/DDrawCompat/DDraw/RealPrimarySurface.cpp b/DDrawCompat/DDraw/RealPrimarySurface.cpp index baae367..7390e59 100644 --- a/DDrawCompat/DDraw/RealPrimarySurface.cpp +++ b/DDrawCompat/DDraw/RealPrimarySurface.cpp @@ -31,6 +31,7 @@ namespace HANDLE g_updateThread = nullptr; HANDLE g_updateEvent = nullptr; std::atomic g_disableUpdateCount = 0; + bool g_isUpdateSuspended = false; long long g_qpcFlipModeTimeout = 0; long long g_qpcLastFlip = 0; long long g_qpcNextUpdate = 0; @@ -42,11 +43,6 @@ namespace { Compat::LogEnter("RealPrimarySurface::compatBlt", dest); - if (g_disableUpdateCount > 0) - { - return false; - } - bool result = false; auto primary(DDraw::PrimarySurface::getPrimary()); @@ -293,15 +289,19 @@ namespace DDraw void RealPrimarySurface::disableUpdates() { - ++g_disableUpdateCount; - ResetEvent(g_updateEvent); + if (0 == g_disableUpdateCount++ && isUpdateScheduled()) + { + ResetEvent(g_updateEvent); + g_isUpdateSuspended = true; + } } void RealPrimarySurface::enableUpdates() { - if (0 == --g_disableUpdateCount) + if (0 == --g_disableUpdateCount && g_isUpdateSuspended) { - update(); + SetEvent(g_updateEvent); + g_isUpdateSuspended = false; } } @@ -313,6 +313,8 @@ namespace DDraw } ResetEvent(g_updateEvent); + g_isUpdateSuspended = false; + g_qpcLastFlip = Time::queryPerformanceCounter(); compatBlt(*g_backBuffer); HRESULT result = g_frontBuffer->Flip(g_frontBuffer, nullptr, flags); @@ -414,24 +416,34 @@ namespace DDraw void RealPrimarySurface::update() { - if (0 == g_disableUpdateCount && (g_isFullScreen || g_clipper)) + if (g_isUpdateSuspended || !(g_isFullScreen || g_clipper)) { - if (!isUpdateScheduled()) + return; + } + + if (!isUpdateScheduled()) + { + const auto qpcNow = Time::queryPerformanceCounter(); + const long long missedIntervals = (qpcNow - g_qpcNextUpdate) / g_qpcUpdateInterval; + g_qpcNextUpdate += g_qpcUpdateInterval * (missedIntervals + 1); + if (Time::qpcToMs(g_qpcNextUpdate - qpcNow) < 2) + { + g_qpcNextUpdate += g_qpcUpdateInterval; + } + + if (g_disableUpdateCount <= 0) { - const auto qpcNow = Time::queryPerformanceCounter(); - const long long missedIntervals = (qpcNow - g_qpcNextUpdate) / g_qpcUpdateInterval; - g_qpcNextUpdate += g_qpcUpdateInterval * (missedIntervals + 1); - if (Time::qpcToMs(g_qpcNextUpdate - qpcNow) < 2) - { - g_qpcNextUpdate += g_qpcUpdateInterval; - } SetEvent(g_updateEvent); } - else if (msUntilNextUpdate() <= 0) + else { - updateNow(); + g_isUpdateSuspended = true; } } + else if (msUntilNextUpdate() <= 0) + { + updateNow(); + } } void RealPrimarySurface::updatePalette(DWORD startingEntry, DWORD count)