[Mesa-dev] [PATCH 13/14] vl/dri3: implement functions for get and set timestamp
Axel Davy
axel.davy at ens.fr
Wed May 11 20:16:47 UTC 2016
Hi,
The present extension has something exactly to set the target ust for
the presentation: PresentOptionUST
Unfortunately, while it is in the spec it looks like the option is
totally ignored, and thus it will be totally buggy (you are supposed to
pass ust instead of msc...).
However PresentNotifyMSC should work well (assuming recent enough
Xserver) and give you the current screen ust (and msc).
I see you use it when last_ust hasn't been filled already. But why not
using it all the time ?
Do some apps assume it's the ust of the last presented buffer ? The doc
of the vdpau function doesn't
seem to tell you should assume that.
Could you add a comment to explain your next_msc calculation ?
Axel
On 11/05/2016 17:06, Leo Liu wrote:
> Signed-off-by: Leo Liu <leo.liu at amd.com>
> ---
> src/gallium/auxiliary/vl/vl_winsys_dri3.c | 59 +++++++++++++++++++++++++++----
> 1 file changed, 53 insertions(+), 6 deletions(-)
>
> diff --git a/src/gallium/auxiliary/vl/vl_winsys_dri3.c b/src/gallium/auxiliary/vl/vl_winsys_dri3.c
> index f917e4b..d8e8319 100644
> --- a/src/gallium/auxiliary/vl/vl_winsys_dri3.c
> +++ b/src/gallium/auxiliary/vl/vl_winsys_dri3.c
> @@ -79,6 +79,8 @@ struct vl_dri3_screen
> uint32_t send_msc_serial, recv_msc_serial;
> uint64_t send_sbc, recv_sbc;
> int64_t last_ust, ns_frame, last_msc, next_msc;
> +
> + bool flushed;
> };
>
> static void
> @@ -467,19 +469,30 @@ vl_dri3_flush_frontbuffer(struct pipe_screen *screen,
> if (!back)
> return;
>
> + if (scrn->flushed) {
> + while (scrn->special_event && scrn->recv_sbc < scrn->send_sbc)
> + if (!dri3_wait_present_events(scrn))
> + return;
> + }
> +
> xshmfence_reset(back->shm_fence);
> back->busy = true;
>
> xcb_present_pixmap(scrn->conn,
> scrn->drawable,
> back->pixmap,
> - 0, 0, 0, 0, 0,
> + (uint32_t)(++scrn->send_sbc),
> + 0, 0, 0, 0,
> None, None,
> back->sync_fence,
> - options, 0, 0, 0, 0, NULL);
> + options,
> + scrn->next_msc,
> + 0, 0, 0, NULL);
>
> xcb_flush(scrn->conn);
>
> + scrn->flushed = true;
> +
> return;
> }
>
> @@ -494,6 +507,13 @@ vl_dri3_screen_texture_from_drawable(struct vl_screen *vscreen, void *drawable)
> if (!dri3_set_drawable(scrn, (Drawable)drawable))
> return NULL;
>
> + if (scrn->flushed) {
> + while (scrn->special_event && scrn->recv_sbc < scrn->send_sbc)
> + if (!dri3_wait_present_events(scrn))
> + return NULL;
> + }
> + scrn->flushed = false;
> +
> buffer = (scrn->is_pixmap) ?
> dri3_get_front_buffer(scrn) :
> dri3_get_back_buffer(scrn);
> @@ -516,15 +536,42 @@ vl_dri3_screen_get_dirty_area(struct vl_screen *vscreen)
> static uint64_t
> vl_dri3_screen_get_timestamp(struct vl_screen *vscreen, void *drawable)
> {
> - /* TODO */
> - return 0;
> + struct vl_dri3_screen *scrn = (struct vl_dri3_screen *)vscreen;
> +
> + assert(scrn);
> +
> + if (!dri3_set_drawable(scrn, (Drawable)drawable))
> + return 0;
> +
> + if (!scrn->last_ust) {
> + xcb_present_notify_msc(scrn->conn,
> + scrn->drawable,
> + ++scrn->send_msc_serial,
> + 0, 0, 0);
> + xcb_flush(scrn->conn);
> +
> + while (scrn->special_event &&
> + scrn->send_msc_serial > scrn->recv_msc_serial) {
> + if (!dri3_wait_present_events(scrn))
> + return 0;
> + }
> + }
> +
> + return scrn->last_ust;
> }
>
> static void
> vl_dri3_screen_set_next_timestamp(struct vl_screen *vscreen, uint64_t stamp)
> {
> - /* TODO */
> - return;
> + struct vl_dri3_screen *scrn = (struct vl_dri3_screen *)vscreen;
> +
> + assert(scrn);
> +
> + if (stamp && scrn->last_ust && scrn->ns_frame && scrn->last_msc)
> + scrn->next_msc = ((int64_t)stamp - scrn->last_ust + scrn->ns_frame/2) /
> + scrn->ns_frame + scrn->last_msc;
> + else
> + scrn->next_msc = 0;
> }
>
> static void *
More information about the mesa-dev
mailing list