diff --git a/include/QF/Vulkan/render.h b/include/QF/Vulkan/render.h index 51a51f33a..83e247534 100644 --- a/include/QF/Vulkan/render.h +++ b/include/QF/Vulkan/render.h @@ -305,6 +305,12 @@ typedef struct qfv_samplerinfo_s { } qfv_samplerinfo_t; #ifndef __QFCC__ +typedef struct qfv_time_s { + int64_t cur_time; + int64_t min_time; + int64_t max_time; +} qfv_time_t; + typedef struct qfv_label_s { vec4f_t color; const char *name; @@ -386,6 +392,7 @@ typedef struct qfv_step_s { qfv_render_t *render; qfv_compute_t *compute; qfv_process_t *process; + qfv_time_t time; } qfv_step_t; typedef struct qfv_job_s { @@ -402,6 +409,7 @@ typedef struct qfv_job_s { qfv_cmdbufferset_t commands; uint32_t num_dsmanagers; struct qfv_dsmanager_s **dsmanager; + qfv_time_t time; } qfv_job_t; typedef struct qfv_renderframe_s { diff --git a/libs/console/cl_debug.c b/libs/console/cl_debug.c index ba2c364b8..32bdf0e38 100644 --- a/libs/console/cl_debug.c +++ b/libs/console/cl_debug.c @@ -549,6 +549,27 @@ system_info (void) } } #endif + static int64_t prev_time; + static int64_t min_delta = INT64_MAX; + static int64_t max_delta = -INT64_MAX; + int64_t cur_time = Sys_LongTime (); + int64_t delta = cur_time - prev_time; + prev_time = cur_time; + min_delta = min (min_delta, delta); + max_delta = max (max_delta, delta); + UI_Horizontal { + UI_Label ("frame: "); + UI_FlexibleSpace (); + UI_Labelf ("%'7zd\u03bcs##frame.time", min_delta); + UI_Labelf ("%'7zd\u03bcs##frame.time", delta); + UI_Labelf ("%'7zd\u03bcs##frame.time", max_delta); + } + UI_Horizontal { + UI_FlexibleSpace (); + if (UI_Button ("Reset##timings")) { + max_delta = -INT64_MAX; + } + } UI_Horizontal { UI_Labelf ("mem: %'zd", Sys_CurrentRSS ()); UI_FlexibleSpace (); diff --git a/libs/video/renderer/vulkan/render.c b/libs/video/renderer/vulkan/render.c index f25624420..e35b38e60 100644 --- a/libs/video/renderer/vulkan/render.c +++ b/libs/video/renderer/vulkan/render.c @@ -40,6 +40,7 @@ #include "QF/cmem.h" #include "QF/hash.h" +#include "QF/mathlib.h" #include "QF/va.h" #include "QF/Vulkan/command.h" #include "QF/Vulkan/debug.h" @@ -70,6 +71,15 @@ QFV_AppendCmdBuffer (vulkan_ctx_t *ctx, VkCommandBuffer cmd) DARRAY_APPEND (&job->commands, cmd); } +static void +update_time (qfv_time_t *time, int64_t start, int64_t end) +{ + int64_t delta = end - start; + time->cur_time = delta; + time->min_time = min (time->min_time, delta); + time->max_time = max (time->max_time, delta); +} + static void run_tasks (uint32_t task_count, qfv_taskinfo_t *tasks, qfv_taskctx_t *ctx) { @@ -223,8 +233,10 @@ QFV_RunRenderJob (vulkan_ctx_t *ctx) { auto rctx = ctx->render_context; auto job = rctx->job; + int64_t start = Sys_LongTime (); for (uint32_t i = 0; i < job->num_steps; i++) { + int64_t step_start = Sys_LongTime (); __auto_type step = &job->steps[i]; if (step->render) { run_renderpass (step->render->active, ctx); @@ -235,6 +247,7 @@ QFV_RunRenderJob (vulkan_ctx_t *ctx) if (step->process) { run_process (step->process, ctx); } + update_time (&step->time, step_start, Sys_LongTime ()); } auto device = ctx->device; @@ -263,6 +276,7 @@ QFV_RunRenderJob (vulkan_ctx_t *ctx) if (++ctx->curFrame >= rctx->frames.size) { ctx->curFrame = 0; } + update_time (&job->time, start, Sys_LongTime ()); } static qfv_imageviewinfo_t * __attribute__((pure)) diff --git a/libs/video/renderer/vulkan/render_ui.c b/libs/video/renderer/vulkan/render_ui.c index 76750068c..1cc1518a3 100644 --- a/libs/video/renderer/vulkan/render_ui.c +++ b/libs/video/renderer/vulkan/render_ui.c @@ -36,6 +36,21 @@ #define IMUI_context imui_ctx +static void +reset_time (qfv_time_t *time) +{ + time->min_time = INT64_MAX; + time->max_time = -INT64_MAX; +} + +static void +show_time (qfv_time_t *time, imui_ctx_t *imui_ctx, const char *suffix) +{ + UI_Labelf ("%'7zd\u03bcs%s", time->min_time, suffix); + UI_Labelf ("%'7zd\u03bcs%s", time->cur_time, suffix); + UI_Labelf ("%'7zd\u03bcs%s", time->max_time, suffix); +} + static void job_window (vulkan_ctx_t *ctx, imui_ctx_t *imui_ctx) { @@ -58,6 +73,23 @@ job_window (vulkan_ctx_t *ctx, imui_ctx_t *imui_ctx) UI_Horizontal { UI_Labelf ("%s##%p.job.step.%d", step->label.name, rctx, i); UI_FlexibleSpace (); + show_time (&step->time, imui_ctx, + va (ctx->va_ctx, "##%p.job.step.%d.time", rctx, i)); + } + } + UI_Horizontal { + UI_FlexibleSpace (); + show_time (&job->time, imui_ctx, + va (ctx->va_ctx, "##%p.job.time", rctx)); + } + UI_Horizontal { + UI_FlexibleSpace (); + if (UI_Button ("Reset##job.timings")) { + for (uint32_t i = 0; i < job->num_steps; i++) { + auto step = &job->steps[i]; + reset_time (&step->time); + } + reset_time (&job->time); } } }