Patch by: Mark Nauwelaerts <manauw at skynet be>
+ * plugins/elements/gstidentity.c: (gst_identity_class_init),
+ (gst_identity_init), (gst_identity_prepare_output_buffer):
+ Identity is not always a passthrough element, it can modify the buffer
+ timestamps when it has a datarate and operates in single-segment mode.
+ We therefore make it an in_place filter with a custom buffer prepare
+ function that conditionally makes the input buffer metadata writable
+ when needed. Fixes #523985.
+
+2008-03-24 Wim Taymans <wim.taymans@collabora.co.uk>
+
+ Patch by: Mark Nauwelaerts <manauw at skynet be>
+
* gst/gstclock.h:
* libs/gst/base/gstbasesrc.h:
* libs/gst/base/gstbasetransform.c:
static gboolean gst_identity_event (GstBaseTransform * trans, GstEvent * event);
static GstFlowReturn gst_identity_transform_ip (GstBaseTransform * trans,
GstBuffer * buf);
+static GstFlowReturn gst_identity_prepare_output_buffer (GstBaseTransform
+ * trans, GstBuffer * in_buf, gint out_size, GstCaps * out_caps,
+ GstBuffer ** out_buf);
static gboolean gst_identity_start (GstBaseTransform * trans);
static gboolean gst_identity_stop (GstBaseTransform * trans);
gstbasetrans_class->event = GST_DEBUG_FUNCPTR (gst_identity_event);
gstbasetrans_class->transform_ip =
GST_DEBUG_FUNCPTR (gst_identity_transform_ip);
+ gstbasetrans_class->prepare_output_buffer =
+ GST_DEBUG_FUNCPTR (gst_identity_prepare_output_buffer);
gstbasetrans_class->start = GST_DEBUG_FUNCPTR (gst_identity_start);
gstbasetrans_class->stop = GST_DEBUG_FUNCPTR (gst_identity_stop);
}
static void
gst_identity_init (GstIdentity * identity, GstIdentityClass * g_class)
{
- gst_base_transform_set_passthrough (GST_BASE_TRANSFORM (identity), TRUE);
-
identity->sleep_time = DEFAULT_SLEEP_TIME;
identity->error_after = DEFAULT_ERROR_AFTER;
identity->drop_probability = DEFAULT_DROP_PROBABILITY;
return ret;
}
+static GstFlowReturn
+gst_identity_prepare_output_buffer (GstBaseTransform * trans,
+ GstBuffer * in_buf, gint out_size, GstCaps * out_caps, GstBuffer ** out_buf)
+{
+ GstIdentity *identity = GST_IDENTITY (trans);
+
+ /* only bother if we may have to alter metadata */
+ if (identity->datarate > 0 || identity->single_segment) {
+ if (gst_buffer_is_metadata_writable (in_buf))
+ *out_buf = gst_buffer_ref (in_buf);
+ else {
+ /* make even less writable */
+ gst_buffer_ref (in_buf);
+ /* extra ref is dropped going through the official process */
+ *out_buf = gst_buffer_make_metadata_writable (in_buf);
+ }
+ } else
+ *out_buf = gst_buffer_ref (in_buf);
+
+ return GST_FLOW_OK;
+}
+
static void
gst_identity_check_perfect (GstIdentity * identity, GstBuffer * buf)
{