mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-27 04:01:08 +00:00
va: filter, vpp: add and use GstVaSample struct
This new struct describes the input and output GstBuffers to post-process, including VA flags. It also contains the VASurfaceID and VARectangle, but those are private, completed inside GstVaFilter. It is used for pass arguments to gst_va_filter_convert_surface() function. Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-bad/-/merge_requests/2058>
This commit is contained in:
parent
b2a4e066ab
commit
c770469a8a
3 changed files with 60 additions and 26 deletions
|
@ -28,6 +28,7 @@
|
|||
|
||||
#include <va/va_drmcommon.h>
|
||||
|
||||
#include "gstvaallocator.h"
|
||||
#include "gstvacaps.h"
|
||||
#include "gstvavideoformat.h"
|
||||
|
||||
|
@ -1234,8 +1235,25 @@ gst_va_filter_drop_filter_buffers (GstVaFilter * self)
|
|||
}
|
||||
|
||||
static gboolean
|
||||
_create_pipeline_buffer (GstVaFilter * self, VASurfaceID surface,
|
||||
VARectangle * src_rect, VARectangle * dst_rect, VABufferID * buffer)
|
||||
_fill_va_sample (GstVaFilter * self, GstVaSample * sample,
|
||||
GstPadDirection direction)
|
||||
{
|
||||
sample->surface = gst_va_buffer_get_surface (sample->buffer);
|
||||
if (sample->surface == VA_INVALID_ID)
|
||||
return FALSE;
|
||||
|
||||
/* TODO: handle GstVideoCropMeta */
|
||||
GST_OBJECT_LOCK (self);
|
||||
sample->rect = (direction == GST_PAD_SRC) ?
|
||||
self->output_region : self->input_region;
|
||||
GST_OBJECT_UNLOCK (self);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
_create_pipeline_buffer (GstVaFilter * self, GstVaSample * src,
|
||||
GstVaSample * dst, VABufferID * buffer)
|
||||
{
|
||||
VADisplay dpy;
|
||||
VAStatus status;
|
||||
|
@ -1252,16 +1270,18 @@ _create_pipeline_buffer (GstVaFilter * self, VASurfaceID surface,
|
|||
}
|
||||
|
||||
params = (VAProcPipelineParameterBuffer) {
|
||||
.surface = surface,
|
||||
.surface_region = src_rect,
|
||||
.surface = src->surface,
|
||||
.surface_region = &src->rect,
|
||||
.surface_color_standard = self->input_color_standard,
|
||||
.output_region = dst_rect,
|
||||
.output_region = &dst->rect,
|
||||
.output_background_color = 0xff000000, /* ARGB black */
|
||||
.output_color_standard = self->output_color_standard,
|
||||
.filters = filters,
|
||||
.num_filters = num_filters,
|
||||
.rotation_state = self->rotation,
|
||||
.mirror_state = self->mirror,
|
||||
.input_surface_flag = src->flags,
|
||||
.output_surface_flag = dst->flags,
|
||||
.input_color_properties = self->input_color_properties,
|
||||
.output_color_properties = self->output_color_properties,
|
||||
};
|
||||
|
@ -1286,31 +1306,28 @@ _create_pipeline_buffer (GstVaFilter * self, VASurfaceID surface,
|
|||
}
|
||||
|
||||
gboolean
|
||||
gst_va_filter_convert_surface (GstVaFilter * self, VASurfaceID in_surface,
|
||||
VASurfaceID out_surface)
|
||||
gst_va_filter_convert_surface (GstVaFilter * self, GstVaSample * src,
|
||||
GstVaSample * dst)
|
||||
{
|
||||
VABufferID buffer;
|
||||
VABufferID buffer, *filters = NULL;
|
||||
VADisplay dpy;
|
||||
VAProcPipelineCaps pipeline_caps = { 0, };
|
||||
VARectangle src_rect;
|
||||
VARectangle dst_rect;
|
||||
VAStatus status;
|
||||
VABufferID *filters = NULL;
|
||||
guint32 num_filters = 0;
|
||||
gboolean ret = FALSE;
|
||||
guint32 num_filters = 0;
|
||||
|
||||
g_return_val_if_fail (GST_IS_VA_FILTER (self), FALSE);
|
||||
g_return_val_if_fail (in_surface != VA_INVALID_ID
|
||||
&& out_surface != VA_INVALID_ID, FALSE);
|
||||
g_return_val_if_fail (src && GST_IS_BUFFER (src->buffer), FALSE);
|
||||
g_return_val_if_fail (dst && GST_IS_BUFFER (dst->buffer), FALSE);
|
||||
|
||||
if (!gst_va_filter_is_open (self))
|
||||
return FALSE;
|
||||
|
||||
GST_TRACE_OBJECT (self, "Processing %#x", in_surface);
|
||||
if (!(_fill_va_sample (self, src, GST_PAD_SINK)
|
||||
&& _fill_va_sample (self, dst, GST_PAD_SRC)))
|
||||
return FALSE;
|
||||
|
||||
GST_OBJECT_LOCK (self);
|
||||
src_rect = self->input_region;
|
||||
dst_rect = self->output_region;
|
||||
|
||||
if (self->filters) {
|
||||
g_array_ref (self->filters);
|
||||
|
@ -1331,12 +1348,11 @@ gst_va_filter_convert_surface (GstVaFilter * self, VASurfaceID in_surface,
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
if (!_create_pipeline_buffer (self, in_surface, &src_rect, &dst_rect,
|
||||
&buffer))
|
||||
if (!_create_pipeline_buffer (self, src, dst, &buffer))
|
||||
return FALSE;
|
||||
|
||||
gst_va_display_lock (self->display);
|
||||
status = vaBeginPicture (dpy, self->context, out_surface);
|
||||
status = vaBeginPicture (dpy, self->context, dst->surface);
|
||||
gst_va_display_unlock (self->display);
|
||||
if (status != VA_STATUS_SUCCESS) {
|
||||
GST_ERROR_OBJECT (self, "vaBeginPicture: %s", vaErrorStr (status));
|
||||
|
|
|
@ -46,6 +46,17 @@ enum {
|
|||
GST_VA_FILTER_PROP_LAST
|
||||
};
|
||||
|
||||
typedef struct _GstVaSample GstVaSample;
|
||||
struct _GstVaSample
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
guint32 flags;
|
||||
|
||||
/*< private >*/
|
||||
VASurfaceID surface;
|
||||
VARectangle rect;
|
||||
};
|
||||
|
||||
GstVaFilter * gst_va_filter_new (GstVaDisplay * display);
|
||||
gboolean gst_va_filter_open (GstVaFilter * self);
|
||||
gboolean gst_va_filter_close (GstVaFilter * self);
|
||||
|
@ -72,7 +83,7 @@ gboolean gst_va_filter_add_filter_buffer (GstVaFilter * self,
|
|||
guint num);
|
||||
gboolean gst_va_filter_drop_filter_buffers (GstVaFilter * self);
|
||||
gboolean gst_va_filter_convert_surface (GstVaFilter * self,
|
||||
VASurfaceID in_surface,
|
||||
VASurfaceID out_surface);
|
||||
GstVaSample * src,
|
||||
GstVaSample * dest);
|
||||
|
||||
G_END_DECLS
|
||||
|
|
|
@ -1235,7 +1235,7 @@ gst_va_vpp_transform (GstBaseTransform * trans, GstBuffer * inbuf,
|
|||
GstVaVpp *self = GST_VA_VPP (trans);
|
||||
GstBuffer *buf = NULL;
|
||||
GstFlowReturn res = GST_FLOW_OK;
|
||||
VASurfaceID in_surface, out_surface;
|
||||
GstVaSample src, dst;
|
||||
|
||||
if (G_UNLIKELY (!self->negotiated))
|
||||
goto unknown_format;
|
||||
|
@ -1244,10 +1244,17 @@ gst_va_vpp_transform (GstBaseTransform * trans, GstBuffer * inbuf,
|
|||
if (res != GST_FLOW_OK)
|
||||
return res;
|
||||
|
||||
in_surface = gst_va_buffer_get_surface (buf);
|
||||
out_surface = gst_va_buffer_get_surface (outbuf);
|
||||
/* *INDENT-OFF* */
|
||||
src = (GstVaSample) {
|
||||
.buffer = buf,
|
||||
};
|
||||
|
||||
if (!gst_va_filter_convert_surface (self->filter, in_surface, out_surface)) {
|
||||
dst = (GstVaSample) {
|
||||
.buffer = outbuf,
|
||||
};
|
||||
/* *INDENT-ON* */
|
||||
|
||||
if (!gst_va_filter_convert_surface (self->filter, &src, &dst)) {
|
||||
gst_buffer_set_flags (outbuf, GST_BUFFER_FLAG_CORRUPTED);
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue