summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSeungha Yang <sh.yang@lge.com>2016-01-28 21:36:54 +0900
committerSebastian Dröge <sebastian@centricular.com>2016-01-29 10:53:39 +0100
commitd8bb6687ea251570c331038279a43d448167d6ad (patch)
tree1b8916b5a4fb204547a9ed9473df0120d7d155b1
parent3edf0737d69a58beecb977817c897e4b718e1f04 (diff)
downloadgstreamer-plugins-good-d8bb6687ea251570c331038279a43d448167d6ad.tar.gz
qtdemux: expose streams with first moof for fragmented format
In case of push mode, qtdemux expose streams after got moov box. We can not guarantee that a moov box has sample data such as sample duration and the number of sample in stbl box for fragmented format case. So, if a moov has no sample data, streams will not be exposed until get the first moof. https://bugzilla.gnome.org/show_bug.cgi?id=760779
-rw-r--r--gst/isomp4/qtdemux.c54
-rw-r--r--gst/isomp4/qtdemux.h1
2 files changed, 39 insertions, 16 deletions
diff --git a/gst/isomp4/qtdemux.c b/gst/isomp4/qtdemux.c
index 1aaafa861..cbba39bc8 100644
--- a/gst/isomp4/qtdemux.c
+++ b/gst/isomp4/qtdemux.c
@@ -583,6 +583,7 @@ gst_qtdemux_init (GstQTDemux * qtdemux)
qtdemux->state = QTDEMUX_STATE_INITIAL;
qtdemux->pullbased = FALSE;
qtdemux->posted_redirect = FALSE;
+ qtdemux->pending_configure = FALSE;
qtdemux->neededbytes = 16;
qtdemux->todrop = 0;
qtdemux->adapter = gst_adapter_new ();
@@ -1983,6 +1984,7 @@ gst_qtdemux_reset (GstQTDemux * qtdemux, gboolean hard)
gst_caps_replace (&qtdemux->media_caps, NULL);
qtdemux->timescale = 0;
qtdemux->got_moov = FALSE;
+ qtdemux->pending_configure = FALSE;
} else if (qtdemux->mss_mode) {
gst_flow_combiner_reset (qtdemux->flowcombiner);
for (n = 0; n < qtdemux->n_streams; n++)
@@ -5778,6 +5780,7 @@ gst_qtdemux_process_adapter (GstQTDemux * demux, gboolean force)
&fourcc);
if (fourcc == FOURCC_moov) {
gint n;
+ gboolean got_samples = FALSE;
/* in usual fragmented setup we could try to scan for more
* and end up at the the moov (after mdat) again */
@@ -5809,19 +5812,27 @@ gst_qtdemux_process_adapter (GstQTDemux * demux, gboolean force)
qtdemux_node_dump (demux, demux->moov_node);
qtdemux_parse_tree (demux);
qtdemux_prepare_streams (demux);
- if (!demux->got_moov)
- qtdemux_expose_streams (demux);
- else {
- for (n = 0; n < demux->n_streams; n++) {
- QtDemuxStream *stream = demux->streams[n];
-
- gst_qtdemux_configure_stream (demux, stream);
+ for (n = 0; n < demux->n_streams; n++) {
+ QtDemuxStream *stream = demux->streams[n];
+ got_samples |= stream->stbl_index >= 0;
+ }
+ if (!demux->fragmented || got_samples) {
+ if (!demux->got_moov) {
+ qtdemux_expose_streams (demux);
+ } else {
+ for (n = 0; n < demux->n_streams; n++) {
+ QtDemuxStream *stream = demux->streams[n];
+ gst_qtdemux_configure_stream (demux, stream);
+ }
}
+ gst_qtdemux_check_send_pending_segment (demux);
+ demux->pending_configure = FALSE;
+ } else {
+ demux->pending_configure = TRUE;
}
demux->got_moov = TRUE;
- gst_qtdemux_check_send_pending_segment (demux);
/* fragmented streams headers shouldn't contain edts atoms */
if (!demux->fragmented) {
@@ -5840,6 +5851,7 @@ gst_qtdemux_process_adapter (GstQTDemux * demux, gboolean force)
guint64 dist = 0;
GstClockTime prev_pts;
guint64 prev_offset;
+ gint n;
GST_DEBUG_OBJECT (demux, "Parsing [moof]");
@@ -5873,15 +5885,25 @@ gst_qtdemux_process_adapter (GstQTDemux * demux, gboolean force)
ret = GST_FLOW_ERROR;
goto done;
}
- /* in MSS we need to expose the pads after the first moof as we won't get a moov */
- if (demux->mss_mode && !demux->exposed) {
- if (!demux->pending_newsegment) {
- GstSegment segment;
- gst_segment_init (&segment, GST_FORMAT_TIME);
- GST_DEBUG_OBJECT (demux, "new pending_newsegment");
- demux->pending_newsegment = gst_event_new_segment (&segment);
+ /* in MSS we need to expose the pads after the first moof as we won't get a moov
+ * Also, fragmented format need to be exposed if a moov have no valid sample data */
+ if (demux->mss_mode || demux->pending_configure) {
+ if (!demux->exposed) {
+ if (!demux->pending_newsegment) {
+ GstSegment segment;
+ gst_segment_init (&segment, GST_FORMAT_TIME);
+ GST_DEBUG_OBJECT (demux, "new pending_newsegment");
+ demux->pending_newsegment = gst_event_new_segment (&segment);
+ }
+ qtdemux_expose_streams (demux);
+ } else {
+ for (n = 0; n < demux->n_streams; n++) {
+ QtDemuxStream *stream = demux->streams[n];
+ gst_qtdemux_configure_stream (demux, stream);
+ }
}
- qtdemux_expose_streams (demux);
+ gst_qtdemux_check_send_pending_segment (demux);
+ demux->pending_configure = FALSE;
}
} else {
GST_DEBUG_OBJECT (demux, "Discarding [moof]");
diff --git a/gst/isomp4/qtdemux.h b/gst/isomp4/qtdemux.h
index 53bd071c3..165435cea 100644
--- a/gst/isomp4/qtdemux.h
+++ b/gst/isomp4/qtdemux.h
@@ -89,6 +89,7 @@ struct _GstQTDemux {
gboolean posted_redirect;
/* push based variables */
+ gboolean pending_configure;
guint neededbytes;
guint todrop;
GstAdapter *adapter;