From 6ec91e81ce433847ef7183bb12610e36aced5ead Mon Sep 17 00:00:00 2001 From: Philip Rebohle Date: Thu, 26 Sep 2024 08:53:53 +0200 Subject: [PATCH] [d3d11] Cache raw mapped pointer rather than allocation object Reduces ref counting overhead again and matches previous behaviour. We should probably do something about the possible case of deferred context execution with MAP_WRITE_DISCARD followed by MAP_WRITE_NO_OVERWRITE on the immediate context, but we haven't seen a game rely on this yet. --- src/d3d11/d3d11_buffer.cpp | 6 +++--- src/d3d11/d3d11_buffer.h | 12 +++++++----- src/d3d11/d3d11_context_imm.cpp | 11 +++++------ src/d3d11/d3d11_initializer.cpp | 2 +- 4 files changed, 16 insertions(+), 15 deletions(-) diff --git a/src/d3d11/d3d11_buffer.cpp b/src/d3d11/d3d11_buffer.cpp index 1895cc7a685..f5f2c34aa42 100644 --- a/src/d3d11/d3d11_buffer.cpp +++ b/src/d3d11/d3d11_buffer.cpp @@ -98,7 +98,7 @@ namespace dxvk { info.usage |= VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT; m_buffer = m_parent->GetDXVKDevice()->importBuffer(info, importInfo, GetMemoryFlags()); - m_allocation = m_buffer->getAllocation(); + m_mapPtr = m_buffer->mapPtr(0); m_mapMode = DetermineMapMode(m_buffer->memFlags()); } else if (!(pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL)) { @@ -114,12 +114,12 @@ namespace dxvk { // Create the buffer and set the entire buffer slice as mapped, // so that we only have to update it when invalidating the buffer m_buffer = m_parent->GetDXVKDevice()->createBuffer(info, memoryFlags); - m_allocation = m_buffer->getAllocation(); + m_mapPtr = m_buffer->mapPtr(0); } else { m_sparseAllocator = m_parent->GetDXVKDevice()->createSparsePageAllocator(); m_sparseAllocator->setCapacity(info.size / SparseMemoryPageSize); - m_allocation = nullptr; + m_mapPtr = nullptr; m_mapMode = D3D11_COMMON_BUFFER_MAP_MODE_NONE; } diff --git a/src/d3d11/d3d11_buffer.h b/src/d3d11/d3d11_buffer.h index d9ca2e3832f..7270b0c09c4 100644 --- a/src/d3d11/d3d11_buffer.h +++ b/src/d3d11/d3d11_buffer.h @@ -118,12 +118,13 @@ namespace dxvk { } Rc DiscardSlice(DxvkLocalAllocationCache* cache) { - m_allocation = m_buffer->allocateSlice(cache); - return m_allocation; + auto allocation = m_buffer->allocateSlice(cache); + m_mapPtr = allocation->mapPtr(); + return allocation; } - Rc GetMappedSlice() const { - return m_allocation; + void* GetMapPtr() const { + return m_mapPtr; } D3D10Buffer* GetD3D10Iface() { @@ -184,9 +185,10 @@ namespace dxvk { Rc m_buffer; Rc m_soCounter; Rc m_sparseAllocator; - Rc m_allocation; uint64_t m_seq = 0ull; + void* m_mapPtr = nullptr; + D3D11DXGIResource m_resource; D3D10Buffer m_d3d10; diff --git a/src/d3d11/d3d11_context_imm.cpp b/src/d3d11/d3d11_context_imm.cpp index b4a627a1403..ff039126732 100644 --- a/src/d3d11/d3d11_context_imm.cpp +++ b/src/d3d11/d3d11_context_imm.cpp @@ -348,7 +348,7 @@ namespace dxvk { } else if (likely(MapType == D3D11_MAP_WRITE_NO_OVERWRITE)) { // Put this on a fast path without any extra checks since it's // a somewhat desired method to partially update large buffers - pMappedResource->pData = pResource->GetMappedSlice()->mapPtr(); + pMappedResource->pData = pResource->GetMapPtr(); pMappedResource->RowPitch = bufferSize; pMappedResource->DepthPitch = bufferSize; return S_OK; @@ -376,10 +376,9 @@ namespace dxvk { } if (doInvalidatePreserve) { - auto srcSlice = pResource->GetMappedSlice(); - auto dstSlice = pResource->DiscardSlice(nullptr); + auto srcPtr = pResource->GetMapPtr(); - auto srcPtr = srcSlice->mapPtr(); + auto dstSlice = pResource->DiscardSlice(nullptr); auto dstPtr = dstSlice->mapPtr(); EmitCs([ @@ -398,7 +397,7 @@ namespace dxvk { if (!WaitForResource(buffer, sequenceNumber, MapType, MapFlags)) return DXGI_ERROR_WAS_STILL_DRAWING; - pMappedResource->pData = pResource->GetMappedSlice()->mapPtr(); + pMappedResource->pData = pResource->GetMapPtr(); pMappedResource->RowPitch = bufferSize; pMappedResource->DepthPitch = bufferSize; return S_OK; @@ -713,7 +712,7 @@ namespace dxvk { ctx->invalidateBuffer(cBuffer, std::move(cBufferSlice)); }); } else { - mapPtr = pDstBuffer->GetMappedSlice()->mapPtr(); + mapPtr = pDstBuffer->GetMapPtr(); } std::memcpy(reinterpret_cast(mapPtr) + Offset, pSrcData, Length); diff --git a/src/d3d11/d3d11_initializer.cpp b/src/d3d11/d3d11_initializer.cpp index 2190fda498b..7a264e385b6 100644 --- a/src/d3d11/d3d11_initializer.cpp +++ b/src/d3d11/d3d11_initializer.cpp @@ -313,4 +313,4 @@ namespace dxvk { } } -} \ No newline at end of file +}