Fix threading issues with GPU buffers mapping

This commit is contained in:
Wojciech Figat
2023-01-04 12:06:56 +01:00
parent 0b8d4850f0
commit 88bd5b2534
6 changed files with 15 additions and 6 deletions

View File

@@ -447,6 +447,8 @@ void GPUDevice::preDispose()
SAFE_DELETE_GPU_RESOURCE(_res->PS_Clear);
SAFE_DELETE_GPU_RESOURCE(_res->FullscreenTriangleVB);
Locker.Unlock();
// Release GPU resources memory and unlink from device
// Note: after that no GPU resources should be used/created, only deleted
_resourcesLock.Lock();
@@ -456,7 +458,6 @@ void GPUDevice::preDispose()
}
_resources.Clear();
_resourcesLock.Unlock();
Locker.Unlock();
}
void GPUDevice::DrawBegin()

View File

@@ -21,6 +21,7 @@ void* GPUBufferDX11::Map(GPUResourceMapMode mode)
{
if (!IsInMainThread())
_device->Locker.Lock();
ASSERT(!_mapped);
D3D11_MAPPED_SUBRESOURCE map;
map.pData = nullptr;
@@ -46,13 +47,18 @@ void* GPUBufferDX11::Map(GPUResourceMapMode mode)
const HRESULT result = _device->GetIM()->Map(_resource, 0, mapType, mapFlags, &map);
if (result != DXGI_ERROR_WAS_STILL_DRAWING)
LOG_DIRECTX_RESULT(result);
_mapped = map.pData != nullptr;
return map.pData;
}
void GPUBufferDX11::Unmap()
{
_device->GetIM()->Unmap(_resource, 0);
if (_mapped)
{
_mapped = false;
_device->GetIM()->Unmap(_resource, 0);
}
if (!IsInMainThread())
_device->Locker.Unlock();
}

View File

@@ -101,6 +101,7 @@ private:
ID3D11Buffer* _resource = nullptr;
GPUBufferViewDX11 _view;
bool _mapped = false;
public:

View File

@@ -77,9 +77,10 @@ void GPUBufferDX12::Unmap()
writtenRangePtr = nullptr;
break;
default:
CRASH;
return;
}
_resource->Unmap(0, writtenRangePtr);
_lastMapMode = (GPUResourceMapMode)255;
}
GPUResource* GPUBufferDX12::AsGPUResource() const

View File

@@ -113,7 +113,7 @@ private:
GPUBufferViewDX12 _view;
GPUBufferDX12* _counter = nullptr;
GPUResourceMapMode _lastMapMode;
GPUResourceMapMode _lastMapMode = (GPUResourceMapMode)255;
public:

View File

@@ -684,13 +684,13 @@ bool GlobalSurfaceAtlasPass::Render(RenderContext& renderContext, GPUContext* co
if (data)
{
uint32 counter = data[surfaceAtlasData.CulledObjectsCounterIndex];
_culledObjectsSizeBuffer->Unmap();
if (counter > 0)
{
objectsBufferCapacity = counter;
notReady = false;
}
}
_culledObjectsSizeBuffer->Unmap();
// Allow to be ready if the buffer was already used
if (notReady && surfaceAtlasData.CulledObjectsBuffer && surfaceAtlasData.CulledObjectsBuffer->IsAllocated())