From aaae07f9ddbf073080fa1eb3f75d728530a1bb5e Mon Sep 17 00:00:00 2001 From: Robert Mader Date: Sat, 9 Mar 2024 11:37:18 +0100 Subject: [PATCH] onscreen/native: Mark GPU rendering duration as valid if supported Since commit e30eb788916d `ClutterFrameClock` assumes that a valid CPU time implies timestamp query support, which is also checked in `cogl_onscreen_egl_swap_buffers_with_damage()`. Unconditionally setting the CPU time on direct scanout meant that the compositing path would be stuck on the last (direct scanout optimized) result on GL implementations without timestamp query support since. be0aa2976e (clutter/frame-clock: Avoid rapidly toggling dynamic max render time) Fix that by explicitly marking the gpu rendering duration as valid when querying the GPU timestamps is supported and check for it ClutterFrameClock. Fixes: 56580ea7c9 ("backends/native: Assume zero rendering time for direct scanout buffers") Part-of: --- clutter/clutter/clutter-frame-clock.c | 3 ++- clutter/clutter/clutter-stage.h | 1 + cogl/cogl/cogl-frame-info-private.h | 1 + cogl/cogl/cogl-frame-info.c | 6 ++++++ cogl/cogl/cogl-frame-info.h | 3 +++ cogl/cogl/winsys/cogl-onscreen-egl.c | 2 ++ src/backends/meta-stage-view.c | 2 ++ src/backends/native/meta-onscreen-native.c | 3 +++ 8 files changed, 20 insertions(+), 1 deletion(-) diff --git a/clutter/clutter/clutter-frame-clock.c b/clutter/clutter/clutter-frame-clock.c index 4eb20d076..93e4c9329 100644 --- a/clutter/clutter/clutter-frame-clock.c +++ b/clutter/clutter/clutter-frame-clock.c @@ -361,7 +361,8 @@ clutter_frame_clock_notify_presented (ClutterFrameClock *frame_clock, frame_clock->got_measurements_last_frame = FALSE; - if (frame_info->cpu_time_before_buffer_swap_us != 0) + if (frame_info->cpu_time_before_buffer_swap_us != 0 && + frame_info->has_valid_gpu_rendering_duration) { int64_t dispatch_to_swap_us, swap_to_rendering_done_us, swap_to_flip_us; diff --git a/clutter/clutter/clutter-stage.h b/clutter/clutter/clutter-stage.h index 9c1c0ae18..b9f21ca39 100644 --- a/clutter/clutter/clutter-stage.h +++ b/clutter/clutter/clutter-stage.h @@ -127,6 +127,7 @@ struct _ClutterFrameInfo unsigned int sequence; + gboolean has_valid_gpu_rendering_duration; int64_t gpu_rendering_duration_ns; int64_t cpu_time_before_buffer_swap_us; }; diff --git a/cogl/cogl/cogl-frame-info-private.h b/cogl/cogl/cogl-frame-info-private.h index 8871377ab..89a1eb3a9 100644 --- a/cogl/cogl/cogl-frame-info-private.h +++ b/cogl/cogl/cogl-frame-info-private.h @@ -74,6 +74,7 @@ struct _CoglFrameInfo unsigned int sequence; CoglTimestampQuery *timestamp_query; + gboolean has_valid_gpu_rendering_duration; int64_t gpu_time_before_buffer_swap_ns; int64_t cpu_time_before_buffer_swap_us; diff --git a/cogl/cogl/cogl-frame-info.c b/cogl/cogl/cogl-frame-info.c index aca208407..40e529176 100644 --- a/cogl/cogl/cogl-frame-info.c +++ b/cogl/cogl/cogl-frame-info.c @@ -132,6 +132,12 @@ cogl_frame_info_get_sequence (CoglFrameInfo *info) return info->sequence; } +gboolean +cogl_frame_info_has_valid_gpu_rendering_duration (CoglFrameInfo *info) +{ + return info->has_valid_gpu_rendering_duration; +} + int64_t cogl_frame_info_get_rendering_duration_ns (CoglFrameInfo *info) { diff --git a/cogl/cogl/cogl-frame-info.h b/cogl/cogl/cogl-frame-info.h index e14e2e5ac..2a24cfab0 100644 --- a/cogl/cogl/cogl-frame-info.h +++ b/cogl/cogl/cogl-frame-info.h @@ -127,6 +127,9 @@ gboolean cogl_frame_info_is_vsync (CoglFrameInfo *info); COGL_EXPORT unsigned int cogl_frame_info_get_sequence (CoglFrameInfo *info); +COGL_EXPORT +gboolean cogl_frame_info_has_valid_gpu_rendering_duration (CoglFrameInfo *info); + COGL_EXPORT int64_t cogl_frame_info_get_rendering_duration_ns (CoglFrameInfo *info); diff --git a/cogl/cogl/winsys/cogl-onscreen-egl.c b/cogl/cogl/winsys/cogl-onscreen-egl.c index 94c52a3ea..6c5bf2654 100644 --- a/cogl/cogl/winsys/cogl-onscreen-egl.c +++ b/cogl/cogl/winsys/cogl-onscreen-egl.c @@ -318,6 +318,8 @@ cogl_onscreen_egl_swap_buffers_with_damage (CoglOnscreen *onscreen, /* Set up a timestamp query for when all rendering will be finished. */ info->timestamp_query = cogl_framebuffer_create_timestamp_query (COGL_FRAMEBUFFER (onscreen)); + + info->has_valid_gpu_rendering_duration = TRUE; } if (n_rectangles && priv->pf_eglSwapBuffersWithDamage) diff --git a/src/backends/meta-stage-view.c b/src/backends/meta-stage-view.c index 45d696931..0808680c1 100644 --- a/src/backends/meta-stage-view.c +++ b/src/backends/meta-stage-view.c @@ -77,6 +77,8 @@ frame_cb (CoglOnscreen *onscreen, cogl_frame_info_get_presentation_time_us (frame_info), .flags = flags, .sequence = cogl_frame_info_get_sequence (frame_info), + .has_valid_gpu_rendering_duration = + cogl_frame_info_has_valid_gpu_rendering_duration (frame_info), .gpu_rendering_duration_ns = cogl_frame_info_get_rendering_duration_ns (frame_info), .cpu_time_before_buffer_swap_us = diff --git a/src/backends/native/meta-onscreen-native.c b/src/backends/native/meta-onscreen-native.c index 5caf702eb..bf3924842 100644 --- a/src/backends/native/meta-onscreen-native.c +++ b/src/backends/native/meta-onscreen-native.c @@ -1631,6 +1631,9 @@ meta_onscreen_native_direct_scanout (CoglOnscreen *onscreen, frame_info->cpu_time_before_buffer_swap_us = g_get_monotonic_time (); + if (cogl_has_feature (cogl_context, COGL_FEATURE_ID_TIMESTAMP_QUERY)) + frame_info->has_valid_gpu_rendering_duration = TRUE; + kms_crtc = meta_crtc_kms_get_kms_crtc (META_CRTC_KMS (onscreen_native->crtc)); kms_device = meta_kms_crtc_get_device (kms_crtc); kms_update = meta_frame_native_ensure_kms_update (frame_native, kms_device);