mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-19 06:46:38 +00:00
queue2: avoid ping-pong between 0% and 100% buffering messages
If upstream is pushing buffers larger than our limits, only 1 buffer is ever in the queue at a time. Once that single buffer has left the queue, a 0% buffering message would be posted followed immediately by a 100% buffering message when the next buffer was inserted into the queue a very short time later. As per the recommendations, This would result in the application pausing for a short while causing the appearance of a short stutter. The first step of a solution involves not posting a buffering message if there is still data waiting on the sink pad for insertion into the queue. This successfully drops the 0% messages from being posted however a message is still posted on each transition to 100% when the new buffer arrives resulting in a string of 100% buffering messages. We silence these by storing the last posted buffering percentage and only posting a new message when it is different from or last posted message.
This commit is contained in:
parent
e1be065293
commit
c4ccff7861
2 changed files with 24 additions and 8 deletions
|
@ -531,6 +531,7 @@ gst_queue2_init (GstQueue2 * queue)
|
|||
|
||||
g_mutex_init (&queue->buffering_post_lock);
|
||||
queue->buffering_percent = 100;
|
||||
queue->last_posted_buffering_percent = -1;
|
||||
|
||||
/* tempfile related */
|
||||
queue->temp_template = NULL;
|
||||
|
@ -1056,17 +1057,31 @@ static GstMessage *
|
|||
gst_queue2_get_buffering_message (GstQueue2 * queue)
|
||||
{
|
||||
GstMessage *msg = NULL;
|
||||
|
||||
if (queue->percent_changed) {
|
||||
gint percent = queue->buffering_percent;
|
||||
/* Don't change the buffering level if the sinkpad is waiting for
|
||||
* space to become available. This prevents the situation where,
|
||||
* upstream is pushing buffers larger than our limits so only 1 buffer
|
||||
* is ever in the queue at a time.
|
||||
* Changing the level causes a buffering message to be posted saying that
|
||||
* we are buffering which the application may pause to wait for another
|
||||
* 100% buffering message which would be posted very soon after the
|
||||
* waiting sink thread adds it's buffer to the queue */
|
||||
/* FIXME: This situation above can still occur later if
|
||||
* the sink pad is waiting to push a serialized event into the queue and
|
||||
* the queue becomes empty for a short period of time. */
|
||||
if (!queue->waiting_del
|
||||
&& queue->last_posted_buffering_percent != queue->buffering_percent) {
|
||||
gint percent = queue->buffering_percent;
|
||||
|
||||
GST_DEBUG_OBJECT (queue, "Going to post buffering: %d%%", percent);
|
||||
msg = gst_message_new_buffering (GST_OBJECT_CAST (queue), percent);
|
||||
|
||||
gst_message_set_buffering_stats (msg, queue->mode, queue->avg_in,
|
||||
queue->avg_out, queue->buffering_left);
|
||||
|
||||
queue->last_posted_buffering_percent = percent;
|
||||
}
|
||||
queue->percent_changed = FALSE;
|
||||
|
||||
GST_DEBUG_OBJECT (queue, "Going to post buffering: %d%%", percent);
|
||||
msg = gst_message_new_buffering (GST_OBJECT_CAST (queue), percent);
|
||||
|
||||
gst_message_set_buffering_stats (msg, queue->mode, queue->avg_in,
|
||||
queue->avg_out, queue->buffering_left);
|
||||
}
|
||||
|
||||
return msg;
|
||||
|
|
|
@ -119,6 +119,7 @@ struct _GstQueue2
|
|||
/* current buffering state */
|
||||
gboolean is_buffering;
|
||||
gint buffering_percent;
|
||||
gint last_posted_buffering_percent;
|
||||
|
||||
/* for measuring input/output rates */
|
||||
GTimer *in_timer;
|
||||
|
|
Loading…
Reference in a new issue