radeonsi/vcn: Implement destroy_fence vfunc
authorDavid Rosca <nowrep@gmail.com>
Tue, 19 Sep 2023 09:00:12 +0000 (11:00 +0200)
committerMarge Bot <emma+marge@anholt.net>
Thu, 21 Sep 2023 13:30:28 +0000 (13:30 +0000)
Now that fences are correctly cleaned up in frontend, we can store
the fence reference in picture->fence again.

The encoder also needs to implement this vfunc because if a surface
from decoder is used directly as encode input it's now up to encoder
to destroy the fence.

Closes: https://gitlab.freedesktop.org/mesa/mesa/-/issues/9834

Reviewed-by: Leo Liu <leo.liu@amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/25296>

src/gallium/drivers/radeonsi/radeon_vcn_dec.c
src/gallium/drivers/radeonsi/radeon_vcn_enc.c

index 5612ccc..112471a 100644 (file)
@@ -2924,9 +2924,9 @@ static void radeon_dec_end_frame(struct pipe_video_codec *decoder, struct pipe_v
       return;
 
    dec->send_cmd(dec, target, picture);
-   flush(dec, PIPE_FLUSH_ASYNC, &dec->prev_fence);
+   flush(dec, PIPE_FLUSH_ASYNC, picture->fence);
    if (picture->fence)
-      *picture->fence = dec->prev_fence;
+      dec->ws->fence_reference(&dec->prev_fence, *picture->fence);
    next_buffer(dec);
 }
 
@@ -2970,12 +2970,18 @@ static int radeon_dec_get_decoder_fence(struct pipe_video_codec *decoder,
                                         uint64_t timeout) {
 
    struct radeon_decoder *dec = (struct radeon_decoder *)decoder;
-   /* Only last fence is valid */
-   if (fence != dec->prev_fence)
-      return true;
+
    return dec->ws->fence_wait(dec->ws, fence, timeout);
 }
 
+static void radeon_dec_destroy_fence(struct pipe_video_codec *decoder,
+                                     struct pipe_fence_handle *fence)
+{
+   struct radeon_decoder *dec = (struct radeon_decoder *)decoder;
+
+   dec->ws->fence_reference(&fence, NULL);
+}
+
 /**
  * update render list when target buffer got updated, use the existing
  * index and update the new buffer to associate with it.
@@ -3064,6 +3070,7 @@ struct pipe_video_codec *radeon_create_decoder(struct pipe_context *context,
    dec->base.end_frame = radeon_dec_end_frame;
    dec->base.flush = radeon_dec_flush;
    dec->base.get_decoder_fence = radeon_dec_get_decoder_fence;
+   dec->base.destroy_fence = radeon_dec_destroy_fence;
    dec->base.update_decoder_target =  radeon_dec_update_render_list;
 
    dec->stream_type = stream_type;
index 4c06adf..2510a33 100644 (file)
@@ -991,6 +991,14 @@ static void radeon_enc_get_feedback(struct pipe_video_codec *encoder, void *feed
    FREE(fb);
 }
 
+static void radeon_enc_destroy_fence(struct pipe_video_codec *encoder,
+                                     struct pipe_fence_handle *fence)
+{
+   struct radeon_encoder *enc = (struct radeon_encoder *)encoder;
+
+   enc->ws->fence_reference(&fence, NULL);
+}
+
 struct pipe_video_codec *radeon_create_encoder(struct pipe_context *context,
                                                const struct pipe_video_codec *templ,
                                                struct radeon_winsys *ws,
@@ -1020,6 +1028,7 @@ struct pipe_video_codec *radeon_create_encoder(struct pipe_context *context,
    enc->base.end_frame = radeon_enc_end_frame;
    enc->base.flush = radeon_enc_flush;
    enc->base.get_feedback = radeon_enc_get_feedback;
+   enc->base.destroy_fence = radeon_enc_destroy_fence;
    enc->get_buffer = get_buffer;
    enc->bits_in_shifter = 0;
    enc->screen = context->screen;