GNOME Bugzilla – Bug 603378
[API][event] New event to flush all buffered data
Last modified: 2012-05-18 08:53:46 UTC
This event would work just like flush, but it would only drop buffers queued along the pipeline and unlock sinks that are rendering data, not segments/time informations reset. Check https://bugzilla.gnome.org/show_bug.cgi?id=537382 for the motivation for this. The use case here is to allow 'instantaneous' track switching. Currently, when using playbin2, a track change simply makes input-selector push data from a new pad to downstream elements. The problem here is that there are buffers queue downstream and already at the sink that will get rendered before the new track buffers are rendered. (In case of a slideshow, like the file of the referred bug, this might take a long time to happen). This new event would drop all those buffers downstream, allowing the new activated track buffers to be rendered immediately. There is still another problem involved in fixing #537382, multiqueue takes a long time to 'detect' that the track it is pushing is now 'not-linked' and he should retry pushing buffers on other pads (the newly activated track is on this group) and all the above would not work. I hacked my way around this for focusing on this new event solution by making input-selector property 'always-ok' true in playbin2.
Created attachment 148745 [details] [review] Adds the new events
Created attachment 148746 [details] [review] basesink patch for the new drain events
Created attachment 148747 [details] [review] patch for queue to handle the new drain events
Created attachment 148750 [details] [review] Make input selector drop buffers only when they get late This patch was already uploaded to 537382, but I'm putting it here as well
Created attachment 148752 [details] [review] Make input-selector use the drain events This is the attempt to make input-selector use the drain events (unsuccessful). I suspect that the closing and sending of new segments is the problem here, because it uses times from the buffers currently passing through, that are probably much ahead of the current running time, causing buffers of the newly activated stream to be clipped/dropped. I tried commenting the code that pushed the segment closing/creation but it still didn't work.
I would like to have this merged into the regular flush events. This could be done by adding new flags to the flush event (default DEEP | RESET). At least we could extend it later on then too. something like: typedef enum { GST_FLUSH_FLAG_DEEP = (1 << 0), GST_FLUSH_FLAG_RESET = (1 << 1) } GstFlushFlags The RESET flag would reset the running_time. The DEEP flag would forward the event downstream instead of unlocking only the current streaming thread. Having the RESET flag bu not the DEEP flag is maybe not so useful.
(In reply to comment #6) > I would like to have this merged into the regular flush events. This could be > done by adding new flags to the flush event (default DEEP | RESET). At least we > could extend it later on then too. > > something like: > > typedef enum { > GST_FLUSH_FLAG_DEEP = (1 << 0), > GST_FLUSH_FLAG_RESET = (1 << 1) > } GstFlushFlags > > The RESET flag would reset the running_time. The DEEP flag would forward the > event downstream instead of unlocking only the current streaming thread. Having > the RESET flag bu not the DEEP flag is maybe not so useful. For 0.11 that's a good idea but in 0.10 we need a different event for this because it is now necessary to look at the content of the event while before this wasn't necessary. All old elements would handle the flush event with flags!=DEEP|RESET as if they are DEEP|RESET and completely break playback (because the running time is reset although upstream elements think it isn't).
> > For 0.11 that's a good idea but in 0.10 we need a different event for this > because it is now necessary to look at the content of the event while before > this wasn't necessary. All old elements would handle the flush event with > flags!=DEEP|RESET as if they are DEEP|RESET and completely break playback > (because the running time is reset although upstream elements think it isn't). We need to change a couple of elements (like queue and basesink) at least. Other elements might need to be updated too. But I guess you are right, old elements can forward the new event without reseting the timing info and then there is more change of backwards compat for non-updated elements.
After some discussion on IRC with Wim I'll be renaming this event to CLEAR instead of DRAIN
Yes, sounds better :) And please add a FIXME 0.11 for merging the events by adding flags as Wim explained in comment #6.
Maybe use the opportunity to make a gst_event_new_clear_start/stop (GstClearFlags flags) flush-start and flush-stop then become a subset of this new event and for 0.11 we can just rename things (when needed).
Created attachment 148779 [details] [review] adds the clear events
Created attachment 148780 [details] [review] gstpad patch for clear events
Created attachment 148781 [details] [review] adds an utility function for clear events
Created attachment 148782 [details] [review] queue patch
Created attachment 148783 [details] [review] basesink patch
Created attachment 148789 [details] [review] inputselector using clear events
Comment on attachment 148750 [details] [review] Make input selector drop buffers only when they get late That's essentially solved by the following commit and Thiago agreed that this is the better approach than using the clock commit 5229a26a7608d66b013fbcca80f8e38f875f4670 Author: Sebastian Dröge <sebastian.droege@collabora.co.uk> Date: Sat Mar 19 10:28:49 2011 +0100 inputselector: Add sync mode that syncs inactive pads to the running time of Fixes bug #645017.
What's the state of this bug in general? Something like a drain/clear event would definitely be useful, at least in 0.11. Maybe as a special variant of the flush events.
flush_stop now has the reset_time property. Drain is implemented with a query.