From 629884aad3a1f110222f096c99fd29fa266091da Mon Sep 17 00:00:00 2001 From: Zaheer Abbas Merali Date: Fri, 24 Aug 2007 15:56:52 +0000 Subject: [PATCH] Make switch more reliable and also not lock up when sink pad caps change. Original commit message from CVS: * examples/switch/switcher.c (main): * gst/switch/gstswitch.c (gst_switch_chain): Make switch more reliable and also not lock up when sink pad caps change. --- ChangeLog | 7 +++++++ examples/switch/switcher.c | 17 +++++++++-------- gst/switch/gstswitch.c | 37 ++++++++++++++++++++++++++----------- 3 files changed, 42 insertions(+), 19 deletions(-) diff --git a/ChangeLog b/ChangeLog index 9dde57efc8..3abc5b55ca 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,10 @@ +2007-08-24 Zaheer Abbas Merali + + * examples/switch/switcher.c (main): + * gst/switch/gstswitch.c (gst_switch_chain): + Make switch more reliable and also not lock up when + sink pad caps change. + 2007-08-24 Julien MOUTTE * gst/flv/gstflvdemux.c: (gst_flv_demux_flush), diff --git a/examples/switch/switcher.c b/examples/switch/switcher.c index 42c6d585be..2874fcc5f2 100644 --- a/examples/switch/switcher.c +++ b/examples/switch/switcher.c @@ -118,11 +118,12 @@ main (int argc, char *argv[]) gst_caps_from_string ("video/x-raw-rgb,width=640,height=480"), NULL); video_switch = gst_element_factory_make ("switch", "video_switch"); segment = gst_element_factory_make ("identity", "identity-segment"); + g_object_set (G_OBJECT (segment), "silent", TRUE, NULL); g_signal_connect (G_OBJECT (segment), "notify::last-message", G_CALLBACK (last_message_received), segment); g_object_set (G_OBJECT (segment), "single-segment", TRUE, NULL); scaler = gst_element_factory_make ("videoscale", "videoscale0"); - video_sink = gst_element_factory_make ("ximagesink", "video_sink"); + video_sink = gst_element_factory_make ("fakesink", "video_sink"); //g_object_set (G_OBJECT (video_sink), "sync", FALSE, NULL); sink1_sync = gst_element_factory_make ("identity", "sink0_sync"); g_object_set (G_OBJECT (sink1_sync), "sync", TRUE, NULL); @@ -130,21 +131,21 @@ main (int argc, char *argv[]) g_object_set (G_OBJECT (sink2_sync), "sync", TRUE, NULL); gst_bin_add_many (GST_BIN (pipeline), src1, src2, segment, video_switch, video_sink, sink1_sync, sink2_sync, scaler, capsfilter, NULL); - gst_element_link (src1, sink1_sync); - gst_element_link (sink1_sync, video_switch); + gst_element_link (src1, /*sink1_sync); + gst_element_link (sink1_sync, */ video_switch); gst_element_link (src2, capsfilter); - gst_element_link (capsfilter, sink2_sync); - gst_element_link (sink2_sync, video_switch); + gst_element_link (capsfilter, /*sink2_sync); + gst_element_link (sink2_sync, */ video_switch); gst_element_link (video_switch, segment); - gst_element_link (segment, scaler); - gst_element_link (scaler, video_sink); + gst_element_link (segment, /*scaler); + gst_element_link (scaler, */ video_sink); bus = gst_pipeline_get_bus (GST_PIPELINE (pipeline)); gst_bus_add_watch (bus, my_bus_callback, NULL); gst_object_unref (bus); gst_element_set_state (GST_ELEMENT (pipeline), GST_STATE_PLAYING); - g_timeout_add (2000, (GSourceFunc) switch_timer, video_switch); + g_timeout_add (200, (GSourceFunc) switch_timer, video_switch); g_main_loop_run (loop); diff --git a/gst/switch/gstswitch.c b/gst/switch/gstswitch.c index 5f9dd05404..6621bc24d8 100644 --- a/gst/switch/gstswitch.c +++ b/gst/switch/gstswitch.c @@ -212,7 +212,7 @@ gst_switch_chain (GstPad * pad, GstBuffer * buf) if (pad != active_sinkpad) { GST_SWITCH_UNLOCK (gstswitch); - GST_DEBUG_OBJECT (gstswitch, "Ignoring buffer %p from pad %s:%s", + GST_LOG_OBJECT (gstswitch, "Ignoring buffer %p from pad %s:%s", buf, GST_DEBUG_PAD_NAME (pad)); gst_object_unref (gstswitch); @@ -238,16 +238,19 @@ gst_switch_chain (GstPad * pad, GstBuffer * buf) gdouble rate, applied_rate; GstFormat format; gint64 start, stop, position; + GstEvent *newsegment_event; gst_event_parse_new_segment_full (prev_newsegment, &update, &rate, &applied_rate, &format, &start, &stop, &position); GST_DEBUG_OBJECT (gstswitch, - "Sending new segment update with stop of %" G_GUINT64_FORMAT, - gstswitch->stop_value); + "Sending new segment update with stop of %" G_GUINT64_FORMAT + "and start of %" G_GUINT64_FORMAT, gstswitch->stop_value, + gstswitch->current_start); + newsegment_event = gst_event_new_new_segment_full (TRUE, rate, + applied_rate, format, gstswitch->current_start, + gstswitch->stop_value, position); GST_SWITCH_UNLOCK (gstswitch); - gst_pad_push_event (gstswitch->srcpad, - gst_event_new_new_segment_full (TRUE, rate, applied_rate, format, - gstswitch->current_start, gstswitch->stop_value, position)); + gst_pad_push_event (gstswitch->srcpad, newsegment_event); GST_SWITCH_LOCK (gstswitch); } } @@ -264,6 +267,7 @@ gst_switch_chain (GstPad * pad, GstBuffer * buf) gdouble rate, applied_rate; GstFormat format; gint64 start, stop, position; + GstEvent *newsegment_event; gst_event_parse_new_segment_full (event, &update, &rate, &applied_rate, &format, &start, &stop, &position); @@ -273,9 +277,20 @@ gst_switch_chain (GstPad * pad, GstBuffer * buf) } else { start = GST_BUFFER_TIMESTAMP (buf); } - gst_pad_push_event (gstswitch->srcpad, - gst_event_new_new_segment_full (FALSE, rate, applied_rate, format, - start, stop, position)); + if (start == GST_CLOCK_TIME_NONE) { + + /*GST_ELEMENT_ERROR (gstswitch, STREAM, FAILED, (NULL), ( */ + g_critical ("Cannot send " + "new segment event because start value is GST_CLOCK_TIME_NONE"); /*); */ + GST_WARNING_OBJECT (gstswitch, + "new segment event requested to be sent but start value is NONE"); + + } + newsegment_event = gst_event_new_new_segment_full (FALSE, rate, + applied_rate, format, start, stop, position); + GST_SWITCH_UNLOCK (gstswitch); + gst_pad_push_event (gstswitch->srcpad, newsegment_event); + GST_SWITCH_LOCK (gstswitch); gstswitch->need_to_send_newsegment = FALSE; gstswitch->current_start = start; GST_DEBUG_OBJECT (gstswitch, @@ -301,12 +316,12 @@ gst_switch_chain (GstPad * pad, GstBuffer * buf) gstswitch->last_ts = GST_BUFFER_TIMESTAMP (buf) + GST_BUFFER_DURATION (buf); if (!gstswitch->queue_buffers) { /* forward */ - GST_DEBUG_OBJECT (gstswitch, "Forwarding buffer %p from pad %s:%s to %s:%s", + GST_LOG_OBJECT (gstswitch, "Forwarding buffer %p from pad %s:%s to %s:%s", buf, GST_DEBUG_PAD_NAME (pad), GST_DEBUG_PAD_NAME (gstswitch->srcpad)); GST_SWITCH_UNLOCK (gstswitch); res = gst_pad_push (gstswitch->srcpad, buf); GST_SWITCH_LOCK (gstswitch); - GST_DEBUG_OBJECT (gstswitch, "Finished pushing buffer"); + GST_LOG_OBJECT (gstswitch, "Finished pushing buffer"); } else { GList *buffers; gboolean lookup_res = TRUE;