mirror of
https://github.com/baldurk/renderdoc.git
synced 2026-07-28 18:31:40 +00:00
Track renderstate as we go, and allow replaying single draws with it
This commit is contained in:
@@ -55,7 +55,7 @@ bool WrappedID3D12GraphicsCommandList::Serialise_Close()
|
||||
{
|
||||
ID3D12GraphicsCommandList *list = m_Cmd->RerecordCmdList(CommandList);
|
||||
#ifdef VERBOSE_PARTIAL_REPLAY
|
||||
RDCDEBUG("Ending partial command buffer for %llu baked to %llu", CommandList, bakeId);
|
||||
RDCDEBUG("Ending partial command list for %llu baked to %llu", CommandList, bakeId);
|
||||
#endif
|
||||
|
||||
list->Close();
|
||||
@@ -151,7 +151,7 @@ bool WrappedID3D12GraphicsCommandList::Serialise_Reset(ID3D12CommandAllocator *p
|
||||
bool partial = false;
|
||||
int partialType = D3D12CommandData::ePartialNum;
|
||||
|
||||
// check for partial execution of this command buffer
|
||||
// check for partial execution of this command list
|
||||
for(int p = 0; p < D3D12CommandData::ePartialNum; p++)
|
||||
{
|
||||
const vector<uint32_t> &baseEvents = m_Cmd->m_Partial[p].cmdListExecs[bakeId];
|
||||
@@ -161,8 +161,8 @@ bool WrappedID3D12GraphicsCommandList::Serialise_Reset(ID3D12CommandAllocator *p
|
||||
if(*it <= m_Cmd->m_LastEventID && m_Cmd->m_LastEventID < (*it + length))
|
||||
{
|
||||
#ifdef VERBOSE_PARTIAL_REPLAY
|
||||
RDCDEBUG("vkBegin - partial detected %u < %u < %u, %llu -> %llu", *it,
|
||||
m_Cmd->m_LastEventID, *it + length, CommandList, bakeId);
|
||||
RDCDEBUG("Reset - partial detected %u < %u < %u, %llu -> %llu", *it, m_Cmd->m_LastEventID,
|
||||
*it + length, CommandList, bakeId);
|
||||
#endif
|
||||
|
||||
m_Cmd->m_Partial[p].partialParent = CommandList;
|
||||
@@ -206,9 +206,9 @@ bool WrappedID3D12GraphicsCommandList::Serialise_Reset(ID3D12CommandAllocator *p
|
||||
// can be found in the subsequent serialised commands that ref the
|
||||
// non-baked ID. The baked ID is referenced by the submit itself.
|
||||
//
|
||||
// In vkEndCommandBuffer we erase the non-baked reference, and since
|
||||
// we know you can only be recording a command buffer once at a time
|
||||
// (even if it's baked to several command buffers in the frame)
|
||||
// In Close() we erase the non-baked reference, and since
|
||||
// we know you can only be recording a command list once at a time
|
||||
// (even if it's baked to several command listsin the frame)
|
||||
// there's no issue with clashes here.
|
||||
m_Cmd->m_RerecordCmds[bakeId] = list;
|
||||
m_Cmd->m_RerecordCmds[CommandList] = list;
|
||||
@@ -230,7 +230,7 @@ bool WrappedID3D12GraphicsCommandList::Serialise_Reset(ID3D12CommandAllocator *p
|
||||
|
||||
GetResourceManager()->AddLiveResource(bakeId, list);
|
||||
|
||||
// whenever a vkCmd command-building chunk asks for the command buffer, it
|
||||
// whenever a command-building chunk asks for the command list, it
|
||||
// will get our baked version.
|
||||
GetResourceManager()->ReplaceResource(CommandList, bakeId);
|
||||
}
|
||||
@@ -539,7 +539,7 @@ bool WrappedID3D12GraphicsCommandList::Serialise_IASetPrimitiveTopology(
|
||||
{
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->IASetPrimitiveTopology(topo);
|
||||
|
||||
// m_RenderState.topo = topo;
|
||||
m_Cmd->m_RenderState.topo = topo;
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -581,12 +581,11 @@ bool WrappedID3D12GraphicsCommandList::Serialise_RSSetViewports(UINT NumViewport
|
||||
{
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->RSSetViewports(num, views);
|
||||
|
||||
/*
|
||||
if(m_RenderState.views.size() < first + count)
|
||||
m_RenderState.views.resize(first + count);
|
||||
if(m_Cmd->m_RenderState.views.size() < num)
|
||||
m_Cmd->m_RenderState.views.resize(num);
|
||||
|
||||
for(uint32_t i = 0; i < count; i++)
|
||||
m_RenderState.views[first + i] = views[i];*/
|
||||
for(UINT i = 0; i < num; i++)
|
||||
m_Cmd->m_RenderState.views[i] = views[i];
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -629,12 +628,11 @@ bool WrappedID3D12GraphicsCommandList::Serialise_RSSetScissorRects(UINT NumRects
|
||||
{
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->RSSetScissorRects(num, rects);
|
||||
|
||||
/*
|
||||
if(m_RenderState.scissors.size() < first + count)
|
||||
m_RenderState.scissors.resize(first + count);
|
||||
if(m_Cmd->m_RenderState.scissors.size() < num)
|
||||
m_Cmd->m_RenderState.scissors.resize(num);
|
||||
|
||||
for(uint32_t i = 0; i < count; i++)
|
||||
m_RenderState.scissors[first + i] = scissors[i];*/
|
||||
for(UINT i = 0; i < num; i++)
|
||||
m_Cmd->m_RenderState.scissors[i] = rects[i];
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -685,7 +683,7 @@ bool WrappedID3D12GraphicsCommandList::Serialise_SetPipelineState(ID3D12Pipeline
|
||||
pPipelineState = GetResourceManager()->GetLiveAs<ID3D12PipelineState>(pipe);
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->SetPipelineState(Unwrap(pPipelineState));
|
||||
|
||||
// m_RenderState.pipe = ;
|
||||
m_Cmd->m_RenderState.pipe = GetResID(pPipelineState);
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -878,6 +876,8 @@ bool WrappedID3D12GraphicsCommandList::Serialise_SetGraphicsRootSignature(
|
||||
{
|
||||
pRootSignature = GetResourceManager()->GetLiveAs<ID3D12RootSignature>(sig);
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->SetGraphicsRootSignature(Unwrap(pRootSignature));
|
||||
|
||||
m_Cmd->m_RenderState.graphics.rootsig = GetResID(pRootSignature);
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -979,6 +979,12 @@ bool WrappedID3D12GraphicsCommandList::Serialise_SetGraphicsRootConstantBufferVi
|
||||
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))
|
||||
->SetGraphicsRootConstantBufferView(idx, pRes->GetGPUVirtualAddress() + byteOffset);
|
||||
|
||||
if(m_Cmd->m_RenderState.graphics.sigelems.size() < idx + 1)
|
||||
m_Cmd->m_RenderState.graphics.sigelems.resize(idx + 1);
|
||||
|
||||
m_Cmd->m_RenderState.graphics.sigelems[idx] =
|
||||
D3D12RenderState::SignatureElement(eRootCBV, GetResID(pRes), byteOffset);
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -1054,17 +1060,18 @@ bool WrappedID3D12GraphicsCommandList::Serialise_IASetIndexBuffer(const D3D12_IN
|
||||
{
|
||||
Unwrap(list)->IASetIndexBuffer(&view);
|
||||
|
||||
// WrappedID3D12Resource::GetResIDFromAddr(view.BufferLocation, m_RenderState.ibuffer.buf,
|
||||
// m_RenderState.ibuffer.offs);
|
||||
// m_RenderState.ibuffer.bytewidth = (view.Format == DXGI_FORMAT_R32_UINT ? 4 : 2);
|
||||
WrappedID3D12Resource::GetResIDFromAddr(
|
||||
view.BufferLocation, m_Cmd->m_RenderState.ibuffer.buf, m_Cmd->m_RenderState.ibuffer.offs);
|
||||
m_Cmd->m_RenderState.ibuffer.bytewidth = (view.Format == DXGI_FORMAT_R32_UINT ? 4 : 2);
|
||||
m_Cmd->m_RenderState.ibuffer.size = view.SizeInBytes;
|
||||
}
|
||||
else
|
||||
{
|
||||
Unwrap(list)->IASetIndexBuffer(NULL);
|
||||
|
||||
// m_RenderState.ibuffer.buf = ResourceId();
|
||||
// m_RenderState.ibuffer.offs = 0;
|
||||
// m_RenderState.ibuffer.bytewidth = 2;
|
||||
m_Cmd->m_RenderState.ibuffer.buf = ResourceId();
|
||||
m_Cmd->m_RenderState.ibuffer.offs = 0;
|
||||
m_Cmd->m_RenderState.ibuffer.bytewidth = 2;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1076,9 +1083,6 @@ bool WrappedID3D12GraphicsCommandList::Serialise_IASetIndexBuffer(const D3D12_IN
|
||||
{
|
||||
list->IASetIndexBuffer(&view);
|
||||
|
||||
UINT64 dummy = 0;
|
||||
WrappedID3D12Resource::GetResIDFromAddr(
|
||||
view.BufferLocation, m_Cmd->m_BakedCmdListInfo[CommandList].state.ibuffer, dummy);
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.idxWidth =
|
||||
(view.Format == DXGI_FORMAT_R32_UINT ? 4 : 2);
|
||||
}
|
||||
@@ -1086,7 +1090,6 @@ bool WrappedID3D12GraphicsCommandList::Serialise_IASetIndexBuffer(const D3D12_IN
|
||||
{
|
||||
list->IASetIndexBuffer(NULL);
|
||||
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.ibuffer = ResourceId();
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.idxWidth = 2;
|
||||
}
|
||||
}
|
||||
@@ -1132,7 +1135,18 @@ bool WrappedID3D12GraphicsCommandList::Serialise_IASetVertexBuffers(
|
||||
{
|
||||
Unwrap(m_Cmd->RerecordCmdList(CommandList))->IASetVertexBuffers(start, num, views);
|
||||
|
||||
// m_RenderState.vbuffers = ;
|
||||
if(m_Cmd->m_RenderState.vbuffers.size() < start + num)
|
||||
m_Cmd->m_RenderState.vbuffers.resize(start + num);
|
||||
|
||||
for(UINT i = 0; i < num; i++)
|
||||
{
|
||||
WrappedID3D12Resource::GetResIDFromAddr(views[i].BufferLocation,
|
||||
m_Cmd->m_RenderState.vbuffers[start + i].buf,
|
||||
m_Cmd->m_RenderState.vbuffers[start + i].offs);
|
||||
|
||||
m_Cmd->m_RenderState.vbuffers[start + i].stride = views[i].StrideInBytes;
|
||||
m_Cmd->m_RenderState.vbuffers[start + i].size = views[i].SizeInBytes;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if(m_State == READING)
|
||||
@@ -1218,6 +1232,15 @@ bool WrappedID3D12GraphicsCommandList::Serialise_OMSetRenderTargets(
|
||||
->OMSetRenderTargets(num, rtHandles, singlehandle ? TRUE : FALSE,
|
||||
dsv.heap != ResourceId() ? &dsvHandle : NULL);
|
||||
|
||||
m_Cmd->m_RenderState.rts.resize(num);
|
||||
|
||||
for(UINT i = 0; i < numHandles; i++)
|
||||
m_Cmd->m_RenderState.rts[i] = rts[i];
|
||||
|
||||
m_Cmd->m_RenderState.rtSingle = singlehandle;
|
||||
|
||||
m_Cmd->m_RenderState.dsv = dsv;
|
||||
|
||||
SAFE_DELETE_ARRAY(rtHandles);
|
||||
}
|
||||
}
|
||||
@@ -1234,6 +1257,48 @@ bool WrappedID3D12GraphicsCommandList::Serialise_OMSetRenderTargets(
|
||||
->OMSetRenderTargets(num, rtHandles, singlehandle ? TRUE : FALSE,
|
||||
dsv.heap != ResourceId() ? &dsvHandle : NULL);
|
||||
|
||||
RDCEraseEl(m_Cmd->m_BakedCmdListInfo[CommandList].state.dsv);
|
||||
RDCEraseEl(m_Cmd->m_BakedCmdListInfo[CommandList].state.rts);
|
||||
|
||||
if(singlehandle)
|
||||
{
|
||||
WrappedID3D12DescriptorHeap *heap =
|
||||
GetResourceManager()->GetLiveAs<WrappedID3D12DescriptorHeap>(rts[0].heap);
|
||||
|
||||
const D3D12Descriptor *descs = heap->GetDescriptors() + rts[0].index;
|
||||
|
||||
for(UINT i = 0; i < num; i++)
|
||||
{
|
||||
RDCASSERT(descs[i].GetType() == D3D12Descriptor::TypeRTV);
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.rts[i] = GetResID(descs[i].nonsamp.resource);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for(UINT i = 0; i < num; i++)
|
||||
{
|
||||
WrappedID3D12DescriptorHeap *heap =
|
||||
GetResourceManager()->GetLiveAs<WrappedID3D12DescriptorHeap>(rts[0].heap);
|
||||
|
||||
const D3D12Descriptor &desc = heap->GetDescriptors()[rts[i].index];
|
||||
|
||||
RDCASSERT(desc.GetType() == D3D12Descriptor::TypeRTV);
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.rts[i] = GetResID(desc.nonsamp.resource);
|
||||
}
|
||||
}
|
||||
|
||||
if(dsv.heap != ResourceId())
|
||||
{
|
||||
WrappedID3D12DescriptorHeap *heap =
|
||||
GetResourceManager()->GetLiveAs<WrappedID3D12DescriptorHeap>(dsv.heap);
|
||||
|
||||
const D3D12Descriptor &desc = heap->GetDescriptors()[dsv.index];
|
||||
|
||||
RDCASSERT(desc.GetType() == D3D12Descriptor::TypeDSV);
|
||||
|
||||
m_Cmd->m_BakedCmdListInfo[CommandList].state.dsv = GetResID(desc.nonsamp.resource);
|
||||
}
|
||||
|
||||
SAFE_DELETE_ARRAY(rtHandles);
|
||||
}
|
||||
|
||||
|
||||
@@ -114,7 +114,7 @@ bool WrappedID3D12CommandQueue::Serialise_ExecuteCommandLists(UINT NumCommandLis
|
||||
|
||||
BakedCmdListInfo &cmdBufInfo = m_Cmd.m_BakedCmdListInfo[cmdIds[c]];
|
||||
|
||||
// insert the baked command buffer in-line into this list of notes, assigning new event and
|
||||
// insert the baked command list in-line into this list of notes, assigning new event and
|
||||
// drawIDs
|
||||
m_Cmd.InsertDrawsAndRefreshIDs(cmdBufInfo.draw->children);
|
||||
|
||||
@@ -136,7 +136,7 @@ bool WrappedID3D12CommandQueue::Serialise_ExecuteCommandLists(UINT NumCommandLis
|
||||
}
|
||||
*/
|
||||
|
||||
// only primary command buffers can be submitted
|
||||
// only primary command lists can be submitted
|
||||
m_Cmd.m_Partial[D3D12CommandData::Primary].cmdListExecs[cmdIds[c]].push_back(
|
||||
m_Cmd.m_RootEventID);
|
||||
|
||||
@@ -165,7 +165,7 @@ bool WrappedID3D12CommandQueue::Serialise_ExecuteCommandLists(UINT NumCommandLis
|
||||
// advance m_CurEventID to match the events added when reading
|
||||
for(uint32_t c = 0; c < numCmds; c++)
|
||||
{
|
||||
// 2 extra for the virtual labels around the command buffer
|
||||
// 2 extra for the virtual labels around the command list
|
||||
m_Cmd.m_RootEventID += 2 + m_Cmd.m_BakedCmdListInfo[cmdIds[c]].eventCount;
|
||||
m_Cmd.m_RootDrawcallID += 2 + m_Cmd.m_BakedCmdListInfo[cmdIds[c]].drawCount;
|
||||
}
|
||||
@@ -222,7 +222,7 @@ bool WrappedID3D12CommandQueue::Serialise_ExecuteCommandLists(UINT NumCommandLis
|
||||
|
||||
for(uint32_t c = 0; c < numCmds; c++)
|
||||
{
|
||||
// account for the virtual vkBeginCommandBuffer label at the start of the events here
|
||||
// account for the virtual label at the start of the events here
|
||||
// so it matches up to baseEvent
|
||||
eid++;
|
||||
|
||||
@@ -254,7 +254,7 @@ bool WrappedID3D12CommandQueue::Serialise_ExecuteCommandLists(UINT NumCommandLis
|
||||
#endif
|
||||
}
|
||||
|
||||
// 1 extra to account for the virtual end command buffer label (begin is accounted for
|
||||
// 1 extra to account for the virtual end command list label (begin is accounted for
|
||||
// above)
|
||||
eid += 1 + m_Cmd.m_BakedCmdListInfo[cmdIds[c]].eventCount;
|
||||
}
|
||||
@@ -340,11 +340,11 @@ void STDMETHODCALLTYPE WrappedID3D12CommandQueue::ExecuteCommandLists(
|
||||
|
||||
if(capframe)
|
||||
{
|
||||
// pull in frame refs from this baked command buffer
|
||||
// pull in frame refs from this baked command list
|
||||
record->bakedCommands->AddResourceReferences(GetResourceManager());
|
||||
record->bakedCommands->AddReferencedIDs(refdIDs);
|
||||
|
||||
// ref the parent command buffer by itself, this will pull in the cmd buffer pool
|
||||
// ref the parent command list by itself, this will pull in the cmd buffer pool
|
||||
GetResourceManager()->MarkResourceFrameReferenced(record->GetResourceID(), eFrameRef_Read);
|
||||
|
||||
// reference all executed bundles as well
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
******************************************************************************/
|
||||
|
||||
#include <algorithm>
|
||||
#include "driver/dxgi/dxgi_common.h"
|
||||
#include "d3d12_command_list.h"
|
||||
#include "d3d12_command_queue.h"
|
||||
|
||||
@@ -357,8 +358,13 @@ void WrappedID3D12CommandQueue::ReplayLog(LogState readType, uint32_t startEvent
|
||||
|
||||
m_pDevice->Serialise_BeginCaptureFrame(!partial);
|
||||
|
||||
m_pDevice->ExecuteLists();
|
||||
m_pDevice->FlushLists();
|
||||
if(readType == READING)
|
||||
{
|
||||
GetResourceManager()->ApplyInitialContents();
|
||||
|
||||
m_pDevice->ExecuteLists();
|
||||
m_pDevice->FlushLists();
|
||||
}
|
||||
|
||||
m_pSerialiser->PopContext(header);
|
||||
|
||||
@@ -370,7 +376,7 @@ void WrappedID3D12CommandQueue::ReplayLog(LogState readType, uint32_t startEvent
|
||||
m_Cmd.m_RootEventID = ev.eventID;
|
||||
|
||||
// if not partial, we need to be sure to replay
|
||||
// past the command buffer records, so can't
|
||||
// past the command list records, so can't
|
||||
// skip to the file offset of the first event
|
||||
if(partial)
|
||||
m_pSerialiser->SetOffset(ev.fileOffset);
|
||||
@@ -391,7 +397,7 @@ void WrappedID3D12CommandQueue::ReplayLog(LogState readType, uint32_t startEvent
|
||||
if(m_State == EXECUTING && m_Cmd.m_RootEventID > endEventID)
|
||||
{
|
||||
// we can just break out if we've done all the events desired.
|
||||
// note that the command buffer events aren't 'real' and we just blaze through them
|
||||
// note that the command list events aren't 'real' and we just blaze through them
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -417,7 +423,7 @@ void WrappedID3D12CommandQueue::ReplayLog(LogState readType, uint32_t startEvent
|
||||
// increment root event ID either if we didn't just replay a cmd
|
||||
// buffer event, OR if we are doing a frame sub-section replay,
|
||||
// in which case it's up to the calling code to make sure we only
|
||||
// replay inside a command buffer (if we crossed command buffer
|
||||
// replay inside a command list (if we crossed command list
|
||||
// boundaries, the event IDs would no longer match up).
|
||||
if(m_Cmd.m_LastCmdListID == ResourceId() || startEventID > 1)
|
||||
{
|
||||
@@ -432,9 +438,6 @@ void WrappedID3D12CommandQueue::ReplayLog(LogState readType, uint32_t startEvent
|
||||
}
|
||||
}
|
||||
|
||||
m_pDevice->ExecuteLists();
|
||||
m_pDevice->FlushLists(true);
|
||||
|
||||
if(m_State == READING)
|
||||
{
|
||||
struct SortEID
|
||||
@@ -708,6 +711,12 @@ void D3D12CommandData::AddDrawcall(const FetchDrawcall &d, bool hasEvents)
|
||||
if(m_LastCmdListID != ResourceId())
|
||||
{
|
||||
// TODO fill from m_BakedCmdListInfo[m_LastCmdListID].state
|
||||
|
||||
draw.topology = MakePrimitiveTopology(m_BakedCmdListInfo[m_LastCmdListID].state.topo);
|
||||
draw.indexByteWidth = m_BakedCmdListInfo[m_LastCmdListID].state.idxWidth;
|
||||
|
||||
memcpy(draw.outputs, m_BakedCmdListInfo[m_LastCmdListID].state.rts, sizeof(draw.outputs));
|
||||
draw.depthOut = m_BakedCmdListInfo[m_LastCmdListID].state.dsv;
|
||||
}
|
||||
|
||||
if(m_LastCmdListID != ResourceId())
|
||||
|
||||
@@ -24,9 +24,10 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "common/common.h"
|
||||
#include "api/replay/renderdoc_replay.h"
|
||||
#include "common/common.h"
|
||||
#include "d3d12_common.h"
|
||||
#include "d3d12_state.h"
|
||||
|
||||
struct D3D12DrawcallTreeNode
|
||||
{
|
||||
@@ -110,13 +111,9 @@ struct BakedCmdListInfo
|
||||
|
||||
struct CmdListState
|
||||
{
|
||||
ResourceId pipeline;
|
||||
|
||||
D3D12_PRIMITIVE_TOPOLOGY topo;
|
||||
|
||||
uint32_t idxWidth;
|
||||
ResourceId ibuffer;
|
||||
vector<ResourceId> vbuffers;
|
||||
|
||||
ResourceId rts[8];
|
||||
ResourceId dsv;
|
||||
@@ -140,6 +137,8 @@ struct D3D12CommandData
|
||||
|
||||
map<ResourceId, BakedCmdListInfo> m_BakedCmdListInfo;
|
||||
|
||||
D3D12RenderState m_RenderState;
|
||||
|
||||
enum PartialReplayIndex
|
||||
{
|
||||
Primary,
|
||||
|
||||
@@ -90,6 +90,17 @@ string ToStrHelper<false, D3D12ComponentMapping>::Get(const D3D12ComponentMappin
|
||||
: Unwrap(rm->GetLiveAs<type>(id)); \
|
||||
}
|
||||
|
||||
#define SerialiseWrappedObject(type, name, obj) \
|
||||
{ \
|
||||
D3D12ResourceManager *rm = (D3D12ResourceManager *)GetUserData(); \
|
||||
ResourceId id; \
|
||||
if(m_Mode >= WRITING) \
|
||||
id = GetResID(obj); \
|
||||
Serialise(name, id); \
|
||||
if(m_Mode < WRITING) \
|
||||
obj = (id == ResourceId() || !rm->HasLiveResource(id)) ? NULL : rm->GetLiveAs<type>(id); \
|
||||
}
|
||||
|
||||
template <>
|
||||
void Serialiser::Serialise(const char *name, D3D12Descriptor &el)
|
||||
{
|
||||
@@ -131,32 +142,31 @@ void Serialiser::Serialise(const char *name, D3D12Descriptor &el)
|
||||
}
|
||||
case D3D12Descriptor::TypeCBV:
|
||||
{
|
||||
SerialiseObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
Serialise("Descriptor", el.nonsamp.cbv);
|
||||
break;
|
||||
}
|
||||
case D3D12Descriptor::TypeSRV:
|
||||
{
|
||||
SerialiseObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
SerialiseWrappedObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
Serialise("Descriptor", el.nonsamp.srv);
|
||||
break;
|
||||
}
|
||||
case D3D12Descriptor::TypeRTV:
|
||||
{
|
||||
SerialiseObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
SerialiseWrappedObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
Serialise("Descriptor", el.nonsamp.rtv);
|
||||
break;
|
||||
}
|
||||
case D3D12Descriptor::TypeDSV:
|
||||
{
|
||||
SerialiseObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
SerialiseWrappedObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
Serialise("Descriptor", el.nonsamp.dsv);
|
||||
break;
|
||||
}
|
||||
case D3D12Descriptor::TypeUAV:
|
||||
{
|
||||
SerialiseObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
SerialiseObject(ID3D12Resource, "CounterResource", el.nonsamp.uav.counterResource);
|
||||
SerialiseWrappedObject(ID3D12Resource, "Resource", el.nonsamp.resource);
|
||||
SerialiseWrappedObject(ID3D12Resource, "CounterResource", el.nonsamp.uav.counterResource);
|
||||
|
||||
// special case because of extra resource and squeezed descriptor
|
||||
D3D12_UNORDERED_ACCESS_VIEW_DESC desc = el.nonsamp.uav.desc.AsDesc();
|
||||
|
||||
@@ -951,7 +951,7 @@ void WrappedID3D12Device::StartFrameCapture(void *dev, void *wnd)
|
||||
Serialise_BeginCaptureFrame(false);
|
||||
|
||||
// need to hold onto this as it must come right after the capture chunk,
|
||||
// before any command buffers
|
||||
// before any command lists
|
||||
m_HeaderChunk = scope.Get();
|
||||
}
|
||||
|
||||
@@ -1082,14 +1082,13 @@ bool WrappedID3D12Device::EndFrameCapture(void *dev, void *wnd)
|
||||
{
|
||||
const vector<D3D12ResourceRecord *> &cmdListRecords = m_Queue->GetCmdLists();
|
||||
|
||||
RDCDEBUG("Flushing %u command buffer records to file serialiser",
|
||||
(uint32_t)cmdListRecords.size());
|
||||
RDCDEBUG("Flushing %u command list records to file serialiser", (uint32_t)cmdListRecords.size());
|
||||
|
||||
for(size_t i = 0; i < cmdListRecords.size(); i++)
|
||||
{
|
||||
cmdListRecords[i]->Insert(recordlist);
|
||||
|
||||
RDCDEBUG("Adding %u chunks to file serialiser from command buffer %llu",
|
||||
RDCDEBUG("Adding %u chunks to file serialiser from command list %llu",
|
||||
(uint32_t)recordlist.size(), cmdListRecords[i]->GetResourceID());
|
||||
}
|
||||
|
||||
@@ -1553,12 +1552,53 @@ void WrappedID3D12Device::ReplayLog(uint32_t startEventID, uint32_t endEventID,
|
||||
|
||||
m_State = EXECUTING;
|
||||
|
||||
if(replayType == eReplay_Full)
|
||||
m_Queue->ReplayLog(EXECUTING, startEventID, endEventID, partial);
|
||||
else if(replayType == eReplay_WithoutDraw)
|
||||
m_Queue->ReplayLog(EXECUTING, startEventID, RDCMAX(1U, endEventID) - 1, partial);
|
||||
else if(replayType == eReplay_OnlyDraw)
|
||||
m_Queue->ReplayLog(EXECUTING, endEventID, endEventID, partial);
|
||||
else
|
||||
RDCFATAL("Unexpected replay type");
|
||||
{
|
||||
D3D12CommandData &cmd = *m_Queue->GetCommandData();
|
||||
|
||||
if(!partial)
|
||||
{
|
||||
RDCASSERT(cmd.m_Partial[D3D12CommandData::Primary].resultPartialCmdList == NULL);
|
||||
RDCASSERT(cmd.m_Partial[D3D12CommandData::Secondary].resultPartialCmdList == NULL);
|
||||
cmd.m_Partial[D3D12CommandData::Primary].Reset();
|
||||
cmd.m_Partial[D3D12CommandData::Secondary].Reset();
|
||||
cmd.m_RenderState = D3D12RenderState();
|
||||
cmd.m_RenderState.m_ResourceManager = GetResourceManager();
|
||||
}
|
||||
|
||||
// we'll need our own command list if we're replaying just a subsection
|
||||
// of events within a single command list record - always if it's only
|
||||
// one drawcall, or if start event ID is > 0 we assume the outside code
|
||||
// has chosen a subsection that lies within a command list
|
||||
if(partial)
|
||||
{
|
||||
ID3D12GraphicsCommandList *list = cmd.m_Partial[D3D12CommandData::Primary].outsideCmdList =
|
||||
GetNewList();
|
||||
|
||||
cmd.m_RenderState.ApplyState(list);
|
||||
}
|
||||
|
||||
if(replayType == eReplay_Full)
|
||||
m_Queue->ReplayLog(EXECUTING, startEventID, endEventID, partial);
|
||||
else if(replayType == eReplay_WithoutDraw)
|
||||
m_Queue->ReplayLog(EXECUTING, startEventID, RDCMAX(1U, endEventID) - 1, partial);
|
||||
else if(replayType == eReplay_OnlyDraw)
|
||||
m_Queue->ReplayLog(EXECUTING, endEventID, endEventID, partial);
|
||||
else
|
||||
RDCFATAL("Unexpected replay type");
|
||||
|
||||
if(cmd.m_Partial[D3D12CommandData::Primary].outsideCmdList != NULL)
|
||||
{
|
||||
ID3D12GraphicsCommandList *list = cmd.m_Partial[D3D12CommandData::Primary].outsideCmdList;
|
||||
|
||||
list->Close();
|
||||
|
||||
ExecuteLists();
|
||||
|
||||
cmd.m_Partial[D3D12CommandData::Primary].outsideCmdList = NULL;
|
||||
}
|
||||
|
||||
#if defined(SINGLE_FLUSH_VALIDATE)
|
||||
FlushLists(true);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
@@ -303,7 +303,7 @@ public:
|
||||
WrappedID3D12Device(ID3D12Device *realDevice, D3D12InitParams *params);
|
||||
virtual ~WrappedID3D12Device();
|
||||
|
||||
UINT GetDescriptorIncrement(D3D12_DESCRIPTOR_HEAP_TYPE type)
|
||||
UINT GetUnwrappedDescriptorIncrement(D3D12_DESCRIPTOR_HEAP_TYPE type)
|
||||
{
|
||||
return m_DescriptorIncrements[type];
|
||||
}
|
||||
|
||||
@@ -845,6 +845,8 @@ void WrappedID3D12Device::CopyDescriptors(
|
||||
NumSrcDescriptorRanges, srcStarts, pSrcDescriptorRangeSizes,
|
||||
DescriptorHeapsType);
|
||||
|
||||
RDCUNIMPLEMENTED("CopyDescriptors does not copy our internal descriptor data");
|
||||
|
||||
SAFE_DELETE_ARRAY(dstStarts);
|
||||
SAFE_DELETE_ARRAY(srcStarts);
|
||||
}
|
||||
@@ -856,6 +858,21 @@ void WrappedID3D12Device::CopyDescriptorsSimple(UINT NumDescriptors,
|
||||
{
|
||||
m_pDevice->CopyDescriptorsSimple(NumDescriptors, Unwrap(DestDescriptorRangeStart),
|
||||
Unwrap(SrcDescriptorRangeStart), DescriptorHeapsType);
|
||||
|
||||
D3D12Descriptor *src = GetWrapped(SrcDescriptorRangeStart);
|
||||
D3D12Descriptor *dst = GetWrapped(DestDescriptorRangeStart);
|
||||
|
||||
for(UINT i = 0; i < NumDescriptors; i++)
|
||||
{
|
||||
// save these so we can do a straight copy then restore them
|
||||
WrappedID3D12DescriptorHeap *heap = dst[i].samp.heap;
|
||||
uint32_t index = dst[i].samp.idx;
|
||||
|
||||
dst[i] = src[i];
|
||||
|
||||
dst[i].samp.heap = heap;
|
||||
dst[i].samp.idx = index;
|
||||
}
|
||||
}
|
||||
|
||||
HRESULT WrappedID3D12Device::OpenSharedHandle(HANDLE NTHandle, REFIID riid, void **ppvObj)
|
||||
|
||||
@@ -469,8 +469,8 @@ bool D3D12ResourceManager::Serialise_InitialState(ResourceId resid, ID3D12Device
|
||||
desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_NONE;
|
||||
|
||||
ID3D12DescriptorHeap *copyheap = NULL;
|
||||
HRESULT hr = m_Device->GetReal()->CreateDescriptorHeap(&desc, __uuidof(ID3D12DescriptorHeap),
|
||||
(void **)©heap);
|
||||
HRESULT hr =
|
||||
m_Device->CreateDescriptorHeap(&desc, __uuidof(ID3D12DescriptorHeap), (void **)©heap);
|
||||
|
||||
if(FAILED(hr))
|
||||
{
|
||||
@@ -480,11 +480,11 @@ bool D3D12ResourceManager::Serialise_InitialState(ResourceId resid, ID3D12Device
|
||||
|
||||
D3D12_CPU_DESCRIPTOR_HANDLE handle = copyheap->GetCPUDescriptorHandleForHeapStart();
|
||||
|
||||
UINT increment = m_Device->GetDescriptorIncrement(desc.Type);
|
||||
UINT increment = m_Device->GetDescriptorHandleIncrementSize(desc.Type);
|
||||
|
||||
for(uint32_t i = 0; i < numElems; i++)
|
||||
{
|
||||
descs[i].Create(m_Device->GetReal(), handle);
|
||||
descs[i].Create(m_Device, handle);
|
||||
|
||||
handle.ptr += increment;
|
||||
}
|
||||
@@ -599,13 +599,13 @@ void D3D12ResourceManager::Apply_InitialState(ID3D12DeviceChild *live, InitialCo
|
||||
|
||||
if(type == Resource_DescriptorHeap)
|
||||
{
|
||||
ID3D12DescriptorHeap *dstheap = Unwrap((ID3D12DescriptorHeap *)live);
|
||||
ID3D12DescriptorHeap *dstheap = (ID3D12DescriptorHeap *)live;
|
||||
ID3D12DescriptorHeap *srcheap = (ID3D12DescriptorHeap *)data.resource;
|
||||
|
||||
if(srcheap)
|
||||
{
|
||||
// copy the whole heap
|
||||
m_Device->GetReal()->CopyDescriptorsSimple(
|
||||
m_Device->CopyDescriptorsSimple(
|
||||
srcheap->GetDesc().NumDescriptors, dstheap->GetCPUDescriptorHandleForHeapStart(),
|
||||
srcheap->GetCPUDescriptorHandleForHeapStart(), srcheap->GetDesc().Type);
|
||||
}
|
||||
|
||||
@@ -130,7 +130,7 @@ struct D3D12Descriptor
|
||||
TypeUndefined,
|
||||
};
|
||||
|
||||
DescriptorType GetType()
|
||||
DescriptorType GetType() const
|
||||
{
|
||||
RDCCOMPILE_ASSERT(sizeof(D3D12Descriptor) <= 64, "D3D12Descriptor has gotten larger");
|
||||
|
||||
@@ -223,7 +223,7 @@ struct CmdListRecordingInfo
|
||||
{
|
||||
vector<D3D12_RESOURCE_BARRIER> barriers;
|
||||
|
||||
// a list of all resources dirtied by this command buffer
|
||||
// a list of all resources dirtied by this command list
|
||||
set<ResourceId> dirtied;
|
||||
|
||||
// bundles executed
|
||||
@@ -291,6 +291,12 @@ public:
|
||||
return (T *)GetLiveResource(id);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
T *GetCurrentAs(ResourceId id)
|
||||
{
|
||||
return (T *)GetCurrentResource(id);
|
||||
}
|
||||
|
||||
void ApplyBarriers(vector<D3D12_RESOURCE_BARRIER> &barriers,
|
||||
map<ResourceId, SubresourceStateVector> &states);
|
||||
|
||||
|
||||
@@ -148,7 +148,7 @@ WrappedID3D12DescriptorHeap::WrappedID3D12DescriptorHeap(ID3D12DescriptorHeap *r
|
||||
realCPUBase = real->GetCPUDescriptorHandleForHeapStart();
|
||||
realGPUBase = real->GetGPUDescriptorHandleForHeapStart();
|
||||
|
||||
increment = device->GetDescriptorIncrement(desc.Type);
|
||||
increment = device->GetUnwrappedDescriptorIncrement(desc.Type);
|
||||
|
||||
descriptors = new D3D12Descriptor[desc.NumDescriptors];
|
||||
|
||||
|
||||
@@ -0,0 +1,153 @@
|
||||
/******************************************************************************
|
||||
* The MIT License (MIT)
|
||||
*
|
||||
* Copyright (c) 2016 Baldur Karlsson
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
|
||||
#include "d3d12_state.h"
|
||||
#include "d3d12_command_list.h"
|
||||
#include "d3d12_manager.h"
|
||||
#include "d3d12_resources.h"
|
||||
|
||||
D3D12RenderState::D3D12RenderState()
|
||||
{
|
||||
views.clear();
|
||||
scissors.clear();
|
||||
|
||||
rts.clear();
|
||||
rtSingle = false;
|
||||
dsv = PortableHandle();
|
||||
|
||||
m_ResourceManager = NULL;
|
||||
|
||||
pipe = graphics.rootsig = compute.rootsig = ResourceId();
|
||||
graphics.sigelems.clear();
|
||||
compute.sigelems.clear();
|
||||
|
||||
topo = D3D_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
|
||||
RDCEraseEl(ibuffer);
|
||||
vbuffers.clear();
|
||||
}
|
||||
|
||||
D3D12RenderState &D3D12RenderState::operator=(const D3D12RenderState &o)
|
||||
{
|
||||
views = o.views;
|
||||
scissors = o.scissors;
|
||||
|
||||
rts = o.rts;
|
||||
rtSingle = o.rtSingle;
|
||||
dsv = o.dsv;
|
||||
|
||||
pipe = o.pipe;
|
||||
|
||||
graphics.rootsig = o.graphics.rootsig;
|
||||
graphics.sigelems = o.graphics.sigelems;
|
||||
compute.rootsig = o.compute.rootsig;
|
||||
compute.sigelems = o.compute.sigelems;
|
||||
|
||||
topo = o.topo;
|
||||
|
||||
ibuffer = o.ibuffer;
|
||||
vbuffers = o.vbuffers;
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
void D3D12RenderState::ApplyState(ID3D12GraphicsCommandList *cmd)
|
||||
{
|
||||
if(pipe != ResourceId())
|
||||
cmd->SetPipelineState(GetResourceManager()->GetCurrentAs<ID3D12PipelineState>(pipe));
|
||||
|
||||
if(!views.empty())
|
||||
cmd->RSSetViewports((UINT)views.size(), &views[0]);
|
||||
|
||||
if(!scissors.empty())
|
||||
cmd->RSSetScissorRects((UINT)scissors.size(), &scissors[0]);
|
||||
|
||||
if(topo != D3D_PRIMITIVE_TOPOLOGY_UNDEFINED)
|
||||
cmd->IASetPrimitiveTopology(topo);
|
||||
|
||||
if(ibuffer.buf != ResourceId())
|
||||
{
|
||||
D3D12_INDEX_BUFFER_VIEW ib;
|
||||
|
||||
ID3D12Resource *res = GetResourceManager()->GetCurrentAs<ID3D12Resource>(ibuffer.buf);
|
||||
if(res)
|
||||
ib.BufferLocation = res->GetGPUVirtualAddress() + ibuffer.offs;
|
||||
else
|
||||
ib.BufferLocation = 0;
|
||||
|
||||
ib.Format = (ibuffer.bytewidth == 2 ? DXGI_FORMAT_R16_UINT : DXGI_FORMAT_R32_UINT);
|
||||
ib.SizeInBytes = ibuffer.size;
|
||||
|
||||
cmd->IASetIndexBuffer(&ib);
|
||||
}
|
||||
|
||||
for(size_t i = 0; i < vbuffers.size(); i++)
|
||||
{
|
||||
D3D12_VERTEX_BUFFER_VIEW vb;
|
||||
|
||||
ID3D12Resource *res = GetResourceManager()->GetCurrentAs<ID3D12Resource>(vbuffers[i].buf);
|
||||
if(res)
|
||||
vb.BufferLocation = res->GetGPUVirtualAddress() + vbuffers[i].offs;
|
||||
else
|
||||
vb.BufferLocation = 0;
|
||||
|
||||
vb.StrideInBytes = vbuffers[i].stride;
|
||||
vb.SizeInBytes = vbuffers[i].size;
|
||||
|
||||
cmd->IASetVertexBuffers((UINT)i, 1, &vb);
|
||||
}
|
||||
|
||||
if(!rts.empty() || dsv.heap != ResourceId())
|
||||
{
|
||||
D3D12_CPU_DESCRIPTOR_HANDLE rtHandles[8];
|
||||
D3D12_CPU_DESCRIPTOR_HANDLE dsvHandle = FromPortableHandle(GetResourceManager(), dsv);
|
||||
|
||||
UINT numActualHandles = rtSingle ? 1 : (UINT)rts.size();
|
||||
|
||||
for(UINT i = 0; i < numActualHandles; i++)
|
||||
rtHandles[i] = FromPortableHandle(GetResourceManager(), rts[i]);
|
||||
|
||||
// need to unwrap here, as FromPortableHandle unwraps too.
|
||||
Unwrap(cmd)->OMSetRenderTargets((UINT)rts.size(), rtHandles, rtSingle ? TRUE : FALSE,
|
||||
dsv.heap != ResourceId() ? &dsvHandle : NULL);
|
||||
}
|
||||
|
||||
if(graphics.rootsig != ResourceId())
|
||||
{
|
||||
cmd->SetGraphicsRootSignature(
|
||||
GetResourceManager()->GetCurrentAs<ID3D12RootSignature>(graphics.rootsig));
|
||||
|
||||
for(size_t i = 0; i < graphics.sigelems.size(); i++)
|
||||
graphics.sigelems[i].SetToCommandList(GetResourceManager(), cmd, (UINT)i);
|
||||
}
|
||||
|
||||
if(compute.rootsig != ResourceId())
|
||||
{
|
||||
cmd->SetComputeRootSignature(
|
||||
GetResourceManager()->GetCurrentAs<ID3D12RootSignature>(compute.rootsig));
|
||||
|
||||
for(size_t i = 0; i < compute.sigelems.size(); i++)
|
||||
compute.sigelems[i].SetToCommandList(GetResourceManager(), cmd, (UINT)i);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,152 @@
|
||||
/******************************************************************************
|
||||
* The MIT License (MIT)
|
||||
*
|
||||
* Copyright (c) 2016 Baldur Karlsson
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include "d3d12_common.h"
|
||||
#include "d3d12_manager.h"
|
||||
|
||||
class D3D12ResourceManager;
|
||||
|
||||
enum SignatureElementType
|
||||
{
|
||||
eRootUnknown,
|
||||
eRootConst,
|
||||
eRootTable,
|
||||
eRootCBV,
|
||||
eRootSRV,
|
||||
eRootUAV,
|
||||
};
|
||||
|
||||
struct D3D12RenderState
|
||||
{
|
||||
D3D12RenderState();
|
||||
D3D12RenderState &operator=(const D3D12RenderState &o);
|
||||
|
||||
void ApplyState(ID3D12GraphicsCommandList *list);
|
||||
|
||||
vector<D3D12_VIEWPORT> views;
|
||||
vector<D3D12_RECT> scissors;
|
||||
|
||||
vector<PortableHandle> rts;
|
||||
bool rtSingle;
|
||||
PortableHandle dsv;
|
||||
|
||||
struct SignatureElement
|
||||
{
|
||||
SignatureElement() : type(eRootUnknown), offset(0) {}
|
||||
SignatureElement(SignatureElementType t, ResourceId i, UINT64 o) : type(t), id(i), offset(o) {}
|
||||
SignatureElement(UINT val) : type(eRootConst), offset(0) { constants.push_back(val); }
|
||||
SignatureElement(UINT numVals, const void *vals, UINT destIdx)
|
||||
{
|
||||
SetValues(numVals, vals, destIdx);
|
||||
}
|
||||
|
||||
void SetValues(UINT numVals, const void *vals, UINT destIdx)
|
||||
{
|
||||
type = eRootConst;
|
||||
offset = 0;
|
||||
|
||||
if(constants.size() < destIdx + numVals)
|
||||
constants.resize(destIdx + numVals);
|
||||
|
||||
memcpy(&constants[destIdx], vals, numVals * sizeof(UINT));
|
||||
}
|
||||
|
||||
void SetToCommandList(D3D12ResourceManager *rm, ID3D12GraphicsCommandList *cmd, UINT slot)
|
||||
{
|
||||
if(type == eRootConst)
|
||||
{
|
||||
if(constants.size() == 1)
|
||||
cmd->SetGraphicsRoot32BitConstant(slot, constants[0], 0);
|
||||
else
|
||||
cmd->SetGraphicsRoot32BitConstants(slot, (UINT)constants.size(), &constants[0], 0);
|
||||
}
|
||||
else if(type == eRootTable)
|
||||
{
|
||||
D3D12_GPU_DESCRIPTOR_HANDLE handle =
|
||||
rm->GetCurrentAs<ID3D12DescriptorHeap>(id)->GetGPUDescriptorHandleForHeapStart();
|
||||
handle.ptr += sizeof(D3D12Descriptor) * offset;
|
||||
cmd->SetGraphicsRootDescriptorTable(slot, handle);
|
||||
}
|
||||
else if(type == eRootCBV)
|
||||
{
|
||||
ID3D12Resource *res = rm->GetCurrentAs<ID3D12Resource>(id);
|
||||
cmd->SetGraphicsRootConstantBufferView(slot, res->GetGPUVirtualAddress() + offset);
|
||||
}
|
||||
else if(type == eRootSRV)
|
||||
{
|
||||
ID3D12Resource *res = rm->GetCurrentAs<ID3D12Resource>(id);
|
||||
cmd->SetGraphicsRootShaderResourceView(slot, res->GetGPUVirtualAddress() + offset);
|
||||
}
|
||||
else if(type == eRootUAV)
|
||||
{
|
||||
ID3D12Resource *res = rm->GetCurrentAs<ID3D12Resource>(id);
|
||||
cmd->SetGraphicsRootUnorderedAccessView(slot, res->GetGPUVirtualAddress() + offset);
|
||||
}
|
||||
else
|
||||
{
|
||||
RDCWARN("Unexpected root signature element of type '%u' - skipping.", type);
|
||||
}
|
||||
}
|
||||
|
||||
SignatureElementType type;
|
||||
|
||||
ResourceId id;
|
||||
UINT64 offset;
|
||||
vector<UINT> constants;
|
||||
};
|
||||
|
||||
struct Pipeline
|
||||
{
|
||||
ResourceId rootsig;
|
||||
|
||||
vector<SignatureElement> sigelems;
|
||||
} compute, graphics;
|
||||
|
||||
ResourceId pipe;
|
||||
|
||||
D3D12_PRIMITIVE_TOPOLOGY topo;
|
||||
|
||||
struct IdxBuffer
|
||||
{
|
||||
ResourceId buf;
|
||||
UINT64 offs;
|
||||
int bytewidth;
|
||||
UINT size;
|
||||
} ibuffer;
|
||||
|
||||
struct VertBuffer
|
||||
{
|
||||
ResourceId buf;
|
||||
UINT64 offs;
|
||||
UINT stride;
|
||||
UINT size;
|
||||
};
|
||||
vector<VertBuffer> vbuffers;
|
||||
|
||||
D3D12ResourceManager *GetResourceManager() { return m_ResourceManager; }
|
||||
D3D12ResourceManager *m_ResourceManager;
|
||||
};
|
||||
@@ -195,6 +195,7 @@
|
||||
<ClCompile Include="d3d12_manager.cpp" />
|
||||
<ClCompile Include="d3d12_replay.cpp" />
|
||||
<ClCompile Include="d3d12_resources.cpp" />
|
||||
<ClCompile Include="d3d12_state.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="d3d12_commands.h" />
|
||||
@@ -208,6 +209,7 @@
|
||||
<ClInclude Include="..\dx\official\d3d12sdklayers.h" />
|
||||
<ClInclude Include="d3d12_replay.h" />
|
||||
<ClInclude Include="d3d12_resources.h" />
|
||||
<ClInclude Include="d3d12_state.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\shaders\dxbc\renderdoc_dxbc.vcxproj">
|
||||
|
||||
@@ -54,6 +54,9 @@
|
||||
<ClInclude Include="d3d12_commands.h">
|
||||
<Filter>Core IFaces</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="d3d12_state.h">
|
||||
<Filter>Util</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="d3d12_common.cpp">
|
||||
@@ -89,5 +92,8 @@
|
||||
<ClCompile Include="d3d12_debug.cpp">
|
||||
<Filter>Replay</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="d3d12_state.cpp">
|
||||
<Filter>Util</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
Reference in New Issue
Block a user