From 7c8a0c135c2d6e5d49be012c74dc77a3c375725f Mon Sep 17 00:00:00 2001 From: David Rosca Date: Tue, 2 Jul 2024 15:08:45 +0200 Subject: [PATCH] frontends/va: Support multi elements slice parameter buffers for H264/5 Same as AV1, this is also valid for H264 and HEVC. Reviewed-by: Ruijing Dong Reviewed-by: Boyuan Zhang Part-of: --- src/gallium/frontends/va/picture_h264.c | 56 ++++++++--------- src/gallium/frontends/va/picture_hevc.c | 82 ++++++++++++------------- 2 files changed, 68 insertions(+), 70 deletions(-) diff --git a/src/gallium/frontends/va/picture_h264.c b/src/gallium/frontends/va/picture_h264.c index f5e99fd795c..6ca6b7c2005 100644 --- a/src/gallium/frontends/va/picture_h264.c +++ b/src/gallium/frontends/va/picture_h264.c @@ -160,7 +160,6 @@ void vlVaHandlePictureParameterBufferH264(vlVaDriver *drv, vlVaContext *context, memset(context->desc.h264.slice_parameter.slice_data_flag, 0, sizeof(context->desc.h264.slice_parameter.slice_data_flag)); memset(context->desc.h264.slice_parameter.slice_data_offset, 0, sizeof(context->desc.h264.slice_parameter.slice_data_offset)); memset(context->desc.h264.slice_parameter.slice_data_size, 0, sizeof(context->desc.h264.slice_parameter.slice_data_size)); - } void vlVaHandleIQMatrixBufferH264(vlVaContext *context, vlVaBuffer *buf) @@ -176,37 +175,36 @@ void vlVaHandleSliceParameterBufferH264(vlVaContext *context, vlVaBuffer *buf) { VASliceParameterBufferH264 *h264 = buf->data; - assert(buf->size >= sizeof(VASliceParameterBufferH264) && buf->num_elements == 1); - context->desc.h264.num_ref_idx_l0_active_minus1 = - h264->num_ref_idx_l0_active_minus1; - context->desc.h264.num_ref_idx_l1_active_minus1 = - h264->num_ref_idx_l1_active_minus1; + context->desc.h264.num_ref_idx_l0_active_minus1 = h264->num_ref_idx_l0_active_minus1; + context->desc.h264.num_ref_idx_l1_active_minus1 = h264->num_ref_idx_l1_active_minus1; - ASSERTED const size_t max_pipe_h264_slices = ARRAY_SIZE(context->desc.h264.slice_parameter.slice_data_offset); - assert(context->desc.h264.slice_count < max_pipe_h264_slices); + for (uint32_t buffer_idx = 0; buffer_idx < buf->num_elements; buffer_idx++, h264++) { + uint32_t slice_index = context->desc.h264.slice_count + buffer_idx; - context->desc.h264.slice_parameter.slice_info_present = true; - context->desc.h264.slice_parameter.slice_type[context->desc.h264.slice_count] = h264->slice_type; - context->desc.h264.slice_parameter.slice_data_size[context->desc.h264.slice_count] = h264->slice_data_size; - context->desc.h264.slice_parameter.slice_data_offset[context->desc.h264.slice_count] = h264->slice_data_offset; + ASSERTED const size_t max_pipe_h264_slices = ARRAY_SIZE(context->desc.h264.slice_parameter.slice_data_offset); + assert(slice_index < max_pipe_h264_slices); - switch (h264->slice_data_flag) { - case VA_SLICE_DATA_FLAG_ALL: - context->desc.h264.slice_parameter.slice_data_flag[context->desc.h264.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_WHOLE; - break; - case VA_SLICE_DATA_FLAG_BEGIN: - context->desc.h264.slice_parameter.slice_data_flag[context->desc.h264.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_BEGIN; - break; - case VA_SLICE_DATA_FLAG_MIDDLE: - context->desc.h264.slice_parameter.slice_data_flag[context->desc.h264.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_MIDDLE; - break; - case VA_SLICE_DATA_FLAG_END: - context->desc.h264.slice_parameter.slice_data_flag[context->desc.h264.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_END; - break; - default: - break; + context->desc.h264.slice_parameter.slice_info_present = true; + context->desc.h264.slice_parameter.slice_type[slice_index] = h264->slice_type; + context->desc.h264.slice_parameter.slice_data_size[slice_index] = h264->slice_data_size; + context->desc.h264.slice_parameter.slice_data_offset[slice_index] = h264->slice_data_offset; + + switch (h264->slice_data_flag) { + case VA_SLICE_DATA_FLAG_ALL: + context->desc.h264.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_WHOLE; + break; + case VA_SLICE_DATA_FLAG_BEGIN: + context->desc.h264.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_BEGIN; + break; + case VA_SLICE_DATA_FLAG_MIDDLE: + context->desc.h264.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_MIDDLE; + break; + case VA_SLICE_DATA_FLAG_END: + context->desc.h264.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_END; + break; + default: + break; + } } - - /* assert(buf->num_elements == 1) above; */ context->desc.h264.slice_count += buf->num_elements; } diff --git a/src/gallium/frontends/va/picture_hevc.c b/src/gallium/frontends/va/picture_hevc.c index f773bd01adc..b4e79558f30 100644 --- a/src/gallium/frontends/va/picture_hevc.c +++ b/src/gallium/frontends/va/picture_hevc.c @@ -227,47 +227,47 @@ void vlVaHandleSliceParameterBufferHEVC(vlVaContext *context, vlVaBuffer *buf) { VASliceParameterBufferHEVC *h265 = buf->data; - assert(buf->size >= sizeof(VASliceParameterBufferHEVC) && buf->num_elements == 1); + for (uint32_t buffer_idx = 0; buffer_idx < buf->num_elements; buffer_idx++, h265++) { + uint32_t slice_index = context->desc.h265.slice_parameter.slice_count + buffer_idx; - switch(h265->LongSliceFlags.fields.slice_type) { - /* Depending on slice_type, only update relevant reference */ - case 0: /* HEVC_SLICE_B */ - for (int j = 0 ; j < 15 ; j++) - context->desc.h265.RefPicList[context->desc.h265.slice_parameter.slice_count][1][j] = h265->RefPicList[1][j]; - FALLTHROUGH; - case 1: /* HEVC_SLICE_P */ - for (int j = 0 ; j < 15 ; j++) - context->desc.h265.RefPicList[context->desc.h265.slice_parameter.slice_count][0][j] = h265->RefPicList[0][j]; - FALLTHROUGH; - default: - break; + ASSERTED const size_t max_pipe_hevc_slices = ARRAY_SIZE(context->desc.h265.slice_parameter.slice_data_offset); + assert(slice_index < max_pipe_hevc_slices); + + switch(h265->LongSliceFlags.fields.slice_type) { + /* Depending on slice_type, only update relevant reference */ + case 0: /* HEVC_SLICE_B */ + for (int j = 0 ; j < 15 ; j++) + context->desc.h265.RefPicList[slice_index][1][j] = h265->RefPicList[1][j]; + FALLTHROUGH; + case 1: /* HEVC_SLICE_P */ + for (int j = 0 ; j < 15 ; j++) + context->desc.h265.RefPicList[slice_index][0][j] = h265->RefPicList[0][j]; + FALLTHROUGH; + default: + break; + } + context->desc.h265.UseRefPicList = true; + + context->desc.h265.slice_parameter.slice_info_present = true; + context->desc.h265.slice_parameter.slice_data_size[slice_index] = h265->slice_data_size; + context->desc.h265.slice_parameter.slice_data_offset[slice_index] = h265->slice_data_offset; + + switch (h265->slice_data_flag) { + case VA_SLICE_DATA_FLAG_ALL: + context->desc.h265.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_WHOLE; + break; + case VA_SLICE_DATA_FLAG_BEGIN: + context->desc.h265.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_BEGIN; + break; + case VA_SLICE_DATA_FLAG_MIDDLE: + context->desc.h265.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_MIDDLE; + break; + case VA_SLICE_DATA_FLAG_END: + context->desc.h265.slice_parameter.slice_data_flag[slice_index] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_END; + break; + default: + break; + } } - context->desc.h265.UseRefPicList = true; - - ASSERTED const size_t max_pipe_hevc_slices = ARRAY_SIZE(context->desc.h265.slice_parameter.slice_data_offset); - assert(context->desc.h265.slice_parameter.slice_count < max_pipe_hevc_slices); - - context->desc.h265.slice_parameter.slice_info_present = true; - context->desc.h265.slice_parameter.slice_data_size[context->desc.h265.slice_parameter.slice_count] = h265->slice_data_size; - context->desc.h265.slice_parameter.slice_data_offset[context->desc.h265.slice_parameter.slice_count] = h265->slice_data_offset; - - switch (h265->slice_data_flag) { - case VA_SLICE_DATA_FLAG_ALL: - context->desc.h265.slice_parameter.slice_data_flag[context->desc.h265.slice_parameter.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_WHOLE; - break; - case VA_SLICE_DATA_FLAG_BEGIN: - context->desc.h265.slice_parameter.slice_data_flag[context->desc.h265.slice_parameter.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_BEGIN; - break; - case VA_SLICE_DATA_FLAG_MIDDLE: - context->desc.h265.slice_parameter.slice_data_flag[context->desc.h265.slice_parameter.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_MIDDLE; - break; - case VA_SLICE_DATA_FLAG_END: - context->desc.h265.slice_parameter.slice_data_flag[context->desc.h265.slice_parameter.slice_count] = PIPE_SLICE_BUFFER_PLACEMENT_TYPE_END; - break; - default: - break; - } - - /* assert(buf->num_elements == 1) above; */ - context->desc.h265.slice_parameter.slice_count++; + context->desc.h265.slice_parameter.slice_count += buf->num_elements; }