1
0
mirror of https://github.com/narzoul/DDrawCompat synced 2024-12-30 08:55:36 +01:00

Updated waitForIdle implementation

Fixes performance issues on old versions of igd9trinity32.dll.
This commit is contained in:
narzoul 2024-08-17 13:51:05 +02:00
parent 1c4445717a
commit c8c6bd0ce9
10 changed files with 66 additions and 47 deletions

View File

@ -586,33 +586,6 @@ namespace D3dDdi
m_state.updateConfig();
}
void Device::waitForIdle()
{
D3dDdi::ScopedCriticalSection lock;
flushPrimitives();
D3DDDIARG_ISSUEQUERY issueQuery = {};
issueQuery.hQuery = m_eventQuery;
issueQuery.Flags.End = 1;
m_origVtable.pfnIssueQuery(m_device, &issueQuery);
if (m_origVtable.pfnFlush1)
{
m_origVtable.pfnFlush1(m_device, 0);
}
else
{
m_origVtable.pfnFlush(m_device);
}
BOOL result = FALSE;
D3DDDIARG_GETQUERYDATA getQueryData = {};
getQueryData.hQuery = m_eventQuery;
getQueryData.pData = &result;
while (S_FALSE == m_origVtable.pfnGetQueryData(m_device, &getQueryData))
{
}
}
std::map<HANDLE, Device> Device::s_devices;
bool Device::s_isFlushEnabled = true;
}

View File

@ -72,7 +72,6 @@ namespace D3dDdi
void setDepthStencil(HANDLE resource);
void setRenderTarget(const D3DDDIARG_SETRENDERTARGET& data);
void updateConfig();
void waitForIdle();
static void add(Adapter& adapter, HANDLE device);
static Device& get(HANDLE device) { return s_devices.find(device)->second; }

View File

@ -1851,4 +1851,46 @@ namespace D3dDdi
m_palettizedTexture->m_isPalettizedTextureUpToDate = true;
m_paletteColorKeyIndex = paletteColorKeyIndex;
}
void Resource::waitForIdle(UINT subResourceIndex)
{
m_device.flushPrimitives();
Resource* srcResource = this;
RECT rect = { 0, 0, 1, 1 };
if (m_lockResource)
{
if (m_lockData[subResourceIndex].isMsaaUpToDate ||
m_lockData[subResourceIndex].isMsaaResolvedUpToDate)
{
if (!m_lockData[subResourceIndex].isMsaaResolvedUpToDate)
{
copySubResourceRegion(*m_msaaResolvedSurface.resource, subResourceIndex, rect,
*m_msaaSurface.resource, subResourceIndex, rect);
}
srcResource = m_msaaResolvedSurface.resource;
}
else if (!m_lockData[subResourceIndex].isVidMemUpToDate)
{
return;
}
}
auto& syncSurface = m_device.getRepo().getSyncSurface(srcResource->m_fixedData.Format);
if (!syncSurface.resource)
{
return;
}
copySubResourceRegion(*syncSurface.resource, 0, rect, *srcResource, subResourceIndex, rect);
D3DDDIARG_LOCK lock = {};
lock.hResource = *syncSurface.resource;
lock.Flags.ReadOnly = 1;
m_device.getOrigVtable().pfnLock(m_device, &lock);
D3DDDIARG_UNLOCK unlock = {};
unlock.hResource = *syncSurface.resource;
m_device.getOrigVtable().pfnUnlock(m_device, &unlock);
}
}

View File

@ -66,6 +66,7 @@ namespace D3dDdi
HRESULT unlock(const D3DDDIARG_UNLOCK& data);
void updateConfig();
void updatePalettizedTexture(UINT stage);
void waitForIdle(UINT subResourceIndex);
static void enableConfig(bool enable);
static void setFormatOverride(D3DDDIFORMAT format);

View File

@ -333,6 +333,11 @@ namespace D3dDdi
return surface;
}
SurfaceRepository::Surface& SurfaceRepository::getSyncSurface(D3DDDIFORMAT format)
{
return getSurface(m_syncSurface[format], 16, 16, format, DDSCAPS_OFFSCREENPLAIN | DDSCAPS_VIDEOMEMORY);
}
SurfaceRepository::Surface& SurfaceRepository::getTempSurface(Surface& surface, DWORD width, DWORD height,
D3DDDIFORMAT format, DWORD caps, UINT surfaceCount)
{

View File

@ -49,6 +49,7 @@ namespace D3dDdi
const Resource* currentSrcRt = nullptr, const Resource* currentDstRt = nullptr);
Surface& getSurface(Surface& surface, DWORD width, DWORD height,
D3DDDIFORMAT format, DWORD caps, UINT surfaceCount = 1, DWORD caps2 = 0);
Surface& getSyncSurface(D3DDDIFORMAT format);
Surface& getTempSysMemSurface(DWORD width, DWORD height);
Surface& getTempSurface(Surface& surface, DWORD width, DWORD height,
D3DDDIFORMAT format, DWORD caps, UINT surfaceCount = 1);
@ -89,6 +90,7 @@ namespace D3dDdi
std::array<Surface, 3> m_hqRenderTargets;
std::map<D3DDDIFORMAT, Surface> m_textures;
std::vector<Surface> m_releasedSurfaces;
std::map<D3DDDIFORMAT, Surface> m_syncSurface;
Surface m_sysMemSurface;
Surface m_windowedBackBuffer;
CompatPtr<IDirectDrawSurface7> m_windowedPrimary;

View File

@ -509,10 +509,9 @@ namespace DDraw
return DD_OK;
}
HRESULT RealPrimarySurface::flip(CompatPtr<IDirectDrawSurface7> surfaceTargetOverride, DWORD flags)
void RealPrimarySurface::flip(CompatPtr<IDirectDrawSurface7> surfaceTargetOverride, DWORD flags)
{
const DWORD flipInterval = getFlipInterval(flags);
PrimarySurface::waitForIdle();
Compat::ScopedCriticalSection lock(g_presentCs);
scheduleUpdate();
@ -527,8 +526,6 @@ namespace DDraw
{
g_lastFlipSurface = nullptr;
}
return DD_OK;
}
int RealPrimarySurface::flush()

View File

@ -13,7 +13,7 @@ namespace DDraw
{
public:
static HRESULT create(CompatRef<IDirectDraw> dd);
static HRESULT flip(CompatPtr<IDirectDrawSurface7> surfaceTargetOverride, DWORD flags);
static void flip(CompatPtr<IDirectDrawSurface7> surfaceTargetOverride, DWORD flags);
static int flush();
static HRESULT getGammaRamp(DDGAMMARAMP* rampData);
static HWND getPresentationWindow();

View File

@ -3,6 +3,7 @@
#include <D3dDdi/Device.h>
#include <D3dDdi/KernelModeThunks.h>
#include <D3dDdi/Resource.h>
#include <D3dDdi/ScopedCriticalSection.h>
#include <D3dDdi/SurfaceRepository.h>
#include <DDraw/DirectDraw.h>
#include <DDraw/DirectDrawSurface.h>
@ -17,10 +18,10 @@
namespace
{
CompatWeakPtr<IDirectDrawSurface7> g_primarySurface;
D3dDdi::Device* g_device = nullptr;
HANDLE g_gdiDriverResource = nullptr;
HANDLE g_gdiRuntimeResource = nullptr;
HANDLE g_frontResource = nullptr;
D3dDdi::Resource* g_frontResource = nullptr;
UINT g_frontResourceIndex = 0;
DWORD g_origCaps = 0;
HWND g_deviceWindow = nullptr;
HPALETTE g_palette = nullptr;
@ -34,10 +35,10 @@ namespace DDraw
{
LOG_FUNC("PrimarySurface::~PrimarySurface");
g_device = nullptr;
g_gdiRuntimeResource = nullptr;
g_gdiDriverResource = nullptr;
g_frontResource = nullptr;
g_frontResourceIndex = 0;
g_primarySurface = nullptr;
g_origCaps = 0;
g_deviceWindow = nullptr;
@ -111,7 +112,6 @@ namespace DDraw
ResizePalette(g_palette, 256);
}
g_device = D3dDdi::Device::findDeviceByResource(DirectDrawSurface::getDriverResourceHandle(*surface));
data->restore();
D3dDdi::Device::updateAllConfig();
return LOG_RESULT(DD_OK);
@ -215,7 +215,7 @@ namespace DDraw
HANDLE PrimarySurface::getFrontResource()
{
return g_frontResource;
return *g_frontResource;
}
HANDLE PrimarySurface::getGdiResource()
@ -260,7 +260,7 @@ namespace DDraw
g_gdiRuntimeResource = DirectDrawSurface::getRuntimeResourceHandle(*g_primarySurface);
updateFrontResource();
g_gdiDriverResource = g_frontResource;
g_gdiDriverResource = *g_frontResource;
D3dDdi::Device::setGdiResourceHandle(g_gdiDriverResource);
DDSCAPS2 caps = {};
@ -324,7 +324,8 @@ namespace DDraw
void PrimarySurface::updateFrontResource()
{
g_frontResource = DirectDrawSurface::getDriverResourceHandle(*g_primarySurface);
g_frontResource = D3dDdi::Device::findResource(DirectDrawSurface::getDriverResourceHandle(*g_primarySurface));
g_frontResourceIndex = DirectDrawSurface::getSubResourceIndex(*g_primarySurface);
}
void PrimarySurface::updatePalette()
@ -360,10 +361,8 @@ namespace DDraw
void PrimarySurface::waitForIdle()
{
if (g_device)
{
g_device->waitForIdle();
}
D3dDdi::ScopedCriticalSection lock;
g_frontResource->waitForIdle(g_frontResourceIndex);
}
CompatWeakPtr<IDirectDrawPalette> PrimarySurface::s_palette;

View File

@ -198,13 +198,14 @@ namespace DDraw
}
PrimarySurface::updateFrontResource();
result = RealPrimarySurface::flip(surfaceTargetOverride, dwFlags);
if (SUCCEEDED(result) && Config::Settings::FpsLimiter::FLIPEND == Config::fpsLimiter.get())
RealPrimarySurface::flip(surfaceTargetOverride, dwFlags);
PrimarySurface::waitForIdle();
if (Config::Settings::FpsLimiter::FLIPEND == Config::fpsLimiter.get())
{
DDraw::RealPrimarySurface::waitForFlip(m_data->getDDS());
RealPrimarySurface::waitForFlipFpsLimit();
}
return result;
return DD_OK;
}
template <typename TSurface>