...
 
Commits (35)
This diff is collapsed.
This diff is collapsed.
# gstreamer-vaapi package version number
m4_define([gst_vaapi_major_version], [1])
m4_define([gst_vaapi_minor_version], [8])
m4_define([gst_vaapi_micro_version], [0])
m4_define([gst_vaapi_micro_version], [3])
m4_define([gst_vaapi_nano_version], [0])
m4_define([gst_vaapi_version],
[gst_vaapi_major_version.gst_vaapi_minor_version.gst_vaapi_micro_version])
......@@ -16,9 +16,9 @@ dnl - interfaces added/removed/changed -> increment CURRENT, REVISION = 0
dnl - interfaces added -> increment AGE
dnl - interfaces removed -> AGE = 0
# gstreamer-vaapi library (libtool) version number
m4_define([gst_vaapi_lt_current], [800])
m4_define([gst_vaapi_lt_current], [803])
m4_define([gst_vaapi_lt_revision], [0])
m4_define([gst_vaapi_lt_age], [800])
m4_define([gst_vaapi_lt_age], [803])
# glib version number
m4_define([glib_version], [2.32])
......@@ -244,8 +244,8 @@ AG_GST_CHECK_MODULES([GST_PBUTILS],
[gstreamer-pbutils-$GST_API_VERSION], [$GST_PBREQ], [yes])
dnl bitstream parsers (gstreamer-codecparsers)
AG_GST_CHECK_MODULES([GST_CODEC_PARSERS],
[gstreamer-codecparsers-$GST_API_VERSION], [$GST_PBADREQ], [yes])
AG_GST_PKG_CHECK_MODULES([GST_CODEC_PARSERS],
[gstreamer-codecparsers-$GST_API_VERSION >= 1.8.0 gstreamer-codecparsers-$GST_API_VERSION <= 1.8.99], [yes])
AS_IF([test "x$enable_glx" = "xyes" -o "x$enable_egl" = "xyes"],
[enable_opengl="yes"], [enable_opengl="no"])
......@@ -280,7 +280,7 @@ GstGLContext gl_context;
CPPFLAGS="$saved_CPPFLAGS"
LIBS="$saved_LIBS"
])
], [])
], [:])
fi
AS_IF([test "x$ac_cv_have_gst_gl_helpers" = "xno"], [HAVE_GSTGL=0])
AM_CONDITIONAL([USE_GST_GL_HELPERS], [test $HAVE_GSTGL -eq 1])
......@@ -306,7 +306,7 @@ if test "x$enable_drm" = "xyes"; then
CPPFLAGS="$CPPFLAGS $DRM_CFLAGS"
AC_CHECK_HEADERS([drm_fourcc.h], [], [USE_DRM=0])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
fi
dnl Check for X11
......@@ -319,7 +319,7 @@ if test "x$enable_x11" = "xyes"; then
CPPFLAGS="$CPPFLAGS $X11_CFLAGS"
AC_CHECK_HEADERS([X11/Xlib.h X11/Xutil.h X11/Xatom.h], [], [USE_X11=0])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
fi
HAVE_XKBLIB=0
......@@ -338,7 +338,7 @@ if test $USE_X11 -eq 1; then
CPPFLAGS="$CPPFLAGS $XRANDR_CFLAGS"
AC_CHECK_HEADERS([X11/extensions/Xrandr.h], [], [HAVE_XRANDR=0])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
dnl Check for XRender
PKG_CHECK_MODULES([XRENDER], [xrender],
......@@ -348,7 +348,7 @@ if test $USE_X11 -eq 1; then
CPPFLAGS="$CPPFLAGS $XRENDER_CFLAGS"
AC_CHECK_HEADERS([X11/extensions/Xrender.h], [], [HAVE_XRENDER=0])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
fi
AC_DEFINE_UNQUOTED([HAVE_XKBLIB], [$HAVE_XKBLIB],
......@@ -463,7 +463,7 @@ if test "x$enable_egl" = "xyes" -a $GLES_VERSION_MASK -ne 0; then
dnl Check for GMODULE
PKG_CHECK_MODULES([GMODULE], [gmodule-2.0 >= $GLIB_REQ])
], [])
], [:])
fi
dnl Check for Wayland
......@@ -476,7 +476,7 @@ if test "x$enable_wayland" = "xyes"; then
CPPFLAGS="$CPPFLAGS $WAYLAND_CFLAGS"
AC_CHECK_HEADERS([wayland-client.h], [], [USE_WAYLAND=0])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
fi
dnl ---------------------------------------------------------------------------
......@@ -717,7 +717,7 @@ if test "x$enable_encoders" = "xyes"; then
#include <va/va.h>
])
CPPFLAGS="$saved_CPPFLAGS"
], [])
], [:])
fi
USE_JPEG_ENCODER=0
......
......@@ -453,6 +453,7 @@ libgstvaapi_egl_la_CFLAGS = \
$(GST_BASE_CFLAGS) \
$(GST_VIDEO_CFLAGS) \
$(LIBVA_CFLAGS) \
$(LIBVA_WAYLAND_CFLAGS) \
$(EGL_CFLAGS) \
$(NULL)
......
......@@ -54,6 +54,7 @@ coded_buffer_pool_init (GstVaapiCodedBufferPool * pool,
static void
coded_buffer_pool_finalize (GstVaapiCodedBufferPool * pool)
{
gst_vaapi_video_pool_finalize (GST_VAAPI_VIDEO_POOL (pool));
gst_vaapi_object_replace (&pool->context, NULL);
}
......
......@@ -4233,7 +4233,7 @@ gst_vaapi_decoder_h264_decode_codec_data (GstVaapiDecoder * base_decoder,
unit.parsed_info = NULL;
if (buf_size < 8)
if (buf_size < 7)
return GST_VAAPI_DECODER_STATUS_ERROR_NO_DATA;
if (buf[0] != 1) {
......
......@@ -622,6 +622,15 @@ get_max_dec_frame_buffering (GstH265SPS * sps)
(sps->max_dec_pic_buffering_minus1[sps->max_sub_layers_minus1] + 1));
}
static void
dpb_remove_all (GstVaapiDecoderH265 * decoder)
{
GstVaapiDecoderH265Private *const priv = &decoder->priv;
while (priv->dpb_count > 0)
gst_vaapi_frame_store_replace (&priv->dpb[--priv->dpb_count], NULL);
}
static void
dpb_remove_index (GstVaapiDecoderH265 * decoder, gint index)
{
......@@ -745,9 +754,7 @@ dpb_clear (GstVaapiDecoderH265 * decoder, gboolean hard_flush)
guint i;
if (hard_flush) {
for (i = 0; i < priv->dpb_count; i++)
dpb_remove_index (decoder, i);
priv->dpb_count = 0;
dpb_remove_all (decoder);
} else {
/* Remove unused pictures from DPB */
i = 0;
......@@ -2650,13 +2657,15 @@ gst_vaapi_decoder_h265_decode_codec_data (GstVaapiDecoder *
ofs = 23;
for (i = 0; i < num_nal_arrays; i++) {
num_nals = GST_READ_UINT16_BE (buf + ofs + 1);
ofs += 3;
for (j = 0; j < num_nals; j++) {
pi = gst_vaapi_parser_info_h265_new ();
if (!pi)
return GST_VAAPI_DECODER_STATUS_ERROR_ALLOCATION_FAILED;
unit.parsed_info = pi;
result = gst_h265_parser_identify_nalu_hevc (priv->parser,
buf, ofs + 3, buf_size, 2, &pi->nalu);
buf, ofs, buf_size, 2, &pi->nalu);
if (result != GST_H265_PARSER_OK) {
status = get_status (result);
goto cleanup;
......@@ -2687,6 +2696,16 @@ gst_vaapi_decoder_h265_decode_codec_data (GstVaapiDecoder *
if (status != GST_VAAPI_DECODER_STATUS_SUCCESS)
goto cleanup;
break;
case GST_H265_NAL_SUFFIX_SEI:
case GST_H265_NAL_PREFIX_SEI:
status = parse_sei (decoder, &unit);
if (status != GST_VAAPI_DECODER_STATUS_SUCCESS)
goto cleanup;
status = decode_sei (decoder, &unit);
if (status != GST_VAAPI_DECODER_STATUS_SUCCESS)
goto cleanup;
break;
}
ofs = pi->nalu.offset + pi->nalu.size;
gst_vaapi_parser_info_h265_replace (&pi, NULL);
......
......@@ -276,6 +276,11 @@ decode_sequence (GstVaapiDecoderVC1 * decoder, GstVC1BDU * rbdu,
priv->has_entrypoint = FALSE;
if (adv_hdr->interlace != 0) {
GST_ERROR ("interlaced sequence unsupported");
return GST_VAAPI_DECODER_STATUS_ERROR_UNSUPPORTED_PROFILE;
}
/* Reset POC */
if (priv->last_non_b_picture) {
if (priv->last_non_b_picture->poc == priv->next_poc)
......
......@@ -2365,15 +2365,17 @@ ensure_bitrate (GstVaapiEncoderH264 * encoder)
thus estimating +15% here ; and using adaptive 8x8 transforms
in I-frames could bring up to +10% improvement. */
guint bits_per_mb = 48;
guint64 factor;
if (!encoder->use_cabac)
bits_per_mb += (bits_per_mb * 15) / 100;
if (!encoder->use_dct8x8)
bits_per_mb += (bits_per_mb * 10) / 100;
factor = encoder->mb_width * encoder->mb_height * bits_per_mb;
base_encoder->bitrate =
encoder->mb_width * encoder->mb_height * bits_per_mb *
GST_VAAPI_ENCODER_FPS_N (encoder) /
GST_VAAPI_ENCODER_FPS_D (encoder) / 1000;
gst_util_uint64_scale (factor, GST_VAAPI_ENCODER_FPS_N (encoder),
GST_VAAPI_ENCODER_FPS_D (encoder)) / 1000;
GST_INFO ("target bitrate computed to %u kbps", base_encoder->bitrate);
}
break;
......@@ -2440,9 +2442,9 @@ reset_properties (GstVaapiEncoderH264 * encoder)
if (encoder->num_bframes > (base_encoder->keyframe_period + 1) / 2)
encoder->num_bframes = (base_encoder->keyframe_period + 1) / 2;
if (encoder->num_bframes)
encoder->cts_offset = GST_SECOND * GST_VAAPI_ENCODER_FPS_D (encoder) /
GST_VAAPI_ENCODER_FPS_N (encoder);
if (encoder->num_bframes > 0 && GST_VAAPI_ENCODER_FPS_N (encoder) > 0)
encoder->cts_offset = gst_util_uint64_scale (GST_SECOND,
GST_VAAPI_ENCODER_FPS_D (encoder), GST_VAAPI_ENCODER_FPS_N (encoder));
else
encoder->cts_offset = 0;
......
......@@ -1823,10 +1823,10 @@ ensure_bitrate (GstVaapiEncoderH265 * encoder)
/* Fixme: Provide better estimation */
/* Using a 1/6 compression ratio */
/* 12 bits per pixel fro yuv420 */
guint64 factor = encoder->luma_width * encoder->luma_height * 12 / 6;
base_encoder->bitrate =
(encoder->luma_width * encoder->luma_height * 12 / 6) *
GST_VAAPI_ENCODER_FPS_N (encoder) /
GST_VAAPI_ENCODER_FPS_D (encoder) / 1000;
gst_util_uint64_scale (factor, GST_VAAPI_ENCODER_FPS_N (encoder),
GST_VAAPI_ENCODER_FPS_D (encoder)) / 1000;
GST_INFO ("target bitrate computed to %u kbps", base_encoder->bitrate);
}
break;
......@@ -1905,9 +1905,9 @@ reset_properties (GstVaapiEncoderH265 * encoder)
if (encoder->num_bframes > (base_encoder->keyframe_period + 1) / 2)
encoder->num_bframes = (base_encoder->keyframe_period + 1) / 2;
if (encoder->num_bframes)
encoder->cts_offset = GST_SECOND * GST_VAAPI_ENCODER_FPS_D (encoder) /
GST_VAAPI_ENCODER_FPS_N (encoder);
if (encoder->num_bframes > 0 && GST_VAAPI_ENCODER_FPS_N (encoder) > 0)
encoder->cts_offset = gst_util_uint64_scale (GST_SECOND,
GST_VAAPI_ENCODER_FPS_D (encoder), GST_VAAPI_ENCODER_FPS_N (encoder));
else
encoder->cts_offset = 0;
......
......@@ -186,10 +186,11 @@ ensure_bitrate (GstVaapiEncoderMpeg2 * encoder)
switch (GST_VAAPI_ENCODER_RATE_CONTROL (encoder)) {
case GST_VAAPI_RATECONTROL_CBR:
if (!base_encoder->bitrate)
base_encoder->bitrate = GST_VAAPI_ENCODER_WIDTH (encoder) *
GST_VAAPI_ENCODER_HEIGHT (encoder) *
GST_VAAPI_ENCODER_FPS_N (encoder) /
GST_VAAPI_ENCODER_FPS_D (encoder) / 4 / 1000;
base_encoder->bitrate =
gst_util_uint64_scale (GST_VAAPI_ENCODER_WIDTH (encoder) *
GST_VAAPI_ENCODER_HEIGHT (encoder),
GST_VAAPI_ENCODER_FPS_N (encoder),
GST_VAAPI_ENCODER_FPS_D (encoder)) / 4 / 1000;
break;
default:
base_encoder->bitrate = 0;
......
......@@ -125,10 +125,11 @@ ensure_bitrate (GstVaapiEncoderVP8 * encoder)
switch (GST_VAAPI_ENCODER_RATE_CONTROL (encoder)) {
case GST_VAAPI_RATECONTROL_CBR:
if (!base_encoder->bitrate) {
base_encoder->bitrate = GST_VAAPI_ENCODER_WIDTH (encoder) *
GST_VAAPI_ENCODER_HEIGHT (encoder) *
GST_VAAPI_ENCODER_FPS_N (encoder) /
GST_VAAPI_ENCODER_FPS_D (encoder) / 4 * 1000;
base_encoder->bitrate =
gst_util_uint64_scale (GST_VAAPI_ENCODER_WIDTH (encoder) *
GST_VAAPI_ENCODER_HEIGHT (encoder),
GST_VAAPI_ENCODER_FPS_N (encoder),
GST_VAAPI_ENCODER_FPS_D (encoder)) / 4 * 1000;
}
default:
base_encoder->bitrate = 0;
......@@ -162,8 +163,9 @@ set_context_info (GstVaapiEncoder * base_encoder)
base_encoder->num_ref_frames = 3;
/* Only YUV 4:2:0 formats are supported for now. */
/* Assumig 4 times compression ratio */
base_encoder->codedbuf_size = GST_ROUND_UP_16 (vip->width) *
GST_ROUND_UP_16 (vip->height) * 3 / 2;
GST_ROUND_UP_16 (vip->height) * 12 / 4;
base_encoder->codedbuf_size +=
MAX_FRAME_TAG_SIZE + MAX_UPDATE_SEGMENTATION_SIZE +
......
......@@ -624,6 +624,7 @@ gst_vaapi_surface_derive_image (GstVaapiSurface * surface)
GstVaapiDisplay *display;
VAImage va_image;
VAStatus status;
GstVaapiImage *image;
g_return_val_if_fail (surface != NULL, NULL);
......@@ -640,7 +641,10 @@ gst_vaapi_surface_derive_image (GstVaapiSurface * surface)
if (va_image.image_id == VA_INVALID_ID || va_image.buf == VA_INVALID_ID)
return NULL;
return gst_vaapi_image_new_with_image (display, &va_image);
image = gst_vaapi_image_new_with_image (display, &va_image);
if (!image)
vaDestroyImage (GST_VAAPI_DISPLAY_VADISPLAY (display), va_image.image_id);
return image;
}
/**
......
......@@ -133,6 +133,7 @@ static const GstVaapiDecoderMap vaapi_decode_map[] = {
};
static GstElementClass *parent_class = NULL;
GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT (parent_class);
static gboolean gst_vaapidecode_update_sink_caps (GstVaapiDecode * decode,
GstCaps * caps);
......@@ -882,7 +883,7 @@ gst_vaapidecode_set_format (GstVideoDecoder * vdec, GstVideoCodecState * state)
return FALSE;
if (!gst_vaapi_plugin_base_set_caps (plugin, decode->sinkpad_caps, NULL))
return FALSE;
if (!gst_vaapidecode_reset_full (decode, decode->sinkpad_caps, FALSE))
if (!gst_vaapidecode_reset_full (decode, decode->sinkpad_caps, TRUE))
return FALSE;
return TRUE;
......@@ -1133,6 +1134,7 @@ gst_vaapidecode_class_init (GstVaapiDecodeClass * klass)
longname = g_strdup ("VA-API decoder");
}
element_class->set_context = gst_vaapi_base_set_context;
gst_element_class_set_static_metadata (element_class, longname,
"Codec/Decoder/Video", GST_PLUGIN_DESC,
"Gwenole Beauchesne <gwenole.beauchesne@intel.com>, "
......
......@@ -30,29 +30,7 @@
G_BEGIN_DECLS
#define GST_TYPE_VAAPIDECODE \
(gst_vaapidecode_get_type())
#define GST_VAAPIDECODE(obj) \
(G_TYPE_CHECK_INSTANCE_CAST((obj), \
GST_TYPE_VAAPIDECODE, \
GstVaapiDecode))
#define GST_VAAPIDECODE_CLASS(klass) \
(G_TYPE_CHECK_CLASS_CAST((klass), \
GST_TYPE_VAAPIDECODE, \
GstVaapiDecodeClass))
#define GST_IS_VAAPIDECODE(obj) \
(G_TYPE_CHECK_INSTANCE_TYPE((obj), GST_TYPE_VAAPIDECODE))
#define GST_IS_VAAPIDECODE_CLASS(klass) \
(G_TYPE_CHECK_CLASS_TYPE((klass), GST_TYPE_VAAPIDECODE))
#define GST_VAAPIDECODE_GET_CLASS(obj) \
(G_TYPE_INSTANCE_GET_CLASS((obj), \
GST_TYPE_VAAPIDECODE, \
GstVaapiDecodeClass))
#define GST_VAAPIDECODE(obj) ((GstVaapiDecode *)(obj))
typedef struct _GstVaapiDecode GstVaapiDecode;
typedef struct _GstVaapiDecodeClass GstVaapiDecodeClass;
......
......@@ -98,6 +98,9 @@ static const char gst_vaapi_decode_bin_sink_caps_str[] =
GST_CAPS_CODEC("video/x-wmv")
#if USE_VP8_DECODER
GST_CAPS_CODEC("video/x-vp8")
#endif
#if USE_VP9_DECODER
GST_CAPS_CODEC("video/x-vp9")
#endif
;
/* *INDENT-ON* */
......
......@@ -44,6 +44,8 @@ G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GstVaapiEncode,
gst_vaapiencode, GST_TYPE_VIDEO_ENCODER,
GST_VAAPI_PLUGIN_BASE_INIT_INTERFACES);
GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT (gst_vaapiencode_parent_class);
enum
{
PROP_0,
......@@ -629,6 +631,7 @@ gst_vaapiencode_class_init (GstVaapiEncodeClass * klass)
object_class->finalize = gst_vaapiencode_finalize;
element_class->set_context = gst_vaapi_base_set_context;
element_class->change_state =
GST_DEBUG_FUNCPTR (gst_vaapiencode_change_state);
......
......@@ -35,8 +35,6 @@
/* Default debug category is from the subclass */
#define GST_CAT_DEFAULT (plugin->debug_category)
static gpointer plugin_parent_class = NULL;
/* GstVideoContext interface */
static void
plugin_set_display (GstVaapiPluginBase * plugin, GstVaapiDisplay * display)
......@@ -57,18 +55,25 @@ plugin_set_display (GstVaapiPluginBase * plugin, GstVaapiDisplay * display)
gst_vaapi_display_unref (display);
}
static void
plugin_set_context (GstElement * element, GstContext * context)
/**
* gst_vaapi_plugin_base_set_context:
* @plugin: a #GstVaapiPluginBase instance
* @context: a #GstContext to set
*
* This is a common set_context() element's vmethod for all the
* GStreamer VA-API elements.
*
* It normally should be used through the macro
* #GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT()
**/
void
gst_vaapi_plugin_base_set_context (GstVaapiPluginBase * plugin,
GstContext * context)
{
GstVaapiPluginBase *const plugin = GST_VAAPI_PLUGIN_BASE (element);
GstElementClass *element_class = GST_ELEMENT_CLASS (plugin_parent_class);
GstVaapiDisplay *display = NULL;
if (gst_vaapi_video_context_get_display (context, &display))
plugin_set_display (plugin, display);
if (element_class->set_context)
element_class->set_context (element, context);
}
void
......@@ -180,14 +185,8 @@ error_create_proxy:
void
gst_vaapi_plugin_base_class_init (GstVaapiPluginBaseClass * klass)
{
GstElementClass *element_class = GST_ELEMENT_CLASS (klass);
klass->has_interface = default_has_interface;
klass->display_changed = default_display_changed;
plugin_parent_class = g_type_class_peek_parent (klass);
element_class->set_context = GST_DEBUG_FUNCPTR (plugin_set_context);
}
void
......@@ -693,8 +692,18 @@ gst_vaapi_plugin_base_decide_allocation (GstVaapiPluginBase * plugin,
gst_buffer_pool_config_set_params (config, caps, size, min, max);
gst_buffer_pool_config_add_option (config,
GST_BUFFER_POOL_OPTION_VAAPI_VIDEO_META);
if (!gst_buffer_pool_set_config (pool, config))
goto config_failed;
if (!gst_buffer_pool_set_config (pool, config)) {
config = gst_buffer_pool_get_config (pool);
if (!gst_buffer_pool_config_validate_params (config, caps, size, min,
max)) {
gst_structure_free (config);
goto config_failed;
}
if (!gst_buffer_pool_set_config (pool, config))
goto config_failed;
}
}
/* Check whether GstVideoMeta, or GstVideoAlignment, is needed (raw video) */
......@@ -923,6 +932,7 @@ ensure_allowed_raw_caps (GstVaapiPluginBase * plugin)
{
GArray *formats, *out_formats;
GstVaapiSurface *surface;
GstVaapiDisplay *display;
guint i;
GstCaps *out_caps;
gboolean ret = FALSE;
......@@ -933,7 +943,8 @@ ensure_allowed_raw_caps (GstVaapiPluginBase * plugin)
out_formats = formats = NULL;
surface = NULL;
formats = gst_vaapi_display_get_image_formats (plugin->display);
display = gst_vaapi_display_ref (plugin->display);
formats = gst_vaapi_display_get_image_formats (display);
if (!formats)
goto bail;
......@@ -943,8 +954,7 @@ ensure_allowed_raw_caps (GstVaapiPluginBase * plugin)
goto bail;
surface =
gst_vaapi_surface_new (plugin->display, GST_VAAPI_CHROMA_TYPE_YUV420, 64,
64);
gst_vaapi_surface_new (display, GST_VAAPI_CHROMA_TYPE_YUV420, 64, 64);
if (!surface)
goto bail;
......@@ -954,7 +964,7 @@ ensure_allowed_raw_caps (GstVaapiPluginBase * plugin)
if (format == GST_VIDEO_FORMAT_UNKNOWN)
continue;
image = gst_vaapi_image_new (plugin->display, format, 64, 64);
image = gst_vaapi_image_new (display, format, 64, 64);
if (!image)
continue;
if (gst_vaapi_surface_put_image (surface, image))
......@@ -977,6 +987,7 @@ bail:
g_array_unref (out_formats);
if (surface)
gst_vaapi_object_unref (surface);
gst_vaapi_display_unref (display);
return ret;
}
......
......@@ -31,7 +31,7 @@
#include <gst/video/gstvideosink.h>
#include <gst/vaapi/gstvaapidisplay.h>
#ifdef USE_GST_GL_HELPERS
#if USE_GST_GL_HELPERS
# include <gst/gl/gstglcontext.h>
#endif
......@@ -102,6 +102,16 @@ typedef struct _GstVaapiPluginBaseClass GstVaapiPluginBaseClass;
(gst_vaapi_display_replace(&GST_VAAPI_PLUGIN_BASE_DISPLAY(plugin), \
(new_display)))
#define GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT(parent_class) \
static void \
gst_vaapi_base_set_context (GstElement * element, GstContext * context) \
{ \
GstVaapiPluginBase *const plugin = GST_VAAPI_PLUGIN_BASE (element); \
\
gst_vaapi_plugin_base_set_context (plugin, context); \
GST_ELEMENT_CLASS (parent_class)->set_context (element, context); \
}
struct _GstVaapiPluginBase
{
/*< private >*/
......@@ -220,6 +230,11 @@ GstFlowReturn
gst_vaapi_plugin_base_get_input_buffer (GstVaapiPluginBase * plugin,
GstBuffer * inbuf, GstBuffer ** outbuf_ptr);
G_GNUC_INTERNAL
void
gst_vaapi_plugin_base_set_context (GstVaapiPluginBase * plugin,
GstContext * context);
G_GNUC_INTERNAL
void
gst_vaapi_plugin_base_set_gl_context (GstVaapiPluginBase * plugin,
......
......@@ -103,6 +103,7 @@ gst_vaapi_create_display (GstVaapiDisplayType display_type,
return display;
}
#if USE_GST_GL_HELPERS
static GstVaapiDisplay *
gst_vaapi_create_display_from_handle (GstVaapiDisplayType display_type,
gpointer handle)
......@@ -122,6 +123,7 @@ gst_vaapi_create_display_from_handle (GstVaapiDisplayType display_type,
}
return NULL;
}
#endif
static GstVaapiDisplay *
gst_vaapi_create_display_from_gl_context (GstObject * gl_context_object)
......
......@@ -92,6 +92,8 @@ G_DEFINE_TYPE_WITH_CODE (GstVaapiPostproc, gst_vaapipostproc,
G_IMPLEMENT_INTERFACE (GST_TYPE_COLOR_BALANCE,
gst_vaapipostproc_colorbalance_init));
GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT (gst_vaapipostproc_parent_class);
static GstVideoFormat native_formats[] =
{ GST_VIDEO_FORMAT_NV12, GST_VIDEO_FORMAT_YV12, GST_VIDEO_FORMAT_I420 };
......@@ -722,9 +724,9 @@ error_process_vpp:
}
error_push_buffer:
{
if (ret != GST_FLOW_FLUSHING)
GST_ERROR ("failed to push output buffer to video sink");
return GST_FLOW_ERROR;
GST_DEBUG_OBJECT (postproc, "failed to push output buffer: %s",
gst_flow_get_name (ret));
return ret;
}
}
......@@ -799,9 +801,9 @@ error_create_buffer:
}
error_push_buffer:
{
if (ret != GST_FLOW_FLUSHING)
GST_ERROR ("failed to push output buffer to video sink");
return GST_FLOW_EOS;
GST_DEBUG_OBJECT (postproc, "failed to push output buffer: %s",
gst_flow_get_name (ret));
return ret;
}
}
......@@ -1501,6 +1503,7 @@ gst_vaapipostproc_class_init (GstVaapiPostprocClass * klass)
trans_class->prepare_output_buffer = gst_vaapipostproc_prepare_output_buffer;
element_class->set_context = gst_vaapi_base_set_context;
gst_element_class_set_static_metadata (element_class,
"VA-API video postprocessing",
"Filter/Converter/Video;Filter/Converter/Video/Scaler;"
......
......@@ -107,6 +107,8 @@ G_DEFINE_TYPE_WITH_CODE (GstVaapiSink,
G_IMPLEMENT_INTERFACE (GST_TYPE_NAVIGATION,
gst_vaapisink_navigation_iface_init));
GST_VAAPI_PLUGIN_BASE_DEFINE_SET_CONTEXT (gst_vaapisink_parent_class);
enum
{
HANDOFF_SIGNAL,
......@@ -1202,6 +1204,7 @@ gst_vaapisink_stop (GstBaseSink * base_sink)
{
GstVaapiSink *const sink = GST_VAAPISINK_CAST (base_sink);
gst_vaapisink_set_event_handling (sink, FALSE);
gst_buffer_replace (&sink->video_buffer, NULL);
gst_vaapi_window_replace (&sink->window, NULL);
......@@ -1213,34 +1216,31 @@ static GstCaps *
gst_vaapisink_get_caps_impl (GstBaseSink * base_sink)
{
GstVaapiSink *const sink = GST_VAAPISINK_CAST (base_sink);
GstCaps *out_caps, *raw_caps;
GstCaps *out_caps, *raw_caps, *feature_caps;
static const char surface_caps_str[] =
GST_VAAPI_MAKE_ENC_SURFACE_CAPS ";"
GST_VIDEO_CAPS_MAKE_WITH_FEATURES (GST_CAPS_FEATURE_MEMORY_VAAPI_SURFACE
"," GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION,
"{ ENCODED, NV12, I420, YV12 }");
GstCapsFeatures *const features = gst_caps_features_new
(GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION, NULL);
out_caps = gst_caps_from_string (surface_caps_str);
if (!GST_VAAPI_PLUGIN_BASE_DISPLAY (sink))
return gst_static_pad_template_get_caps (&gst_vaapisink_sink_factory);
if (GST_VAAPI_PLUGIN_BASE_DISPLAY (sink)) {
raw_caps =
gst_vaapi_plugin_base_get_allowed_raw_caps (GST_VAAPI_PLUGIN_BASE
(sink));
if (raw_caps) {
GstCaps *feature_caps;
GstCapsFeatures *const features =
gst_caps_features_new
(GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION, NULL);
out_caps = gst_caps_from_string (surface_caps_str);
raw_caps =
gst_vaapi_plugin_base_get_allowed_raw_caps (GST_VAAPI_PLUGIN_BASE (sink));
if (!raw_caps)
return out_caps;
out_caps = gst_caps_make_writable (out_caps);
out_caps = gst_caps_make_writable (out_caps);
gst_caps_append (out_caps, gst_caps_copy (raw_caps));
gst_caps_append (out_caps, gst_caps_copy (raw_caps));
feature_caps = gst_caps_copy (raw_caps);
gst_caps_set_features (feature_caps, 0, features);
gst_caps_append (out_caps, feature_caps);
feature_caps = gst_caps_copy (raw_caps);
gst_caps_set_features (feature_caps, 0, features);
gst_caps_append (out_caps, feature_caps);
}
}
return out_caps;
}
......@@ -1496,8 +1496,6 @@ gst_vaapisink_query (GstBaseSink * base_sink, GstQuery * query)
static void
gst_vaapisink_destroy (GstVaapiSink * sink)
{
gst_vaapisink_set_event_handling (sink, FALSE);
cb_channels_finalize (sink);
gst_buffer_replace (&sink->video_buffer, NULL);
gst_caps_replace (&sink->caps, NULL);
......@@ -1663,6 +1661,7 @@ gst_vaapisink_class_init (GstVaapiSinkClass * klass)
videosink_class->show_frame = GST_DEBUG_FUNCPTR (gst_vaapisink_show_frame);
element_class->set_context = gst_vaapi_base_set_context;
element_class->set_bus = gst_vaapisink_set_bus;
gst_element_class_set_static_metadata (element_class,
"VA-API sink", "Sink/Video", GST_PLUGIN_DESC,
......
......@@ -141,7 +141,7 @@ gst_vaapi_video_buffer_pool_set_config (GstBufferPool * pool,
GstVideoInfo *const new_vip = &priv->video_info[!priv->video_info_index];
GstVideoAlignment align;
GstAllocator *allocator;
gboolean changed_caps, use_dmabuf_memory;
gboolean changed_caps, use_dmabuf_memory, ret, updated = FALSE;
if (!gst_buffer_pool_config_get_params (config, &caps, NULL, NULL, NULL))
goto error_invalid_config;
......@@ -191,6 +191,21 @@ gst_vaapi_video_buffer_pool_set_config (GstBufferPool * pool,
priv->has_video_meta = gst_buffer_pool_config_has_option (config,
GST_BUFFER_POOL_OPTION_VIDEO_META);
if (!priv->has_video_meta) {
gint i;
for (i = 0; i < GST_VIDEO_INFO_N_PLANES (new_vip); i++) {
if (GST_VIDEO_INFO_PLANE_OFFSET (new_vip, i) !=
GST_VIDEO_INFO_PLANE_OFFSET (&priv->alloc_info, i) ||
GST_VIDEO_INFO_PLANE_STRIDE (new_vip, i) !=
GST_VIDEO_INFO_PLANE_STRIDE (&priv->alloc_info, i)) {
priv->has_video_meta = TRUE;
gst_buffer_pool_config_add_option (config,
GST_BUFFER_POOL_OPTION_VIDEO_META);
updated = TRUE;
break;
}
}
}
priv->has_video_alignment = gst_buffer_pool_config_has_option (config,
GST_BUFFER_POOL_OPTION_VIDEO_ALIGNMENT);
......@@ -202,9 +217,10 @@ gst_vaapi_video_buffer_pool_set_config (GstBufferPool * pool,
priv->has_texture_upload_meta = gst_buffer_pool_config_has_option (config,
GST_BUFFER_POOL_OPTION_VIDEO_GL_TEXTURE_UPLOAD_META);
return
ret =
GST_BUFFER_POOL_CLASS
(gst_vaapi_video_buffer_pool_parent_class)->set_config (pool, config);
return !updated && ret;
/* ERRORS */
error_invalid_config:
......
......@@ -141,6 +141,9 @@ _gst_context_get_from_query (GstElement * element, GstQuery * query,
return FALSE;
gst_query_parse_context (query, &ctxt);
if (!ctxt)
return FALSE;
GST_CAT_INFO_OBJECT (GST_CAT_CONTEXT, element,
"found context (%" GST_PTR_FORMAT ") in %s query", ctxt,
direction == GST_PAD_SRC ? "downstream" : "upstream");
......
......@@ -201,7 +201,7 @@ gst_video_meta_map_vaapi_memory (GstVideoMeta * meta, guint plane,
goto error_incompatible_map;
/* Map for writing */
if (++mem->map_count == 1) {
if (mem->map_count == 0) {
if (!ensure_surface (mem))
goto error_ensure_surface;
if (!ensure_image (mem))
......@@ -220,6 +220,7 @@ gst_video_meta_map_vaapi_memory (GstVideoMeta * meta, guint plane,
GST_VAAPI_VIDEO_MEMORY_FLAG_UNSET (mem,
GST_VAAPI_VIDEO_MEMORY_FLAG_SURFACE_IS_CURRENT);
}
mem->map_count++;
*data = gst_vaapi_image_get_plane (mem->image, plane);
*stride = gst_vaapi_image_get_pitch (mem->image, plane);
......
......@@ -40,7 +40,7 @@
struct _GstVaapiVideoMetaTexture
{
GstVaapiTexture *texture;
GstVideoGLTextureType texture_type;
GstVideoGLTextureType texture_type[4];
guint gl_format;
guint width;
guint height;
......@@ -73,15 +73,17 @@ static gboolean
meta_texture_ensure_format (GstVaapiVideoMetaTexture * meta,
GstVideoFormat format)
{
memset (meta->texture_type, 0, sizeof (meta->texture_type));
switch (format) {
case GST_VIDEO_FORMAT_RGBA:
meta->gl_format = GL_RGBA;
meta->texture_type = GST_VIDEO_GL_TEXTURE_TYPE_RGBA;
meta->texture_type[0] = GST_VIDEO_GL_TEXTURE_TYPE_RGBA;
break;
case GST_VIDEO_FORMAT_BGRA:
meta->gl_format = GL_BGRA_EXT;
/* FIXME: add GST_VIDEO_GL_TEXTURE_TYPE_BGRA extension */
meta->texture_type = GST_VIDEO_GL_TEXTURE_TYPE_RGBA;
meta->texture_type[0] = GST_VIDEO_GL_TEXTURE_TYPE_RGBA;
break;
default:
goto error_unsupported_format;
......@@ -155,7 +157,7 @@ meta_texture_copy (GstVaapiVideoMetaTexture * meta)
if (!copy)
return NULL;
copy->texture_type = meta->texture_type;
memcpy (copy->texture_type, meta->texture_type, sizeof (meta->texture_type));
copy->gl_format = meta->gl_format;
copy->width = meta->width;
copy->height = meta->height;
......@@ -220,7 +222,7 @@ gst_buffer_add_texture_upload_meta (GstBuffer * buffer)
meta = gst_buffer_add_video_gl_texture_upload_meta (buffer,
GST_VIDEO_GL_TEXTURE_ORIENTATION_X_NORMAL_Y_NORMAL,
1, &meta_texture->texture_type, gst_vaapi_texture_upload,
1, meta_texture->texture_type, gst_vaapi_texture_upload,
meta_texture, (GBoxedCopyFunc) meta_texture_copy,
(GBoxedFreeFunc) meta_texture_free);
if (!meta)
......
......@@ -25,6 +25,33 @@
</GitRepository>
</repository>
<release>
<Version>
<revision>1.8.3</revision>
<branch>1.8</branch>
<created>2016-06-09</created>
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gstreamer-vaapi/gstreamer-vaapi-1.8.3.tar.xz" />
</Version>
</release>
<release>
<Version>
<revision>1.8.2</revision>
<branch>1.8</branch>
<created>2016-06-09</created>
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gstreamer-vaapi/gstreamer-vaapi-1.8.2.tar.xz" />
</Version>
</release>
<release>
<Version>
<revision>1.8.1</revision>
<branch>1.8</branch>
<created>2016-04-20</created>
<file-release rdf:resource="http://gstreamer.freedesktop.org/src/gstreamer-vaapi/gstreamer-vaapi-1.8.1.tar.xz" />
</Version>
</release>
<release>
<Version>
<revision>1.8.0</revision>
......
......@@ -269,8 +269,14 @@ dump_info(GstVaapiDisplay *display)
int
main(int argc, char *argv[])
{
GstVaapiDisplay *display, *display2;
guint width, height, par_n, par_d;
GstVaapiDisplay *display;
#if USE_X11
GstVaapiDisplay *display2;
#endif
#if USE_X11 || USE_WAYLAND
guint width, height;
guint par_n, par_d;
#endif
gst_init(&argc, &argv);
......