mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2025-12-24 21:50:12 +01:00
st/va: add motion adaptive deinterlacing v2
v2: minor cleanup Signed-off-by: Christian König <christian.koenig@amd.com>
This commit is contained in:
parent
ad20be1f30
commit
eaf7ec9cfc
4 changed files with 82 additions and 7 deletions
|
|
@ -31,6 +31,7 @@
|
|||
#include "util/u_memory.h"
|
||||
#include "util/u_handle_table.h"
|
||||
#include "util/u_video.h"
|
||||
#include "vl/vl_deint_filter.h"
|
||||
#include "vl/vl_winsys.h"
|
||||
|
||||
#include "va_private.h"
|
||||
|
|
@ -296,6 +297,10 @@ vlVaDestroyContext(VADriverContextP ctx, VAContextID context_id)
|
|||
}
|
||||
context->decoder->destroy(context->decoder);
|
||||
}
|
||||
if (context->deint) {
|
||||
vl_deint_filter_cleanup(context->deint);
|
||||
FREE(context->deint);
|
||||
}
|
||||
FREE(context);
|
||||
handle_table_remove(drv->htab, context_id);
|
||||
pipe_mutex_unlock(drv->mutex);
|
||||
|
|
|
|||
|
|
@ -29,6 +29,7 @@
|
|||
|
||||
#include "vl/vl_defines.h"
|
||||
#include "vl/vl_video_buffer.h"
|
||||
#include "vl/vl_deint_filter.h"
|
||||
|
||||
#include "va_private.h"
|
||||
|
||||
|
|
@ -174,6 +175,51 @@ static VAStatus vlVaPostProcBlit(vlVaDriver *drv, vlVaContext *context,
|
|||
return VA_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
static struct pipe_video_buffer *
|
||||
vlVaApplyDeint(vlVaDriver *drv, vlVaContext *context,
|
||||
VAProcPipelineParameterBuffer *param,
|
||||
struct pipe_video_buffer *current,
|
||||
unsigned field)
|
||||
{
|
||||
vlVaSurface *prevprev, *prev, *next;
|
||||
|
||||
if (param->num_forward_references < 1 ||
|
||||
param->num_backward_references < 2)
|
||||
return current;
|
||||
|
||||
prevprev = handle_table_get(drv->htab, param->backward_references[1]);
|
||||
prev = handle_table_get(drv->htab, param->backward_references[0]);
|
||||
next = handle_table_get(drv->htab, param->forward_references[0]);
|
||||
|
||||
if (!prevprev || !prev || !next)
|
||||
return current;
|
||||
|
||||
if (context->deint && (context->deint->video_width != current->width ||
|
||||
context->deint->video_height != current->height)) {
|
||||
vl_deint_filter_cleanup(context->deint);
|
||||
FREE(context->deint);
|
||||
context->deint = NULL;
|
||||
}
|
||||
|
||||
if (!context->deint) {
|
||||
context->deint = MALLOC(sizeof(struct vl_deint_filter));
|
||||
if (!vl_deint_filter_init(context->deint, drv->pipe, current->width,
|
||||
current->height, false, false)) {
|
||||
FREE(context->deint);
|
||||
context->deint = NULL;
|
||||
return current;
|
||||
}
|
||||
}
|
||||
|
||||
if (!vl_deint_filter_check_buffers(context->deint, prevprev->buffer,
|
||||
prev->buffer, current, next->buffer))
|
||||
return current;
|
||||
|
||||
vl_deint_filter_render(context->deint, prevprev->buffer, prev->buffer,
|
||||
current, next->buffer, field);
|
||||
return context->deint->video_buffer;
|
||||
}
|
||||
|
||||
VAStatus
|
||||
vlVaHandleVAProcPipelineParameterBufferType(vlVaDriver *drv, vlVaContext *context, vlVaBuffer *buf)
|
||||
{
|
||||
|
|
@ -181,6 +227,7 @@ vlVaHandleVAProcPipelineParameterBufferType(vlVaDriver *drv, vlVaContext *contex
|
|||
VARectangle def_src_region, def_dst_region;
|
||||
const VARectangle *src_region, *dst_region;
|
||||
VAProcPipelineParameterBuffer *param;
|
||||
struct pipe_video_buffer *src;
|
||||
vlVaSurface *src_surface;
|
||||
unsigned i;
|
||||
|
||||
|
|
@ -199,6 +246,8 @@ vlVaHandleVAProcPipelineParameterBufferType(vlVaDriver *drv, vlVaContext *contex
|
|||
if (!src_surface || !src_surface->buffer)
|
||||
return VA_STATUS_ERROR_INVALID_SURFACE;
|
||||
|
||||
src = src_surface->buffer;
|
||||
|
||||
for (i = 0; i < param->num_filters; i++) {
|
||||
vlVaBuffer *buf = handle_table_get(drv->htab, param->filters[i]);
|
||||
VAProcFilterParameterBufferBase *filter;
|
||||
|
|
@ -222,6 +271,11 @@ vlVaHandleVAProcPipelineParameterBufferType(vlVaDriver *drv, vlVaContext *contex
|
|||
deinterlace = VL_COMPOSITOR_WEAVE;
|
||||
break;
|
||||
|
||||
case VAProcDeinterlacingMotionAdaptive:
|
||||
src = vlVaApplyDeint(drv, context, param, src,
|
||||
deint->flags & VA_DEINTERLACING_BOTTOM_FIELD);
|
||||
break;
|
||||
|
||||
default:
|
||||
return VA_STATUS_ERROR_UNIMPLEMENTED;
|
||||
}
|
||||
|
|
@ -239,10 +293,8 @@ vlVaHandleVAProcPipelineParameterBufferType(vlVaDriver *drv, vlVaContext *contex
|
|||
|
||||
if (context->target->buffer_format != PIPE_FORMAT_NV12)
|
||||
return vlVaPostProcCompositor(drv, context, src_region, dst_region,
|
||||
src_surface->buffer, context->target,
|
||||
deinterlace);
|
||||
src, context->target, deinterlace);
|
||||
else
|
||||
return vlVaPostProcBlit(drv, context, src_region, dst_region,
|
||||
src_surface->buffer, context->target,
|
||||
deinterlace);
|
||||
src, context->target, deinterlace);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -691,13 +691,14 @@ vlVaQueryVideoProcFilterCaps(VADriverContextP ctx, VAContextID context,
|
|||
case VAProcFilterDeinterlacing: {
|
||||
VAProcFilterCapDeinterlacing *deint = filter_caps;
|
||||
|
||||
if (*num_filter_caps < 2) {
|
||||
*num_filter_caps = 2;
|
||||
if (*num_filter_caps < 3) {
|
||||
*num_filter_caps = 3;
|
||||
return VA_STATUS_ERROR_MAX_NUM_EXCEEDED;
|
||||
}
|
||||
|
||||
deint[i++].type = VAProcDeinterlacingBob;
|
||||
deint[i++].type = VAProcDeinterlacingWeave;
|
||||
deint[i++].type = VAProcDeinterlacingMotionAdaptive;
|
||||
break;
|
||||
}
|
||||
|
||||
|
|
@ -750,9 +751,24 @@ vlVaQueryVideoProcPipelineCaps(VADriverContextP ctx, VAContextID context,
|
|||
|
||||
for (i = 0; i < num_filters; i++) {
|
||||
vlVaBuffer *buf = handle_table_get(VL_VA_DRIVER(ctx)->htab, filters[i]);
|
||||
VAProcFilterParameterBufferBase *filter;
|
||||
|
||||
if (!buf || buf->type >= VABufferTypeMax)
|
||||
if (!buf || buf->type != VAProcFilterParameterBufferType)
|
||||
return VA_STATUS_ERROR_INVALID_BUFFER;
|
||||
|
||||
filter = buf->data;
|
||||
switch (filter->type) {
|
||||
case VAProcFilterDeinterlacing: {
|
||||
VAProcFilterParameterBufferDeinterlacing *deint = buf->data;
|
||||
if (deint->algorithm == VAProcDeinterlacingMotionAdaptive) {
|
||||
pipeline_cap->num_forward_references = 1;
|
||||
pipeline_cap->num_backward_references = 2;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
return VA_STATUS_ERROR_UNIMPLEMENTED;
|
||||
}
|
||||
}
|
||||
|
||||
return VA_STATUS_SUCCESS;
|
||||
|
|
|
|||
|
|
@ -236,6 +236,8 @@ typedef struct {
|
|||
VAPictureParameterBufferMPEG4 pps;
|
||||
uint8_t start_code[32];
|
||||
} mpeg4;
|
||||
|
||||
struct vl_deint_filter *deint;
|
||||
} vlVaContext;
|
||||
|
||||
typedef struct {
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue