Implement GetBufferData() for D3D12

This commit is contained in:
baldurk
2016-09-23 13:28:54 +02:00
parent e12ebb67a3
commit d0fe1fb56f
3 changed files with 116 additions and 16 deletions
+96
View File
@@ -1391,6 +1391,102 @@ void D3D12DebugManager::PickPixel(ResourceId texture, uint32_t x, uint32_t y, ui
m_ReadbackBuffer->Unmap(0, &range);
}
void D3D12DebugManager::GetBufferData(ResourceId buff, uint64_t offset, uint64_t length,
vector<byte> &retData)
{
auto it = WrappedID3D12Resource::m_List.find(buff);
if(it == WrappedID3D12Resource::m_List.end())
{
RDCERR("Getting buffer data for unknown buffer %llu!", buff);
return;
}
WrappedID3D12Resource *buffer = it->second;
RDCASSERT(buffer);
GetBufferData(buffer, offset, length, retData);
}
void D3D12DebugManager::GetBufferData(ID3D12Resource *buffer, uint64_t offset, uint64_t length,
vector<byte> &ret)
{
if(buffer == NULL)
return;
D3D12_RESOURCE_DESC desc = buffer->GetDesc();
if(offset >= desc.Width)
{
// can't read past the end of the buffer, return empty
return;
}
if(length == 0)
{
length = desc.Width - offset;
}
if(length > 0 && offset + length > desc.Width)
{
RDCWARN("Attempting to read off the end of the buffer (%llu %llu). Will be clamped (%llu)",
offset, length, desc.Width);
length = RDCMIN(length, desc.Width - offset);
}
uint64_t outOffs = 0;
ret.resize(length);
ID3D12GraphicsCommandList *list = m_WrappedDevice->GetNewList();
D3D12_RESOURCE_BARRIER barrier = {};
barrier.Transition.pResource = buffer;
barrier.Transition.StateBefore = m_WrappedDevice->GetSubresourceStates(GetResID(buffer))[0];
barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_COPY_SOURCE;
list->ResourceBarrier(1, &barrier);
while(length > 0)
{
uint64_t chunkSize = RDCMIN(length, m_ReadbackSize);
list->CopyBufferRegion(m_ReadbackBuffer, 0, buffer, offset, chunkSize);
list->Close();
m_WrappedDevice->ExecuteLists();
m_WrappedDevice->FlushLists();
D3D12_RANGE range = {0, chunkSize};
void *data;
HRESULT hr = m_ReadbackBuffer->Map(0, &range, &data);
if(FAILED(hr))
{
RDCERR("Failed to map bufferdata buffer %08x", hr);
return;
}
else
{
memcpy(&ret[outOffs], data, chunkSize);
range.End = 0;
m_ReadbackBuffer->Unmap(0, &range);
}
outOffs += chunkSize;
length -= chunkSize;
if(length > 0)
list = m_WrappedDevice->GetNewList();
}
}
void D3D12DebugManager::RenderCheckerboard(Vec3f light, Vec3f dark)
{
DebugVertexCBuffer vertexData;
+4 -1
View File
@@ -73,6 +73,9 @@ public:
void PickPixel(ResourceId texture, uint32_t x, uint32_t y, uint32_t sliceFace, uint32_t mip,
uint32_t sample, FormatComponentType typeHint, float pixel[4]);
void GetBufferData(ResourceId buff, uint64_t offset, uint64_t length, vector<byte> &retData);
void GetBufferData(ID3D12Resource *buff, uint64_t offset, uint64_t length, vector<byte> &retData);
D3D12_CPU_DESCRIPTOR_HANDLE AllocRTV();
void FreeRTV(D3D12_CPU_DESCRIPTOR_HANDLE handle);
@@ -179,7 +182,7 @@ private:
ID3D12Resource *m_ReadbackBuffer;
static const uint32_t m_ReadbackSize = 8 * 1024 * 1024;
static const uint64_t m_ReadbackSize = 16 * 1024 * 1024;
static const uint32_t m_ShaderCacheMagic = 0xbaafd1d1;
static const uint32_t m_ShaderCacheVersion = 1;
+16 -15
View File
@@ -57,6 +57,17 @@ void D3D12Replay::ReadLogInitialisation()
m_pDevice->ReadLogInitialisation();
}
APIProperties D3D12Replay::GetAPIProperties()
{
APIProperties ret;
ret.pipelineType = eGraphicsAPI_D3D12;
ret.localRenderer = eGraphicsAPI_D3D12;
ret.degraded = false;
return ret;
}
void D3D12Replay::ReplayLog(uint32_t endEventID, ReplayLogType replayType)
{
m_pDevice->ReplayLog(0, endEventID, replayType);
@@ -1135,6 +1146,11 @@ bool D3D12Replay::RenderTexture(TextureDisplay cfg)
return m_pDevice->GetDebugManager()->RenderTexture(cfg, true);
}
void D3D12Replay::GetBufferData(ResourceId buff, uint64_t offset, uint64_t len, vector<byte> &retData)
{
m_pDevice->GetDebugManager()->GetBufferData(buff, offset, len, retData);
}
void D3D12Replay::PickPixel(ResourceId texture, uint32_t x, uint32_t y, uint32_t sliceFace,
uint32_t mip, uint32_t sample, FormatComponentType typeHint,
float pixel[4])
@@ -1214,17 +1230,6 @@ Callstack::StackResolver *D3D12Replay::GetCallstackResolver()
#pragma region not yet implemented
APIProperties D3D12Replay::GetAPIProperties()
{
APIProperties ret;
ret.pipelineType = eGraphicsAPI_D3D12;
ret.localRenderer = eGraphicsAPI_D3D12;
ret.degraded = false;
return ret;
}
vector<DebugMessage> D3D12Replay::GetDebugMessages()
{
return vector<DebugMessage>();
@@ -1266,10 +1271,6 @@ MeshFormat D3D12Replay::GetPostVSBuffers(uint32_t eventID, uint32_t instID, Mesh
return MeshFormat();
}
void D3D12Replay::GetBufferData(ResourceId buff, uint64_t offset, uint64_t len, vector<byte> &retData)
{
}
byte *D3D12Replay::GetTextureData(ResourceId tex, uint32_t arrayIdx, uint32_t mip, bool forDiskSave,
FormatComponentType typeHint, bool resolve, bool forceRGBA8unorm,
float blackPoint, float whitePoint, size_t &dataSize)