Remove dependency of DXBCDebug::State on ShaderDebugTrace

* This means the quad doesn't have a trace per thread. All per-thread data is in
  the State itself, and anything that's not per-thread is in the GlobalState.
This commit is contained in:
baldurk
2020-02-05 11:41:39 +00:00
parent c037aac6b3
commit fa9289c372
4 changed files with 178 additions and 164 deletions
+50 -34
View File
@@ -1815,12 +1815,14 @@ ShaderDebugTrace D3D11Replay::DebugVertex(uint32_t eventId, uint32_t vertid, uin
GlobalState global;
global.PopulateGroupshared(dxbc->GetDXBCByteCode());
State initialState;
CreateShaderDebugStateAndTrace(initialState, ret, -1, dxbc, refl, vs->GetMapping());
State initialState(-1, &global, dxbc);
CreateShaderDebugStateAndTrace(initialState, ret, dxbc, refl, vs->GetMapping());
AddCBuffersToDebugTrace(*dxbc->GetDXBCByteCode(), *GetDebugManager(), ret, rs->VS, refl,
vs->GetMapping());
global.constantBlocks = ret.constantBlocks;
for(size_t i = 0; i < ret.inputs.size(); i++)
{
if(dxbc->GetReflection()->InputSig[i].systemValue == ShaderBuiltin::Undefined ||
@@ -2067,8 +2069,6 @@ ShaderDebugTrace D3D11Replay::DebugVertex(uint32_t eventId, uint32_t vertid, uin
delete[] instData;
State last;
rdcarray<ShaderDebugState> states;
dxbc->FillStateInstructionInfo(initialState);
@@ -2084,7 +2084,7 @@ ShaderDebugTrace D3D11Replay::DebugVertex(uint32_t eventId, uint32_t vertid, uin
if(initialState.Finished())
break;
initialState = initialState.GetNext(global, &apiWrapper, NULL);
initialState = initialState.GetNext(&apiWrapper, NULL);
dxbc->FillStateInstructionInfo(initialState);
@@ -2631,9 +2631,6 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
// of which fragment was the last to successfully depth test and debug that, just by
// checking if the depth test is ordered and picking the final fragment in the series
// our debugging quad. Order is TL, TR, BL, BR
State quad[4];
// figure out the TL pixel's coords. Assume even top left (towards 0,0)
// this isn't spec'd but is a reasonable assumption.
int xTL = x & (~1);
@@ -2708,7 +2705,7 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
return empty;
}
ShaderDebugTrace traces[4];
ShaderDebugTrace ret;
tracker.State().ApplyState(m_pImmediateContext);
@@ -2716,25 +2713,36 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
global.PopulateGroupshared(dxbc->GetDXBCByteCode());
global.sampleEvalRegisterMask = sampleEvalRegisterMask;
State initialState;
CreateShaderDebugStateAndTrace(initialState, traces[destIdx], destIdx, dxbc, refl,
ps->GetMapping());
State quad[4] = {
// top-left
State(0, &global, dxbc),
// top-right
State(1, &global, dxbc),
// bottom-left
State(2, &global, dxbc),
// bottom-right
State(3, &global, dxbc),
};
AddCBuffersToDebugTrace(*dxbc->GetDXBCByteCode(), *GetDebugManager(), traces[destIdx], rs->PS,
refl, ps->GetMapping());
CreateShaderDebugStateAndTrace(quad[destIdx], ret, dxbc, refl, ps->GetMapping());
AddCBuffersToDebugTrace(*dxbc->GetDXBCByteCode(), *GetDebugManager(), ret, rs->PS, refl,
ps->GetMapping());
global.constantBlocks = ret.constantBlocks;
{
DebugHit *hit = winner;
rdcarray<ShaderVariable> &ins = traces[destIdx].inputs;
rdcarray<ShaderVariable> &ins = quad[destIdx].inputs;
if(!ins.empty() &&
ins.back().name ==
dxbc->GetDXBCByteCode()->GetRegisterName(DXBCBytecode::TYPE_INPUT_COVERAGE_MASK, 0))
ins.back().value.u.x = hit->coverage;
initialState.semantics.coverage = hit->coverage;
initialState.semantics.primID = hit->primitive;
initialState.semantics.isFrontFace = hit->isFrontFace;
quad[destIdx].semantics.coverage = hit->coverage;
quad[destIdx].semantics.primID = hit->primitive;
quad[destIdx].semantics.isFrontFace = hit->isFrontFace;
uint32_t *data = &hit->rawdata;
@@ -2757,7 +2765,7 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
if(initialValues[i].reg >= 0)
{
ShaderVariable &invar = traces[destIdx].inputs[initialValues[i].reg];
ShaderVariable &invar = ins[initialValues[i].reg];
if(initialValues[i].sysattribute == ShaderBuiltin::PrimitiveIndex)
{
@@ -2790,18 +2798,19 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
for(int i = 0; i < 4; i++)
{
if(i != destIdx)
traces[i] = traces[destIdx];
quad[i] = initialState;
quad[i].SetTrace(i, &traces[i]);
if(i != destIdx)
{
quad[i].inputs = quad[destIdx].inputs;
quad[i].semantics = quad[destIdx].semantics;
quad[i].variables = quad[destIdx].variables;
quad[i].SetHelper();
}
}
// fetch any inputs that were evaluated at sample granularity
for(const GlobalState::SampleEvalCacheKey &key : evalSampleCacheData)
{
// start with the basic input value
ShaderVariable var = traces[destIdx].inputs[key.inputRegisterIndex];
ShaderVariable var = ret.inputs[key.inputRegisterIndex];
// copy over the value into the variable
memcpy(var.value.fv, evalSampleCache, var.columns * sizeof(float));
@@ -2818,9 +2827,11 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
evalSampleCache += 4;
}
ApplyAllDerivatives(global, traces, destIdx, initialValues, (float *)data);
ApplyAllDerivatives(global, quad, destIdx, initialValues, (float *)data);
}
ret.inputs = quad[destIdx].inputs;
SAFE_DELETE_ARRAY(initialData);
SAFE_DELETE_ARRAY(evalData);
@@ -2831,7 +2842,10 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
states.push_back((State)quad[destIdx]);
// ping pong between so that we can have 'current' quad to update into new one
State quad2[4];
State quad2[4] = {
State(0, &global, dxbc), State(1, &global, dxbc), State(2, &global, dxbc),
State(3, &global, dxbc),
};
State *curquad = quad;
State *newquad = quad2;
@@ -2852,7 +2866,7 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
for(size_t i = 0; i < 4; i++)
{
if(activeMask[i])
newquad[i] = curquad[i].GetNext(global, &apiWrapper, curquad);
newquad[i] = curquad[i].GetNext(&apiWrapper, curquad);
else
newquad[i] = curquad[i];
}
@@ -2959,13 +2973,13 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
}
} while(!finished);
traces[destIdx].states = states;
ret.states = states;
traces[destIdx].hasSourceMapping = dxbc->GetDebugInfo() && dxbc->GetDebugInfo()->HasSourceMapping();
ret.hasSourceMapping = dxbc->GetDebugInfo() && dxbc->GetDebugInfo()->HasSourceMapping();
dxbc->FillTraceLineInfo(traces[destIdx]);
dxbc->FillTraceLineInfo(ret);
return traces[destIdx];
return ret;
}
ShaderDebugTrace D3D11Replay::DebugThread(uint32_t eventId, const uint32_t groupid[3],
@@ -3006,12 +3020,14 @@ ShaderDebugTrace D3D11Replay::DebugThread(uint32_t eventId, const uint32_t group
GlobalState global;
global.PopulateGroupshared(dxbc->GetDXBCByteCode());
State initialState;
CreateShaderDebugStateAndTrace(initialState, ret, -1, dxbc, refl, cs->GetMapping());
State initialState(-1, &global, dxbc);
CreateShaderDebugStateAndTrace(initialState, ret, dxbc, refl, cs->GetMapping());
AddCBuffersToDebugTrace(*dxbc->GetDXBCByteCode(), *GetDebugManager(), ret, rs->CS, refl,
cs->GetMapping());
global.constantBlocks = ret.constantBlocks;
for(int i = 0; i < 3; i++)
{
initialState.semantics.GroupID[i] = groupid[i];
@@ -3031,7 +3047,7 @@ ShaderDebugTrace D3D11Replay::DebugThread(uint32_t eventId, const uint32_t group
if(initialState.Finished())
break;
initialState = initialState.GetNext(global, &apiWrapper, NULL);
initialState = initialState.GetNext(&apiWrapper, NULL);
dxbc->FillStateInstructionInfo(initialState);
+42 -29
View File
@@ -1509,9 +1509,6 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
// of which fragment was the last to successfully depth test and debug that, just by
// checking if the depth test is ordered and picking the final fragment in the series
// our debugging quad. Order is TL, TR, BL, BR
State quad[4];
// figure out the TL pixel's coords. Assume even top left (towards 0,0)
// this isn't spec'd but is a reasonable assumption.
int xTL = x & (~1);
@@ -1573,29 +1570,40 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
return empty;
}
ShaderDebugTrace traces[4];
ShaderDebugTrace ret;
GlobalState global;
global.PopulateGroupshared(dxbc->GetDXBCByteCode());
State initialState;
CreateShaderDebugStateAndTrace(initialState, traces[destIdx], destIdx, dxbc, refl,
origPSO->PS()->GetMapping());
State quad[4] = {
// top-left
State(0, &global, dxbc),
// top-right
State(1, &global, dxbc),
// bottom-left
State(2, &global, dxbc),
// bottom-right
State(3, &global, dxbc),
};
CreateShaderDebugStateAndTrace(quad[destIdx], ret, dxbc, refl, origPSO->PS()->GetMapping());
// Fetch constant buffer data from root signature
GatherConstantBuffers(m_pDevice, *dxbc->GetDXBCByteCode(), rs.graphics, refl,
origPSO->PS()->GetMapping(), traces[destIdx]);
origPSO->PS()->GetMapping(), ret);
global.constantBlocks = ret.constantBlocks;
{
DebugHit *pHit = pWinnerHit;
rdcarray<ShaderVariable> &ins = traces[destIdx].inputs;
rdcarray<ShaderVariable> &ins = quad[destIdx].inputs;
if(!ins.empty() && ins.back().name == "vCoverage")
ins.back().value.u.x = pHit->coverage;
initialState.semantics.coverage = pHit->coverage;
initialState.semantics.primID = pHit->primitive;
initialState.semantics.isFrontFace = pHit->isFrontFace;
quad[destIdx].semantics.coverage = pHit->coverage;
quad[destIdx].semantics.primID = pHit->primitive;
quad[destIdx].semantics.isFrontFace = pHit->isFrontFace;
uint32_t *data = &pHit->rawdata;
@@ -1616,7 +1624,7 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
if(initialValues[i].reg >= 0)
{
ShaderVariable &invar = traces[destIdx].inputs[initialValues[i].reg];
ShaderVariable &invar = ins[initialValues[i].reg];
if(initialValues[i].sysattribute == ShaderBuiltin::PrimitiveIndex)
{
@@ -1648,19 +1656,19 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
for(int i = 0; i < 4; i++)
{
if(i != destIdx)
traces[i] = traces[destIdx];
quad[i] = initialState;
quad[i].SetTrace(i, &traces[i]);
if(i != destIdx)
quad[i].SetHelper();
quad[i].inputs = quad[destIdx].inputs;
quad[i].semantics = quad[destIdx].semantics;
quad[i].variables = quad[destIdx].variables;
quad[i].SetHelper();
}
// TODO: Handle inputs that were evaluated at sample granularity (MSAA)
ApplyAllDerivatives(global, traces, destIdx, initialValues, (float *)data);
ApplyAllDerivatives(global, quad, destIdx, initialValues, (float *)data);
}
ret.inputs = quad[destIdx].inputs;
rdcarray<ShaderDebugState> states;
dxbc->FillStateInstructionInfo(quad[destIdx]);
@@ -1668,7 +1676,10 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
states.push_back(quad[destIdx]);
// ping pong between so that we can have 'current' quad to update into new one
State quad2[4];
State quad2[4] = {
State(0, &global, dxbc), State(1, &global, dxbc), State(2, &global, dxbc),
State(3, &global, dxbc),
};
State *curquad = quad;
State *newquad = quad2;
@@ -1689,7 +1700,7 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
for(size_t i = 0; i < 4; i++)
{
if(activeMask[i])
newquad[i] = curquad[i].GetNext(global, &apiWrapper, curquad);
newquad[i] = curquad[i].GetNext(&apiWrapper, curquad);
else
newquad[i] = curquad[i];
}
@@ -1796,13 +1807,13 @@ void ExtractInputsPS(PSInput IN, float4 debug_pixelPos : SV_Position, uint prim
}
} while(!finished);
traces[destIdx].states = states;
ret.states = states;
traces[destIdx].hasSourceMapping = dxbc->GetDebugInfo() && dxbc->GetDebugInfo()->HasSourceMapping();
ret.hasSourceMapping = dxbc->GetDebugInfo() && dxbc->GetDebugInfo()->HasSourceMapping();
dxbc->FillTraceLineInfo(traces[destIdx]);
dxbc->FillTraceLineInfo(ret);
return traces[destIdx];
return ret;
}
#endif // D3D12SHADERDEBUG_PIXEL
@@ -1856,12 +1867,14 @@ ShaderDebugTrace D3D12Replay::DebugThread(uint32_t eventId, const uint32_t group
GlobalState global;
global.PopulateGroupshared(dxbc->GetDXBCByteCode());
State initialState;
CreateShaderDebugStateAndTrace(initialState, ret, -1, dxbc, refl, pso->CS()->GetMapping());
State initialState(-1, &global, dxbc);
CreateShaderDebugStateAndTrace(initialState, ret, dxbc, refl, pso->CS()->GetMapping());
GatherConstantBuffers(m_pDevice, *dxbc->GetDXBCByteCode(), rs.compute, refl,
pso->CS()->GetMapping(), ret);
global.constantBlocks = ret.constantBlocks;
for(int i = 0; i < 3; i++)
{
initialState.semantics.GroupID[i] = groupid[i];
@@ -1881,7 +1894,7 @@ ShaderDebugTrace D3D12Replay::DebugThread(uint32_t eventId, const uint32_t group
if(initialState.Finished())
break;
initialState = initialState.GetNext(global, &apiWrapper, NULL);
initialState = initialState.GetNext(&apiWrapper, NULL);
dxbc->FillStateInstructionInfo(initialState);
+74 -64
View File
@@ -1079,6 +1079,18 @@ ShaderVariable sub(const ShaderVariable &a, const ShaderVariable &b, const VarTy
return add(a, neg(b, type), type);
}
State::State(int quadIdx, GlobalState *globalState, const DXBC::DXBCContainer *dxbc)
: global(globalState)
{
quadIndex = quadIdx;
nextInstruction = 0;
flags = ShaderEvents::NoEvent;
done = false;
reflection = dxbc->GetReflection();
program = dxbc->GetDXBCByteCode();
RDCEraseEl(semantics);
}
bool State::Finished() const
{
return program && (done || nextInstruction >= (int)program->GetNumInstructions());
@@ -1372,10 +1384,10 @@ ShaderVariable State::GetSrc(const Operand &oper, const Operation &op, bool allo
}
case TYPE_INPUT:
{
RDCASSERT(indices[0] < (uint32_t)trace->inputs.size());
RDCASSERT(indices[0] < (uint32_t)inputs.size());
if(indices[0] < (uint32_t)trace->inputs.size())
v = s = trace->inputs[indices[0]];
if(indices[0] < (uint32_t)inputs.size())
v = s = inputs[indices[0]];
else
v = s = ShaderVariable("", indices[0], indices[0], indices[0], indices[0]);
@@ -1456,17 +1468,17 @@ ShaderVariable State::GetSrc(const Operand &oper, const Operation &op, bool allo
}
}
RDCASSERTMSG("Invalid cbuffer lookup", cb != -1 && cb < trace->constantBlocks.count(), cb,
trace->constantBlocks.count());
RDCASSERTMSG("Invalid cbuffer lookup", cb != -1 && cb < global->constantBlocks.count(), cb,
global->constantBlocks.count());
if(cb >= 0 && cb < trace->constantBlocks.count())
if(cb >= 0 && cb < global->constantBlocks.count())
{
RDCASSERTMSG("Out of bounds cbuffer lookup",
cbLookup < (uint32_t)trace->constantBlocks[cb].members.count(), cbLookup,
trace->constantBlocks[cb].members.count());
cbLookup < (uint32_t)global->constantBlocks[cb].members.count(), cbLookup,
global->constantBlocks[cb].members.count());
if(cbLookup < (uint32_t)trace->constantBlocks[cb].members.count())
v = s = trace->constantBlocks[cb].members[cbLookup];
if(cbLookup < (uint32_t)global->constantBlocks[cb].members.count())
v = s = global->constantBlocks[cb].members[cbLookup];
else
v = s = ShaderVariable("", 0U, 0U, 0U, 0U);
}
@@ -1778,7 +1790,7 @@ void FlattenVariables(const rdcstr &cbname, const rdcarray<ShaderConstant> &cons
}
}
State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State quad[4]) const
State State::GetNext(DebugAPIWrapper *apiWrapper, State quad[4]) const
{
State s = *this;
@@ -2696,15 +2708,15 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
{
BindingSlot slot =
GetBindingSlotForIdentifier(*program, TYPE_UNORDERED_ACCESS_VIEW, srcOpers[0].value.u.x);
GlobalState::UAVIterator uav = global.uavs.find(slot);
if(uav == global.uavs.end())
GlobalState::UAVIterator uav = global->uavs.find(slot);
if(uav == global->uavs.end())
{
if(!apiWrapper->FetchUAV(slot))
{
RDCERR("Invalid UAV reg=%u, space=%u", slot.shaderRegister, slot.registerSpace);
return s;
}
uav = global.uavs.find(slot);
uav = global->uavs.find(slot);
}
uint32_t count = uav->second.hiddenCounter++;
@@ -2716,15 +2728,15 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
{
BindingSlot slot =
GetBindingSlotForIdentifier(*program, TYPE_UNORDERED_ACCESS_VIEW, srcOpers[0].value.u.x);
GlobalState::UAVIterator uav = global.uavs.find(slot);
if(uav == global.uavs.end())
GlobalState::UAVIterator uav = global->uavs.find(slot);
if(uav == global->uavs.end())
{
if(!apiWrapper->FetchUAV(slot))
{
RDCERR("Invalid UAV reg=%u, space=%u", slot.shaderRegister, slot.registerSpace);
return s;
}
uav = global.uavs.find(slot);
uav = global->uavs.find(slot);
}
uint32_t count = --uav->second.hiddenCounter;
@@ -2825,7 +2837,7 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
if(gsm)
{
offset = 0;
if(resIndex > global.groupshared.size())
if(resIndex > global->groupshared.size())
{
numElems = 0;
stride = 4;
@@ -2833,25 +2845,25 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
}
else
{
numElems = global.groupshared[resIndex].count;
stride = global.groupshared[resIndex].bytestride;
data = &global.groupshared[resIndex].data[0];
structured = global.groupshared[resIndex].structured;
numElems = global->groupshared[resIndex].count;
stride = global->groupshared[resIndex].bytestride;
data = &global->groupshared[resIndex].data[0];
structured = global->groupshared[resIndex].structured;
}
}
else
{
BindingSlot slot =
GetBindingSlotForIdentifier(*program, TYPE_UNORDERED_ACCESS_VIEW, resIndex);
GlobalState::UAVIterator uav = global.uavs.find(slot);
if(uav == global.uavs.end())
GlobalState::UAVIterator uav = global->uavs.find(slot);
if(uav == global->uavs.end())
{
if(!apiWrapper->FetchUAV(slot))
{
RDCERR("Invalid UAV reg=%u, space=%u", slot.shaderRegister, slot.registerSpace);
return s;
}
uav = global.uavs.find(slot);
uav = global->uavs.find(slot);
}
offset = uav->second.firstElement;
@@ -2996,9 +3008,9 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
if(stride == 0)
{
if(gsm && resIndex < global.groupshared.size())
if(gsm && resIndex < global->groupshared.size())
{
stride = global.groupshared[resIndex].bytestride;
stride = global->groupshared[resIndex].bytestride;
}
else if(!gsm)
{
@@ -3072,7 +3084,7 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
if(gsm)
{
offset = 0;
if(resIndex > global.groupshared.size())
if(resIndex > global->groupshared.size())
{
numElems = 0;
stride = 4;
@@ -3080,13 +3092,13 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
}
else
{
numElems = global.groupshared[resIndex].count;
stride = global.groupshared[resIndex].bytestride;
data = global.groupshared[resIndex].data.data();
dataSize = global.groupshared[resIndex].data.size();
numElems = global->groupshared[resIndex].count;
stride = global->groupshared[resIndex].bytestride;
data = global->groupshared[resIndex].data.data();
dataSize = global->groupshared[resIndex].data.size();
fmt.fmt = CompType::UInt;
fmt.byteWidth = 4;
fmt.numComps = global.groupshared[resIndex].bytestride / 4;
fmt.numComps = global->groupshared[resIndex].bytestride / 4;
fmt.stride = 0;
}
texData = false;
@@ -3098,15 +3110,15 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
if(srv)
{
GlobalState::SRVIterator srvIter = global.srvs.find(slot);
if(srvIter == global.srvs.end())
GlobalState::SRVIterator srvIter = global->srvs.find(slot);
if(srvIter == global->srvs.end())
{
if(!apiWrapper->FetchSRV(slot))
{
RDCERR("Invalid SRV reg=%u, space=%u", slot.shaderRegister, slot.registerSpace);
return s;
}
srvIter = global.srvs.find(slot);
srvIter = global->srvs.find(slot);
}
data = srvIter->second.data.data();
@@ -3116,15 +3128,15 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
}
else
{
GlobalState::UAVIterator uavIter = global.uavs.find(slot);
if(uavIter == global.uavs.end())
GlobalState::UAVIterator uavIter = global->uavs.find(slot);
if(uavIter == global->uavs.end())
{
if(!apiWrapper->FetchUAV(slot))
{
RDCERR("Invalid UAV reg=%u, space=%u", slot.shaderRegister, slot.registerSpace);
return s;
}
uavIter = global.uavs.find(slot);
uavIter = global->uavs.find(slot);
}
data = uavIter->second.data.data();
@@ -3289,8 +3301,8 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
}
// look up this combination in the cache, if we get a hit then return that value.
auto it = global.sampleEvalCache.find(key);
if(it != global.sampleEvalCache.end())
auto it = global->sampleEvalCache.find(key);
if(it != global->sampleEvalCache.end())
{
// perform source operand swizzling
ShaderVariable var = it->second;
@@ -3307,7 +3319,7 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
// just return the interpolant, or something went wrong and the item we want isn't cached so
// the best we can do is return the interpolant.
if(!global.sampleEvalCache.empty())
if(!global->sampleEvalCache.empty())
{
apiWrapper->AddDebugMessage(
MessageCategory::Shaders, MessageSeverity::Medium, MessageSource::RuntimeWarning,
@@ -3663,8 +3675,8 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
resourceDim = decl.dim;
resourceBinding = GetBindingSlotForDeclaration(*program, decl);
GlobalState::SRVIterator srv = global.srvs.find(resourceBinding);
if(srv == global.srvs.end())
GlobalState::SRVIterator srv = global->srvs.find(resourceBinding);
if(srv == global->srvs.end())
{
if(!apiWrapper->FetchSRV(resourceBinding))
{
@@ -3672,7 +3684,7 @@ State State::GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State qua
resourceBinding.registerSpace);
return s;
}
srv = global.srvs.find(resourceBinding);
srv = global->srvs.find(resourceBinding);
}
const byte *data = &srv->second.data[0];
@@ -4162,12 +4174,10 @@ void GlobalState::PopulateGroupshared(const DXBCBytecode::Program *pBytecode)
}
}
void CreateShaderDebugStateAndTrace(State &initialState, ShaderDebugTrace &trace, int quadIdx,
void CreateShaderDebugStateAndTrace(State &initialState, ShaderDebugTrace &trace,
DXBC::DXBCContainer *dxbc, const ShaderReflection &refl,
const ShaderBindpointMapping &mapping)
{
initialState = State(quadIdx, &trace, dxbc->GetReflection(), dxbc->GetDXBCByteCode());
bool hasSourceMapping = dxbc->GetDebugInfo() && dxbc->GetDebugInfo()->HasSourceMapping();
dxbc->GetDXBCByteCode()->SetupRegisterFile(initialState.variables);
@@ -4513,14 +4523,14 @@ bool PromptDebugTimeout(uint32_t cycleCounter)
return false;
}
void ApplyDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int reg, int element,
int numWords, float *data, float signmul, int32_t quadIdxA, int32_t quadIdxB)
void ApplyDerivatives(GlobalState &global, State quad[4], int reg, int element, int numWords,
float *data, float signmul, int32_t quadIdxA, int32_t quadIdxB)
{
for(int w = 0; w < numWords; w++)
{
traces[quadIdxA].inputs[reg].value.fv[element + w] += signmul * data[w];
quad[quadIdxA].inputs[reg].value.fv[element + w] += signmul * data[w];
if(quadIdxB >= 0)
traces[quadIdxB].inputs[reg].value.fv[element + w] += signmul * data[w];
quad[quadIdxB].inputs[reg].value.fv[element + w] += signmul * data[w];
}
// quick check to see if this register was evaluated
@@ -4539,7 +4549,7 @@ void ApplyDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int reg,
}
}
void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int destIdx,
void ApplyAllDerivatives(GlobalState &global, State quad[4], int destIdx,
const rdcarray<PSInputElement> &initialValues, float *data)
{
// We make the assumption that the coarse derivatives are generated from (0,0) in the quad, and
@@ -4600,16 +4610,16 @@ void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int de
if(initialValues[i].reg >= 0)
{
if(destIdx == 0)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddx_coarse, 1.0f, 1, 3);
else if(destIdx == 1)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddx_coarse, -1.0f, 0, 2);
else if(destIdx == 2)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddx_coarse, 1.0f, 1, -1);
else if(destIdx == 3)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddx_coarse, -1.0f, 0, -1);
}
@@ -4627,13 +4637,13 @@ void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int de
if(initialValues[i].reg >= 0)
{
if(destIdx == 0)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddy_coarse, 1.0f, 2, 3);
else if(destIdx == 1)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddy_coarse, 1.0f, 2, -1);
else if(destIdx == 2)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddy_coarse, -1.0f, 0, 1);
}
@@ -4650,10 +4660,10 @@ void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int de
if(initialValues[i].reg >= 0)
{
if(destIdx == 2)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddxfine, 1.0f, 3, -1);
else if(destIdx == 3)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddxfine, -1.0f, 2, -1);
}
@@ -4670,10 +4680,10 @@ void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int de
if(initialValues[i].reg >= 0)
{
if(destIdx == 1)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddyfine, 1.0f, 3, -1);
else if(destIdx == 3)
ApplyDerivatives(global, traces, initialValues[i].reg, initialValues[i].elem,
ApplyDerivatives(global, quad, initialValues[i].reg, initialValues[i].elem,
initialValues[i].numwords, ddyfine, -1.0f, 0, 1);
}
+12 -37
View File
@@ -174,6 +174,9 @@ public:
// a bitmask of which registers were fetched into the cache, for quick checking
uint64_t sampleEvalRegisterMask = 0;
std::map<SampleEvalCacheKey, ShaderVariable> sampleEvalCache;
// copied from the parent trace
rdcarray<ShaderVariable> constantBlocks;
};
#define SHADER_DEBUG_WARN_THRESHOLD 100000
@@ -199,12 +202,6 @@ struct PSInputElement
bool included;
};
void ApplyDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int reg, int element,
int numWords, float *data, float signmul, int32_t quadIdxA, int32_t quadIdxB);
void ApplyAllDerivatives(GlobalState &global, ShaderDebugTrace traces[4], int destIdx,
const rdcarray<PSInputElement> &initialValues, float *data);
void FlattenSingleVariable(uint32_t byteOffset, const rdcstr &basename, const ShaderVariable &v,
rdcarray<ShaderVariable> &outvars);
@@ -278,34 +275,7 @@ public:
class State : public ShaderDebugState
{
public:
State()
{
quadIndex = 0;
nextInstruction = 0;
flags = ShaderEvents::NoEvent;
done = false;
trace = NULL;
program = NULL;
RDCEraseEl(semantics);
}
State(int quadIdx, const ShaderDebugTrace *t, const DXBC::Reflection *r,
const DXBCBytecode::Program *p)
{
quadIndex = quadIdx;
nextInstruction = 0;
flags = ShaderEvents::NoEvent;
done = false;
trace = t;
reflection = r;
program = p;
RDCEraseEl(semantics);
}
void SetTrace(int quadIdx, const ShaderDebugTrace *t)
{
quadIndex = quadIdx;
trace = t;
}
State(int quadIdx, GlobalState *globalState, const DXBC::DXBCContainer *dxbc);
void SetHelper() { done = true; }
struct
@@ -319,7 +289,10 @@ public:
bool Finished() const;
State GetNext(GlobalState &global, DebugAPIWrapper *apiWrapper, State quad[4]) const;
State GetNext(DebugAPIWrapper *apiWrapper, State quad[4]) const;
rdcarray<ShaderVariable> inputs;
GlobalState *global;
private:
// index in the pixel quad
@@ -351,10 +324,12 @@ private:
const DXBC::Reflection *reflection;
const DXBCBytecode::Program *program;
const ShaderDebugTrace *trace;
};
void CreateShaderDebugStateAndTrace(State &initialState, ShaderDebugTrace &trace, int quadIdx,
void ApplyAllDerivatives(GlobalState &global, State quad[4], int destIdx,
const rdcarray<PSInputElement> &initialValues, float *data);
void CreateShaderDebugStateAndTrace(State &initialState, ShaderDebugTrace &trace,
DXBC::DXBCContainer *dxbc, const ShaderReflection &refl,
const ShaderBindpointMapping &mapping);
void AddCBufferToDebugTrace(const DXBCBytecode::Program &program, ShaderDebugTrace &trace,