summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gnl/gnlcomposition.c72
1 files changed, 58 insertions, 14 deletions
diff --git a/gnl/gnlcomposition.c b/gnl/gnlcomposition.c
index 006ed4e..376e483 100644
--- a/gnl/gnlcomposition.c
+++ b/gnl/gnlcomposition.c
@@ -258,6 +258,7 @@ static void update_start_stop_duration (GnlComposition * comp);
struct _GnlCompositionEntry
{
GnlObject *object;
+ GnlComposition *comp;
/* handler id for 'no-more-pads' signal */
gulong nomorepadshandler;
@@ -266,6 +267,7 @@ struct _GnlCompositionEntry
/* handler id for block probe */
gulong probeid;
+ gulong dataprobeid;
};
static void
@@ -339,11 +341,28 @@ gnl_composition_class_init (GnlCompositionClass * klass)
static void
hash_value_destroy (GnlCompositionEntry * entry)
{
+ GstPad *srcpad;
+ GstElement *element = GST_ELEMENT (entry->object);
+
g_signal_handler_disconnect (entry->object, entry->padremovedhandler);
g_signal_handler_disconnect (entry->object, entry->padaddedhandler);
if (entry->nomorepadshandler)
g_signal_handler_disconnect (entry->object, entry->nomorepadshandler);
+
+ if ((srcpad = get_src_pad (element))) {
+ if (entry->probeid) {
+ gst_pad_remove_probe (srcpad, entry->probeid);
+ entry->probeid = 0;
+ }
+
+ if (entry->dataprobeid) {
+ gst_pad_remove_probe (srcpad, entry->dataprobeid);
+ entry->dataprobeid = 0;
+ }
+ gst_object_unref (srcpad);
+ }
+
g_slice_free (GnlCompositionEntry, entry);
}
@@ -1210,12 +1229,20 @@ pad_blocked (GstPad * pad, GstPadProbeInfo * info, GnlComposition * comp)
{
GST_DEBUG_OBJECT (comp, "Pad : %s:%s", GST_DEBUG_PAD_NAME (pad));
+ return GST_PAD_PROBE_OK;
+}
+
+static GstPadProbeReturn
+drop_data (GstPad * pad, GstPadProbeInfo * info, GnlCompositionEntry * entry)
+{
+ GnlCompositionPrivate *priv = entry->comp->priv;
+
/* When updating the pipeline, do not let data flowing */
- if (comp->priv->stackvalid == FALSE &&
- GST_IS_BUFFER (GST_PAD_PROBE_INFO_DATA (info)))
+ if (priv->stackvalid == FALSE || priv->childseek != NULL)
return GST_PAD_PROBE_DROP;
- return GST_PAD_PROBE_OK;
+ entry->dataprobeid = 0;
+ return GST_PAD_PROBE_REMOVE;
}
static inline void
@@ -1296,6 +1323,12 @@ gnl_composition_ghost_pad_set_target (GnlComposition * comp, GstPad * target,
(GstPadProbeCallback) pad_blocked, comp, NULL);
}
+ if (!priv->toplevelentry->dataprobeid) {
+ priv->toplevelentry->dataprobeid = gst_pad_add_probe (ptarget,
+ GST_PAD_PROBE_TYPE_BUFFER | GST_PAD_PROBE_TYPE_BUFFER_LIST,
+ (GstPadProbeCallback) drop_data, priv->toplevelentry, NULL);
+ }
+
/* remove event probe */
if (priv->ghosteventprobe) {
gst_pad_remove_probe (ptarget, priv->ghosteventprobe);
@@ -2219,6 +2252,11 @@ compare_relink_single_node (GnlComposition * comp, GNode * node,
GST_PAD_PROBE_TYPE_BLOCK_DOWNSTREAM | GST_PAD_PROBE_TYPE_IDLE,
(GstPadProbeCallback) pad_blocked, comp, NULL);
}
+ if (!oldentry->dataprobeid) {
+ oldentry->dataprobeid = gst_pad_add_probe (srcpad,
+ GST_PAD_PROBE_TYPE_BUFFER | GST_PAD_PROBE_TYPE_BUFFER_LIST,
+ (GstPadProbeCallback) drop_data, oldentry, NULL);
+ }
}
entry = COMP_ENTRY (comp, newobj);
@@ -2371,6 +2409,11 @@ compare_deactivate_single_node (GnlComposition * comp, GNode * node,
GST_PAD_PROBE_TYPE_BLOCK_DOWNSTREAM | GST_PAD_PROBE_TYPE_IDLE,
(GstPadProbeCallback) pad_blocked, comp, NULL);
}
+ if (entry && !entry->dataprobeid) {
+ entry->dataprobeid = gst_pad_add_probe (srcpad,
+ GST_PAD_PROBE_TYPE_BUFFER | GST_PAD_PROBE_TYPE_BUFFER_LIST,
+ (GstPadProbeCallback) drop_data, entry, NULL);
+ }
/* 2. If we have to modify or we have a parent, flush downstream
* This ensures the streaming thread going through the current object has
@@ -2674,8 +2717,6 @@ update_pipeline (GnlComposition * comp, GstClockTime currenttime,
if (priv->current) {
GstEvent *event;
- priv->stackvalid = TRUE;
-
/* 7.1. Create new seek event for newly configured timeline stack */
if (samestack && (startchanged || stopchanged))
event =
@@ -2734,6 +2775,7 @@ update_pipeline (GnlComposition * comp, GstClockTime currenttime,
priv->childseek = event;
ret = TRUE;
}
+ priv->stackvalid = TRUE;
} else {
if ((!priv->objects_start) && priv->ghostpad) {
GST_DEBUG_OBJECT (comp, "composition is now empty, removing ghostpad");
@@ -2770,6 +2812,10 @@ object_pad_removed (GnlObject * object, GstPad * pad, GnlComposition * comp)
gst_pad_remove_probe (pad, entry->probeid);
entry->probeid = 0;
}
+ if (entry && entry->dataprobeid) {
+ gst_pad_remove_probe (pad, entry->dataprobeid);
+ entry->dataprobeid = 0;
+ }
}
}
}
@@ -2793,6 +2839,12 @@ object_pad_added (GnlObject * object G_GNUC_UNUSED, GstPad * pad,
GST_PAD_PROBE_TYPE_BLOCK_DOWNSTREAM | GST_PAD_PROBE_TYPE_IDLE,
(GstPadProbeCallback) pad_blocked, comp, NULL);
}
+
+ if (!entry->dataprobeid) {
+ entry->dataprobeid = gst_pad_add_probe (pad,
+ GST_PAD_PROBE_TYPE_BUFFER | GST_PAD_PROBE_TYPE_BUFFER_LIST,
+ (GstPadProbeCallback) drop_data, entry, NULL);
+ }
}
static gboolean
@@ -2841,6 +2893,7 @@ gnl_composition_add_object (GstBin * bin, GstElement * element)
/* wrap new element in a GnlCompositionEntry ... */
entry = g_slice_new0 (GnlCompositionEntry);
entry->object = (GnlObject *) element;
+ entry->comp = comp;
if (GNL_OBJECT_IS_EXPANDABLE (element)) {
/* Only react on non-default objects properties */
@@ -2911,8 +2964,6 @@ gnl_composition_remove_object (GstBin * bin, GstElement * element)
gboolean ret = FALSE;
gboolean update_required;
GnlCompositionEntry *entry;
- GstPad *srcpad;
- gulong probeid;
GST_DEBUG_OBJECT (bin, "element %s", GST_OBJECT_NAME (element));
@@ -2941,8 +2992,6 @@ gnl_composition_remove_object (GstBin * bin, GstElement * element)
GST_LOG_OBJECT (element, "Removed from the objects start/stop list");
}
- probeid = entry->probeid;
-
g_hash_table_remove (priv->objects_hash, element);
update_required = OBJECT_IN_ACTIVE_SEGMENT (comp, element) ||
(GNL_OBJECT_PRIORITY (element) == G_MAXUINT32) ||
@@ -2957,11 +3006,6 @@ gnl_composition_remove_object (GstBin * bin, GstElement * element)
GST_LOG_OBJECT (element, "Done removing from the composition, now updating");
COMP_OBJECTS_UNLOCK (comp);
- /* unblock source pad */
- if (probeid && (srcpad = get_src_pad (element))) {
- gst_pad_remove_probe (srcpad, probeid);
- gst_object_unref (srcpad);
- }
/* Make it possible to reuse the same object later */
gnl_object_reset (GNL_OBJECT (element));