mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-27 20:21:24 +00:00
matroska-demux: Don't handle parse errors at the end of file as an error
But only if they happen after the Matroska segment. https://bugzilla.gnome.org/show_bug.cgi?id=735833
This commit is contained in:
parent
4b697df494
commit
a3a5530518
2 changed files with 28 additions and 10 deletions
|
@ -3890,7 +3890,7 @@ gst_matroska_demux_check_read_size (GstMatroskaDemux * demux, guint64 bytes)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* returns TRUE if we truely are in error state, and should give up */
|
/* returns TRUE if we truely are in error state, and should give up */
|
||||||
static inline gboolean
|
static inline GstFlowReturn
|
||||||
gst_matroska_demux_check_parse_error (GstMatroskaDemux * demux)
|
gst_matroska_demux_check_parse_error (GstMatroskaDemux * demux)
|
||||||
{
|
{
|
||||||
if (!demux->streaming && demux->next_cluster_offset > 0) {
|
if (!demux->streaming && demux->next_cluster_offset > 0) {
|
||||||
|
@ -3899,22 +3899,23 @@ gst_matroska_demux_check_parse_error (GstMatroskaDemux * demux)
|
||||||
G_GUINT64_FORMAT, demux->next_cluster_offset);
|
G_GUINT64_FORMAT, demux->next_cluster_offset);
|
||||||
demux->common.offset = demux->next_cluster_offset;
|
demux->common.offset = demux->next_cluster_offset;
|
||||||
demux->next_cluster_offset = 0;
|
demux->next_cluster_offset = 0;
|
||||||
return FALSE;
|
return GST_FLOW_OK;
|
||||||
} else {
|
} else {
|
||||||
gint64 pos;
|
gint64 pos;
|
||||||
|
GstFlowReturn ret;
|
||||||
|
|
||||||
/* sigh, one last attempt above and beyond call of duty ...;
|
/* sigh, one last attempt above and beyond call of duty ...;
|
||||||
* search for cluster mark following current pos */
|
* search for cluster mark following current pos */
|
||||||
pos = demux->common.offset;
|
pos = demux->common.offset;
|
||||||
GST_WARNING_OBJECT (demux, "parse error, looking for next cluster");
|
GST_WARNING_OBJECT (demux, "parse error, looking for next cluster");
|
||||||
if (gst_matroska_demux_search_cluster (demux, &pos) != GST_FLOW_OK) {
|
if ((ret = gst_matroska_demux_search_cluster (demux, &pos)) != GST_FLOW_OK) {
|
||||||
/* did not work, give up */
|
/* did not work, give up */
|
||||||
return TRUE;
|
return ret;
|
||||||
} else {
|
} else {
|
||||||
GST_DEBUG_OBJECT (demux, "... found at %" G_GUINT64_FORMAT, pos);
|
GST_DEBUG_OBJECT (demux, "... found at %" G_GUINT64_FORMAT, pos);
|
||||||
/* try that position */
|
/* try that position */
|
||||||
demux->common.offset = pos;
|
demux->common.offset = pos;
|
||||||
return FALSE;
|
return GST_FLOW_OK;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4113,11 +4114,14 @@ gst_matroska_demux_parse_id (GstMatroskaDemux * demux, guint32 id,
|
||||||
/* eat segment prefix */
|
/* eat segment prefix */
|
||||||
GST_READ_CHECK (gst_matroska_demux_flush (demux, needed));
|
GST_READ_CHECK (gst_matroska_demux_flush (demux, needed));
|
||||||
GST_DEBUG_OBJECT (demux,
|
GST_DEBUG_OBJECT (demux,
|
||||||
"Found Segment start at offset %" G_GUINT64_FORMAT,
|
"Found Segment start at offset %" G_GUINT64_FORMAT " with size %"
|
||||||
demux->common.offset);
|
G_GUINT64_FORMAT, demux->common.offset, length);
|
||||||
/* seeks are from the beginning of the segment,
|
/* seeks are from the beginning of the segment,
|
||||||
* after the segment ID/length */
|
* after the segment ID/length */
|
||||||
demux->common.ebml_segment_start = demux->common.offset;
|
demux->common.ebml_segment_start = demux->common.offset;
|
||||||
|
if (length == 0)
|
||||||
|
length = G_MAXUINT64;
|
||||||
|
demux->common.ebml_segment_length = length;
|
||||||
demux->common.state = GST_MATROSKA_READ_STATE_HEADER;
|
demux->common.state = GST_MATROSKA_READ_STATE_HEADER;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
@ -4385,7 +4389,15 @@ gst_matroska_demux_loop (GstPad * pad)
|
||||||
} else if (ret == GST_FLOW_FLUSHING) {
|
} else if (ret == GST_FLOW_FLUSHING) {
|
||||||
goto pause;
|
goto pause;
|
||||||
} else if (ret != GST_FLOW_OK) {
|
} else if (ret != GST_FLOW_OK) {
|
||||||
if (gst_matroska_demux_check_parse_error (demux))
|
ret = gst_matroska_demux_check_parse_error (demux);
|
||||||
|
|
||||||
|
/* Only handle EOS as no error if we're outside the segment already */
|
||||||
|
if (ret == GST_FLOW_EOS && (demux->common.ebml_segment_length != G_MAXUINT64
|
||||||
|
&& demux->common.offset >=
|
||||||
|
demux->common.ebml_segment_start +
|
||||||
|
demux->common.ebml_segment_length))
|
||||||
|
goto eos;
|
||||||
|
else if (ret != GST_FLOW_OK)
|
||||||
goto pause;
|
goto pause;
|
||||||
else
|
else
|
||||||
return;
|
return;
|
||||||
|
@ -4552,8 +4564,13 @@ next:
|
||||||
|
|
||||||
ret = gst_matroska_read_common_peek_id_length_push (&demux->common,
|
ret = gst_matroska_read_common_peek_id_length_push (&demux->common,
|
||||||
GST_ELEMENT_CAST (demux), &id, &length, &needed);
|
GST_ELEMENT_CAST (demux), &id, &length, &needed);
|
||||||
if (G_UNLIKELY (ret != GST_FLOW_OK && ret != GST_FLOW_EOS))
|
if (G_UNLIKELY (ret != GST_FLOW_OK && ret != GST_FLOW_EOS)) {
|
||||||
|
if (demux->common.ebml_segment_length != G_MAXUINT64
|
||||||
|
&& demux->common.offset >=
|
||||||
|
demux->common.ebml_segment_start + demux->common.ebml_segment_length)
|
||||||
|
ret = GST_FLOW_EOS;
|
||||||
return ret;
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
GST_LOG_OBJECT (demux, "Offset %" G_GUINT64_FORMAT ", Element id 0x%x, "
|
GST_LOG_OBJECT (demux, "Offset %" G_GUINT64_FORMAT ", Element id 0x%x, "
|
||||||
"size %" G_GUINT64_FORMAT ", needed %d, available %d",
|
"size %" G_GUINT64_FORMAT ", needed %d, available %d",
|
||||||
|
|
|
@ -76,8 +76,9 @@ typedef struct _GstMatroskaReadCommon {
|
||||||
GstToc *toc;
|
GstToc *toc;
|
||||||
gboolean toc_updated;
|
gboolean toc_updated;
|
||||||
|
|
||||||
/* start-of-segment */
|
/* start-of-segment and length */
|
||||||
guint64 ebml_segment_start;
|
guint64 ebml_segment_start;
|
||||||
|
guint64 ebml_segment_length;
|
||||||
|
|
||||||
/* a cue (index) table */
|
/* a cue (index) table */
|
||||||
GArray *index;
|
GArray *index;
|
||||||
|
|
Loading…
Reference in a new issue