baseparse: use only upstream duration if it provides one

This commit is contained in:
Mark Nauwelaerts 2010-10-29 14:08:58 +02:00 committed by Tim-Philipp Müller
parent 78ef0387e7
commit 0f9435888a

View file

@ -258,6 +258,7 @@ struct _GstBaseParsePrivate
gboolean own_index; gboolean own_index;
/* seek table entries only maintained if upstream is BYTE seekable */ /* seek table entries only maintained if upstream is BYTE seekable */
gboolean upstream_seekable; gboolean upstream_seekable;
gboolean upstream_has_duration;
/* minimum distance between two index entries */ /* minimum distance between two index entries */
GstClockTimeDiff idx_interval; GstClockTimeDiff idx_interval;
/* ts and offset of last entry added */ /* ts and offset of last entry added */
@ -529,6 +530,7 @@ gst_base_parse_reset (GstBaseParse * parse)
parse->priv->index_last_ts = 0; parse->priv->index_last_ts = 0;
parse->priv->index_last_offset = 0; parse->priv->index_last_offset = 0;
parse->priv->upstream_seekable = FALSE; parse->priv->upstream_seekable = FALSE;
parse->priv->upstream_has_duration = FALSE;
parse->priv->idx_interval = 0; parse->priv->idx_interval = 0;
parse->priv->exact_position = TRUE; parse->priv->exact_position = TRUE;
@ -1298,6 +1300,24 @@ done:
parse->priv->idx_interval = idx_interval * GST_MSECOND; parse->priv->idx_interval = idx_interval * GST_MSECOND;
} }
/* some misc checks on upstream */
static void
gst_base_parse_check_upstream (GstBaseParse * parse)
{
GstFormat fmt = GST_FORMAT_TIME;
gint64 stop;
if (gst_pad_query_peer_duration (parse->sinkpad, &fmt, &stop))
if (GST_CLOCK_TIME_IS_VALID (stop) && stop) {
/* upstream has one, accept it also, and no further updates */
gst_base_parse_set_duration (parse, GST_FORMAT_TIME, stop, 0);
parse->priv->upstream_has_duration = TRUE;
}
GST_DEBUG_OBJECT (parse, "upstream_has_duration: %d",
parse->priv->upstream_has_duration);
}
/** /**
* gst_base_parse_handle_and_push_buffer: * gst_base_parse_handle_and_push_buffer:
* @parse: #GstBaseParse. * @parse: #GstBaseParse.
@ -1323,6 +1343,12 @@ gst_base_parse_handle_and_push_buffer (GstBaseParse * parse,
parse->priv->discont = FALSE; parse->priv->discont = FALSE;
} }
/* some one-time start-up */
if (G_UNLIKELY (!parse->priv->framecount)) {
gst_base_parse_check_seekability (parse);
gst_base_parse_check_upstream (parse);
}
GST_LOG_OBJECT (parse, GST_LOG_OBJECT (parse,
"parsing frame at offset %" G_GUINT64_FORMAT "parsing frame at offset %" G_GUINT64_FORMAT
" (%#" G_GINT64_MODIFIER "x) of size %d", " (%#" G_GINT64_MODIFIER "x) of size %d",
@ -1383,11 +1409,6 @@ gst_base_parse_push_buffer (GstBaseParse * parse, GstBuffer * buffer)
GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (buffer)), GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (buffer)),
GST_TIME_ARGS (GST_BUFFER_DURATION (buffer))); GST_TIME_ARGS (GST_BUFFER_DURATION (buffer)));
/* some one-time start-up */
if (G_UNLIKELY (!parse->priv->framecount)) {
gst_base_parse_check_seekability (parse);
}
/* update stats */ /* update stats */
parse->priv->bytecount += GST_BUFFER_SIZE (buffer); parse->priv->bytecount += GST_BUFFER_SIZE (buffer);
if (!GST_BUFFER_FLAG_IS_SET (buffer, GST_BASE_PARSE_BUFFER_FLAG_NO_FRAME)) { if (!GST_BUFFER_FLAG_IS_SET (buffer, GST_BASE_PARSE_BUFFER_FLAG_NO_FRAME)) {
@ -2386,6 +2407,11 @@ gst_base_parse_set_duration (GstBaseParse * parse,
g_return_if_fail (parse != NULL); g_return_if_fail (parse != NULL);
GST_BASE_PARSE_LOCK (parse); GST_BASE_PARSE_LOCK (parse);
if (parse->priv->upstream_has_duration) {
GST_DEBUG_OBJECT (parse, "using upstream duration; discarding update");
goto exit;
}
if (duration != parse->priv->duration) { if (duration != parse->priv->duration) {
GstMessage *m; GstMessage *m;
@ -2405,6 +2431,7 @@ gst_base_parse_set_duration (GstBaseParse * parse,
} }
GST_DEBUG_OBJECT (parse, "set update interval: %d", interval); GST_DEBUG_OBJECT (parse, "set update interval: %d", interval);
parse->priv->update_interval = interval; parse->priv->update_interval = interval;
exit:
GST_BASE_PARSE_UNLOCK (parse); GST_BASE_PARSE_UNLOCK (parse);
} }