diff options
author | Wim Taymans <wim.taymans@gmail.com> | 2002-06-18 19:17:04 +0000 |
---|---|---|
committer | Wim Taymans <wim.taymans@gmail.com> | 2002-06-18 19:17:04 +0000 |
commit | d9b0cf77a21cab38cad36b2e948a532645ac4a54 (patch) | |
tree | 318ef84f4def46272492fb034a3f71bd2c22bf31 /gst | |
parent | 8b72069ccbc553b9a2f9604ef2469463e28cdf1c (diff) |
Separate the movi processing loop from the index/entry parsing loop
Original commit message from CVS:
Separate the movi processing loop from the index/entry parsing loop
Detect when the index starts from 0 or from the movi chunck offset
Diffstat (limited to 'gst')
-rw-r--r-- | gst/avi/gstavidemux.c | 70 | ||||
-rw-r--r-- | gst/avi/gstavidemux.h | 1 |
2 files changed, 56 insertions, 15 deletions
diff --git a/gst/avi/gstavidemux.c b/gst/avi/gstavidemux.c index 0fec9953..67d42dfa 100644 --- a/gst/avi/gstavidemux.c +++ b/gst/avi/gstavidemux.c @@ -153,6 +153,10 @@ static void gst_avi_demux_init (GstAviDemux *avi_demux); static void gst_avi_demux_loop (GstElement *element); +static gboolean gst_avi_demux_process_chunk (GstAviDemux *avi_demux, guint64 *filepos, + guint32 desired_tag, + gint rec_depth, guint32 *chunksize); + static gboolean gst_avi_demux_send_event (GstElement *element, GstEvent *event); static gboolean gst_avi_demux_handle_src_event (GstPad *pad, GstEvent *event); @@ -231,6 +235,7 @@ gst_avi_demux_init (GstAviDemux *avi_demux) avi_demux->index_entries = NULL; avi_demux->index_size = 0; avi_demux->seek_pending = 0; + avi_demux->restart = FALSE; } @@ -681,6 +686,14 @@ gst_avi_demux_parse_index (GstAviDemux *avi_demux, target->size = entry[i].size; target->offset = entry[i].offset; + /* figure out if the index is 0 based or relative to the MOVI start */ + if (i == 0) { + if (target->offset < filepos) + avi_demux->index_offset = filepos; + else + avi_demux->index_offset = 0; + } + target->bytes_before = stream->total_bytes; target->frames_before = stream->total_frames; @@ -714,7 +727,6 @@ gst_avi_demux_parse_index (GstAviDemux *avi_demux, gst_buffer_unref (buf); end: - avi_demux->index_offset = filepos; GST_DEBUG (GST_CAT_PLUGIN_INFO, "index offset at %08lx", filepos); if (!gst_bytestream_seek (avi_demux->bs, filepos, GST_SEEK_METHOD_SET)) { @@ -1060,14 +1072,6 @@ gst_avi_demux_read_chunk (GstAviDemux *avi_demux, guint32 *id, guint32 *size) GstByteStream *bs = avi_demux->bs; guint32 got_bytes; - if (avi_demux->seek_pending) { - GST_DEBUG (0, "avidemux: seek pending to %lld %08llx", avi_demux->seek_offset, avi_demux->seek_offset); - if (!gst_bytestream_seek (avi_demux->bs, avi_demux->seek_offset, GST_SEEK_METHOD_SET)) { - GST_INFO (GST_CAT_PLUGIN_INFO, "avidemux: could not seek"); - } - avi_demux->seek_pending = FALSE; - } - do { got_bytes = gst_bytestream_peek_bytes (bs, (guint8**)&chunk, sizeof (gst_riff_chunk)); if (got_bytes == sizeof (gst_riff_chunk)) { @@ -1084,6 +1088,36 @@ gst_avi_demux_read_chunk (GstAviDemux *avi_demux, guint32 *id, guint32 *size) } static gboolean +gst_avi_demux_process_movi (GstAviDemux *avi_demux, gint rec_depth, guint64 *filepos) +{ + guint32 subchunksize = 0; + + while (!avi_demux->restart) { /* while not showed all: */ + if (avi_demux->seek_pending) { + GST_DEBUG (0, "avidemux: seek pending to %lld %08llx", avi_demux->seek_offset, avi_demux->seek_offset); + if (!gst_bytestream_seek (avi_demux->bs, avi_demux->seek_offset, GST_SEEK_METHOD_SET)) { + GST_INFO (GST_CAT_PLUGIN_INFO, "avidemux: could not seek"); + } + else { + *filepos = avi_demux->seek_offset; + } + avi_demux->seek_pending = FALSE; + } + + GST_INFO (GST_CAT_PLUGIN_INFO, "process chunk filepos %08llx", *filepos); + /* recurse for subchunks of RIFF and LIST chunks: */ + if (!gst_avi_demux_process_chunk (avi_demux, filepos, 0, + rec_depth + 1, &subchunksize)) { + return FALSE; + } + /* we are running in an infinite loop, we need to _yield + * from time to time */ + gst_element_yield (GST_ELEMENT (avi_demux)); + } + return TRUE; +} + +static gboolean gst_avi_demux_process_chunk (GstAviDemux *avi_demux, guint64 *filepos, guint32 desired_tag, gint rec_depth, guint32 *chunksize) @@ -1133,7 +1167,9 @@ gst_avi_demux_process_chunk (GstAviDemux *avi_demux, guint64 *filepos, } if (avi_demux->avih.bufsize) gst_bytestream_size_hint (avi_demux->bs, avi_demux->avih.bufsize); - break; + + gst_avi_demux_process_movi (avi_demux, rec_depth, filepos); + goto done; default: /* flush the form type */ gst_bytestream_flush_fast (bs, sizeof (guint32)); @@ -1154,6 +1190,8 @@ gst_avi_demux_process_chunk (GstAviDemux *avi_demux, guint64 *filepos, %u %u\n", *filepos, *chunksize, datashowed); return FALSE; } + if (avi_demux->restart) + goto done; subchunksize = ((subchunksize + 1) & ~1); @@ -1261,9 +1299,6 @@ gst_avi_demux_process_chunk (GstAviDemux *avi_demux, guint64 *filepos, } done: - /* we are running in an infinite loop, we need to _yield - * from time to time */ - gst_element_yield (GST_ELEMENT (avi_demux)); return TRUE; } @@ -1280,13 +1315,16 @@ gst_avi_demux_loop (GstElement *element) avi_demux = GST_AVI_DEMUX (element); + avi_demux->restart = FALSE; + /* this is basically an infinite loop */ if (!gst_avi_demux_process_chunk (avi_demux, &filepos, GST_RIFF_TAG_RIFF, 0, &chunksize)) { gst_element_error (element, "This doesn't appear to be an AVI file"); return; } - /* if we exit the loop we are EOS */ - gst_pad_event_default (avi_demux->sinkpad, gst_event_new (GST_EVENT_EOS)); + if (!avi_demux->restart) + /* if we exit the loop we are EOS */ + gst_pad_event_default (avi_demux->sinkpad, gst_event_new (GST_EVENT_EOS)); } static GstElementStateReturn @@ -1299,6 +1337,7 @@ gst_avi_demux_change_state (GstElement *element) break; case GST_STATE_READY_TO_PAUSED: avi_demux->bs = gst_bytestream_new (avi_demux->sinkpad); + avi_demux->last_seek = 0; break; case GST_STATE_PAUSED_TO_PLAYING: break; @@ -1306,6 +1345,7 @@ gst_avi_demux_change_state (GstElement *element) break; case GST_STATE_PAUSED_TO_READY: gst_bytestream_destroy (avi_demux->bs); + avi_demux->restart = TRUE; break; case GST_STATE_READY_TO_NULL: break; diff --git a/gst/avi/gstavidemux.h b/gst/avi/gstavidemux.h index 4323af08..8a5fc6d3 100644 --- a/gst/avi/gstavidemux.h +++ b/gst/avi/gstavidemux.h @@ -108,6 +108,7 @@ struct _GstAviDemux { gboolean seek_pending; gint64 seek_offset; guint64 last_seek; + gboolean restart; }; struct _GstAviDemuxClass { |