diff --git a/framework/decode/vulkan_replay_consumer_base.cpp b/framework/decode/vulkan_replay_consumer_base.cpp index 919a5f0d..ba2d569a 100644 --- a/framework/decode/vulkan_replay_consumer_base.cpp +++ b/framework/decode/vulkan_replay_consumer_base.cpp @@ -3524,6 +3524,10 @@ VkResult VulkanReplayConsumerBase::OverrideGetQueryPoolResults(PFN_vkGetQueryPoo return result; } +extern int drawcall_num; +extern VkQueryPool queryPool; +extern const uint32_t maxNumDrawCalls; + VkResult VulkanReplayConsumerBase::OverrideQueueSubmit(PFN_vkQueueSubmit func, uint64_t index, VkResult original_result, @@ -3701,6 +3705,23 @@ VkResult VulkanReplayConsumerBase::OverrideQueueSubmit(PFN_vkQueueSubmit fu decode::EndInjectedCommands(); } + std::vector timestamps(drawcall_num * 2); + GetDeviceTable(queue_info->handle)->GetQueryPoolResults(vkDevice_g, + queryPool, + 0, + drawcall_num * 2, + timestamps.size() * sizeof(uint64_t), + timestamps.data(), + sizeof(uint64_t), + VK_QUERY_RESULT_64_BIT | VK_QUERY_RESULT_WAIT_BIT); + + // Calculate and print elapsed times for each draw call + for (uint32_t i = 0; i < drawcall_num; i++) + { + uint64_t elapsedTime = timestamps[i * 2 + 1] - timestamps[i * 2]; // End - Start + GFXRECON_LOG_INFO("Elapsed time for drawcall %d is %" PRIu64 "", i, elapsedTime); + } + return result; } diff --git a/framework/generated/generated_vulkan_replay_consumer.cpp b/framework/generated/generated_vulkan_replay_consumer.cpp index eb6678fa..44710573 100644 --- a/framework/generated/generated_vulkan_replay_consumer.cpp +++ b/framework/generated/generated_vulkan_replay_consumer.cpp @@ -1046,6 +1046,10 @@ void VulkanReplayConsumer::Process_vkDestroyPipeline( RemoveHandle(pipeline, &CommonObjectInfoTable::RemoveVkPipelineInfo); } +int drawcall_num = 0; +const uint32_t maxNumDrawCalls = 5; // Adjust based on your needs +VkQueryPool queryPool; + void VulkanReplayConsumer::Process_vkCreatePipelineLayout( const ApiCallInfo& call_info, VkResult returnValue, @@ -1061,6 +1065,16 @@ void VulkanReplayConsumer::Process_vkCreatePipelineLayout( if (!pPipelineLayout->IsNull()) { pPipelineLayout->SetHandleLength(1); } VkPipelineLayout* out_pPipelineLayout = pPipelineLayout->GetHandlePointer(); + VkQueryPoolCreateInfo queryPoolInfo = {}; + queryPoolInfo.sType = VK_STRUCTURE_TYPE_QUERY_POOL_CREATE_INFO; + queryPoolInfo.queryType = VK_QUERY_TYPE_TIMESTAMP; + queryPoolInfo.queryCount = maxNumDrawCalls * 2; // Two timestamps per draw call (start and end) + VkResult result = GetDeviceTable(in_device)->CreateQueryPool(in_device, &queryPoolInfo, nullptr, &queryPool); + if (result != VK_SUCCESS) { + // Handle error + GFXRECON_LOG_INFO("Failed to create query pool"); + } + VkResult replay_result = GetDeviceTable(in_device)->CreatePipelineLayout(in_device, in_pCreateInfo, in_pAllocator, out_pPipelineLayout); CheckResult("vkCreatePipelineLayout", returnValue, replay_result, call_info); @@ -1420,7 +1434,8 @@ void VulkanReplayConsumer::Process_vkBeginCommandBuffer( StructPointerDecoder* pBeginInfo) { auto in_commandBuffer = GetObjectInfoTable().GetVkCommandBufferInfo(commandBuffer); - + drawcall_num = 0; + MapStructHandles(pBeginInfo->GetMetaStructPointer(), GetObjectInfoTable()); VkResult replay_result = OverrideBeginCommandBuffer(GetDeviceTable(in_commandBuffer->handle)->BeginCommandBuffer, call_info.index, returnValue, in_commandBuffer, pBeginInfo); @@ -1711,7 +1726,12 @@ void VulkanReplayConsumer::Process_vkCmdDrawIndexed( { VkCommandBuffer in_commandBuffer = MapHandle(commandBuffer, &CommonObjectInfoTable::GetVkCommandBufferInfo); + if(drawcall_num == 0) + GetDeviceTable(in_commandBuffer)->CmdResetQueryPool(in_commandBuffer, queryPool, 0, maxNumDrawCalls * 2); + + GetDeviceTable(in_commandBuffer)->CmdWriteTimestamp(in_commandBuffer, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, queryPool, drawcall_num * 2); // Start timestamp GetDeviceTable(in_commandBuffer)->CmdDrawIndexed(in_commandBuffer, indexCount, instanceCount, firstIndex, vertexOffset, firstInstance); + GetDeviceTable(in_commandBuffer)->CmdWriteTimestamp(in_commandBuffer, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, queryPool, drawcall_num * 2 + 1); // End timestamp if (options_.dumping_resources) {