Include new ILDN chunk and global flags in disassembly

* This is used for both DXBC and DXIL bytecode
This commit is contained in:
baldurk
2020-06-18 17:22:42 +01:00
parent 6641030fbc
commit 57721e4688
2 changed files with 119 additions and 3 deletions
@@ -262,6 +262,7 @@ static const uint32_t FOURCC_DXIL = MAKE_FOURCC('D', 'X', 'I', 'L');
static const uint32_t FOURCC_ILDB = MAKE_FOURCC('I', 'L', 'D', 'B');
static const uint32_t FOURCC_ILDN = MAKE_FOURCC('I', 'L', 'D', 'N');
static const uint32_t FOURCC_HASH = MAKE_FOURCC('H', 'A', 'S', 'H');
static const uint32_t FOURCC_SFI0 = MAKE_FOURCC('S', 'F', 'I', '0');
int TypeByteSize(VariableType t)
{
@@ -507,16 +508,87 @@ const rdcstr &DXBCContainer::GetDisassembly()
{
if(m_Disassembly.empty())
{
rdcstr globalFlagsString;
const rdcstr commentString = m_DXBCByteCode ? "//" : ";";
if(m_GlobalFlags != GlobalShaderFlags::None)
{
globalFlagsString += commentString + " Note: shader requires additional functionality:\n";
if(m_GlobalFlags & GlobalShaderFlags::DoublePrecision)
globalFlagsString += commentString + " Double-precision floating point\n";
if(m_GlobalFlags & GlobalShaderFlags::RawStructured)
globalFlagsString += commentString + " Raw and Structured buffers\n";
if(m_GlobalFlags & GlobalShaderFlags::UAVsEveryStage)
globalFlagsString += commentString + " UAVs at every shader stage\n";
if(m_GlobalFlags & GlobalShaderFlags::UAVCount64)
globalFlagsString += commentString + " 64 UAV slots\n";
if(m_GlobalFlags & GlobalShaderFlags::MinPrecision)
globalFlagsString += commentString + " Minimum-precision data types\n";
if(m_GlobalFlags & GlobalShaderFlags::DoubleExtensions11_1)
globalFlagsString += commentString + " Double-precision extensions for 11.1\n";
if(m_GlobalFlags & GlobalShaderFlags::ShaderExtensions11_1)
globalFlagsString += commentString + " Shader extensions for 11.1\n";
if(m_GlobalFlags & GlobalShaderFlags::ComparisonFilter)
globalFlagsString += commentString + " Comparison filtering for feature level 9\n";
if(m_GlobalFlags & GlobalShaderFlags::TiledResources)
globalFlagsString += commentString + " Tiled resources\n";
if(m_GlobalFlags & GlobalShaderFlags::PSOutStencilref)
globalFlagsString += commentString + " PS Output Stencil Ref\n";
if(m_GlobalFlags & GlobalShaderFlags::PSInnerCoverage)
globalFlagsString += commentString + " PS Inner Coverage\n";
if(m_GlobalFlags & GlobalShaderFlags::TypedUAVAdditional)
globalFlagsString += commentString + " Typed UAV Load Additional Formats\n";
if(m_GlobalFlags & GlobalShaderFlags::RasterOrderViews)
globalFlagsString += commentString + " Raster Ordered UAVs\n";
if(m_GlobalFlags & GlobalShaderFlags::ArrayIndexFromVert)
globalFlagsString += commentString +
" SV_RenderTargetArrayIndex or SV_ViewportArrayIndex from any "
"shader feeding rasterizer\n";
if(m_GlobalFlags & GlobalShaderFlags::WaveOps)
globalFlagsString += commentString + " Wave level operations\n";
if(m_GlobalFlags & GlobalShaderFlags::Int64)
globalFlagsString += commentString + " 64-Bit integer\n";
if(m_GlobalFlags & GlobalShaderFlags::ViewInstancing)
globalFlagsString += commentString + " View Instancing\n";
if(m_GlobalFlags & GlobalShaderFlags::Barycentrics)
globalFlagsString += commentString + " Barycentrics\n";
if(m_GlobalFlags & GlobalShaderFlags::NativeLowPrecision)
globalFlagsString += commentString + " Use native low precision\n";
if(m_GlobalFlags & GlobalShaderFlags::ShadingRate)
globalFlagsString += commentString + " Shading Rate\n";
if(m_GlobalFlags & GlobalShaderFlags::Raytracing1_1)
globalFlagsString += commentString + " Raytracing tier 1.1 features\n";
if(m_GlobalFlags & GlobalShaderFlags::SamplerFeedback)
globalFlagsString += commentString + " Sampler feedback\n";
globalFlagsString += commentString + "\n";
}
if(m_DXBCByteCode)
{
m_Disassembly = StringFormat::Fmt("Shader hash %08x-%08x-%08x-%08x\n\n", m_Hash[0], m_Hash[1],
m_Hash[2], m_Hash[3]);
if(m_GlobalFlags != GlobalShaderFlags::None)
m_Disassembly += globalFlagsString;
if(!m_DebugFileName.empty())
m_Disassembly += StringFormat::Fmt("// Debug name: %s\n", m_DebugFileName.c_str());
m_Disassembly += m_DXBCByteCode->GetDisassembly();
}
else if(m_DXILByteCode)
{
m_Disassembly = "; shader hash: ";
m_Disassembly.clear();
if(m_GlobalFlags != GlobalShaderFlags::None)
m_Disassembly += globalFlagsString;
if(!m_DebugFileName.empty())
m_Disassembly += StringFormat::Fmt("; shader debug name: %s\n", m_DebugFileName.c_str());
m_Disassembly += "; shader hash: ";
byte *hashBytes = (byte *)m_Hash;
for(size_t i = 0; i < sizeof(m_Hash); i++)
m_Disassembly += StringFormat::Fmt("%02x", hashBytes[i]);
@@ -541,9 +613,19 @@ void DXBCContainer::FillTraceLineInfo(ShaderDebugTrace &trace) const
if(m_DebugInfo)
m_DebugInfo->GetLineInfo(i, op.offset, trace.lineInfo[i]);
// we add two lines for the shader hash on top of what the bytecode disassembler did
// we add some number of lines for the header we added with shader hash, debug name, etc on
// top of what the bytecode disassembler did
// 2 minimum for the shader hash we always print
uint32_t extraLines = 2;
if(!m_DebugFileName.empty())
extraLines++;
if(m_GlobalFlags != GlobalShaderFlags::None)
extraLines += (uint32_t)Bits::CountOnes((uint64_t)m_GlobalFlags) + 2;
if(op.line > 0)
trace.lineInfo[i].disassemblyLine = 2 + op.line;
trace.lineInfo[i].disassemblyLine = extraLines + op.line;
}
}
}
@@ -1052,6 +1134,10 @@ DXBCContainer::DXBCContainer(const void *ByteCode, size_t ByteCodeLength)
memcpy(m_Hash, h->hashValue, sizeof(h->hashValue));
}
else if(*fourcc == FOURCC_SFI0)
{
m_GlobalFlags = *(const GlobalShaderFlags *)chunkContents;
}
else if(*fourcc == FOURCC_ISGN || *fourcc == FOURCC_OSGN || *fourcc == FOURCC_ISG1 ||
*fourcc == FOURCC_OSG1 || *fourcc == FOURCC_OSG5 || *fourcc == FOURCC_PCSG)
{
@@ -108,6 +108,35 @@ struct ShaderStatistics
} version;
};
enum class GlobalShaderFlags : int64_t
{
None = 0,
DoublePrecision = 0x000001,
RawStructured = 0x000002,
UAVsEveryStage = 0x000004,
UAVCount64 = 0x000008,
MinPrecision = 0x000010,
DoubleExtensions11_1 = 0x000020,
ShaderExtensions11_1 = 0x000040,
ComparisonFilter = 0x000080,
TiledResources = 0x000100,
PSOutStencilref = 0x000200,
PSInnerCoverage = 0x000400,
TypedUAVAdditional = 0x000800,
RasterOrderViews = 0x001000,
ArrayIndexFromVert = 0x002000,
WaveOps = 0x004000,
Int64 = 0x008000,
ViewInstancing = 0x010000,
Barycentrics = 0x020000,
NativeLowPrecision = 0x040000,
ShadingRate = 0x080000,
Raytracing1_1 = 0x100000,
SamplerFeedback = 0x200000,
};
BITMASK_OPERATORS(GlobalShaderFlags);
rdcstr TypeName(CBufferVariableType::Descriptor desc);
struct RDEFHeader;
@@ -183,6 +212,7 @@ private:
uint32_t m_Hash[4];
rdcstr m_DebugFileName;
GlobalShaderFlags m_GlobalFlags = GlobalShaderFlags::None;
ShaderStatistics m_ShaderStats;
DXBCBytecode::Program *m_DXBCByteCode = NULL;