mirror of
https://github.com/baldurk/renderdoc.git
synced 2026-07-08 16:50:44 +00:00
Add UI to vulkan pipeline state viewer to allow compute debugging
This commit is contained in:
@@ -30,6 +30,7 @@
|
||||
#include <QXmlStreamWriter>
|
||||
#include "Code/Resources.h"
|
||||
#include "Widgets/Extended/RDHeaderView.h"
|
||||
#include "flowlayout/FlowLayout.h"
|
||||
#include "toolwindowmanager/ToolWindowManager.h"
|
||||
#include "PipelineStateViewer.h"
|
||||
#include "ui_VulkanPipelineStateViewer.h"
|
||||
@@ -135,6 +136,23 @@ VulkanPipelineStateViewer::VulkanPipelineStateViewer(ICaptureContext &ctx,
|
||||
ui->vsUBOs, ui->tcsUBOs, ui->tesUBOs, ui->gsUBOs, ui->fsUBOs, ui->csUBOs,
|
||||
};
|
||||
|
||||
// setup FlowLayout for CS shader group, with debugging controls
|
||||
{
|
||||
QLayout *oldLayout = ui->csShaderGroup->layout();
|
||||
|
||||
QObjectList childs = ui->csShaderGroup->children();
|
||||
childs.removeOne((QObject *)oldLayout);
|
||||
|
||||
delete oldLayout;
|
||||
|
||||
FlowLayout *csShaderFlow = new FlowLayout(ui->csShaderGroup, -1, 3, 3);
|
||||
|
||||
for(QObject *o : childs)
|
||||
csShaderFlow->addWidget(qobject_cast<QWidget *>(o));
|
||||
|
||||
ui->csShaderGroup->setLayout(csShaderFlow);
|
||||
}
|
||||
|
||||
for(QToolButton *b : viewButtons)
|
||||
QObject::connect(b, &QToolButton::clicked, this, &VulkanPipelineStateViewer::shaderView_clicked);
|
||||
|
||||
@@ -749,6 +767,18 @@ void VulkanPipelineStateViewer::clearState()
|
||||
|
||||
ui->stencils->clear();
|
||||
|
||||
{
|
||||
ui->groupX->setEnabled(false);
|
||||
ui->groupY->setEnabled(false);
|
||||
ui->groupZ->setEnabled(false);
|
||||
|
||||
ui->threadX->setEnabled(false);
|
||||
ui->threadY->setEnabled(false);
|
||||
ui->threadZ->setEnabled(false);
|
||||
|
||||
ui->debugThread->setEnabled(false);
|
||||
}
|
||||
|
||||
ui->conditionalRenderingGroup->setVisible(false);
|
||||
ui->csConditionalRenderingGroup->setVisible(false);
|
||||
}
|
||||
@@ -2501,6 +2531,51 @@ void VulkanPipelineStateViewer::setState()
|
||||
ui->stencils->clearSelection();
|
||||
ui->stencils->endUpdate();
|
||||
|
||||
// set up thread debugging inputs
|
||||
if(m_Ctx.APIProps().shaderDebugging && state.computeShader.reflection && draw &&
|
||||
(draw->flags & DrawFlags::Dispatch))
|
||||
{
|
||||
ui->groupX->setEnabled(true);
|
||||
ui->groupY->setEnabled(true);
|
||||
ui->groupZ->setEnabled(true);
|
||||
|
||||
ui->threadX->setEnabled(true);
|
||||
ui->threadY->setEnabled(true);
|
||||
ui->threadZ->setEnabled(true);
|
||||
|
||||
ui->debugThread->setEnabled(true);
|
||||
|
||||
// set maximums for CS debugging
|
||||
ui->groupX->setMaximum((int)draw->dispatchDimension[0] - 1);
|
||||
ui->groupY->setMaximum((int)draw->dispatchDimension[1] - 1);
|
||||
ui->groupZ->setMaximum((int)draw->dispatchDimension[2] - 1);
|
||||
|
||||
if(draw->dispatchThreadsDimension[0] == 0)
|
||||
{
|
||||
ui->threadX->setMaximum((int)state.computeShader.reflection->dispatchThreadsDimension[0] - 1);
|
||||
ui->threadY->setMaximum((int)state.computeShader.reflection->dispatchThreadsDimension[1] - 1);
|
||||
ui->threadZ->setMaximum((int)state.computeShader.reflection->dispatchThreadsDimension[2] - 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
ui->threadX->setMaximum((int)draw->dispatchThreadsDimension[0] - 1);
|
||||
ui->threadY->setMaximum((int)draw->dispatchThreadsDimension[1] - 1);
|
||||
ui->threadZ->setMaximum((int)draw->dispatchThreadsDimension[2] - 1);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ui->groupX->setEnabled(false);
|
||||
ui->groupY->setEnabled(false);
|
||||
ui->groupZ->setEnabled(false);
|
||||
|
||||
ui->threadX->setEnabled(false);
|
||||
ui->threadY->setEnabled(false);
|
||||
ui->threadZ->setEnabled(false);
|
||||
|
||||
ui->debugThread->setEnabled(false);
|
||||
}
|
||||
|
||||
// highlight the appropriate stages in the flowchart
|
||||
if(draw == NULL)
|
||||
{
|
||||
@@ -3722,3 +3797,94 @@ void VulkanPipelineStateViewer::on_meshView_clicked()
|
||||
m_Ctx.ShowMeshPreview();
|
||||
ToolWindowManager::raiseToolWindow(m_Ctx.GetMeshPreview()->Widget());
|
||||
}
|
||||
|
||||
void VulkanPipelineStateViewer::on_debugThread_clicked()
|
||||
{
|
||||
if(!m_Ctx.APIProps().shaderDebugging)
|
||||
return;
|
||||
|
||||
if(!m_Ctx.IsCaptureLoaded())
|
||||
return;
|
||||
|
||||
const DrawcallDescription *draw = m_Ctx.CurDrawcall();
|
||||
|
||||
if(!draw || !(draw->flags & DrawFlags::Dispatch))
|
||||
return;
|
||||
|
||||
ShaderReflection *shaderDetails = m_Ctx.CurVulkanPipelineState()->computeShader.reflection;
|
||||
const ShaderBindpointMapping &bindMapping =
|
||||
m_Ctx.CurVulkanPipelineState()->computeShader.bindpointMapping;
|
||||
|
||||
if(!shaderDetails)
|
||||
return;
|
||||
|
||||
uint32_t groupdim[3] = {};
|
||||
|
||||
for(int i = 0; i < 3; i++)
|
||||
groupdim[i] = draw->dispatchDimension[i];
|
||||
|
||||
uint32_t threadsdim[3] = {};
|
||||
for(int i = 0; i < 3; i++)
|
||||
threadsdim[i] = draw->dispatchThreadsDimension[i];
|
||||
|
||||
if(threadsdim[0] == 0)
|
||||
{
|
||||
for(int i = 0; i < 3; i++)
|
||||
threadsdim[i] = shaderDetails->dispatchThreadsDimension[i];
|
||||
}
|
||||
|
||||
struct threadSelect
|
||||
{
|
||||
uint32_t g[3];
|
||||
uint32_t t[3];
|
||||
} thread = {
|
||||
// g[]
|
||||
{(uint32_t)ui->groupX->value(), (uint32_t)ui->groupY->value(), (uint32_t)ui->groupZ->value()},
|
||||
// t[]
|
||||
{(uint32_t)ui->threadX->value(), (uint32_t)ui->threadY->value(), (uint32_t)ui->threadZ->value()},
|
||||
};
|
||||
|
||||
bool done = false;
|
||||
ShaderDebugTrace *trace = NULL;
|
||||
|
||||
m_Ctx.Replay().AsyncInvoke([&trace, &done, thread](IReplayController *r) {
|
||||
trace = r->DebugThread(thread.g, thread.t);
|
||||
|
||||
if(trace->debugger == NULL)
|
||||
{
|
||||
r->FreeTrace(trace);
|
||||
trace = NULL;
|
||||
}
|
||||
|
||||
done = true;
|
||||
});
|
||||
|
||||
QString debugContext = lit("Group [%1,%2,%3] Thread [%4,%5,%6]")
|
||||
.arg(thread.g[0])
|
||||
.arg(thread.g[1])
|
||||
.arg(thread.g[2])
|
||||
.arg(thread.t[0])
|
||||
.arg(thread.t[1])
|
||||
.arg(thread.t[2]);
|
||||
|
||||
// wait a short while before displaying the progress dialog (which won't show if we're already
|
||||
// done by the time we reach it)
|
||||
for(int i = 0; !done && i < 100; i++)
|
||||
QThread::msleep(5);
|
||||
|
||||
ShowProgressDialog(this, tr("Debugging %1").arg(debugContext), [&done]() { return done; });
|
||||
|
||||
if(!trace)
|
||||
{
|
||||
RDDialog::critical(
|
||||
this, tr("Error debugging"),
|
||||
tr("Error debugging thread - make sure a valid group and thread is selected"));
|
||||
return;
|
||||
}
|
||||
|
||||
// viewer takes ownership of the trace
|
||||
IShaderViewer *s =
|
||||
m_Ctx.DebugShader(&bindMapping, shaderDetails, ResourceId(), trace, debugContext);
|
||||
|
||||
m_Ctx.AddDockWindow(s->Widget(), DockReference::AddTo, this);
|
||||
}
|
||||
|
||||
@@ -82,6 +82,8 @@ private slots:
|
||||
void ubo_itemActivated(RDTreeWidgetItem *item, int column);
|
||||
void vertex_leave(QEvent *e);
|
||||
|
||||
void on_debugThread_clicked();
|
||||
|
||||
private:
|
||||
Ui::VulkanPipelineStateViewer *ui;
|
||||
ICaptureContext &m_Ctx;
|
||||
|
||||
@@ -3546,90 +3546,191 @@
|
||||
<number>4</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="RDLabel" name="csShader">
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::Box</enum>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<widget class="QFrame" name="csShaderControlsFrame">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_29">
|
||||
<property name="spacing">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="RDLabel" name="csShader">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::Box</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderViewButton">
|
||||
<property name="cursor">
|
||||
<cursorShape>PointingHandCursor</cursorShape>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Open Shader Source</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>View</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/action.png</normaloff>:/action.png
|
||||
</iconset>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderEditButton">
|
||||
<property name="toolTip">
|
||||
<string>Edit Shader</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Edit</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/page_white_edit.png</normaloff>:/page_white_edit.png
|
||||
</iconset>
|
||||
</property>
|
||||
<property name="popupMode">
|
||||
<enum>QToolButton::MenuButtonPopup</enum>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderSaveButton">
|
||||
<property name="toolTip">
|
||||
<string>Save Shader DXBC</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Save</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/save.png</normaloff>:/save.png
|
||||
</iconset>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderViewButton">
|
||||
<property name="cursor">
|
||||
<cursorShape>PointingHandCursor</cursorShape>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Open Shader Source</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>View</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/action.png</normaloff>:/action.png</iconset>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<widget class="QFrame" name="csDebugFrame">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_34">
|
||||
<property name="spacing">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QLabel" name="groupDebugLabel">
|
||||
<property name="text">
|
||||
<string>Debug Group:</string>
|
||||
</property>
|
||||
<property name="indent">
|
||||
<number>20</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="groupX"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="groupY"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="groupZ"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="threadDebugLabel">
|
||||
<property name="text">
|
||||
<string>Thread:</string>
|
||||
</property>
|
||||
<property name="indent">
|
||||
<number>20</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="threadX"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="threadY"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QSpinBox" name="threadZ"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="debugThread">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/wrench.png</normaloff>:/wrench.png
|
||||
</iconset>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderEditButton">
|
||||
<property name="toolTip">
|
||||
<string>Edit Shader</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Edit</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/page_white_edit.png</normaloff>:/page_white_edit.png</iconset>
|
||||
</property>
|
||||
<property name="popupMode">
|
||||
<enum>QToolButton::MenuButtonPopup</enum>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="csShaderSaveButton">
|
||||
<property name="toolTip">
|
||||
<string>Save Shader SPIR-V</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Save</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../../Resources/resources.qrc">
|
||||
<normaloff>:/save.png</normaloff>:/save.png</iconset>
|
||||
</property>
|
||||
<property name="toolButtonStyle">
|
||||
<enum>Qt::ToolButtonTextBesideIcon</enum>
|
||||
</property>
|
||||
<property name="autoRaise">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="csShaderSpacer">
|
||||
<spacer name="horizontalSpacer_4">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>0</height>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
|
||||
Reference in New Issue
Block a user