Skip to content

Commit

Permalink
Rewrite how we handle DGC indirect pipelines.
Browse files Browse the repository at this point in the history
  • Loading branch information
Themaister committed Oct 30, 2024
1 parent 555acf8 commit 834d68f
Show file tree
Hide file tree
Showing 10 changed files with 286 additions and 111 deletions.
5 changes: 4 additions & 1 deletion tests/assets/shaders/dgc_compute.comp
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,12 @@ layout(set = 0, binding = 0) buffer SSBO
layout(push_constant) uniform Registers
{
uint index;
uint sequence;
};

layout(constant_id = 0) const uint C = 1;

void main()
{
atomicAdd(data[index], 1u);
atomicAdd(data[index], C + sequence);
}
58 changes: 48 additions & 10 deletions tests/dgc_test_compute.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,13 +42,14 @@ struct DGCComputeApplication : Granite::Application, Granite::EventHandler

struct DGC
{
uint32_t shader;
uint32_t push;
VkDispatchIndirectCommand dispatch;
};

void on_device_created(const DeviceCreatedEvent &e)
{
IndirectLayoutToken tokens[2] = {};
IndirectLayoutToken tokens[4] = {};

{
BufferCreateInfo buf_info = {};
Expand All @@ -67,20 +68,36 @@ struct DGCComputeApplication : Granite::Application, Granite::EventHandler
"assets://shaders/dgc_compute.comp")->
register_variant({})->get_program()->get_pipeline_layout();

tokens[0].type = IndirectLayoutToken::Type::PushConstant;
tokens[0].offset = offsetof(DGC, push);
tokens[0].data.push.range = 4;
tokens[0].data.push.offset = 0;
tokens[1].type = IndirectLayoutToken::Type::Dispatch;
tokens[1].offset = offsetof(DGC, dispatch);
tokens[0].type = IndirectLayoutToken::Type::Shader;
tokens[0].offset = offsetof(DGC, shader);
tokens[1].type = IndirectLayoutToken::Type::SequenceCount;
tokens[1].data.push.offset = 4;
tokens[1].data.push.range = 4;
tokens[2].type = IndirectLayoutToken::Type::PushConstant;
tokens[2].offset = offsetof(DGC, push);
tokens[2].data.push.range = 4;
tokens[2].data.push.offset = 0;
tokens[3].type = IndirectLayoutToken::Type::Dispatch;
tokens[3].offset = offsetof(DGC, dispatch);

if (e.get_device().get_device_features().device_generated_commands_features.deviceGeneratedCommands)
indirect_layout = e.get_device().request_indirect_layout(layout, tokens, 2, sizeof(DGC));
{
if (e.get_device().get_device_features().device_generated_commands_properties.
supportedIndirectCommandsShaderStagesPipelineBinding & VK_SHADER_STAGE_COMPUTE_BIT)
{
indirect_layout = e.get_device().request_indirect_layout(layout, tokens, 4, sizeof(DGC));
}
else
{
indirect_layout = e.get_device().request_indirect_layout(layout, tokens + 1, 3, sizeof(DGC));
}
}

std::vector<DGC> dgc_data(options.max_count);
for (unsigned i = 0; i < options.max_count; i++)
{
auto &dgc = dgc_data[i];
dgc.shader = i & 1;
dgc.push = i;
dgc.dispatch = options.dispatch;
}
Expand Down Expand Up @@ -137,6 +154,27 @@ struct DGCComputeApplication : Granite::Application, Granite::EventHandler

cmd->set_storage_buffer(0, 0, *ssbo);
cmd->set_program("assets://shaders/dgc_compute.comp");

VkIndirectExecutionSetEXT exec_sec = VK_NULL_HANDLE;

if ((device.get_device_features().device_generated_commands_properties.supportedIndirectCommandsShaderStagesPipelineBinding &
VK_SHADER_STAGE_COMPUTE_BIT) != 0)
{
auto *program =
device.get_shader_manager().register_compute(
"assets://shaders/dgc_compute.comp")->register_variant({})->get_program();

Vulkan::Program *programs[] = { program, program };
CommandBuffer::ExecutionSetSpecializationConstants spec_constants[2] = {};

spec_constants[0].mask = 0x01;
spec_constants[0].constants[0] = 3;
spec_constants[1].mask = 0x01;
spec_constants[1].constants[0] = 5;

exec_sec = cmd->bake_and_set_program_group(programs, 2, spec_constants, program->get_pipeline_layout());
}

auto start_ts = cmd->write_timestamp(VK_PIPELINE_STAGE_2_COMPUTE_SHADER_BIT);
for (uint32_t i = 0; i < options.iterations; i++)
{
Expand All @@ -146,9 +184,9 @@ struct DGCComputeApplication : Granite::Application, Granite::EventHandler

if (options.use_dgc)
{
cmd->execute_indirect_commands(indirect_layout, options.max_count, *dgc_buffer, 0,
cmd->execute_indirect_commands(exec_sec, indirect_layout, options.max_count, *dgc_buffer, 0,
options.use_indirect_count ? dgc_count_buffer.get() : nullptr, 0,
*preprocess_cmd);
*preprocess_cmd);
}
else if (options.use_indirect)
{
Expand Down
2 changes: 1 addition & 1 deletion tests/dgc_test_graphics.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,7 @@ struct DGCTriangleApplication : Granite::Application, Granite::EventHandler

if (options.use_dgc)
{
cmd->execute_indirect_commands(indirect_layout, options.max_count, *dgc_buffer, 0,
cmd->execute_indirect_commands(VK_NULL_HANDLE, indirect_layout, options.max_count, *dgc_buffer, 0,
options.use_indirect_count ? dgc_count_buffer.get() : nullptr, 0,
*preprocess_cmd);
}
Expand Down
Loading

0 comments on commit 834d68f

Please sign in to comment.