diff --git a/gst/debugutils/gstwatchdog.c b/gst/debugutils/gstwatchdog.c index eb77765f34..1a30ed1f63 100644 --- a/gst/debugutils/gstwatchdog.c +++ b/gst/debugutils/gstwatchdog.c @@ -66,7 +66,8 @@ static gboolean gst_watchdog_src_event (GstBaseTransform * trans, GstEvent * event); static GstFlowReturn gst_watchdog_transform_ip (GstBaseTransform * trans, GstBuffer * buf); -static void gst_watchdog_feed (GstWatchdog * watchdog); +static void gst_watchdog_feed (GstWatchdog * watchdog, gpointer mini_object, + gboolean force); static GstStateChangeReturn gst_watchdog_change_state (GstElement * element, GstStateChange transition); @@ -140,7 +141,7 @@ gst_watchdog_set_property (GObject * object, guint property_id, case PROP_TIMEOUT: GST_OBJECT_LOCK (watchdog); watchdog->timeout = g_value_get_int (value); - gst_watchdog_feed (watchdog); + gst_watchdog_feed (watchdog, NULL, FALSE); GST_OBJECT_UNLOCK (watchdog); break; default: @@ -207,20 +208,41 @@ gst_watchdog_quit_mainloop (gpointer ptr) } static void -gst_watchdog_feed (GstWatchdog * watchdog) +gst_watchdog_feed (GstWatchdog * watchdog, gpointer mini_object, gboolean force) { if (watchdog->source) { + if (watchdog->waiting_for_a_buffer) { + if (mini_object && GST_IS_BUFFER (mini_object)) { + watchdog->waiting_for_a_buffer = FALSE; + GST_DEBUG_OBJECT (watchdog, "Got a buffer \\o/"); + } else { + GST_DEBUG_OBJECT (watchdog, "Waiting for a buffer and did not get it," + " keep trying even in PAUSED state"); + force = TRUE; + } + } g_source_destroy (watchdog->source); g_source_unref (watchdog->source); watchdog->source = NULL; + } - if (watchdog->timeout != 0 && watchdog->main_context) { + GST_STATE_LOCK (watchdog); + + if (watchdog->timeout == 0) { + GST_LOG_OBJECT (watchdog, "Timeout is 0 => nothing to do"); + } else if (watchdog->main_context == NULL) { + GST_LOG_OBJECT (watchdog, "No maincontext => nothing to do"); + } else if ((GST_STATE (watchdog) != GST_STATE_PLAYING) && force == FALSE) { + GST_LOG_OBJECT (watchdog, + "Not in playing and force is FALSE => Nothing to do"); + } else { watchdog->source = g_timeout_source_new (watchdog->timeout); - g_source_set_callback (watchdog->source, gst_watchdog_trigger, gst_object_ref (watchdog), - gst_object_unref); + g_source_set_callback (watchdog->source, gst_watchdog_trigger, + gst_object_ref (watchdog), gst_object_unref); g_source_attach (watchdog->source, watchdog->main_context); } + GST_STATE_UNLOCK (watchdog); } static gboolean @@ -283,7 +305,7 @@ gst_watchdog_sink_event (GstBaseTransform * trans, GstEvent * event) GST_DEBUG_OBJECT (watchdog, "sink_event"); GST_OBJECT_LOCK (watchdog); - gst_watchdog_feed (watchdog); + gst_watchdog_feed (watchdog, event, FALSE); GST_OBJECT_UNLOCK (watchdog); return @@ -294,12 +316,25 @@ gst_watchdog_sink_event (GstBaseTransform * trans, GstEvent * event) static gboolean gst_watchdog_src_event (GstBaseTransform * trans, GstEvent * event) { + gboolean force = FALSE; GstWatchdog *watchdog = GST_WATCHDOG (trans); GST_DEBUG_OBJECT (watchdog, "src_event"); GST_OBJECT_LOCK (watchdog); - gst_watchdog_feed (watchdog); + if (GST_EVENT_TYPE (event) == GST_EVENT_SEEK) { + GstSeekFlags flags; + + gst_event_parse_seek (event, NULL, NULL, &flags, NULL, NULL, NULL, NULL); + + if (flags & GST_SEEK_FLAG_FLUSH) { + force = TRUE; + GST_DEBUG_OBJECT (watchdog, "Got a FLUSHING seek, we need a buffer now!"); + watchdog->waiting_for_a_buffer = TRUE; + } + } + + gst_watchdog_feed (watchdog, event, force); GST_OBJECT_UNLOCK (watchdog); return GST_BASE_TRANSFORM_CLASS (gst_watchdog_parent_class)->src_event (trans, @@ -314,7 +349,7 @@ gst_watchdog_transform_ip (GstBaseTransform * trans, GstBuffer * buf) GST_DEBUG_OBJECT (watchdog, "transform_ip"); GST_OBJECT_LOCK (watchdog); - gst_watchdog_feed (watchdog); + gst_watchdog_feed (watchdog, buf, FALSE); GST_OBJECT_UNLOCK (watchdog); return GST_FLOW_OK; @@ -332,11 +367,10 @@ gst_watchdog_change_state (GstElement * element, GstStateChange transition) GST_DEBUG_OBJECT (watchdog, "gst_watchdog_change_state"); switch (transition) { - case GST_STATE_CHANGE_READY_TO_PAUSED: case GST_STATE_CHANGE_PAUSED_TO_PLAYING: /* Activate timer */ GST_OBJECT_LOCK (watchdog); - gst_watchdog_feed (watchdog); + gst_watchdog_feed (watchdog, NULL, FALSE); GST_OBJECT_UNLOCK (watchdog); break; default: @@ -348,6 +382,12 @@ gst_watchdog_change_state (GstElement * element, GstStateChange transition) transition); switch (transition) { + case GST_STATE_CHANGE_READY_TO_PAUSED: + GST_OBJECT_LOCK (watchdog); + watchdog->waiting_for_a_buffer = TRUE; + gst_watchdog_feed (watchdog, NULL, TRUE); + GST_OBJECT_UNLOCK (watchdog); + break; case GST_STATE_CHANGE_PLAYING_TO_PAUSED: /* Disable the timer */ GST_OBJECT_LOCK (watchdog); diff --git a/gst/debugutils/gstwatchdog.h b/gst/debugutils/gstwatchdog.h index 40740ef401..c146c66dbd 100644 --- a/gst/debugutils/gstwatchdog.h +++ b/gst/debugutils/gstwatchdog.h @@ -45,6 +45,8 @@ struct _GstWatchdog GMainLoop *main_loop; GThread *thread; GSource *source; + + gboolean waiting_for_a_buffer; }; struct _GstWatchdogClass