/* GStreamer
 * Copyright (C) <1999> Erik Walthinsen <omega@cse.ogi.edu>
 * Copyright (C) <2003> David A. Schleef <ds@schleef.org>
 * Copyright (C) <2006> Wim Taymans <wim@fluendo.com>
 * Copyright (C) <2007> Julien Moutte <julien@fluendo.com>
 * Copyright (C) <2009> Tim-Philipp Müller <tim centricular net>
 * Copyright (C) <2009> STEricsson <benjamin.gaignard@stericsson.com>
 * Copyright (C) <2013> Sreerenj Balachandran <sreerenj.balachandran@intel.com>
 * Copyright (C) <2013> Intel Corporation
 * Copyright (C) <2014> Centricular Ltd
 * Copyright (C) <2015> YouView TV Ltd.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this library; if not, write to the
 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */

/**
 * SECTION:element-qtdemux
 *
 * Demuxes a .mov file into raw or compressed audio and/or video streams.
 *
 * This element supports both push and pull-based scheduling, depending on the
 * capabilities of the upstream elements.
 *
 * <refsect2>
 * <title>Example launch line</title>
 * |[
 * gst-launch-1.0 filesrc location=test.mov ! qtdemux name=demux  demux.audio_0 ! queue ! decodebin ! audioconvert ! audioresample ! autoaudiosink   demux.video_0 ! queue ! decodebin ! videoconvert ! videoscale ! autovideosink
 * ]| Play (parse and decode) a .mov file and try to output it to
 * an automatically detected soundcard and videosink. If the MOV file contains
 * compressed audio or video data, this will only work if you have the
 * right decoder elements/plugins installed.
 * </refsect2>
 */

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include "gst/gst-i18n-plugin.h"

#include <glib/gprintf.h>
#include <gst/tag/tag.h>
#include <gst/audio/audio.h>
#include <gst/video/video.h>

#include "qtatomparser.h"
#include "qtdemux_types.h"
#include "qtdemux_dump.h"
#include "fourcc.h"
#include "descriptors.h"
#include "qtdemux_lang.h"
#include "qtdemux.h"
#include "qtpalette.h"

#include "gst/riff/riff-media.h"
#include "gst/riff/riff-read.h"

#include <gst/pbutils/pbutils.h>

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <math.h>
#include <gst/math-compat.h>

#ifdef HAVE_ZLIB
# include <zlib.h>
#endif

/* max. size considered 'sane' for non-mdat atoms */
#define QTDEMUX_MAX_ATOM_SIZE (25*1024*1024)

/* if the sample index is larger than this, something is likely wrong */
#define QTDEMUX_MAX_SAMPLE_INDEX_SIZE (50*1024*1024)

/* For converting qt creation times to unix epoch times */
#define QTDEMUX_SECONDS_PER_DAY (60 * 60 * 24)
#define QTDEMUX_LEAP_YEARS_FROM_1904_TO_1970 17
#define QTDEMUX_SECONDS_FROM_1904_TO_1970 (((1970 - 1904) * (guint64) 365 + \
    QTDEMUX_LEAP_YEARS_FROM_1904_TO_1970) * QTDEMUX_SECONDS_PER_DAY)

#define STREAM_IS_EOS(s) (s->time_position == GST_CLOCK_TIME_NONE)

GST_DEBUG_CATEGORY (qtdemux_debug);

/*typedef struct _QtNode QtNode; */
typedef struct _QtDemuxSegment QtDemuxSegment;
typedef struct _QtDemuxSample QtDemuxSample;

typedef struct _QtDemuxCencSampleSetInfo QtDemuxCencSampleSetInfo;

/*struct _QtNode
{
  guint32 type;
  guint8 *data;
  gint len;
};*/

struct _QtDemuxSample
{
  guint32 size;
  gint32 pts_offset;            /* Add this value to timestamp to get the pts */
  guint64 offset;
  guint64 timestamp;            /* DTS In mov time */
  guint32 duration;             /* In mov time */
  gboolean keyframe;            /* TRUE when this packet is a keyframe */
};

/* Macros for converting to/from timescale */
#define QTSTREAMTIME_TO_GSTTIME(stream, value) (gst_util_uint64_scale((value), GST_SECOND, (stream)->timescale))
#define GSTTIME_TO_QTSTREAMTIME(stream, value) (gst_util_uint64_scale((value), (stream)->timescale, GST_SECOND))

#define QTTIME_TO_GSTTIME(qtdemux, value) (gst_util_uint64_scale((value), GST_SECOND, (qtdemux)->timescale))
#define GSTTIME_TO_QTTIME(qtdemux, value) (gst_util_uint64_scale((value), (qtdemux)->timescale, GST_SECOND))

/* timestamp is the DTS */
#define QTSAMPLE_DTS(stream,sample) (QTSTREAMTIME_TO_GSTTIME((stream), (sample)->timestamp))
/* timestamp + offset is the PTS */
#define QTSAMPLE_PTS(stream,sample) (QTSTREAMTIME_TO_GSTTIME((stream), (sample)->timestamp + (stream)->cslg_shift + (sample)->pts_offset))
/* timestamp + duration - dts is the duration */
#define QTSAMPLE_DUR_DTS(stream, sample, dts) (QTSTREAMTIME_TO_GSTTIME ((stream), (sample)->timestamp + (sample)->duration) - (dts))

#define QTSAMPLE_KEYFRAME(stream,sample) ((stream)->all_keyframe || (sample)->keyframe)

/*
 * Quicktime has tracks and segments. A track is a continuous piece of
 * multimedia content. The track is not always played from start to finish but
 * instead, pieces of the track are 'cut out' and played in sequence. This is
 * what the segments do.
 *
 * Inside the track we have keyframes (K) and delta frames. The track has its
 * own timing, which starts from 0 and extends to end. The position in the track
 * is called the media_time.
 *
 * The segments now describe the pieces that should be played from this track
 * and are basically tuples of media_time/duration/rate entries. We can have
 * multiple segments and they are all played after one another. An example:
 *
 * segment 1: media_time: 1 second, duration: 1 second, rate 1
 * segment 2: media_time: 3 second, duration: 2 second, rate 2
 *
 * To correctly play back this track, one must play: 1 second of media starting
 * from media_time 1 followed by 2 seconds of media starting from media_time 3
 * at a rate of 2.
 *
 * Each of the segments will be played at a specific time, the first segment at
 * time 0, the second one after the duration of the first one, etc.. Note that
 * the time in resulting playback is not identical to the media_time of the
 * track anymore.
 *
 * Visually, assuming the track has 4 second of media_time:
 *
 *                (a)                   (b)          (c)              (d)
 *         .-----------------------------------------------------------.
 * track:  | K.....K.........K........K.......K.......K...........K... |
 *         '-----------------------------------------------------------'
 *         0              1              2              3              4
 *           .------------^              ^   .----------^              ^
 *          /              .-------------'  /       .------------------'
 *         /              /          .-----'       /
 *         .--------------.         .--------------.
 *         | segment 1    |         | segment 2    |
 *         '--------------'         '--------------'
 *
 * The challenge here is to cut out the right pieces of the track for each of
 * the playback segments. This fortunately can easily be done with the SEGMENT
 * events of GStreamer.
 *
 * For playback of segment 1, we need to provide the decoder with the keyframe
 * (a), in the above figure, but we must instruct it only to output the decoded
 * data between second 1 and 2. We do this with a SEGMENT event for 1 to 2, time
 * position set to the time of the segment: 0.
 *
 * We then proceed to push data from keyframe (a) to frame (b). The decoder
 * decodes but clips all before media_time 1.
 *
 * After finishing a segment, we push out a new SEGMENT event with the clipping
 * boundaries of the new data.
 *
 * This is a good usecase for the GStreamer accumulated SEGMENT events.
 */

struct _QtDemuxSegment
{
  /* global time and duration, all gst time */
  GstClockTime time;
  GstClockTime stop_time;
  GstClockTime duration;
  /* media time of trak, all gst time */
  GstClockTime media_start;
  GstClockTime media_stop;
  gdouble rate;
  /* Media start time in trak timescale units */
  guint32 trak_media_start;
};

#define QTSEGMENT_IS_EMPTY(s) ((s)->media_start == GST_CLOCK_TIME_NONE)

/* Used with fragmented MP4 files (mfra atom) */
typedef struct
{
  GstClockTime ts;
  guint64 moof_offset;
} QtDemuxRandomAccessEntry;

struct _QtDemuxStream
{
  GstPad *pad;

  /* stream type */
  guint32 subtype;
  GstCaps *caps;
  guint32 fourcc;
  gboolean sparse;

  gboolean new_caps;
  gboolean new_stream;          /* signals that a stream_start is required */
  gboolean on_keyframe;         /* if this stream last pushed buffer was a
                                 * keyframe. This is important to identify
                                 * where to stop pushing buffers after a
                                 * segment stop time */

  /* if the stream has a redirect URI in its headers, we store it here */
  gchar *redirect_uri;

  /* track id */
  guint track_id;

  /* duration/scale */
  guint64 duration;             /* in timescale */
  guint32 timescale;

  /* language */
  gchar lang_id[4];             /* ISO 639-2T language code */

  /* our samples */
  guint32 n_samples;
  QtDemuxSample *samples;
  gboolean all_keyframe;        /* TRUE when all samples are keyframes (no stss) */
  guint32 first_duration;       /* duration in timescale of first sample, used for figuring out
                                   the framerate, in timescale units */
  guint32 n_samples_moof;       /* sample count in a moof */
  guint64 duration_moof;        /* duration in timescale of a moof, used for figure out
                                 * the framerate of fragmented format stream */
  guint32 offset_in_sample;
  guint32 max_buffer_size;

  /* if we use chunks or samples */
  gboolean sampled;
  guint padding;

  /* video info */
  gint width;
  gint height;
  /* aspect ratio */
  gint display_width;
  gint display_height;
  gint par_w;
  gint par_h;
  /* Numerator/denominator framerate */
  gint fps_n;
  gint fps_d;
  guint16 bits_per_sample;
  guint16 color_table_id;
  GstMemory *rgb8_palette;

  /* audio info */
  gdouble rate;
  gint n_channels;
  guint samples_per_packet;
  guint samples_per_frame;
  guint bytes_per_packet;
  guint bytes_per_sample;
  guint bytes_per_frame;
  guint compression;

  /* allocation */
  gboolean use_allocator;
  GstAllocator *allocator;
  GstAllocationParams params;

  /* when a discontinuity is pending */
  gboolean discont;

  /* list of buffers to push first */
  GSList *buffers;

  /* if we need to clip this buffer. This is only needed for uncompressed
   * data */
  gboolean need_clip;

  /* buffer needs some custom processing, e.g. subtitles */
  gboolean need_process;

  /* current position */
  guint32 segment_index;
  guint32 sample_index;
  GstClockTime time_position;   /* in gst time */
  guint64 accumulated_base;

  /* the Gst segment we are processing out, used for clipping */
  GstSegment segment;

  /* quicktime segments */
  guint32 n_segments;
  QtDemuxSegment *segments;
  gboolean dummy_segment;
  guint32 from_sample;
  guint32 to_sample;

  gboolean sent_eos;
  GstTagList *pending_tags;
  gboolean send_global_tags;

  GstEvent *pending_event;

  GstByteReader stco;
  GstByteReader stsz;
  GstByteReader stsc;
  GstByteReader stts;
  GstByteReader stss;
  GstByteReader stps;
  GstByteReader ctts;

  gboolean chunks_are_samples;  /* TRUE means treat chunks as samples */
  gint64 stbl_index;
  /* stco */
  guint co_size;
  GstByteReader co_chunk;
  guint32 first_chunk;
  guint32 current_chunk;
  guint32 last_chunk;
  guint32 samples_per_chunk;
  guint32 stco_sample_index;
  /* stsz */
  guint32 sample_size;          /* 0 means variable sizes are stored in stsz */
  /* stsc */
  guint32 stsc_index;
  guint32 n_samples_per_chunk;
  guint32 stsc_chunk_index;
  guint32 stsc_sample_index;
  guint64 chunk_offset;
  /* stts */
  guint32 stts_index;
  guint32 stts_samples;
  guint32 n_sample_times;
  guint32 stts_sample_index;
  guint64 stts_time;
  guint32 stts_duration;
  /* stss */
  gboolean stss_present;
  guint32 n_sample_syncs;
  guint32 stss_index;
  /* stps */
  gboolean stps_present;
  guint32 n_sample_partial_syncs;
  guint32 stps_index;
  QtDemuxRandomAccessEntry *ra_entries;
  guint n_ra_entries;

  const QtDemuxRandomAccessEntry *pending_seek;

  /* ctts */
  gboolean ctts_present;
  guint32 n_composition_times;
  guint32 ctts_index;
  guint32 ctts_sample_index;
  guint32 ctts_count;
  gint32 ctts_soffset;

  /* cslg */
  guint32 cslg_shift;

  /* fragmented */
  gboolean parsed_trex;
  guint32 def_sample_duration;
  guint32 def_sample_size;
  guint32 def_sample_flags;

  gboolean disabled;

  /* stereoscopic video streams */
  GstVideoMultiviewMode multiview_mode;
  GstVideoMultiviewFlags multiview_flags;

  /* protected streams */
  gboolean protected;
  guint32 protection_scheme_type;
  guint32 protection_scheme_version;
  gpointer protection_scheme_info;      /* specific to the protection scheme */
  GQueue protection_scheme_event_queue;
};

/* Contains properties and cryptographic info for a set of samples from a
 * track protected using Common Encryption (cenc) */
struct _QtDemuxCencSampleSetInfo
{
  GstStructure *default_properties;

  /* @crypto_info holds one GstStructure per sample */
  GPtrArray *crypto_info;
};

enum QtDemuxState
{
  QTDEMUX_STATE_INITIAL,        /* Initial state (haven't got the header yet) */
  QTDEMUX_STATE_HEADER,         /* Parsing the header */
  QTDEMUX_STATE_MOVIE,          /* Parsing/Playing the media data */
  QTDEMUX_STATE_BUFFER_MDAT     /* Buffering the mdat atom */
};

static GNode *qtdemux_tree_get_child_by_type (GNode * node, guint32 fourcc);
static GNode *qtdemux_tree_get_child_by_type_full (GNode * node,
    guint32 fourcc, GstByteReader * parser);
static GNode *qtdemux_tree_get_sibling_by_type (GNode * node, guint32 fourcc);
static GNode *qtdemux_tree_get_sibling_by_type_full (GNode * node,
    guint32 fourcc, GstByteReader * parser);

static GstFlowReturn qtdemux_add_fragmented_samples (GstQTDemux * qtdemux);

static GstStaticPadTemplate gst_qtdemux_sink_template =
    GST_STATIC_PAD_TEMPLATE ("sink",
    GST_PAD_SINK,
    GST_PAD_ALWAYS,
    GST_STATIC_CAPS ("video/quicktime; video/mj2; audio/x-m4a; "
        "application/x-3gp")
    );

static GstStaticPadTemplate gst_qtdemux_videosrc_template =
GST_STATIC_PAD_TEMPLATE ("video_%u",
    GST_PAD_SRC,
    GST_PAD_SOMETIMES,
    GST_STATIC_CAPS_ANY);

static GstStaticPadTemplate gst_qtdemux_audiosrc_template =
GST_STATIC_PAD_TEMPLATE ("audio_%u",
    GST_PAD_SRC,
    GST_PAD_SOMETIMES,
    GST_STATIC_CAPS_ANY);

static GstStaticPadTemplate gst_qtdemux_subsrc_template =
GST_STATIC_PAD_TEMPLATE ("subtitle_%u",
    GST_PAD_SRC,
    GST_PAD_SOMETIMES,
    GST_STATIC_CAPS_ANY);

#define gst_qtdemux_parent_class parent_class
G_DEFINE_TYPE (GstQTDemux, gst_qtdemux, GST_TYPE_ELEMENT);

static void gst_qtdemux_dispose (GObject * object);

static guint32
gst_qtdemux_find_index_linear (GstQTDemux * qtdemux, QtDemuxStream * str,
    GstClockTime media_time);
static guint32
gst_qtdemux_find_index_for_given_media_offset_linear (GstQTDemux * qtdemux,
    QtDemuxStream * str, gint64 media_offset);

#if 0
static void gst_qtdemux_set_index (GstElement * element, GstIndex * index);
static GstIndex *gst_qtdemux_get_index (GstElement * element);
#endif
static GstStateChangeReturn gst_qtdemux_change_state (GstElement * element,
    GstStateChange transition);
static gboolean qtdemux_sink_activate (GstPad * sinkpad, GstObject * parent);
static gboolean qtdemux_sink_activate_mode (GstPad * sinkpad,
    GstObject * parent, GstPadMode mode, gboolean active);

static void gst_qtdemux_loop (GstPad * pad);
static GstFlowReturn gst_qtdemux_chain (GstPad * sinkpad, GstObject * parent,
    GstBuffer * inbuf);
static gboolean gst_qtdemux_handle_sink_event (GstPad * pad, GstObject * parent,
    GstEvent * event);
static gboolean gst_qtdemux_setcaps (GstQTDemux * qtdemux, GstCaps * caps);
static gboolean gst_qtdemux_configure_stream (GstQTDemux * qtdemux,
    QtDemuxStream * stream);
static GstFlowReturn gst_qtdemux_process_adapter (GstQTDemux * demux,
    gboolean force);

static gboolean qtdemux_parse_moov (GstQTDemux * qtdemux,
    const guint8 * buffer, guint length);
static gboolean qtdemux_parse_node (GstQTDemux * qtdemux, GNode * node,
    const guint8 * buffer, guint length);
static gboolean qtdemux_parse_tree (GstQTDemux * qtdemux);
static void qtdemux_parse_udta (GstQTDemux * qtdemux, GstTagList * taglist,
    GNode * udta);

static void gst_qtdemux_handle_esds (GstQTDemux * qtdemux,
    QtDemuxStream * stream, GNode * esds, GstTagList * list);
static GstCaps *qtdemux_video_caps (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 fourcc, const guint8 * stsd_data,
    gchar ** codec_name);
static GstCaps *qtdemux_audio_caps (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 fourcc, const guint8 * data, int len,
    gchar ** codec_name);
static GstCaps *qtdemux_sub_caps (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 fourcc, const guint8 * data,
    gchar ** codec_name);
static GstCaps *qtdemux_generic_caps (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 fourcc, const guint8 * stsd_data,
    gchar ** codec_name);

static gboolean qtdemux_parse_samples (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 n);
static GstFlowReturn qtdemux_expose_streams (GstQTDemux * qtdemux);
static void gst_qtdemux_stream_free (GstQTDemux * qtdemux,
    QtDemuxStream * stream);
static void gst_qtdemux_stream_clear (GstQTDemux * qtdemux,
    QtDemuxStream * stream);
static void gst_qtdemux_remove_stream (GstQTDemux * qtdemux, int index);
static GstFlowReturn qtdemux_prepare_streams (GstQTDemux * qtdemux);
static void qtdemux_do_allocation (GstQTDemux * qtdemux,
    QtDemuxStream * stream);
static gboolean gst_qtdemux_activate_segment (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 seg_idx, GstClockTime offset);
static gboolean gst_qtdemux_stream_update_segment (GstQTDemux * qtdemux,
    QtDemuxStream * stream, gint seg_idx, GstClockTime offset,
    GstClockTime * _start, GstClockTime * _stop);

static gboolean qtdemux_pull_mfro_mfra (GstQTDemux * qtdemux);
static void check_update_duration (GstQTDemux * qtdemux, GstClockTime duration);

static void gst_qtdemux_append_protection_system_id (GstQTDemux * qtdemux,
    const gchar * id);

static void
gst_qtdemux_class_init (GstQTDemuxClass * klass)
{
  GObjectClass *gobject_class;
  GstElementClass *gstelement_class;

  gobject_class = (GObjectClass *) klass;
  gstelement_class = (GstElementClass *) klass;

  parent_class = g_type_class_peek_parent (klass);

  gobject_class->dispose = gst_qtdemux_dispose;

  gstelement_class->change_state = GST_DEBUG_FUNCPTR (gst_qtdemux_change_state);
#if 0
  gstelement_class->set_index = GST_DEBUG_FUNCPTR (gst_qtdemux_set_index);
  gstelement_class->get_index = GST_DEBUG_FUNCPTR (gst_qtdemux_get_index);
#endif

  gst_tag_register_musicbrainz_tags ();

  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&gst_qtdemux_sink_template));
  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&gst_qtdemux_videosrc_template));
  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&gst_qtdemux_audiosrc_template));
  gst_element_class_add_pad_template (gstelement_class,
      gst_static_pad_template_get (&gst_qtdemux_subsrc_template));
  gst_element_class_set_static_metadata (gstelement_class, "QuickTime demuxer",
      "Codec/Demuxer",
      "Demultiplex a QuickTime file into audio and video streams",
      "David Schleef <ds@schleef.org>, Wim Taymans <wim@fluendo.com>");

  GST_DEBUG_CATEGORY_INIT (qtdemux_debug, "qtdemux", 0, "qtdemux plugin");

}

static void
gst_qtdemux_init (GstQTDemux * qtdemux)
{
  qtdemux->sinkpad =
      gst_pad_new_from_static_template (&gst_qtdemux_sink_template, "sink");
  gst_pad_set_activate_function (qtdemux->sinkpad, qtdemux_sink_activate);
  gst_pad_set_activatemode_function (qtdemux->sinkpad,
      qtdemux_sink_activate_mode);
  gst_pad_set_chain_function (qtdemux->sinkpad, gst_qtdemux_chain);
  gst_pad_set_event_function (qtdemux->sinkpad, gst_qtdemux_handle_sink_event);
  gst_element_add_pad (GST_ELEMENT_CAST (qtdemux), qtdemux->sinkpad);

  qtdemux->state = QTDEMUX_STATE_INITIAL;
  qtdemux->pullbased = FALSE;
  qtdemux->posted_redirect = FALSE;
  qtdemux->neededbytes = 16;
  qtdemux->todrop = 0;
  qtdemux->adapter = gst_adapter_new ();
  qtdemux->offset = 0;
  qtdemux->first_mdat = -1;
  qtdemux->got_moov = FALSE;
  qtdemux->mdatoffset = -1;
  qtdemux->mdatbuffer = NULL;
  qtdemux->restoredata_buffer = NULL;
  qtdemux->restoredata_offset = -1;
  qtdemux->fragment_start = -1;
  qtdemux->fragment_start_offset = -1;
  qtdemux->media_caps = NULL;
  qtdemux->exposed = FALSE;
  qtdemux->mss_mode = FALSE;
  qtdemux->pending_newsegment = NULL;
  qtdemux->upstream_format_is_time = FALSE;
  qtdemux->have_group_id = FALSE;
  qtdemux->group_id = G_MAXUINT;
  qtdemux->cenc_aux_info_offset = 0;
  qtdemux->cenc_aux_info_sizes = NULL;
  qtdemux->cenc_aux_sample_count = 0;
  qtdemux->protection_system_ids = NULL;
  g_queue_init (&qtdemux->protection_event_queue);
  gst_segment_init (&qtdemux->segment, GST_FORMAT_TIME);
  qtdemux->flowcombiner = gst_flow_combiner_new ();

  GST_OBJECT_FLAG_SET (qtdemux, GST_ELEMENT_FLAG_INDEXABLE);
}

static void
gst_qtdemux_dispose (GObject * object)
{
  GstQTDemux *qtdemux = GST_QTDEMUX (object);

  if (qtdemux->adapter) {
    g_object_unref (G_OBJECT (qtdemux->adapter));
    qtdemux->adapter = NULL;
  }
  gst_flow_combiner_free (qtdemux->flowcombiner);
  g_queue_foreach (&qtdemux->protection_event_queue, (GFunc) gst_event_unref,
      NULL);
  g_queue_clear (&qtdemux->protection_event_queue);

  g_free (qtdemux->cenc_aux_info_sizes);
  qtdemux->cenc_aux_info_sizes = NULL;

  G_OBJECT_CLASS (parent_class)->dispose (object);
}

static void
gst_qtdemux_post_no_playable_stream_error (GstQTDemux * qtdemux)
{
  if (qtdemux->posted_redirect) {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file contains no playable streams.")),
        ("no known streams found, a redirect message has been posted"));
  } else {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file contains no playable streams.")),
        ("no known streams found"));
  }
}

static GstBuffer *
_gst_buffer_new_wrapped (gpointer mem, gsize size, GFreeFunc free_func)
{
  return gst_buffer_new_wrapped_full (free_func ? 0 : GST_MEMORY_FLAG_READONLY,
      mem, size, 0, size, mem, free_func);
}

static GstFlowReturn
gst_qtdemux_pull_atom (GstQTDemux * qtdemux, guint64 offset, guint64 size,
    GstBuffer ** buf)
{
  GstFlowReturn flow;
  GstMapInfo map;
  gsize bsize;

  if (G_UNLIKELY (size == 0)) {
    GstFlowReturn ret;
    GstBuffer *tmp = NULL;

    ret = gst_qtdemux_pull_atom (qtdemux, offset, sizeof (guint32), &tmp);
    if (ret != GST_FLOW_OK)
      return ret;

    gst_buffer_map (tmp, &map, GST_MAP_READ);
    size = QT_UINT32 (map.data);
    GST_DEBUG_OBJECT (qtdemux, "size 0x%08" G_GINT64_MODIFIER "x", size);

    gst_buffer_unmap (tmp, &map);
    gst_buffer_unref (tmp);
  }

  /* Sanity check: catch bogus sizes (fuzzed/broken files) */
  if (G_UNLIKELY (size > QTDEMUX_MAX_ATOM_SIZE)) {
    if (qtdemux->state != QTDEMUX_STATE_MOVIE && qtdemux->got_moov) {
      /* we're pulling header but already got most interesting bits,
       * so never mind the rest (e.g. tags) (that much) */
      GST_WARNING_OBJECT (qtdemux, "atom has bogus size %" G_GUINT64_FORMAT,
          size);
      return GST_FLOW_EOS;
    } else {
      GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
          (_("This file is invalid and cannot be played.")),
          ("atom has bogus size %" G_GUINT64_FORMAT, size));
      return GST_FLOW_ERROR;
    }
  }

  flow = gst_pad_pull_range (qtdemux->sinkpad, offset, size, buf);

  if (G_UNLIKELY (flow != GST_FLOW_OK))
    return flow;

  bsize = gst_buffer_get_size (*buf);
  /* Catch short reads - we don't want any partial atoms */
  if (G_UNLIKELY (bsize < size)) {
    GST_WARNING_OBJECT (qtdemux,
        "short read: %" G_GSIZE_FORMAT " < %" G_GUINT64_FORMAT, bsize, size);
    gst_buffer_unref (*buf);
    *buf = NULL;
    return GST_FLOW_EOS;
  }

  return flow;
}

#if 1
static gboolean
gst_qtdemux_src_convert (GstQTDemux * qtdemux, GstPad * pad,
    GstFormat src_format, gint64 src_value, GstFormat dest_format,
    gint64 * dest_value)
{
  gboolean res = TRUE;
  QtDemuxStream *stream = gst_pad_get_element_private (pad);
  gint32 index;

  if (stream->subtype != FOURCC_vide) {
    res = FALSE;
    goto done;
  }

  switch (src_format) {
    case GST_FORMAT_TIME:
      switch (dest_format) {
        case GST_FORMAT_BYTES:{
          index = gst_qtdemux_find_index_linear (qtdemux, stream, src_value);
          if (-1 == index) {
            res = FALSE;
            goto done;
          }

          *dest_value = stream->samples[index].offset;

          GST_DEBUG_OBJECT (qtdemux, "Format Conversion Time->Offset :%"
              GST_TIME_FORMAT "->%" G_GUINT64_FORMAT,
              GST_TIME_ARGS (src_value), *dest_value);
          break;
        }
        default:
          res = FALSE;
          break;
      }
      break;
    case GST_FORMAT_BYTES:
      switch (dest_format) {
        case GST_FORMAT_TIME:{
          index =
              gst_qtdemux_find_index_for_given_media_offset_linear (qtdemux,
              stream, src_value);

          if (-1 == index) {
            res = FALSE;
            goto done;
          }

          *dest_value =
              QTSTREAMTIME_TO_GSTTIME (stream,
              stream->samples[index].timestamp);
          GST_DEBUG_OBJECT (qtdemux,
              "Format Conversion Offset->Time :%" G_GUINT64_FORMAT "->%"
              GST_TIME_FORMAT, src_value, GST_TIME_ARGS (*dest_value));
          break;
        }
        default:
          res = FALSE;
          break;
      }
      break;
    default:
      res = FALSE;
      break;
  }

done:
  return res;
}
#endif

static gboolean
gst_qtdemux_get_duration (GstQTDemux * qtdemux, GstClockTime * duration)
{
  gboolean res = TRUE;

  *duration = GST_CLOCK_TIME_NONE;

  if (qtdemux->duration != 0) {
    if (qtdemux->duration != G_MAXINT64 && qtdemux->timescale != 0) {
      *duration = QTTIME_TO_GSTTIME (qtdemux, qtdemux->duration);
    }
  }
  return res;
}

static gboolean
gst_qtdemux_handle_src_query (GstPad * pad, GstObject * parent,
    GstQuery * query)
{
  gboolean res = FALSE;
  GstQTDemux *qtdemux = GST_QTDEMUX (parent);

  GST_LOG_OBJECT (pad, "%s query", GST_QUERY_TYPE_NAME (query));

  switch (GST_QUERY_TYPE (query)) {
    case GST_QUERY_POSITION:{
      GstFormat fmt;

      gst_query_parse_position (query, &fmt, NULL);
      if (fmt == GST_FORMAT_TIME
          && GST_CLOCK_TIME_IS_VALID (qtdemux->segment.position)) {
        gst_query_set_position (query, GST_FORMAT_TIME,
            qtdemux->segment.position);
        res = TRUE;
      }
    }
      break;
    case GST_QUERY_DURATION:{
      GstFormat fmt;

      gst_query_parse_duration (query, &fmt, NULL);
      if (fmt == GST_FORMAT_TIME) {
        /* First try to query upstream */
        res = gst_pad_query_default (pad, parent, query);
        if (!res) {
          guint64 duration;
          if (gst_qtdemux_get_duration (qtdemux, &duration) && duration > 0) {
            gst_query_set_duration (query, GST_FORMAT_TIME, duration);
            res = TRUE;
          }
        }
      }
      break;
    }
    case GST_QUERY_CONVERT:{
      GstFormat src_fmt, dest_fmt;
      gint64 src_value, dest_value = 0;

      gst_query_parse_convert (query, &src_fmt, &src_value, &dest_fmt, NULL);

      res = gst_qtdemux_src_convert (qtdemux, pad,
          src_fmt, src_value, dest_fmt, &dest_value);
      if (res) {
        gst_query_set_convert (query, src_fmt, src_value, dest_fmt, dest_value);
        res = TRUE;
      }
      break;
    }
    case GST_QUERY_FORMATS:
      gst_query_set_formats (query, 2, GST_FORMAT_TIME, GST_FORMAT_BYTES);
      res = TRUE;
      break;
    case GST_QUERY_SEEKING:{
      GstFormat fmt;
      gboolean seekable;

      /* try upstream first */
      res = gst_pad_query_default (pad, parent, query);

      if (!res) {
        gst_query_parse_seeking (query, &fmt, NULL, NULL, NULL);
        if (fmt == GST_FORMAT_TIME) {
          GstClockTime duration = GST_CLOCK_TIME_NONE;

          gst_qtdemux_get_duration (qtdemux, &duration);
          seekable = TRUE;
          if (!qtdemux->pullbased) {
            GstQuery *q;

            /* we might be able with help from upstream */
            seekable = FALSE;
            q = gst_query_new_seeking (GST_FORMAT_BYTES);
            if (gst_pad_peer_query (qtdemux->sinkpad, q)) {
              gst_query_parse_seeking (q, &fmt, &seekable, NULL, NULL);
              GST_LOG_OBJECT (qtdemux, "upstream BYTE seekable %d", seekable);
            }
            gst_query_unref (q);
          }
          gst_query_set_seeking (query, GST_FORMAT_TIME, seekable, 0, duration);
          res = TRUE;
        }
      }
      break;
    }
    case GST_QUERY_SEGMENT:
    {
      GstFormat format;
      gint64 start, stop;

      format = qtdemux->segment.format;

      start =
          gst_segment_to_stream_time (&qtdemux->segment, format,
          qtdemux->segment.start);
      if ((stop = qtdemux->segment.stop) == -1)
        stop = qtdemux->segment.duration;
      else
        stop = gst_segment_to_stream_time (&qtdemux->segment, format, stop);

      gst_query_set_segment (query, qtdemux->segment.rate, format, start, stop);
      res = TRUE;
      break;
    }
    default:
      res = gst_pad_query_default (pad, parent, query);
      break;
  }

  return res;
}

static void
gst_qtdemux_push_tags (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
  if (G_LIKELY (stream->pad)) {
    GST_DEBUG_OBJECT (qtdemux, "Checking pad %s:%s for tags",
        GST_DEBUG_PAD_NAME (stream->pad));

    if (G_UNLIKELY (stream->pending_tags)) {
      GST_DEBUG_OBJECT (qtdemux, "Sending tags %" GST_PTR_FORMAT,
          stream->pending_tags);
      gst_pad_push_event (stream->pad,
          gst_event_new_tag (stream->pending_tags));
      stream->pending_tags = NULL;
    }

    if (G_UNLIKELY (stream->send_global_tags && qtdemux->tag_list)) {
      GST_DEBUG_OBJECT (qtdemux, "Sending global tags %" GST_PTR_FORMAT,
          qtdemux->tag_list);
      gst_pad_push_event (stream->pad,
          gst_event_new_tag (gst_tag_list_ref (qtdemux->tag_list)));
      stream->send_global_tags = FALSE;
    }
  }
}

/* push event on all source pads; takes ownership of the event */
static void
gst_qtdemux_push_event (GstQTDemux * qtdemux, GstEvent * event)
{
  guint n;
  gboolean has_valid_stream = FALSE;
  GstEventType etype = GST_EVENT_TYPE (event);

  GST_DEBUG_OBJECT (qtdemux, "pushing %s event on all source pads",
      GST_EVENT_TYPE_NAME (event));

  for (n = 0; n < qtdemux->n_streams; n++) {
    GstPad *pad;
    QtDemuxStream *stream = qtdemux->streams[n];
    GST_DEBUG_OBJECT (qtdemux, "pushing on pad %i", n);

    if ((pad = stream->pad)) {
      has_valid_stream = TRUE;

      if (etype == GST_EVENT_EOS) {
        /* let's not send twice */
        if (stream->sent_eos)
          continue;
        stream->sent_eos = TRUE;
      }

      gst_pad_push_event (pad, gst_event_ref (event));
    }
  }

  gst_event_unref (event);

  /* if it is EOS and there are no pads, post an error */
  if (!has_valid_stream && etype == GST_EVENT_EOS) {
    gst_qtdemux_post_no_playable_stream_error (qtdemux);
  }
}

/* push a pending newsegment event, if any from the streaming thread */
static void
gst_qtdemux_push_pending_newsegment (GstQTDemux * qtdemux)
{
  if (qtdemux->pending_newsegment) {
    gst_qtdemux_push_event (qtdemux, qtdemux->pending_newsegment);
    qtdemux->pending_newsegment = NULL;
  }
}

typedef struct
{
  guint64 media_time;
} FindData;

static gint
find_func (QtDemuxSample * s1, gint64 * media_time, gpointer user_data)
{
  if ((gint64) s1->timestamp + s1->pts_offset > *media_time)
    return 1;
  if ((gint64) s1->timestamp + s1->pts_offset == *media_time)
    return 0;

  return -1;
}

/* find the index of the sample that includes the data for @media_time using a
 * binary search.  Only to be called in optimized cases of linear search below.
 *
 * Returns the index of the sample.
 */
static guint32
gst_qtdemux_find_index (GstQTDemux * qtdemux, QtDemuxStream * str,
    guint64 media_time)
{
  QtDemuxSample *result;
  guint32 index;

  /* convert media_time to mov format */
  media_time =
      gst_util_uint64_scale_ceil (media_time, str->timescale, GST_SECOND);

  result = gst_util_array_binary_search (str->samples, str->stbl_index + 1,
      sizeof (QtDemuxSample), (GCompareDataFunc) find_func,
      GST_SEARCH_MODE_BEFORE, &media_time, NULL);

  if (G_LIKELY (result))
    index = result - str->samples;
  else
    index = 0;

  return index;
}



/* find the index of the sample that includes the data for @media_offset using a
 * linear search
 *
 * Returns the index of the sample.
 */
static guint32
gst_qtdemux_find_index_for_given_media_offset_linear (GstQTDemux * qtdemux,
    QtDemuxStream * str, gint64 media_offset)
{
  QtDemuxSample *result = str->samples;
  guint32 index = 0;

  if (result == NULL || str->n_samples == 0)
    return -1;

  if (media_offset == result->offset)
    return index;

  result++;
  while (index < str->n_samples - 1) {
    if (!qtdemux_parse_samples (qtdemux, str, index + 1))
      goto parse_failed;

    if (media_offset < result->offset)
      break;

    index++;
    result++;
  }
  return index;

  /* ERRORS */
parse_failed:
  {
    GST_LOG_OBJECT (qtdemux, "Parsing of index %u failed!", index + 1);
    return -1;
  }
}

/* find the index of the sample that includes the data for @media_time using a
 * linear search, and keeping in mind that not all samples may have been parsed
 * yet.  If possible, it will delegate to binary search.
 *
 * Returns the index of the sample.
 */
static guint32
gst_qtdemux_find_index_linear (GstQTDemux * qtdemux, QtDemuxStream * str,
    GstClockTime media_time)
{
  guint32 index = 0;
  guint64 mov_time;
  QtDemuxSample *sample;

  /* convert media_time to mov format */
  mov_time =
      gst_util_uint64_scale_ceil (media_time, str->timescale, GST_SECOND);

  sample = str->samples;
  if (mov_time == sample->timestamp + sample->pts_offset)
    return index;

  /* use faster search if requested time in already parsed range */
  sample = str->samples + str->stbl_index;
  if (str->stbl_index >= 0 &&
      mov_time <= (sample->timestamp + sample->pts_offset))
    return gst_qtdemux_find_index (qtdemux, str, media_time);

  while (index < str->n_samples - 1) {
    if (!qtdemux_parse_samples (qtdemux, str, index + 1))
      goto parse_failed;

    sample = str->samples + index + 1;
    if (mov_time < (sample->timestamp + sample->pts_offset))
      break;

    index++;
  }
  return index;

  /* ERRORS */
parse_failed:
  {
    GST_LOG_OBJECT (qtdemux, "Parsing of index %u failed!", index + 1);
    return -1;
  }
}

/* find the index of the keyframe needed to decode the sample at @index
 * of stream @str.
 *
 * Returns the index of the keyframe.
 */
static guint32
gst_qtdemux_find_keyframe (GstQTDemux * qtdemux, QtDemuxStream * str,
    guint32 index)
{
  guint32 new_index = index;

  if (index >= str->n_samples) {
    new_index = str->n_samples;
    goto beach;
  }

  /* all keyframes, return index */
  if (str->all_keyframe) {
    new_index = index;
    goto beach;
  }

  /* else go back until we have a keyframe */
  while (TRUE) {
    if (str->samples[new_index].keyframe)
      break;

    if (new_index == 0)
      break;

    new_index--;
  }

beach:
  GST_DEBUG_OBJECT (qtdemux, "searching for keyframe index before index %u "
      "gave %u", index, new_index);

  return new_index;
}

/* find the segment for @time_position for @stream
 *
 * Returns the index of the segment containing @time_position.
 * Returns the last segment and sets the @eos variable to TRUE
 * if the time is beyond the end. @eos may be NULL
 */
static guint32
gst_qtdemux_find_segment (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstClockTime time_position)
{
  gint i;
  guint32 seg_idx;

  GST_LOG_OBJECT (stream->pad, "finding segment for %" GST_TIME_FORMAT,
      GST_TIME_ARGS (time_position));

  seg_idx = -1;
  for (i = 0; i < stream->n_segments; i++) {
    QtDemuxSegment *segment = &stream->segments[i];

    GST_LOG_OBJECT (stream->pad,
        "looking at segment %" GST_TIME_FORMAT "-%" GST_TIME_FORMAT,
        GST_TIME_ARGS (segment->time), GST_TIME_ARGS (segment->stop_time));

    /* For the last segment we include stop_time in the last segment */
    if (i < stream->n_segments - 1) {
      if (segment->time <= time_position && time_position < segment->stop_time) {
        GST_LOG_OBJECT (stream->pad, "segment %d matches", i);
        seg_idx = i;
        break;
      }
    } else {
      /* Last segment always matches */
      seg_idx = i;
      break;
    }
  }
  return seg_idx;
}

/* move the stream @str to the sample position @index.
 *
 * Updates @str->sample_index and marks discontinuity if needed.
 */
static void
gst_qtdemux_move_stream (GstQTDemux * qtdemux, QtDemuxStream * str,
    guint32 index)
{
  /* no change needed */
  if (index == str->sample_index)
    return;

  GST_DEBUG_OBJECT (qtdemux, "moving to sample %u of %u", index,
      str->n_samples);

  /* position changed, we have a discont */
  str->sample_index = index;
  str->offset_in_sample = 0;
  /* Each time we move in the stream we store the position where we are
   * starting from */
  str->from_sample = index;
  str->discont = TRUE;
}

static void
gst_qtdemux_adjust_seek (GstQTDemux * qtdemux, gint64 desired_time,
    gboolean use_sparse, gint64 * key_time, gint64 * key_offset)
{
  guint64 min_offset;
  gint64 min_byte_offset = -1;
  gint n;

  min_offset = desired_time;

  /* for each stream, find the index of the sample in the segment
   * and move back to the previous keyframe. */
  for (n = 0; n < qtdemux->n_streams; n++) {
    QtDemuxStream *str;
    guint32 index, kindex;
    guint32 seg_idx;
    GstClockTime media_start;
    GstClockTime media_time;
    GstClockTime seg_time;
    QtDemuxSegment *seg;
    gboolean empty_segment = FALSE;

    str = qtdemux->streams[n];

    if (str->sparse && !use_sparse)
      continue;

    seg_idx = gst_qtdemux_find_segment (qtdemux, str, desired_time);
    GST_DEBUG_OBJECT (qtdemux, "align segment %d", seg_idx);

    /* get segment and time in the segment */
    seg = &str->segments[seg_idx];
    seg_time = desired_time - seg->time;

    while (QTSEGMENT_IS_EMPTY (seg)) {
      seg_time = 0;
      empty_segment = TRUE;
      GST_DEBUG_OBJECT (str->pad, "Segment %d is empty, moving to next one",
          seg_idx);
      seg_idx++;
      if (seg_idx == str->n_segments)
        break;
      seg = &str->segments[seg_idx];
    }

    if (seg_idx == str->n_segments) {
      /* FIXME track shouldn't have the last segment as empty, but if it
       * happens we better handle it */
      continue;
    }

    /* get the media time in the segment */
    media_start = seg->media_start + seg_time;

    /* get the index of the sample with media time */
    index = gst_qtdemux_find_index_linear (qtdemux, str, media_start);
    GST_DEBUG_OBJECT (qtdemux, "sample for %" GST_TIME_FORMAT " at %u"
        " at offset %" G_GUINT64_FORMAT " (empty segment: %d)",
        GST_TIME_ARGS (media_start), index, str->samples[index].offset,
        empty_segment);

    if (!empty_segment) {
      /* find previous keyframe */
      kindex = gst_qtdemux_find_keyframe (qtdemux, str, index);

      /* if the keyframe is at a different position, we need to update the
       * requested seek time */
      if (index != kindex) {
        index = kindex;

        /* get timestamp of keyframe */
        media_time = QTSAMPLE_DTS (str, &str->samples[kindex]);
        GST_DEBUG_OBJECT (qtdemux,
            "keyframe at %u with time %" GST_TIME_FORMAT " at offset %"
            G_GUINT64_FORMAT, kindex, GST_TIME_ARGS (media_time),
            str->samples[kindex].offset);

        /* keyframes in the segment get a chance to change the
         * desired_offset. keyframes out of the segment are
         * ignored. */
        if (media_time >= seg->media_start) {
          GstClockTime seg_time;

          /* this keyframe is inside the segment, convert back to
           * segment time */
          seg_time = (media_time - seg->media_start) + seg->time;
          if (seg_time < min_offset)
            min_offset = seg_time;
        }
      }
    }

    if (min_byte_offset < 0 || str->samples[index].offset < min_byte_offset)
      min_byte_offset = str->samples[index].offset;
  }

  if (key_time)
    *key_time = min_offset;
  if (key_offset)
    *key_offset = min_byte_offset;
}

static gboolean
gst_qtdemux_convert_seek (GstPad * pad, GstFormat * format,
    GstSeekType cur_type, gint64 * cur, GstSeekType stop_type, gint64 * stop)
{
  gboolean res;

  g_return_val_if_fail (format != NULL, FALSE);
  g_return_val_if_fail (cur != NULL, FALSE);
  g_return_val_if_fail (stop != NULL, FALSE);

  if (*format == GST_FORMAT_TIME)
    return TRUE;

  res = TRUE;
  if (cur_type != GST_SEEK_TYPE_NONE)
    res = gst_pad_query_convert (pad, *format, *cur, GST_FORMAT_TIME, cur);
  if (res && stop_type != GST_SEEK_TYPE_NONE)
    res = gst_pad_query_convert (pad, *format, *stop, GST_FORMAT_TIME, stop);

  if (res)
    *format = GST_FORMAT_TIME;

  return res;
}

/* perform seek in push based mode:
   find BYTE position to move to based on time and delegate to upstream
*/
static gboolean
gst_qtdemux_do_push_seek (GstQTDemux * qtdemux, GstPad * pad, GstEvent * event)
{
  gdouble rate;
  GstFormat format;
  GstSeekFlags flags;
  GstSeekType cur_type, stop_type;
  gint64 cur, stop, key_cur;
  gboolean res;
  gint64 byte_cur;
  gint64 original_stop;
  guint32 seqnum;

  GST_DEBUG_OBJECT (qtdemux, "doing push-based seek");

  gst_event_parse_seek (event, &rate, &format, &flags,
      &cur_type, &cur, &stop_type, &stop);
  seqnum = gst_event_get_seqnum (event);

  /* only forward streaming and seeking is possible */
  if (rate <= 0)
    goto unsupported_seek;

  /* convert to TIME if needed and possible */
  if (!gst_qtdemux_convert_seek (pad, &format, cur_type, &cur,
          stop_type, &stop))
    goto no_format;

  /* Upstream seek in bytes will have undefined stop, but qtdemux stores
   * the original stop position to use when upstream pushes the new segment
   * for this seek */
  original_stop = stop;
  stop = -1;

  /* find reasonable corresponding BYTE position,
   * also try to mind about keyframes, since we can not go back a bit for them
   * later on */
  gst_qtdemux_adjust_seek (qtdemux, cur, FALSE, &key_cur, &byte_cur);

  if (byte_cur == -1)
    goto abort_seek;

  GST_DEBUG_OBJECT (qtdemux, "Pushing BYTE seek rate %g, "
      "start %" G_GINT64_FORMAT ", stop %" G_GINT64_FORMAT, rate, byte_cur,
      stop);

  GST_OBJECT_LOCK (qtdemux);
  qtdemux->seek_offset = byte_cur;
  if (!(flags & GST_SEEK_FLAG_KEY_UNIT)) {
    qtdemux->push_seek_start = cur;
  } else {
    qtdemux->push_seek_start = key_cur;
  }

  if (stop_type == GST_SEEK_TYPE_NONE) {
    qtdemux->push_seek_stop = qtdemux->segment.stop;
  } else {
    qtdemux->push_seek_stop = original_stop;
  }
  GST_OBJECT_UNLOCK (qtdemux);

  /* BYTE seek event */
  event = gst_event_new_seek (rate, GST_FORMAT_BYTES, flags, cur_type, byte_cur,
      stop_type, stop);
  gst_event_set_seqnum (event, seqnum);
  res = gst_pad_push_event (qtdemux->sinkpad, event);

  return res;

  /* ERRORS */
abort_seek:
  {
    GST_DEBUG_OBJECT (qtdemux, "could not determine byte position to seek to, "
        "seek aborted.");
    return FALSE;
  }
unsupported_seek:
  {
    GST_DEBUG_OBJECT (qtdemux, "unsupported seek, seek aborted.");
    return FALSE;
  }
no_format:
  {
    GST_DEBUG_OBJECT (qtdemux, "unsupported format given, seek aborted.");
    return FALSE;
  }
}

/* perform the seek.
 *
 * We set all segment_indexes in the streams to unknown and
 * adjust the time_position to the desired position. this is enough
 * to trigger a segment switch in the streaming thread to start
 * streaming from the desired position.
 *
 * Keyframe seeking is a little more complicated when dealing with
 * segments. Ideally we want to move to the previous keyframe in
 * the segment but there might not be a keyframe in the segment. In
 * fact, none of the segments could contain a keyframe. We take a
 * practical approach: seek to the previous keyframe in the segment,
 * if there is none, seek to the beginning of the segment.
 *
 * Called with STREAM_LOCK
 */
static gboolean
gst_qtdemux_perform_seek (GstQTDemux * qtdemux, GstSegment * segment,
    guint32 seqnum, GstSeekFlags flags)
{
  gint64 desired_offset;
  gint n;

  desired_offset = segment->position;

  GST_DEBUG_OBJECT (qtdemux, "seeking to %" GST_TIME_FORMAT,
      GST_TIME_ARGS (desired_offset));

  /* may not have enough fragmented info to do this adjustment,
   * and we can't scan (and probably should not) at this time with
   * possibly flushing upstream */
  if ((flags & GST_SEEK_FLAG_KEY_UNIT) && !qtdemux->fragmented) {
    gint64 min_offset;

    gst_qtdemux_adjust_seek (qtdemux, desired_offset, TRUE, &min_offset, NULL);
    GST_DEBUG_OBJECT (qtdemux, "keyframe seek, align to %"
        GST_TIME_FORMAT, GST_TIME_ARGS (min_offset));
    desired_offset = min_offset;
  }

  /* and set all streams to the final position */
  gst_flow_combiner_reset (qtdemux->flowcombiner);
  qtdemux->segment_seqnum = seqnum;
  for (n = 0; n < qtdemux->n_streams; n++) {
    QtDemuxStream *stream = qtdemux->streams[n];

    stream->time_position = desired_offset;
    stream->accumulated_base = 0;
    stream->sample_index = -1;
    stream->offset_in_sample = 0;
    stream->segment_index = -1;
    stream->sent_eos = FALSE;

    if (segment->flags & GST_SEEK_FLAG_FLUSH)
      gst_segment_init (&stream->segment, GST_FORMAT_TIME);
  }
  segment->position = desired_offset;
  segment->time = desired_offset;
  if (segment->rate >= 0) {
    segment->start = desired_offset;

    /* we stop at the end */
    if (segment->stop == -1)
      segment->stop = segment->duration;
  } else {
    segment->stop = desired_offset;
  }

  if (qtdemux->fragmented)
    qtdemux->fragmented_seek_pending = TRUE;

  return TRUE;
}

/* do a seek in pull based mode */
static gboolean
gst_qtdemux_do_seek (GstQTDemux * qtdemux, GstPad * pad, GstEvent * event)
{
  gdouble rate;
  GstFormat format;
  GstSeekFlags flags;
  GstSeekType cur_type, stop_type;
  gint64 cur, stop;
  gboolean flush;
  gboolean update;
  GstSegment seeksegment;
  guint32 seqnum = 0;
  GstEvent *flush_event;

  if (event) {
    GST_DEBUG_OBJECT (qtdemux, "doing seek with event");

    gst_event_parse_seek (event, &rate, &format, &flags,
        &cur_type, &cur, &stop_type, &stop);
    seqnum = gst_event_get_seqnum (event);

    /* we have to have a format as the segment format. Try to convert
     * if not. */
    if (!gst_qtdemux_convert_seek (pad, &format, cur_type, &cur,
            stop_type, &stop))
      goto no_format;

    GST_DEBUG_OBJECT (qtdemux, "seek format %s", gst_format_get_name (format));
  } else {
    GST_DEBUG_OBJECT (qtdemux, "doing seek without event");
    flags = 0;
  }

  flush = flags & GST_SEEK_FLAG_FLUSH;

  /* stop streaming, either by flushing or by pausing the task */
  if (flush) {
    flush_event = gst_event_new_flush_start ();
    if (seqnum)
      gst_event_set_seqnum (flush_event, seqnum);
    /* unlock upstream pull_range */
    gst_pad_push_event (qtdemux->sinkpad, gst_event_ref (flush_event));
    /* make sure out loop function exits */
    gst_qtdemux_push_event (qtdemux, flush_event);
  } else {
    /* non flushing seek, pause the task */
    gst_pad_pause_task (qtdemux->sinkpad);
  }

  /* wait for streaming to finish */
  GST_PAD_STREAM_LOCK (qtdemux->sinkpad);

  /* copy segment, we need this because we still need the old
   * segment when we close the current segment. */
  memcpy (&seeksegment, &qtdemux->segment, sizeof (GstSegment));

  if (event) {
    /* configure the segment with the seek variables */
    GST_DEBUG_OBJECT (qtdemux, "configuring seek");
    gst_segment_do_seek (&seeksegment, rate, format, flags,
        cur_type, cur, stop_type, stop, &update);
  }

  /* now do the seek, this actually never returns FALSE */
  gst_qtdemux_perform_seek (qtdemux, &seeksegment, seqnum, flags);

  /* prepare for streaming again */
  if (flush) {
    flush_event = gst_event_new_flush_stop (TRUE);
    if (seqnum)
      gst_event_set_seqnum (flush_event, seqnum);

    gst_pad_push_event (qtdemux->sinkpad, gst_event_ref (flush_event));
    gst_qtdemux_push_event (qtdemux, flush_event);
  }

  /* commit the new segment */
  memcpy (&qtdemux->segment, &seeksegment, sizeof (GstSegment));

  if (qtdemux->segment.flags & GST_SEEK_FLAG_SEGMENT) {
    GstMessage *msg = gst_message_new_segment_start (GST_OBJECT_CAST (qtdemux),
        qtdemux->segment.format, qtdemux->segment.position);
    if (seqnum)
      gst_message_set_seqnum (msg, seqnum);
    gst_element_post_message (GST_ELEMENT_CAST (qtdemux), msg);
  }

  /* restart streaming, NEWSEGMENT will be sent from the streaming thread. */
  gst_pad_start_task (qtdemux->sinkpad, (GstTaskFunction) gst_qtdemux_loop,
      qtdemux->sinkpad, NULL);

  GST_PAD_STREAM_UNLOCK (qtdemux->sinkpad);

  return TRUE;

  /* ERRORS */
no_format:
  {
    GST_DEBUG_OBJECT (qtdemux, "unsupported format given, seek aborted.");
    return FALSE;
  }
}

static gboolean
qtdemux_ensure_index (GstQTDemux * qtdemux)
{
  guint i;

  GST_DEBUG_OBJECT (qtdemux, "collecting all metadata for all streams");

  /* Build complete index */
  for (i = 0; i < qtdemux->n_streams; i++) {
    QtDemuxStream *stream = qtdemux->streams[i];

    if (!qtdemux_parse_samples (qtdemux, stream, stream->n_samples - 1))
      goto parse_error;
  }
  return TRUE;

  /* ERRORS */
parse_error:
  {
    GST_LOG_OBJECT (qtdemux,
        "Building complete index of stream %u for seeking failed!", i);
    return FALSE;
  }
}

static gboolean
gst_qtdemux_handle_src_event (GstPad * pad, GstObject * parent,
    GstEvent * event)
{
  gboolean res = TRUE;
  GstQTDemux *qtdemux = GST_QTDEMUX (parent);

  switch (GST_EVENT_TYPE (event)) {
    case GST_EVENT_SEEK:
    {
#ifndef GST_DISABLE_GST_DEBUG
      GstClockTime ts = gst_util_get_timestamp ();
#endif

      if (qtdemux->upstream_format_is_time && qtdemux->fragmented) {
        /* seek should be handled by upstream, we might need to re-download fragments */
        GST_DEBUG_OBJECT (qtdemux,
            "let upstream handle seek for fragmented playback");
        goto upstream;
      }

      /* Build complete index for seeking;
       * if not a fragmented file at least */
      if (!qtdemux->fragmented)
        if (!qtdemux_ensure_index (qtdemux))
          goto index_failed;
#ifndef GST_DISABLE_GST_DEBUG
      ts = gst_util_get_timestamp () - ts;
      GST_INFO_OBJECT (qtdemux,
          "Time taken to parse index %" GST_TIME_FORMAT, GST_TIME_ARGS (ts));
#endif
    }
      if (qtdemux->pullbased) {
        res = gst_qtdemux_do_seek (qtdemux, pad, event);
      } else if (gst_pad_push_event (qtdemux->sinkpad, gst_event_ref (event))) {
        GST_DEBUG_OBJECT (qtdemux, "Upstream successfully seeked");
        res = TRUE;
      } else if (qtdemux->state == QTDEMUX_STATE_MOVIE && qtdemux->n_streams
          && !qtdemux->fragmented) {
        res = gst_qtdemux_do_push_seek (qtdemux, pad, event);
      } else {
        GST_DEBUG_OBJECT (qtdemux,
            "ignoring seek in push mode in current state");
        res = FALSE;
      }
      gst_event_unref (event);
      break;
    case GST_EVENT_QOS:
    case GST_EVENT_NAVIGATION:
      res = FALSE;
      gst_event_unref (event);
      break;
    default:
    upstream:
      res = gst_pad_event_default (pad, parent, event);
      break;
  }

done:
  return res;

  /* ERRORS */
index_failed:
  {
    GST_ERROR_OBJECT (qtdemux, "Index failed");
    gst_event_unref (event);
    res = FALSE;
    goto done;
  }
}

/* stream/index return sample that is min/max w.r.t. byte position,
 * time is min/max w.r.t. time of samples,
 * the latter need not be time of the former sample */
static void
gst_qtdemux_find_sample (GstQTDemux * qtdemux, gint64 byte_pos, gboolean fw,
    gboolean set, QtDemuxStream ** _stream, gint * _index, gint64 * _time)
{
  gint i, n, index;
  gint64 time, min_time;
  QtDemuxStream *stream;

  min_time = -1;
  stream = NULL;
  index = -1;

  for (n = 0; n < qtdemux->n_streams; ++n) {
    QtDemuxStream *str;
    gint inc;
    gboolean set_sample;

    str = qtdemux->streams[n];
    set_sample = !set;

    if (fw) {
      i = 0;
      inc = 1;
    } else {
      i = str->n_samples - 1;
      inc = -1;
    }

    for (; (i >= 0) && (i < str->n_samples); i += inc) {
      if (str->samples[i].size == 0)
        continue;

      if (fw && (str->samples[i].offset < byte_pos))
        continue;

      if (!fw && (str->samples[i].offset + str->samples[i].size > byte_pos))
        continue;

      /* move stream to first available sample */
      if (set) {
        gst_qtdemux_move_stream (qtdemux, str, i);
        set_sample = TRUE;
      }

      /* avoid index from sparse streams since they might be far away */
      if (!str->sparse) {
        /* determine min/max time */
        time = QTSAMPLE_PTS (str, &str->samples[i]);
        if (min_time == -1 || (!fw && time > min_time) ||
            (fw && time < min_time)) {
          min_time = time;
        }

        /* determine stream with leading sample, to get its position */
        if (!stream ||
            (fw && (str->samples[i].offset < stream->samples[index].offset)) ||
            (!fw && (str->samples[i].offset > stream->samples[index].offset))) {
          stream = str;
          index = i;
        }
      }
      break;
    }

    /* no sample for this stream, mark eos */
    if (!set_sample)
      gst_qtdemux_move_stream (qtdemux, str, str->n_samples);
  }

  if (_time)
    *_time = min_time;
  if (_stream)
    *_stream = stream;
  if (_index)
    *_index = index;
}

static QtDemuxStream *
_create_stream (void)
{
  QtDemuxStream *stream;

  stream = g_new0 (QtDemuxStream, 1);
  /* new streams always need a discont */
  stream->discont = TRUE;
  /* we enable clipping for raw audio/video streams */
  stream->need_clip = FALSE;
  stream->need_process = FALSE;
  stream->segment_index = -1;
  stream->time_position = 0;
  stream->sample_index = -1;
  stream->offset_in_sample = 0;
  stream->new_stream = TRUE;
  stream->multiview_mode = GST_VIDEO_MULTIVIEW_MODE_NONE;
  stream->multiview_flags = GST_VIDEO_MULTIVIEW_FLAGS_NONE;
  stream->protected = FALSE;
  stream->protection_scheme_type = 0;
  stream->protection_scheme_version = 0;
  stream->protection_scheme_info = NULL;
  stream->n_samples_moof = 0;
  stream->duration_moof = 0;
  g_queue_init (&stream->protection_scheme_event_queue);
  return stream;
}

static gboolean
gst_qtdemux_setcaps (GstQTDemux * demux, GstCaps * caps)
{
  GstStructure *structure;
  const gchar *variant;
  const GstCaps *mediacaps = NULL;

  GST_DEBUG_OBJECT (demux, "Sink set caps: %" GST_PTR_FORMAT, caps);

  structure = gst_caps_get_structure (caps, 0);
  variant = gst_structure_get_string (structure, "variant");

  if (variant && strcmp (variant, "mss-fragmented") == 0) {
    QtDemuxStream *stream;
    const GValue *value;

    demux->fragmented = TRUE;
    demux->mss_mode = TRUE;

    if (demux->n_streams > 1) {
      /* can't do this, we can only renegotiate for another mss format */
      return FALSE;
    }

    value = gst_structure_get_value (structure, "media-caps");
    /* create stream */
    if (value) {
      const GValue *timescale_v;

      /* TODO update when stream changes during playback */

      if (demux->n_streams == 0) {
        stream = _create_stream ();
        demux->streams[demux->n_streams] = stream;
        demux->n_streams = 1;
      } else {
        stream = demux->streams[0];
      }

      timescale_v = gst_structure_get_value (structure, "timescale");
      if (timescale_v) {
        stream->timescale = g_value_get_uint64 (timescale_v);
      } else {
        /* default mss timescale */
        stream->timescale = 10000000;
      }
      demux->timescale = stream->timescale;

      mediacaps = gst_value_get_caps (value);
      if (!stream->caps || !gst_caps_is_equal_fixed (mediacaps, stream->caps)) {
        GST_DEBUG_OBJECT (demux, "We have a new caps %" GST_PTR_FORMAT,
            mediacaps);
        stream->new_caps = TRUE;
      }
      gst_caps_replace (&stream->caps, (GstCaps *) mediacaps);
      structure = gst_caps_get_structure (mediacaps, 0);
      if (g_str_has_prefix (gst_structure_get_name (structure), "video")) {
        stream->subtype = FOURCC_vide;

        gst_structure_get_int (structure, "width", &stream->width);
        gst_structure_get_int (structure, "height", &stream->height);
        gst_structure_get_fraction (structure, "framerate", &stream->fps_n,
            &stream->fps_d);
      } else if (g_str_has_prefix (gst_structure_get_name (structure), "audio")) {
        gint rate = 0;
        stream->subtype = FOURCC_soun;
        gst_structure_get_int (structure, "channels", &stream->n_channels);
        gst_structure_get_int (structure, "rate", &rate);
        stream->rate = rate;
      }
    }
    gst_caps_replace (&demux->media_caps, (GstCaps *) mediacaps);
  } else {
    demux->mss_mode = FALSE;
  }

  return TRUE;
}

static void
gst_qtdemux_reset (GstQTDemux * qtdemux, gboolean hard)
{
  gint n;

  GST_DEBUG_OBJECT (qtdemux, "Resetting demux");
  gst_pad_stop_task (qtdemux->sinkpad);

  if (hard || qtdemux->upstream_format_is_time) {
    qtdemux->state = QTDEMUX_STATE_INITIAL;
    qtdemux->neededbytes = 16;
    qtdemux->todrop = 0;
    qtdemux->pullbased = FALSE;
    qtdemux->posted_redirect = FALSE;
    qtdemux->first_mdat = -1;
    qtdemux->header_size = 0;
    qtdemux->mdatoffset = -1;
    qtdemux->restoredata_offset = -1;
    if (qtdemux->mdatbuffer)
      gst_buffer_unref (qtdemux->mdatbuffer);
    if (qtdemux->restoredata_buffer)
      gst_buffer_unref (qtdemux->restoredata_buffer);
    qtdemux->mdatbuffer = NULL;
    qtdemux->restoredata_buffer = NULL;
    qtdemux->mdatleft = 0;
    if (qtdemux->comp_brands)
      gst_buffer_unref (qtdemux->comp_brands);
    qtdemux->comp_brands = NULL;
    qtdemux->last_moov_offset = -1;
    if (qtdemux->moov_node)
      g_node_destroy (qtdemux->moov_node);
    qtdemux->moov_node = NULL;
    qtdemux->moov_node_compressed = NULL;
    if (qtdemux->tag_list)
      gst_mini_object_unref (GST_MINI_OBJECT_CAST (qtdemux->tag_list));
    qtdemux->tag_list = NULL;
#if 0
    if (qtdemux->element_index)
      gst_object_unref (qtdemux->element_index);
    qtdemux->element_index = NULL;
#endif
    qtdemux->major_brand = 0;
    if (qtdemux->pending_newsegment)
      gst_event_unref (qtdemux->pending_newsegment);
    qtdemux->pending_newsegment = NULL;
    qtdemux->upstream_format_is_time = FALSE;
    qtdemux->upstream_seekable = FALSE;
    qtdemux->upstream_size = 0;

    qtdemux->fragment_start = -1;
    qtdemux->fragment_start_offset = -1;
    qtdemux->duration = 0;
    qtdemux->moof_offset = 0;
    qtdemux->chapters_track_id = 0;
    qtdemux->have_group_id = FALSE;
    qtdemux->group_id = G_MAXUINT;

    g_queue_foreach (&qtdemux->protection_event_queue, (GFunc) gst_event_unref,
        NULL);
    g_queue_clear (&qtdemux->protection_event_queue);
  }
  qtdemux->offset = 0;
  gst_adapter_clear (qtdemux->adapter);
  gst_segment_init (&qtdemux->segment, GST_FORMAT_TIME);
  qtdemux->segment_seqnum = 0;

  if (hard) {
    for (n = 0; n < qtdemux->n_streams; n++) {
      gst_qtdemux_stream_free (qtdemux, qtdemux->streams[n]);
      qtdemux->streams[n] = NULL;
    }
    qtdemux->n_streams = 0;
    qtdemux->n_video_streams = 0;
    qtdemux->n_audio_streams = 0;
    qtdemux->n_sub_streams = 0;
    qtdemux->exposed = FALSE;
    qtdemux->fragmented = FALSE;
    qtdemux->mss_mode = FALSE;
    gst_caps_replace (&qtdemux->media_caps, NULL);
    qtdemux->timescale = 0;
    qtdemux->got_moov = FALSE;
    if (qtdemux->protection_system_ids) {
      g_ptr_array_free (qtdemux->protection_system_ids, TRUE);
      qtdemux->protection_system_ids = NULL;
    }
  } else if (qtdemux->mss_mode) {
    gst_flow_combiner_reset (qtdemux->flowcombiner);
    for (n = 0; n < qtdemux->n_streams; n++)
      gst_qtdemux_stream_clear (qtdemux, qtdemux->streams[n]);
  } else {
    gst_flow_combiner_reset (qtdemux->flowcombiner);
    for (n = 0; n < qtdemux->n_streams; n++) {
      qtdemux->streams[n]->sent_eos = FALSE;
      qtdemux->streams[n]->time_position = 0;
      qtdemux->streams[n]->accumulated_base = 0;
    }
    if (!qtdemux->pending_newsegment) {
      qtdemux->pending_newsegment = gst_event_new_segment (&qtdemux->segment);
      if (qtdemux->segment_seqnum)
        gst_event_set_seqnum (qtdemux->pending_newsegment,
            qtdemux->segment_seqnum);
    }
  }
}

static gboolean
gst_qtdemux_handle_sink_event (GstPad * sinkpad, GstObject * parent,
    GstEvent * event)
{
  GstQTDemux *demux = GST_QTDEMUX (parent);
  gboolean res = TRUE;

  GST_LOG_OBJECT (demux, "handling %s event", GST_EVENT_TYPE_NAME (event));

  switch (GST_EVENT_TYPE (event)) {
    case GST_EVENT_SEGMENT:
    {
      gint64 offset = 0;
      QtDemuxStream *stream;
      gint idx;
      GstSegment segment;
      GstEvent *segment_event;

      /* some debug output */
      gst_event_copy_segment (event, &segment);
      GST_DEBUG_OBJECT (demux, "received newsegment %" GST_SEGMENT_FORMAT,
          &segment);

      /* erase any previously set segment */
      gst_event_replace (&demux->pending_newsegment, NULL);

      if (segment.format == GST_FORMAT_TIME) {
        GST_DEBUG_OBJECT (demux, "new pending_newsegment");
        gst_event_replace (&demux->pending_newsegment, event);
        demux->upstream_format_is_time = TRUE;
      } else {
        GST_DEBUG_OBJECT (demux, "Not storing upstream newsegment, "
            "not in time format");

        /* chain will send initial newsegment after pads have been added */
        if (demux->state != QTDEMUX_STATE_MOVIE || !demux->n_streams) {
          GST_DEBUG_OBJECT (demux, "still starting, eating event");
          goto exit;
        }
      }

      /* check if this matches a time seek we received previously
       * FIXME for backwards compatibility reasons we use the
       * seek_offset here to compare. In the future we might want to
       * change this to use the seqnum as it uniquely should identify
       * the segment that corresponds to the seek. */
      GST_DEBUG_OBJECT (demux, "Stored seek offset: %" G_GINT64_FORMAT
          ", received segment offset %" G_GINT64_FORMAT,
          demux->seek_offset, segment.start);
      if (segment.format == GST_FORMAT_BYTES
          && demux->seek_offset == segment.start) {
        GST_OBJECT_LOCK (demux);
        offset = segment.start;

        segment.format = GST_FORMAT_TIME;
        segment.start = demux->push_seek_start;
        segment.stop = demux->push_seek_stop;
        GST_DEBUG_OBJECT (demux, "Replaced segment with stored seek "
            "segment %" GST_TIME_FORMAT " - %" GST_TIME_FORMAT,
            GST_TIME_ARGS (segment.start), GST_TIME_ARGS (segment.stop));
        GST_OBJECT_UNLOCK (demux);
      }

      /* we only expect a BYTE segment, e.g. following a seek */
      if (segment.format == GST_FORMAT_BYTES) {
        if (GST_CLOCK_TIME_IS_VALID (segment.start)) {
          offset = segment.start;

          gst_qtdemux_find_sample (demux, segment.start, TRUE, FALSE, NULL,
              NULL, (gint64 *) & segment.start);
          if ((gint64) segment.start < 0)
            segment.start = 0;
        }
        if (GST_CLOCK_TIME_IS_VALID (segment.stop)) {
          gst_qtdemux_find_sample (demux, segment.stop, FALSE, FALSE, NULL,
              NULL, (gint64 *) & segment.stop);
          /* keyframe seeking should already arrange for start >= stop,
           * but make sure in other rare cases */
          segment.stop = MAX (segment.stop, segment.start);
        }
      } else if (segment.format == GST_FORMAT_TIME) {
        /* push all data on the adapter before starting this
         * new segment */
        gst_qtdemux_process_adapter (demux, TRUE);
      } else {
        GST_DEBUG_OBJECT (demux, "unsupported segment format, ignoring");
        goto exit;
      }

      /* accept upstream's notion of segment and distribute along */
      segment.format = GST_FORMAT_TIME;
      segment.position = segment.time = segment.start;
      segment.duration = demux->segment.duration;
      segment.base = gst_segment_to_running_time (&demux->segment,
          GST_FORMAT_TIME, demux->segment.position);

      gst_segment_copy_into (&segment, &demux->segment);
      GST_DEBUG_OBJECT (demux, "Pushing newseg %" GST_SEGMENT_FORMAT, &segment);
      if (demux->n_streams) {
        gst_event_replace (&demux->pending_newsegment, NULL);
        segment_event = gst_event_new_segment (&segment);
        gst_event_set_seqnum (segment_event, gst_event_get_seqnum (event));
        gst_qtdemux_push_event (demux, segment_event);
      }

      /* clear leftover in current segment, if any */
      gst_adapter_clear (demux->adapter);

      /* set up streaming thread */
      demux->offset = offset;
      if (demux->upstream_format_is_time) {
        GST_DEBUG_OBJECT (demux, "Upstream is driving in time format, "
            "set values to restart reading from a new atom");
        demux->neededbytes = 16;
        demux->todrop = 0;
      } else {
        gst_qtdemux_find_sample (demux, offset, TRUE, TRUE, &stream, &idx,
            NULL);
        if (stream) {
          demux->todrop = stream->samples[idx].offset - offset;
          demux->neededbytes = demux->todrop + stream->samples[idx].size;
        } else {
          /* set up for EOS */
          demux->neededbytes = -1;
          demux->todrop = 0;
        }
      }
    exit:
      gst_event_unref (event);
      res = TRUE;
      goto drop;
    }
    case GST_EVENT_FLUSH_START:
    {
      if (gst_event_get_seqnum (event) == demux->offset_seek_seqnum) {
        gst_event_unref (event);
        goto drop;
      }
      break;
    }
    case GST_EVENT_FLUSH_STOP:
    {
      guint64 dur;

      dur = demux->segment.duration;
      gst_qtdemux_reset (demux, FALSE);
      demux->segment.duration = dur;

      if (gst_event_get_seqnum (event) == demux->offset_seek_seqnum) {
        gst_event_unref (event);
        goto drop;
      }
      break;
    }
    case GST_EVENT_EOS:
      /* If we are in push mode, and get an EOS before we've seen any streams,
       * then error out - we have nowhere to send the EOS */
      if (!demux->pullbased) {
        gint i;
        gboolean has_valid_stream = FALSE;
        for (i = 0; i < demux->n_streams; i++) {
          if (demux->streams[i]->pad != NULL) {
            has_valid_stream = TRUE;
            break;
          }
        }
        if (!has_valid_stream)
          gst_qtdemux_post_no_playable_stream_error (demux);
        else {
          GST_DEBUG_OBJECT (demux, "Data still available after EOS: %u",
              (guint) gst_adapter_available (demux->adapter));
          if (gst_qtdemux_process_adapter (demux, TRUE) != GST_FLOW_OK) {
            res = FALSE;
          }
        }
      }
      break;
    case GST_EVENT_CAPS:{
      GstCaps *caps = NULL;

      gst_event_parse_caps (event, &caps);
      gst_qtdemux_setcaps (demux, caps);
      res = TRUE;
      gst_event_unref (event);
      goto drop;
    }
    case GST_EVENT_PROTECTION:
    {
      const gchar *system_id = NULL;

      gst_event_parse_protection (event, &system_id, NULL, NULL);
      GST_DEBUG_OBJECT (demux, "Received protection event for system ID %s",
          system_id);
      gst_qtdemux_append_protection_system_id (demux, system_id);
      /* save the event for later, for source pads that have not been created */
      g_queue_push_tail (&demux->protection_event_queue, gst_event_ref (event));
      /* send it to all pads that already exist */
      gst_qtdemux_push_event (demux, event);
      res = TRUE;
      goto drop;
    }
    default:
      break;
  }

  res = gst_pad_event_default (demux->sinkpad, parent, event) & res;

drop:
  return res;
}

#if 0
static void
gst_qtdemux_set_index (GstElement * element, GstIndex * index)
{
  GstQTDemux *demux = GST_QTDEMUX (element);

  GST_OBJECT_LOCK (demux);
  if (demux->element_index)
    gst_object_unref (demux->element_index);
  if (index) {
    demux->element_index = gst_object_ref (index);
  } else {
    demux->element_index = NULL;
  }
  GST_OBJECT_UNLOCK (demux);
  /* object lock might be taken again */
  if (index)
    gst_index_get_writer_id (index, GST_OBJECT (element), &demux->index_id);
  GST_DEBUG_OBJECT (demux, "Set index %" GST_PTR_FORMAT "for writer id %d",
      demux->element_index, demux->index_id);
}

static GstIndex *
gst_qtdemux_get_index (GstElement * element)
{
  GstIndex *result = NULL;
  GstQTDemux *demux = GST_QTDEMUX (element);

  GST_OBJECT_LOCK (demux);
  if (demux->element_index)
    result = gst_object_ref (demux->element_index);
  GST_OBJECT_UNLOCK (demux);

  GST_DEBUG_OBJECT (demux, "Returning index %" GST_PTR_FORMAT, result);

  return result;
}
#endif

static void
gst_qtdemux_stbl_free (QtDemuxStream * stream)
{
  g_free ((gpointer) stream->stco.data);
  stream->stco.data = NULL;
  g_free ((gpointer) stream->stsz.data);
  stream->stsz.data = NULL;
  g_free ((gpointer) stream->stsc.data);
  stream->stsc.data = NULL;
  g_free ((gpointer) stream->stts.data);
  stream->stts.data = NULL;
  g_free ((gpointer) stream->stss.data);
  stream->stss.data = NULL;
  g_free ((gpointer) stream->stps.data);
  stream->stps.data = NULL;
  g_free ((gpointer) stream->ctts.data);
  stream->ctts.data = NULL;
}

static void
gst_qtdemux_stream_flush_segments_data (GstQTDemux * qtdemux,
    QtDemuxStream * stream)
{
  g_free (stream->segments);
  stream->segments = NULL;
  stream->segment_index = -1;
  stream->accumulated_base = 0;
}

static void
gst_qtdemux_stream_flush_samples_data (GstQTDemux * qtdemux,
    QtDemuxStream * stream)
{
  g_free (stream->samples);
  stream->samples = NULL;
  gst_qtdemux_stbl_free (stream);

  /* fragments */
  g_free (stream->ra_entries);
  stream->ra_entries = NULL;
  stream->n_ra_entries = 0;

  stream->sample_index = -1;
  stream->stbl_index = -1;
  stream->n_samples = 0;
  stream->time_position = 0;

  stream->n_samples_moof = 0;
  stream->duration_moof = 0;
}

static void
gst_qtdemux_stream_clear (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
  if (stream->allocator)
    gst_object_unref (stream->allocator);
  while (stream->buffers) {
    gst_buffer_unref (GST_BUFFER_CAST (stream->buffers->data));
    stream->buffers = g_slist_delete_link (stream->buffers, stream->buffers);
  }
  if (stream->rgb8_palette) {
    gst_memory_unref (stream->rgb8_palette);
    stream->rgb8_palette = NULL;
  }

  if (stream->pending_tags)
    gst_tag_list_unref (stream->pending_tags);
  stream->pending_tags = NULL;
  g_free (stream->redirect_uri);
  stream->redirect_uri = NULL;
  stream->sent_eos = FALSE;
  stream->sparse = FALSE;
  stream->protected = FALSE;
  if (stream->protection_scheme_info) {
    if (stream->protection_scheme_type == FOURCC_cenc) {
      QtDemuxCencSampleSetInfo *info =
          (QtDemuxCencSampleSetInfo *) stream->protection_scheme_info;
      if (info->default_properties)
        gst_structure_free (info->default_properties);
      if (info->crypto_info)
        g_ptr_array_free (info->crypto_info, TRUE);
    }
    g_free (stream->protection_scheme_info);
    stream->protection_scheme_info = NULL;
  }
  stream->protection_scheme_type = 0;
  stream->protection_scheme_version = 0;
  g_queue_foreach (&stream->protection_scheme_event_queue,
      (GFunc) gst_event_unref, NULL);
  g_queue_clear (&stream->protection_scheme_event_queue);
  gst_qtdemux_stream_flush_segments_data (qtdemux, stream);
  gst_qtdemux_stream_flush_samples_data (qtdemux, stream);
}

static void
gst_qtdemux_stream_free (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
  gst_qtdemux_stream_clear (qtdemux, stream);
  if (stream->caps)
    gst_caps_unref (stream->caps);
  stream->caps = NULL;
  if (stream->pad) {
    gst_element_remove_pad (GST_ELEMENT_CAST (qtdemux), stream->pad);
    gst_flow_combiner_remove_pad (qtdemux->flowcombiner, stream->pad);
  }
  g_free (stream);
}

static void
gst_qtdemux_remove_stream (GstQTDemux * qtdemux, int i)
{
  g_assert (i >= 0 && i < qtdemux->n_streams && qtdemux->streams[i] != NULL);

  gst_qtdemux_stream_free (qtdemux, qtdemux->streams[i]);
  qtdemux->streams[i] = qtdemux->streams[qtdemux->n_streams - 1];
  qtdemux->streams[qtdemux->n_streams - 1] = NULL;
  qtdemux->n_streams--;
}

static GstStateChangeReturn
gst_qtdemux_change_state (GstElement * element, GstStateChange transition)
{
  GstQTDemux *qtdemux = GST_QTDEMUX (element);
  GstStateChangeReturn result = GST_STATE_CHANGE_FAILURE;

  switch (transition) {
    case GST_STATE_CHANGE_PAUSED_TO_READY:
      break;
    default:
      break;
  }

  result = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition);

  switch (transition) {
    case GST_STATE_CHANGE_PAUSED_TO_READY:{
      gst_qtdemux_reset (qtdemux, TRUE);
      break;
    }
    default:
      break;
  }

  return result;
}

static void
qtdemux_parse_ftyp (GstQTDemux * qtdemux, const guint8 * buffer, gint length)
{
  /* counts as header data */
  qtdemux->header_size += length;

  /* only consider at least a sufficiently complete ftyp atom */
  if (length >= 20) {
    GstBuffer *buf;

    qtdemux->major_brand = QT_FOURCC (buffer + 8);
    GST_DEBUG_OBJECT (qtdemux, "major brand: %" GST_FOURCC_FORMAT,
        GST_FOURCC_ARGS (qtdemux->major_brand));
    if (qtdemux->comp_brands)
      gst_buffer_unref (qtdemux->comp_brands);
    buf = qtdemux->comp_brands = gst_buffer_new_and_alloc (length - 16);
    gst_buffer_fill (buf, 0, buffer + 16, length - 16);
  }
}

static void
qtdemux_handle_xmp_taglist (GstQTDemux * qtdemux, GstTagList * taglist,
    GstTagList * xmptaglist)
{
  /* Strip out bogus fields */
  if (xmptaglist) {
    if (gst_tag_list_get_scope (taglist) == GST_TAG_SCOPE_GLOBAL) {
      gst_tag_list_remove_tag (xmptaglist, GST_TAG_VIDEO_CODEC);
      gst_tag_list_remove_tag (xmptaglist, GST_TAG_AUDIO_CODEC);
    } else {
      gst_tag_list_remove_tag (xmptaglist, GST_TAG_CONTAINER_FORMAT);
    }

    GST_DEBUG_OBJECT (qtdemux, "Found XMP tags %" GST_PTR_FORMAT, xmptaglist);

    /* prioritize native tags using _KEEP mode */
    gst_tag_list_insert (taglist, xmptaglist, GST_TAG_MERGE_KEEP);
    gst_tag_list_unref (xmptaglist);
  }
}

static void
qtdemux_parse_uuid (GstQTDemux * qtdemux, const guint8 * buffer, gint length)
{
  static const guint8 xmp_uuid[] = { 0xBE, 0x7A, 0xCF, 0xCB,
    0x97, 0xA9, 0x42, 0xE8,
    0x9C, 0x71, 0x99, 0x94,
    0x91, 0xE3, 0xAF, 0xAC
  };
  static const guint8 playready_uuid[] = {
    0xd0, 0x8a, 0x4f, 0x18, 0x10, 0xf3, 0x4a, 0x82,
    0xb6, 0xc8, 0x32, 0xd8, 0xab, 0xa1, 0x83, 0xd3
  };
  guint offset;

  /* counts as header data */
  qtdemux->header_size += length;

  offset = (QT_UINT32 (buffer) == 0) ? 16 : 8;

  if (length <= offset + 16) {
    GST_DEBUG_OBJECT (qtdemux, "uuid atom is too short, skipping");
    return;
  }

  if (memcmp (buffer + offset, xmp_uuid, 16) == 0) {
    GstBuffer *buf;
    GstTagList *taglist;

    buf = _gst_buffer_new_wrapped ((guint8 *) buffer + offset + 16,
        length - offset - 16, NULL);
    taglist = gst_tag_list_from_xmp_buffer (buf);
    gst_buffer_unref (buf);

    qtdemux_handle_xmp_taglist (qtdemux, qtdemux->tag_list, taglist);

  } else if (memcmp (buffer + offset, playready_uuid, 16) == 0) {
    int len;
    const gunichar2 *s_utf16;
    char *contents;

    len = GST_READ_UINT16_LE (buffer + offset + 0x30);
    s_utf16 = (const gunichar2 *) (buffer + offset + 0x32);
    contents = g_utf16_to_utf8 (s_utf16, len / 2, NULL, NULL, NULL);
    GST_ERROR_OBJECT (qtdemux, "contents: %s", contents);

    g_free (contents);

    GST_ELEMENT_ERROR (qtdemux, STREAM, DECRYPT,
        (_("Cannot play stream because it is encrypted with PlayReady DRM.")),
        (NULL));
  } else {
    GST_DEBUG_OBJECT (qtdemux, "Ignoring unknown uuid: %08x-%08x-%08x-%08x",
        GST_READ_UINT32_LE (buffer + offset),
        GST_READ_UINT32_LE (buffer + offset + 4),
        GST_READ_UINT32_LE (buffer + offset + 8),
        GST_READ_UINT32_LE (buffer + offset + 12));
  }
}

static void
qtdemux_parse_sidx (GstQTDemux * qtdemux, const guint8 * buffer, gint length)
{
  GstSidxParser sidx_parser;
  GstIsoffParserResult res;
  guint consumed;

  gst_isoff_qt_sidx_parser_init (&sidx_parser);

  res =
      gst_isoff_qt_sidx_parser_add_data (&sidx_parser, buffer, length,
      &consumed);
  GST_DEBUG_OBJECT (qtdemux, "sidx parse result: %d", res);
  if (res == GST_ISOFF_QT_PARSER_DONE) {
    check_update_duration (qtdemux, sidx_parser.cumulative_pts);
  }
  gst_isoff_qt_sidx_parser_clear (&sidx_parser);
}

/* caller verifies at least 8 bytes in buf */
static void
extract_initial_length_and_fourcc (const guint8 * data, guint size,
    guint64 * plength, guint32 * pfourcc)
{
  guint64 length;
  guint32 fourcc;

  length = QT_UINT32 (data);
  GST_DEBUG ("length 0x%08" G_GINT64_MODIFIER "x", length);
  fourcc = QT_FOURCC (data + 4);
  GST_DEBUG ("atom type %" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));

  if (length == 0) {
    length = G_MAXUINT64;
  } else if (length == 1 && size >= 16) {
    /* this means we have an extended size, which is the 64 bit value of
     * the next 8 bytes */
    length = QT_UINT64 (data + 8);
    GST_DEBUG ("length 0x%08" G_GINT64_MODIFIER "x", length);
  }

  if (plength)
    *plength = length;
  if (pfourcc)
    *pfourcc = fourcc;
}

static gboolean
qtdemux_parse_mehd (GstQTDemux * qtdemux, GstByteReader * br)
{
  guint32 version = 0;
  GstClockTime duration = 0;

  if (!gst_byte_reader_get_uint32_be (br, &version))
    goto failed;

  version >>= 24;
  if (version == 1) {
    if (!gst_byte_reader_get_uint64_be (br, &duration))
      goto failed;
  } else {
    guint32 dur = 0;

    if (!gst_byte_reader_get_uint32_be (br, &dur))
      goto failed;
    duration = dur;
  }

  GST_INFO_OBJECT (qtdemux, "mehd duration: %" G_GUINT64_FORMAT, duration);
  qtdemux->duration = duration;

  return TRUE;

failed:
  {
    GST_DEBUG_OBJECT (qtdemux, "parsing mehd failed");
    return FALSE;
  }
}

static gboolean
qtdemux_parse_trex (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 * ds_duration, guint32 * ds_size, guint32 * ds_flags)
{
  if (!stream->parsed_trex && qtdemux->moov_node) {
    GNode *mvex, *trex;
    GstByteReader trex_data;

    mvex = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_mvex);
    if (mvex) {
      trex = qtdemux_tree_get_child_by_type_full (mvex, FOURCC_trex,
          &trex_data);
      while (trex) {
        guint32 id = 0, dur = 0, size = 0, flags = 0, dummy = 0;

        /* skip version/flags */
        if (!gst_byte_reader_skip (&trex_data, 4))
          goto next;
        if (!gst_byte_reader_get_uint32_be (&trex_data, &id))
          goto next;
        if (id != stream->track_id)
          goto next;
        /* sample description index; ignore */
        if (!gst_byte_reader_get_uint32_be (&trex_data, &dummy))
          goto next;
        if (!gst_byte_reader_get_uint32_be (&trex_data, &dur))
          goto next;
        if (!gst_byte_reader_get_uint32_be (&trex_data, &size))
          goto next;
        if (!gst_byte_reader_get_uint32_be (&trex_data, &flags))
          goto next;

        GST_DEBUG_OBJECT (qtdemux, "fragment defaults for stream %d; "
            "duration %d,  size %d, flags 0x%x", stream->track_id,
            dur, size, flags);

        stream->parsed_trex = TRUE;
        stream->def_sample_duration = dur;
        stream->def_sample_size = size;
        stream->def_sample_flags = flags;

      next:
        /* iterate all siblings */
        trex = qtdemux_tree_get_sibling_by_type_full (trex, FOURCC_trex,
            &trex_data);
      }
    }
  }

  *ds_duration = stream->def_sample_duration;
  *ds_size = stream->def_sample_size;
  *ds_flags = stream->def_sample_flags;

  /* even then, above values are better than random ... */
  if (G_UNLIKELY (!stream->parsed_trex)) {
    GST_WARNING_OBJECT (qtdemux,
        "failed to find fragment defaults for stream %d", stream->track_id);
    return FALSE;
  }

  return TRUE;
}

/* This method should be called whenever a more accurate duration might
 * have been found. It will update all relevant variables if/where needed
 */
static void
check_update_duration (GstQTDemux * qtdemux, GstClockTime duration)
{
  guint i;
  guint64 movdur;
  GstClockTime prevdur;

  movdur = GSTTIME_TO_QTTIME (qtdemux, duration);

  if (movdur > qtdemux->duration) {
    prevdur = QTTIME_TO_GSTTIME (qtdemux, qtdemux->duration);
    GST_DEBUG_OBJECT (qtdemux,
        "Updating total duration to %" GST_TIME_FORMAT " was %" GST_TIME_FORMAT,
        GST_TIME_ARGS (duration), GST_TIME_ARGS (prevdur));
    qtdemux->duration = movdur;
    GST_DEBUG_OBJECT (qtdemux,
        "qtdemux->segment.duration: %" GST_TIME_FORMAT " .stop: %"
        GST_TIME_FORMAT, GST_TIME_ARGS (qtdemux->segment.duration),
        GST_TIME_ARGS (qtdemux->segment.stop));
    if (qtdemux->segment.duration == prevdur) {
      /* If the current segment has duration/stop identical to previous duration
       * update them also (because they were set at that point in time with
       * the wrong duration */
      /* We convert the value *from* the timescale version to avoid rounding errors */
      GstClockTime fixeddur = QTTIME_TO_GSTTIME (qtdemux, movdur);
      GST_DEBUG_OBJECT (qtdemux, "Updated segment.duration and segment.stop");
      qtdemux->segment.duration = fixeddur;
      qtdemux->segment.stop = fixeddur;
    }
  }
  for (i = 0; i < qtdemux->n_streams; i++) {
    QtDemuxStream *stream = qtdemux->streams[i];
    if (stream) {
      movdur = GSTTIME_TO_QTSTREAMTIME (stream, duration);
      if (movdur > stream->duration) {
        GST_DEBUG_OBJECT (qtdemux,
            "Updating stream #%d duration to %" GST_TIME_FORMAT, i,
            GST_TIME_ARGS (duration));
        stream->duration = movdur;
        if (stream->dummy_segment) {
          /* Update all dummy values to new duration */
          stream->segments[0].stop_time = duration;
          stream->segments[0].duration = duration;
          stream->segments[0].media_stop = duration;

          /* let downstream know we possibly have a new stop time */
          if (stream->segment_index != -1) {
            GstClockTime pos;

            if (qtdemux->segment.rate >= 0) {
              pos = stream->segment.start;
            } else {
              pos = stream->segment.stop;
            }

            gst_qtdemux_stream_update_segment (qtdemux, stream,
                stream->segment_index, pos, NULL, NULL);
          }
        }
      }
    }
  }
}

static gboolean
qtdemux_parse_trun (GstQTDemux * qtdemux, GstByteReader * trun,
    QtDemuxStream * stream, guint32 d_sample_duration, guint32 d_sample_size,
    guint32 d_sample_flags, gint64 moof_offset, gint64 moof_length,
    gint64 * base_offset, gint64 * running_offset, gint64 decode_ts)
{
  GstClockTime gst_ts = GST_CLOCK_TIME_NONE;
  guint64 timestamp;
  gint32 data_offset = 0;
  guint32 flags = 0, first_flags = 0, samples_count = 0;
  gint i;
  guint8 *data;
  guint entry_size, dur_offset, size_offset, flags_offset = 0, ct_offset = 0;
  QtDemuxSample *sample;
  gboolean ismv = FALSE;

  GST_LOG_OBJECT (qtdemux, "parsing trun stream %d; "
      "default dur %d, size %d, flags 0x%x, base offset %" G_GINT64_FORMAT ", "
      "decode ts %" G_GINT64_FORMAT, stream->track_id, d_sample_duration,
      d_sample_size, d_sample_flags, *base_offset, decode_ts);

  if (stream->pending_seek && moof_offset < stream->pending_seek->moof_offset) {
    GST_INFO_OBJECT (stream->pad, "skipping trun before seek target fragment");
    return TRUE;
  }

  /* presence of stss or not can't really tell us much,
   * and flags and so on tend to be marginally reliable in these files */
  if (stream->subtype == FOURCC_soun) {
    GST_DEBUG_OBJECT (qtdemux,
        "sound track in fragmented file; marking all keyframes");
    stream->all_keyframe = TRUE;
  }

  if (!gst_byte_reader_skip (trun, 1) ||
      !gst_byte_reader_get_uint24_be (trun, &flags))
    goto fail;

  if (!gst_byte_reader_get_uint32_be (trun, &samples_count))
    goto fail;

  if (flags & TR_DATA_OFFSET) {
    /* note this is really signed */
    if (!gst_byte_reader_get_int32_be (trun, &data_offset))
      goto fail;
    GST_LOG_OBJECT (qtdemux, "trun data offset %d", data_offset);
    /* default base offset = first byte of moof */
    if (*base_offset == -1) {
      GST_LOG_OBJECT (qtdemux, "base_offset at moof");
      *base_offset = moof_offset;
    }
    *running_offset = *base_offset + data_offset;
  } else {
    /* if no offset at all, that would mean data starts at moof start,
     * which is a bit wrong and is ismv crappy way, so compensate
     * assuming data is in mdat following moof */
    if (*base_offset == -1) {
      *base_offset = moof_offset + moof_length + 8;
      GST_LOG_OBJECT (qtdemux, "base_offset assumed in mdat after moof");
      ismv = TRUE;
    }
    if (*running_offset == -1)
      *running_offset = *base_offset;
  }

  GST_LOG_OBJECT (qtdemux, "running offset now %" G_GINT64_FORMAT,
      *running_offset);
  GST_LOG_OBJECT (qtdemux, "trun offset %d, flags 0x%x, entries %d",
      data_offset, flags, samples_count);

  if (flags & TR_FIRST_SAMPLE_FLAGS) {
    if (G_UNLIKELY (flags & TR_SAMPLE_FLAGS)) {
      GST_DEBUG_OBJECT (qtdemux,
          "invalid flags; SAMPLE and FIRST_SAMPLE present, discarding latter");
      flags ^= TR_FIRST_SAMPLE_FLAGS;
    } else {
      if (!gst_byte_reader_get_uint32_be (trun, &first_flags))
        goto fail;
      GST_LOG_OBJECT (qtdemux, "first flags: 0x%x", first_flags);
    }
  }

  /* FIXME ? spec says other bits should also be checked to determine
   * entry size (and prefix size for that matter) */
  entry_size = 0;
  dur_offset = size_offset = 0;
  if (flags & TR_SAMPLE_DURATION) {
    GST_LOG_OBJECT (qtdemux, "entry duration present");
    dur_offset = entry_size;
    entry_size += 4;
  }
  if (flags & TR_SAMPLE_SIZE) {
    GST_LOG_OBJECT (qtdemux, "entry size present");
    size_offset = entry_size;
    entry_size += 4;
  }
  if (flags & TR_SAMPLE_FLAGS) {
    GST_LOG_OBJECT (qtdemux, "entry flags present");
    flags_offset = entry_size;
    entry_size += 4;
  }
  if (flags & TR_COMPOSITION_TIME_OFFSETS) {
    GST_LOG_OBJECT (qtdemux, "entry ct offset present");
    ct_offset = entry_size;
    entry_size += 4;
  }

  if (!qt_atom_parser_has_chunks (trun, samples_count, entry_size))
    goto fail;
  data = (guint8 *) gst_byte_reader_peek_data_unchecked (trun);

  if (stream->n_samples + samples_count >=
      QTDEMUX_MAX_SAMPLE_INDEX_SIZE / sizeof (QtDemuxSample))
    goto index_too_big;

  GST_DEBUG_OBJECT (qtdemux, "allocating n_samples %u * %u (%.2f MB)",
      stream->n_samples + samples_count, (guint) sizeof (QtDemuxSample),
      (stream->n_samples + samples_count) *
      sizeof (QtDemuxSample) / (1024.0 * 1024.0));

  /* create a new array of samples if it's the first sample parsed */
  if (stream->n_samples == 0) {
    g_assert (stream->samples == NULL);
    stream->samples = g_try_new0 (QtDemuxSample, samples_count);
    /* or try to reallocate it with space enough to insert the new samples */
  } else
    stream->samples = g_try_renew (QtDemuxSample, stream->samples,
        stream->n_samples + samples_count);
  if (stream->samples == NULL)
    goto out_of_memory;

  if (qtdemux->fragment_start != -1) {
    timestamp = GSTTIME_TO_QTSTREAMTIME (stream, qtdemux->fragment_start);
    qtdemux->fragment_start = -1;
  } else {
    if (stream->n_samples == 0) {
      if (decode_ts > 0) {
        timestamp = decode_ts;
      } else if (stream->pending_seek != NULL) {
        /* if we don't have a timestamp from a tfdt box, we'll use the one
         * from the mfra seek table */
        GST_INFO_OBJECT (stream->pad, "pending seek ts = %" GST_TIME_FORMAT,
            GST_TIME_ARGS (stream->pending_seek->ts));

        /* FIXME: this is not fully correct, the timestamp refers to the random
         * access sample refered to in the tfra entry, which may not necessarily
         * be the first sample in the tfrag/trun (but hopefully/usually is) */
        timestamp = GSTTIME_TO_QTSTREAMTIME (stream, stream->pending_seek->ts);
      } else {
        timestamp = 0;
      }

      gst_ts = QTSTREAMTIME_TO_GSTTIME (stream, timestamp);
      GST_INFO_OBJECT (stream->pad, "first sample ts %" GST_TIME_FORMAT,
          GST_TIME_ARGS (gst_ts));
    } else {
      /* subsequent fragments extend stream */
      timestamp =
          stream->samples[stream->n_samples - 1].timestamp +
          stream->samples[stream->n_samples - 1].duration;

      gst_ts = QTSTREAMTIME_TO_GSTTIME (stream, timestamp);
      GST_INFO_OBJECT (qtdemux, "first sample ts %" GST_TIME_FORMAT
          " (extends previous samples)", GST_TIME_ARGS (gst_ts));
    }
  }

  sample = stream->samples + stream->n_samples;
  for (i = 0; i < samples_count; i++) {
    guint32 dur, size, sflags, ct;

    /* first read sample data */
    if (flags & TR_SAMPLE_DURATION) {
      dur = QT_UINT32 (data + dur_offset);
    } else {
      dur = d_sample_duration;
    }
    if (flags & TR_SAMPLE_SIZE) {
      size = QT_UINT32 (data + size_offset);
    } else {
      size = d_sample_size;
    }
    if (flags & TR_FIRST_SAMPLE_FLAGS) {
      if (i == 0) {
        sflags = first_flags;
      } else {
        sflags = d_sample_flags;
      }
    } else if (flags & TR_SAMPLE_FLAGS) {
      sflags = QT_UINT32 (data + flags_offset);
    } else {
      sflags = d_sample_flags;
    }
    if (flags & TR_COMPOSITION_TIME_OFFSETS) {
      ct = QT_UINT32 (data + ct_offset);
    } else {
      ct = 0;
    }
    data += entry_size;

    /* fill the sample information */
    sample->offset = *running_offset;
    sample->pts_offset = ct;
    sample->size = size;
    sample->timestamp = timestamp;
    sample->duration = dur;
    /* sample-is-difference-sample */
    /* ismv seems to use 0x40 for keyframe, 0xc0 for non-keyframe,
     * now idea how it relates to bitfield other than massive LE/BE confusion */
    sample->keyframe = ismv ? ((sflags & 0xff) == 0x40) : !(sflags & 0x10000);
    *running_offset += size;
    timestamp += dur;
    stream->duration_moof += dur;
    sample++;
  }

  /* Update total duration if needed */
  check_update_duration (qtdemux, QTSTREAMTIME_TO_GSTTIME (stream, timestamp));

  stream->n_samples += samples_count;
  stream->n_samples_moof += samples_count;

  if (stream->pending_seek != NULL)
    stream->pending_seek = NULL;

  return TRUE;

fail:
  {
    GST_WARNING_OBJECT (qtdemux, "failed to parse trun");
    return FALSE;
  }
out_of_memory:
  {
    GST_WARNING_OBJECT (qtdemux, "failed to allocate %d samples",
        stream->n_samples);
    return FALSE;
  }
index_too_big:
  {
    GST_WARNING_OBJECT (qtdemux, "not allocating index of %d samples, would "
        "be larger than %uMB (broken file?)", stream->n_samples,
        QTDEMUX_MAX_SAMPLE_INDEX_SIZE >> 20);
    return FALSE;
  }
}

/* find stream with @id */
static inline QtDemuxStream *
qtdemux_find_stream (GstQTDemux * qtdemux, guint32 id)
{
  QtDemuxStream *stream;
  gint i;

  /* check */
  if (G_UNLIKELY (!id)) {
    GST_DEBUG_OBJECT (qtdemux, "invalid track id 0");
    return NULL;
  }

  /* try to get it fast and simple */
  if (G_LIKELY (id <= qtdemux->n_streams)) {
    stream = qtdemux->streams[id - 1];
    if (G_LIKELY (stream->track_id == id))
      return stream;
  }

  /* linear search otherwise */
  for (i = 0; i < qtdemux->n_streams; i++) {
    stream = qtdemux->streams[i];
    if (stream->track_id == id)
      return stream;
  }
  if (qtdemux->mss_mode) {
    /* mss should have only 1 stream anyway */
    return qtdemux->streams[0];
  }

  return NULL;
}

static gboolean
qtdemux_parse_mfhd (GstQTDemux * qtdemux, GstByteReader * mfhd,
    guint32 * fragment_number)
{
  if (!gst_byte_reader_skip (mfhd, 4))
    goto fail;
  if (!gst_byte_reader_get_uint32_be (mfhd, fragment_number))
    goto fail;
  return TRUE;
fail:
  {
    GST_WARNING_OBJECT (qtdemux, "Failed to parse mfhd atom");
    return FALSE;
  }
}

static gboolean
qtdemux_parse_tfhd (GstQTDemux * qtdemux, GstByteReader * tfhd,
    QtDemuxStream ** stream, guint32 * default_sample_duration,
    guint32 * default_sample_size, guint32 * default_sample_flags,
    gint64 * base_offset)
{
  guint32 flags = 0;
  guint32 track_id = 0;

  if (!gst_byte_reader_skip (tfhd, 1) ||
      !gst_byte_reader_get_uint24_be (tfhd, &flags))
    goto invalid_track;

  if (!gst_byte_reader_get_uint32_be (tfhd, &track_id))
    goto invalid_track;

  *stream = qtdemux_find_stream (qtdemux, track_id);
  if (G_UNLIKELY (!*stream))
    goto unknown_stream;

  if (flags & TF_DEFAULT_BASE_IS_MOOF)
    *base_offset = qtdemux->moof_offset;

  if (flags & TF_BASE_DATA_OFFSET)
    if (!gst_byte_reader_get_uint64_be (tfhd, (guint64 *) base_offset))
      goto invalid_track;

  /* obtain stream defaults */
  qtdemux_parse_trex (qtdemux, *stream,
      default_sample_duration, default_sample_size, default_sample_flags);

  /* FIXME: Handle TF_SAMPLE_DESCRIPTION_INDEX properly */
  if (flags & TF_SAMPLE_DESCRIPTION_INDEX)
    if (!gst_byte_reader_skip (tfhd, 4))
      goto invalid_track;

  if (flags & TF_DEFAULT_SAMPLE_DURATION)
    if (!gst_byte_reader_get_uint32_be (tfhd, default_sample_duration))
      goto invalid_track;

  if (flags & TF_DEFAULT_SAMPLE_SIZE)
    if (!gst_byte_reader_get_uint32_be (tfhd, default_sample_size))
      goto invalid_track;

  if (flags & TF_DEFAULT_SAMPLE_FLAGS)
    if (!gst_byte_reader_get_uint32_be (tfhd, default_sample_flags))
      goto invalid_track;

  return TRUE;

invalid_track:
  {
    GST_WARNING_OBJECT (qtdemux, "invalid track fragment header");
    return FALSE;
  }
unknown_stream:
  {
    GST_DEBUG_OBJECT (qtdemux, "unknown stream in tfhd");
    return TRUE;
  }
}

static gboolean
qtdemux_parse_tfdt (GstQTDemux * qtdemux, GstByteReader * br,
    guint64 * decode_time)
{
  guint32 version = 0;

  if (!gst_byte_reader_get_uint32_be (br, &version))
    return FALSE;

  version >>= 24;
  if (version == 1) {
    if (!gst_byte_reader_get_uint64_be (br, decode_time))
      goto failed;
  } else {
    guint32 dec_time = 0;
    if (!gst_byte_reader_get_uint32_be (br, &dec_time))
      goto failed;
    *decode_time = dec_time;
  }

  GST_INFO_OBJECT (qtdemux, "Track fragment decode time: %" G_GUINT64_FORMAT,
      *decode_time);

  return TRUE;

failed:
  {
    GST_DEBUG_OBJECT (qtdemux, "parsing tfdt failed");
    return FALSE;
  }
}

/* Returns a pointer to a GstStructure containing the properties of
 * the stream sample identified by @sample_index. The caller must unref
 * the returned object after use. Returns NULL if unsuccessful. */
static GstStructure *
qtdemux_get_cenc_sample_properties (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint sample_index)
{
  QtDemuxCencSampleSetInfo *info = NULL;

  g_return_val_if_fail (stream != NULL, NULL);
  g_return_val_if_fail (stream->protected, NULL);
  g_return_val_if_fail (stream->protection_scheme_info != NULL, NULL);

  info = (QtDemuxCencSampleSetInfo *) stream->protection_scheme_info;

  /* Currently, cenc properties for groups of samples are not supported, so
   * simply return a copy of the default sample properties */
  return gst_structure_copy (info->default_properties);
}

/* Parses the sizes of sample auxiliary information contained within a stream,
 * as given in a saiz box. Returns array of sample_count guint8 size values,
 * or NULL on failure */
static guint8 *
qtdemux_parse_saiz (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstByteReader * br, guint32 * sample_count)
{
  guint32 flags = 0;
  guint8 *info_sizes;
  guint8 default_info_size;

  g_return_val_if_fail (qtdemux != NULL, NULL);
  g_return_val_if_fail (stream != NULL, NULL);
  g_return_val_if_fail (br != NULL, NULL);
  g_return_val_if_fail (sample_count != NULL, NULL);

  if (!gst_byte_reader_get_uint32_be (br, &flags))
    return NULL;

  if (flags & 0x1) {
    /* aux_info_type and aux_info_type_parameter are ignored */
    if (!gst_byte_reader_skip (br, 8))
      return NULL;
  }

  if (!gst_byte_reader_get_uint8 (br, &default_info_size))
    return NULL;
  GST_DEBUG_OBJECT (qtdemux, "default_info_size: %u", default_info_size);

  if (!gst_byte_reader_get_uint32_be (br, sample_count))
    return NULL;
  GST_DEBUG_OBJECT (qtdemux, "sample_count: %u", *sample_count);


  if (default_info_size == 0) {
    if (!gst_byte_reader_dup_data (br, *sample_count, &info_sizes)) {
      return NULL;
    }
  } else {
    info_sizes = g_new (guint8, *sample_count);
    memset (info_sizes, default_info_size, *sample_count);
  }

  return info_sizes;
}

/* Parses the offset of sample auxiliary information contained within a stream,
 * as given in a saio box. Returns TRUE if successful; FALSE otherwise. */
static gboolean
qtdemux_parse_saio (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstByteReader * br, guint32 * info_type, guint32 * info_type_parameter,
    guint64 * offset)
{
  guint8 version = 0;
  guint32 flags = 0;
  guint32 aux_info_type = 0;
  guint32 aux_info_type_parameter = 0;
  guint32 entry_count;
  guint32 off_32;
  guint64 off_64;
  const guint8 *aux_info_type_data = NULL;

  g_return_val_if_fail (qtdemux != NULL, FALSE);
  g_return_val_if_fail (stream != NULL, FALSE);
  g_return_val_if_fail (br != NULL, FALSE);
  g_return_val_if_fail (offset != NULL, FALSE);

  if (!gst_byte_reader_get_uint8 (br, &version))
    return FALSE;

  if (!gst_byte_reader_get_uint24_be (br, &flags))
    return FALSE;

  if (flags & 0x1) {

    if (!gst_byte_reader_get_data (br, 4, &aux_info_type_data))
      return FALSE;
    aux_info_type = QT_FOURCC (aux_info_type_data);

    if (!gst_byte_reader_get_uint32_be (br, &aux_info_type_parameter))
      return FALSE;
  } else if (stream->protected) {
    aux_info_type = stream->protection_scheme_type;
  } else {
    aux_info_type = stream->fourcc;
  }

  if (info_type)
    *info_type = aux_info_type;
  if (info_type_parameter)
    *info_type_parameter = aux_info_type_parameter;

  GST_DEBUG_OBJECT (qtdemux, "aux_info_type: '%" GST_FOURCC_FORMAT "', "
      "aux_info_type_parameter:  %#06x",
      GST_FOURCC_ARGS (aux_info_type), aux_info_type_parameter);

  if (!gst_byte_reader_get_uint32_be (br, &entry_count))
    return FALSE;

  if (entry_count != 1) {
    GST_ERROR_OBJECT (qtdemux, "multiple offsets are not supported");
    return FALSE;
  }

  if (version == 0) {
    if (!gst_byte_reader_get_uint32_be (br, &off_32))
      return FALSE;
    *offset = (guint64) off_32;
  } else {
    if (!gst_byte_reader_get_uint64_be (br, &off_64))
      return FALSE;
    *offset = off_64;
  }

  GST_DEBUG_OBJECT (qtdemux, "offset: %" G_GUINT64_FORMAT, *offset);
  return TRUE;
}

static void
qtdemux_gst_structure_free (GstStructure * gststructure)
{
  if (gststructure) {
    gst_structure_free (gststructure);
  }
}

/* Parses auxiliary information relating to samples protected using Common
 * Encryption (cenc); the format of this information is defined in
 * ISO/IEC 23001-7. Returns TRUE if successful; FALSE otherwise. */
static gboolean
qtdemux_parse_cenc_aux_info (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstByteReader * br, guint8 * info_sizes, guint32 sample_count)
{
  QtDemuxCencSampleSetInfo *ss_info = NULL;
  guint8 size;
  gint i;

  g_return_val_if_fail (qtdemux != NULL, FALSE);
  g_return_val_if_fail (stream != NULL, FALSE);
  g_return_val_if_fail (br != NULL, FALSE);
  g_return_val_if_fail (stream->protected, FALSE);
  g_return_val_if_fail (stream->protection_scheme_info != NULL, FALSE);

  ss_info = (QtDemuxCencSampleSetInfo *) stream->protection_scheme_info;

  if (ss_info->crypto_info) {
    GST_LOG_OBJECT (qtdemux, "unreffing existing crypto_info");
    g_ptr_array_free (ss_info->crypto_info, TRUE);
  }

  ss_info->crypto_info =
      g_ptr_array_new_full (sample_count,
      (GDestroyNotify) qtdemux_gst_structure_free);

  for (i = 0; i < sample_count; ++i) {
    GstStructure *properties;
    guint16 n_subsamples = 0;
    guint8 *data;
    guint iv_size;
    GstBuffer *buf;

    properties = qtdemux_get_cenc_sample_properties (qtdemux, stream, i);
    if (properties == NULL) {
      GST_ERROR_OBJECT (qtdemux, "failed to get properties for sample %u", i);
      return FALSE;
    }
    if (!gst_structure_get_uint (properties, "iv_size", &iv_size)) {
      GST_ERROR_OBJECT (qtdemux, "failed to get iv_size for sample %u", i);
      gst_structure_free (properties);
      return FALSE;
    }
    if (!gst_byte_reader_dup_data (br, iv_size, &data)) {
      GST_ERROR_OBJECT (qtdemux, "failed to get IV for sample %u", i);
      gst_structure_free (properties);
      return FALSE;
    }
    buf = gst_buffer_new_wrapped (data, iv_size);
    gst_structure_set (properties, "iv", GST_TYPE_BUFFER, buf, NULL);
    gst_buffer_unref (buf);
    size = info_sizes[i];
    if (size > iv_size) {
      if (!gst_byte_reader_get_uint16_be (br, &n_subsamples)
          || !(n_subsamples > 0)) {
        gst_structure_free (properties);
        GST_ERROR_OBJECT (qtdemux,
            "failed to get subsample count for sample %u", i);
        return FALSE;
      }
      GST_LOG_OBJECT (qtdemux, "subsample count: %u", n_subsamples);
      if (!gst_byte_reader_dup_data (br, n_subsamples * 6, &data)) {
        GST_ERROR_OBJECT (qtdemux, "failed to get subsample data for sample %u",
            i);
        gst_structure_free (properties);
        return FALSE;
      }
      buf = gst_buffer_new_wrapped (data, n_subsamples * 6);
      if (!buf) {
        gst_structure_free (properties);
        return FALSE;
      }
      gst_structure_set (properties,
          "subsample_count", G_TYPE_UINT, n_subsamples,
          "subsamples", GST_TYPE_BUFFER, buf, NULL);
      gst_buffer_unref (buf);
    } else {
      gst_structure_set (properties, "subsample_count", G_TYPE_UINT, 0, NULL);
    }
    g_ptr_array_add (ss_info->crypto_info, properties);
  }
  return TRUE;
}

/* Converts a UUID in raw byte form to a string representation, as defined in
 * RFC 4122. The caller takes ownership of the returned string and is
 * responsible for freeing it after use. */
static gchar *
qtdemux_uuid_bytes_to_string (gconstpointer uuid_bytes)
{
  const guint8 *uuid = (const guint8 *) uuid_bytes;

  return g_strdup_printf ("%02x%02x%02x%02x-%02x%02x-%02x%02x-"
      "%02x%02x-%02x%02x%02x%02x%02x%02x",
      uuid[0], uuid[1], uuid[2], uuid[3],
      uuid[4], uuid[5], uuid[6], uuid[7],
      uuid[8], uuid[9], uuid[10], uuid[11],
      uuid[12], uuid[13], uuid[14], uuid[15]);
}

/* Parses a Protection System Specific Header box (pssh), as defined in the
 * Common Encryption (cenc) standard (ISO/IEC 23001-7), which contains
 * information needed by a specific content protection system in order to
 * decrypt cenc-protected tracks. Returns TRUE if successful; FALSE
 * otherwise. */
static gboolean
qtdemux_parse_pssh (GstQTDemux * qtdemux, GNode * node)
{
  gchar *sysid_string;
  guint32 pssh_size = QT_UINT32 (node->data);
  GstBuffer *pssh = NULL;
  GstEvent *event = NULL;
  guint32 parent_box_type;
  gint i;

  if (G_UNLIKELY (pssh_size < 32U)) {
    GST_ERROR_OBJECT (qtdemux, "invalid box size");
    return FALSE;
  }

  sysid_string =
      qtdemux_uuid_bytes_to_string ((const guint8 *) node->data + 12);

  gst_qtdemux_append_protection_system_id (qtdemux, sysid_string);

  pssh = gst_buffer_new_wrapped (g_memdup (node->data, pssh_size), pssh_size);
  GST_LOG_OBJECT (qtdemux, "cenc pssh size: %" G_GSIZE_FORMAT,
      gst_buffer_get_size (pssh));

  parent_box_type = QT_FOURCC ((const guint8 *) node->parent->data + 4);

  /* Push an event containing the pssh box onto the queues of all streams. */
  event = gst_event_new_protection (sysid_string, pssh,
      (parent_box_type == FOURCC_moov) ? "isobmff/moov" : "isobmff/moof");
  for (i = 0; i < qtdemux->n_streams; ++i) {
    g_queue_push_tail (&qtdemux->streams[i]->protection_scheme_event_queue,
        gst_event_ref (event));
  }
  g_free (sysid_string);
  gst_event_unref (event);
  gst_buffer_unref (pssh);
  return TRUE;
}

static gboolean
qtdemux_parse_moof (GstQTDemux * qtdemux, const guint8 * buffer, guint length,
    guint64 moof_offset, QtDemuxStream * stream)
{
  GNode *moof_node, *traf_node, *tfhd_node, *trun_node, *tfdt_node, *mfhd_node;
  GstByteReader mfhd_data, trun_data, tfhd_data, tfdt_data;
  GNode *saiz_node, *saio_node, *pssh_node;
  GstByteReader saiz_data, saio_data;
  guint32 ds_size = 0, ds_duration = 0, ds_flags = 0;
  gint64 base_offset, running_offset;
  guint32 frag_num;

  /* NOTE @stream ignored */

  moof_node = g_node_new ((guint8 *) buffer);
  qtdemux_parse_node (qtdemux, moof_node, buffer, length);
  qtdemux_node_dump (qtdemux, moof_node);

  /* Get fragment number from mfhd and check it's valid */
  mfhd_node =
      qtdemux_tree_get_child_by_type_full (moof_node, FOURCC_mfhd, &mfhd_data);
  if (mfhd_node == NULL)
    goto missing_mfhd;
  if (!qtdemux_parse_mfhd (qtdemux, &mfhd_data, &frag_num))
    goto fail;
  GST_DEBUG_OBJECT (qtdemux, "Fragment #%d", frag_num);

  /* unknown base_offset to start with */
  base_offset = running_offset = -1;
  traf_node = qtdemux_tree_get_child_by_type (moof_node, FOURCC_traf);
  while (traf_node) {
    guint64 decode_time = 0;

    /* Fragment Header node */
    tfhd_node =
        qtdemux_tree_get_child_by_type_full (traf_node, FOURCC_tfhd,
        &tfhd_data);
    if (!tfhd_node)
      goto missing_tfhd;
    if (!qtdemux_parse_tfhd (qtdemux, &tfhd_data, &stream, &ds_duration,
            &ds_size, &ds_flags, &base_offset))
      goto missing_tfhd;

    /* The following code assumes at most a single set of sample auxiliary
     * data in the fragment (consisting of a saiz box and a corresponding saio
     * box); in theory, however, there could be multiple sets of sample
     * auxiliary data in a fragment. */
    saiz_node =
        qtdemux_tree_get_child_by_type_full (traf_node, FOURCC_saiz,
        &saiz_data);
    if (saiz_node) {
      guint32 info_type = 0;
      guint64 offset = 0;
      guint32 info_type_parameter = 0;

      g_free (qtdemux->cenc_aux_info_sizes);

      qtdemux->cenc_aux_info_sizes =
          qtdemux_parse_saiz (qtdemux, stream, &saiz_data,
          &qtdemux->cenc_aux_sample_count);
      if (qtdemux->cenc_aux_info_sizes == NULL) {
        GST_ERROR_OBJECT (qtdemux, "failed to parse saiz box");
        goto fail;
      }
      saio_node =
          qtdemux_tree_get_child_by_type_full (traf_node, FOURCC_saio,
          &saio_data);
      if (!saio_node) {
        GST_ERROR_OBJECT (qtdemux, "saiz box without a corresponding saio box");
        g_free (qtdemux->cenc_aux_info_sizes);
        qtdemux->cenc_aux_info_sizes = NULL;
        goto fail;
      }

      if (G_UNLIKELY (!qtdemux_parse_saio (qtdemux, stream, &saio_data,
                  &info_type, &info_type_parameter, &offset))) {
        GST_ERROR_OBJECT (qtdemux, "failed to parse saio box");
        g_free (qtdemux->cenc_aux_info_sizes);
        qtdemux->cenc_aux_info_sizes = NULL;
        goto fail;
      }
      if (base_offset > -1 && base_offset > qtdemux->moof_offset)
        offset += (guint64) (base_offset - qtdemux->moof_offset);
      if (info_type == FOURCC_cenc && info_type_parameter == 0U) {
        GstByteReader br;
        if (offset > length) {
          GST_DEBUG_OBJECT (qtdemux, "cenc auxiliary info stored out of moof");
          qtdemux->cenc_aux_info_offset = offset;
        } else {
          gst_byte_reader_init (&br, buffer + offset, length - offset);
          if (!qtdemux_parse_cenc_aux_info (qtdemux, stream, &br,
                  qtdemux->cenc_aux_info_sizes,
                  qtdemux->cenc_aux_sample_count)) {
            GST_ERROR_OBJECT (qtdemux, "failed to parse cenc auxiliary info");
            g_free (qtdemux->cenc_aux_info_sizes);
            qtdemux->cenc_aux_info_sizes = NULL;
            goto fail;
          }
        }
      }
    }

    tfdt_node =
        qtdemux_tree_get_child_by_type_full (traf_node, FOURCC_tfdt,
        &tfdt_data);
    if (tfdt_node) {
      GstClockTime decode_time_ts;

      /* We'll use decode_time to interpolate timestamps
       * in case the input timestamps are missing */
      qtdemux_parse_tfdt (qtdemux, &tfdt_data, &decode_time);

      decode_time_ts = QTSTREAMTIME_TO_GSTTIME (stream, decode_time);

      GST_DEBUG_OBJECT (qtdemux, "decode time %" G_GINT64_FORMAT
          " (%" GST_TIME_FORMAT ")", decode_time,
          GST_TIME_ARGS (decode_time_ts));

      /* Discard the fragment buffer timestamp info to avoid using it.
       * Rely on tfdt instead as it is more accurate than the timestamp
       * that is fetched from a manifest/playlist and is usually
       * less accurate. */
      qtdemux->fragment_start = -1;
    }

    if (G_UNLIKELY (!stream)) {
      /* we lost track of offset, we'll need to regain it,
       * but can delay complaining until later or avoid doing so altogether */
      base_offset = -2;
      goto next;
    }
    if (G_UNLIKELY (base_offset < -1))
      goto lost_offset;

    if (qtdemux->upstream_format_is_time)
      gst_qtdemux_stream_flush_samples_data (qtdemux, stream);

    /* initialise moof sample data */
    stream->n_samples_moof = 0;
    stream->duration_moof = 0;

    /* Track Run node */
    trun_node =
        qtdemux_tree_get_child_by_type_full (traf_node, FOURCC_trun,
        &trun_data);
    while (trun_node) {
      qtdemux_parse_trun (qtdemux, &trun_data, stream,
          ds_duration, ds_size, ds_flags, moof_offset, length, &base_offset,
          &running_offset, decode_time);
      /* iterate all siblings */
      trun_node = qtdemux_tree_get_sibling_by_type_full (trun_node, FOURCC_trun,
          &trun_data);
    }
    /* if no new base_offset provided for next traf,
     * base is end of current traf */
    base_offset = running_offset;
    running_offset = -1;

    if (stream->n_samples_moof && stream->duration_moof)
      stream->new_caps = TRUE;

  next:
    /* iterate all siblings */
    traf_node = qtdemux_tree_get_sibling_by_type (traf_node, FOURCC_traf);
  }

  /* parse any protection system info */
  pssh_node = qtdemux_tree_get_child_by_type (moof_node, FOURCC_pssh);
  while (pssh_node) {
    GST_LOG_OBJECT (qtdemux, "Parsing pssh box.");
    qtdemux_parse_pssh (qtdemux, pssh_node);
    pssh_node = qtdemux_tree_get_sibling_by_type (pssh_node, FOURCC_pssh);
  }

  g_node_destroy (moof_node);
  return TRUE;

missing_tfhd:
  {
    GST_DEBUG_OBJECT (qtdemux, "missing tfhd box");
    goto fail;
  }
missing_mfhd:
  {
    GST_DEBUG_OBJECT (qtdemux, "Missing mfhd box");
    goto fail;
  }
lost_offset:
  {
    GST_DEBUG_OBJECT (qtdemux, "lost offset");
    goto fail;
  }
fail:
  {
    g_node_destroy (moof_node);
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")), (NULL));
    return FALSE;
  }
}

#if 0
/* might be used if some day we actually use mfra & co
 * for random access to fragments,
 * but that will require quite some modifications and much less relying
 * on a sample array */
#endif

static gboolean
qtdemux_parse_tfra (GstQTDemux * qtdemux, GNode * tfra_node)
{
  QtDemuxStream *stream;
  guint32 ver_flags, track_id, len, num_entries, i;
  guint value_size, traf_size, trun_size, sample_size;
  guint64 time = 0, moof_offset = 0;
#if 0
  GstBuffer *buf = NULL;
  GstFlowReturn ret;
#endif
  GstByteReader tfra;

  gst_byte_reader_init (&tfra, tfra_node->data, QT_UINT32 (tfra_node->data));

  if (!gst_byte_reader_skip (&tfra, 8))
    return FALSE;

  if (!gst_byte_reader_get_uint32_be (&tfra, &ver_flags))
    return FALSE;

  if (!gst_byte_reader_get_uint32_be (&tfra, &track_id)
      || !gst_byte_reader_get_uint32_be (&tfra, &len)
      || !gst_byte_reader_get_uint32_be (&tfra, &num_entries))
    return FALSE;

  GST_DEBUG_OBJECT (qtdemux, "parsing tfra box for track id %u", track_id);

  stream = qtdemux_find_stream (qtdemux, track_id);
  if (stream == NULL)
    goto unknown_trackid;

  value_size = ((ver_flags >> 24) == 1) ? sizeof (guint64) : sizeof (guint32);
  sample_size = (len & 3) + 1;
  trun_size = ((len & 12) >> 2) + 1;
  traf_size = ((len & 48) >> 4) + 1;

  GST_DEBUG_OBJECT (qtdemux, "%u entries, sizes: value %u, traf %u, trun %u, "
      "sample %u", num_entries, value_size, traf_size, trun_size, sample_size);

  if (num_entries == 0)
    goto no_samples;

  if (!qt_atom_parser_has_chunks (&tfra, num_entries,
          value_size + value_size + traf_size + trun_size + sample_size))
    goto corrupt_file;

  g_free (stream->ra_entries);
  stream->ra_entries = g_new (QtDemuxRandomAccessEntry, num_entries);
  stream->n_ra_entries = num_entries;

  for (i = 0; i < num_entries; i++) {
    qt_atom_parser_get_offset (&tfra, value_size, &time);
    qt_atom_parser_get_offset (&tfra, value_size, &moof_offset);
    qt_atom_parser_get_uint_with_size_unchecked (&tfra, traf_size);
    qt_atom_parser_get_uint_with_size_unchecked (&tfra, trun_size);
    qt_atom_parser_get_uint_with_size_unchecked (&tfra, sample_size);

    time = QTSTREAMTIME_TO_GSTTIME (stream, time);

    GST_LOG_OBJECT (qtdemux, "fragment time: %" GST_TIME_FORMAT ", "
        " moof_offset: %" G_GUINT64_FORMAT, GST_TIME_ARGS (time), moof_offset);

    stream->ra_entries[i].ts = time;
    stream->ra_entries[i].moof_offset = moof_offset;

    /* don't want to go through the entire file and read all moofs at startup */
#if 0
    ret = gst_qtdemux_pull_atom (qtdemux, moof_offset, 0, &buf);
    if (ret != GST_FLOW_OK)
      goto corrupt_file;
    qtdemux_parse_moof (qtdemux, GST_BUFFER_DATA (buf), GST_BUFFER_SIZE (buf),
        moof_offset, stream);
    gst_buffer_unref (buf);
#endif
  }

  check_update_duration (qtdemux, time);

  return TRUE;

/* ERRORS */
unknown_trackid:
  {
    GST_WARNING_OBJECT (qtdemux, "Couldn't find stream for track %u", track_id);
    return FALSE;
  }
corrupt_file:
  {
    GST_WARNING_OBJECT (qtdemux, "broken traf box, ignoring");
    return FALSE;
  }
no_samples:
  {
    GST_WARNING_OBJECT (qtdemux, "stream has no samples");
    return FALSE;
  }
}

static gboolean
qtdemux_pull_mfro_mfra (GstQTDemux * qtdemux)
{
  GstMapInfo mfro_map = GST_MAP_INFO_INIT;
  GstMapInfo mfra_map = GST_MAP_INFO_INIT;
  GstBuffer *mfro = NULL, *mfra = NULL;
  GstFlowReturn flow;
  gboolean ret = FALSE;
  GNode *mfra_node, *tfra_node;
  guint64 mfra_offset = 0;
  guint32 fourcc, mfra_size;
  gint64 len;

  /* query upstream size in bytes */
  if (!gst_pad_peer_query_duration (qtdemux->sinkpad, GST_FORMAT_BYTES, &len))
    goto size_query_failed;

  /* mfro box should be at the very end of the file */
  flow = gst_qtdemux_pull_atom (qtdemux, len - 16, 16, &mfro);
  if (flow != GST_FLOW_OK)
    goto exit;

  gst_buffer_map (mfro, &mfro_map, GST_MAP_READ);

  fourcc = QT_FOURCC (mfro_map.data + 4);
  if (fourcc != FOURCC_mfro)
    goto exit;

  GST_INFO_OBJECT (qtdemux, "Found mfro box");
  if (mfro_map.size < 16)
    goto invalid_mfro_size;

  mfra_size = QT_UINT32 (mfro_map.data + 12);
  if (mfra_size >= len)
    goto invalid_mfra_size;

  mfra_offset = len - mfra_size;

  GST_INFO_OBJECT (qtdemux, "mfra offset: %" G_GUINT64_FORMAT ", size %u",
      mfra_offset, mfra_size);

  /* now get and parse mfra box */
  flow = gst_qtdemux_pull_atom (qtdemux, mfra_offset, mfra_size, &mfra);
  if (flow != GST_FLOW_OK)
    goto broken_file;

  gst_buffer_map (mfra, &mfra_map, GST_MAP_READ);

  mfra_node = g_node_new ((guint8 *) mfra_map.data);
  qtdemux_parse_node (qtdemux, mfra_node, mfra_map.data, mfra_map.size);

  tfra_node = qtdemux_tree_get_child_by_type (mfra_node, FOURCC_tfra);

  while (tfra_node) {
    qtdemux_parse_tfra (qtdemux, tfra_node);
    /* iterate all siblings */
    tfra_node = qtdemux_tree_get_sibling_by_type (tfra_node, FOURCC_tfra);
  }
  g_node_destroy (mfra_node);

  GST_INFO_OBJECT (qtdemux, "parsed movie fragment random access box (mfra)");
  ret = TRUE;

exit:

  if (mfro) {
    if (mfro_map.memory != NULL)
      gst_buffer_unmap (mfro, &mfro_map);
    gst_buffer_unref (mfro);
  }
  if (mfra) {
    if (mfra_map.memory != NULL)
      gst_buffer_unmap (mfra, &mfra_map);
    gst_buffer_unref (mfra);
  }
  return ret;

/* ERRORS */
size_query_failed:
  {
    GST_WARNING_OBJECT (qtdemux, "could not query upstream size");
    goto exit;
  }
invalid_mfro_size:
  {
    GST_WARNING_OBJECT (qtdemux, "mfro size is too small");
    goto exit;
  }
invalid_mfra_size:
  {
    GST_WARNING_OBJECT (qtdemux, "mfra_size in mfro box is invalid");
    goto exit;
  }
broken_file:
  {
    GST_WARNING_OBJECT (qtdemux, "bogus mfra offset or size, broken file");
    goto exit;
  }
}

static guint64
add_offset (guint64 offset, guint64 advance)
{
  /* Avoid 64-bit overflow by clamping */
  if (offset > G_MAXUINT64 - advance)
    return G_MAXUINT64;
  return offset + advance;
}

static GstFlowReturn
gst_qtdemux_loop_state_header (GstQTDemux * qtdemux)
{
  guint64 length = 0;
  guint32 fourcc = 0;
  GstBuffer *buf = NULL;
  GstFlowReturn ret = GST_FLOW_OK;
  guint64 cur_offset = qtdemux->offset;
  GstMapInfo map;

  ret = gst_pad_pull_range (qtdemux->sinkpad, cur_offset, 16, &buf);
  if (G_UNLIKELY (ret != GST_FLOW_OK))
    goto beach;
  gst_buffer_map (buf, &map, GST_MAP_READ);
  if (G_LIKELY (map.size >= 8))
    extract_initial_length_and_fourcc (map.data, map.size, &length, &fourcc);
  gst_buffer_unmap (buf, &map);
  gst_buffer_unref (buf);

  /* maybe we already got most we needed, so only consider this eof */
  if (G_UNLIKELY (length == 0)) {
    GST_ELEMENT_WARNING (qtdemux, STREAM, DEMUX,
        (_("Invalid atom size.")),
        ("Header atom '%" GST_FOURCC_FORMAT "' has empty length",
            GST_FOURCC_ARGS (fourcc)));
    ret = GST_FLOW_EOS;
    goto beach;
  }

  switch (fourcc) {
    case FOURCC_moof:
      /* record for later parsing when needed */
      if (!qtdemux->moof_offset) {
        qtdemux->moof_offset = qtdemux->offset;
      }
      if (qtdemux_pull_mfro_mfra (qtdemux)) {
        /* FIXME */
      } else {
        qtdemux->offset += length;      /* skip moof and keep going */
      }
      if (qtdemux->got_moov) {
        GST_INFO_OBJECT (qtdemux, "moof header, got moov, done with headers");
        ret = GST_FLOW_EOS;
        goto beach;
      }
      break;
    case FOURCC_mdat:
    case FOURCC_free:
    case FOURCC_wide:
    case FOURCC_PICT:
    case FOURCC_pnot:
    {
      GST_LOG_OBJECT (qtdemux,
          "skipping atom '%" GST_FOURCC_FORMAT "' at %" G_GUINT64_FORMAT,
          GST_FOURCC_ARGS (fourcc), cur_offset);
      qtdemux->offset = add_offset (qtdemux->offset, length);
      break;
    }
    case FOURCC_moov:
    {
      GstBuffer *moov = NULL;

      if (qtdemux->got_moov) {
        GST_DEBUG_OBJECT (qtdemux, "Skipping moov atom as we have one already");
        qtdemux->offset = add_offset (qtdemux->offset, length);
        goto beach;
      }

      ret = gst_pad_pull_range (qtdemux->sinkpad, cur_offset, length, &moov);
      if (ret != GST_FLOW_OK)
        goto beach;
      gst_buffer_map (moov, &map, GST_MAP_READ);

      if (length != map.size) {
        /* Some files have a 'moov' atom at the end of the file which contains
         * a terminal 'free' atom where the body of the atom is missing.
         * Check for, and permit, this special case.
         */
        if (map.size >= 8) {
          guint8 *final_data = map.data + (map.size - 8);
          guint32 final_length = QT_UINT32 (final_data);
          guint32 final_fourcc = QT_FOURCC (final_data + 4);

          if (final_fourcc == FOURCC_free
              && map.size + final_length - 8 == length) {
            /* Ok, we've found that special case. Allocate a new buffer with
             * that free atom actually present. */
            GstBuffer *newmoov = gst_buffer_new_and_alloc (length);
            gst_buffer_fill (newmoov, 0, map.data, map.size);
            gst_buffer_memset (newmoov, map.size, 0, final_length - 8);
            gst_buffer_unmap (moov, &map);
            gst_buffer_unref (moov);
            moov = newmoov;
            gst_buffer_map (moov, &map, GST_MAP_READ);
          }
        }
      }

      if (length != map.size) {
        GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
            (_("This file is incomplete and cannot be played.")),
            ("We got less than expected (received %" G_GSIZE_FORMAT
                ", wanted %u, offset %" G_GUINT64_FORMAT ")", map.size,
                (guint) length, cur_offset));
        gst_buffer_unmap (moov, &map);
        gst_buffer_unref (moov);
        ret = GST_FLOW_ERROR;
        goto beach;
      }
      qtdemux->offset += length;

      qtdemux_parse_moov (qtdemux, map.data, length);
      qtdemux_node_dump (qtdemux, qtdemux->moov_node);

      qtdemux_parse_tree (qtdemux);
      g_node_destroy (qtdemux->moov_node);
      gst_buffer_unmap (moov, &map);
      gst_buffer_unref (moov);
      qtdemux->moov_node = NULL;
      qtdemux->got_moov = TRUE;

      break;
    }
    case FOURCC_ftyp:
    {
      GstBuffer *ftyp = NULL;

      /* extract major brand; might come in handy for ISO vs QT issues */
      ret = gst_qtdemux_pull_atom (qtdemux, cur_offset, length, &ftyp);
      if (ret != GST_FLOW_OK)
        goto beach;
      qtdemux->offset += length;
      gst_buffer_map (ftyp, &map, GST_MAP_READ);
      qtdemux_parse_ftyp (qtdemux, map.data, map.size);
      gst_buffer_unmap (ftyp, &map);
      gst_buffer_unref (ftyp);
      break;
    }
    case FOURCC_uuid:
    {
      GstBuffer *uuid = NULL;

      /* uuid are extension atoms */
      ret = gst_qtdemux_pull_atom (qtdemux, cur_offset, length, &uuid);
      if (ret != GST_FLOW_OK)
        goto beach;
      qtdemux->offset += length;
      gst_buffer_map (uuid, &map, GST_MAP_READ);
      qtdemux_parse_uuid (qtdemux, map.data, map.size);
      gst_buffer_unmap (uuid, &map);
      gst_buffer_unref (uuid);
      break;
    }
    case FOURCC_sidx:
    {
      GstBuffer *sidx = NULL;
      ret = gst_qtdemux_pull_atom (qtdemux, cur_offset, length, &sidx);
      if (ret != GST_FLOW_OK)
        goto beach;
      qtdemux->offset += length;
      gst_buffer_map (sidx, &map, GST_MAP_READ);
      qtdemux_parse_sidx (qtdemux, map.data, map.size);
      gst_buffer_unmap (sidx, &map);
      gst_buffer_unref (sidx);
      break;
    }
    default:
    {
      GstBuffer *unknown = NULL;

      GST_LOG_OBJECT (qtdemux,
          "unknown %08x '%" GST_FOURCC_FORMAT "' of size %" G_GUINT64_FORMAT
          " at %" G_GUINT64_FORMAT, fourcc, GST_FOURCC_ARGS (fourcc), length,
          cur_offset);
      ret = gst_qtdemux_pull_atom (qtdemux, cur_offset, length, &unknown);
      if (ret != GST_FLOW_OK)
        goto beach;
      gst_buffer_map (unknown, &map, GST_MAP_READ);
      GST_MEMDUMP ("Unknown tag", map.data, map.size);
      gst_buffer_unmap (unknown, &map);
      gst_buffer_unref (unknown);
      qtdemux->offset += length;
      break;
    }
  }

beach:
  if (ret == GST_FLOW_EOS && (qtdemux->got_moov || qtdemux->media_caps)) {
    /* digested all data, show what we have */
    qtdemux_prepare_streams (qtdemux);
    ret = qtdemux_expose_streams (qtdemux);

    qtdemux->state = QTDEMUX_STATE_MOVIE;
    GST_DEBUG_OBJECT (qtdemux, "switching state to STATE_MOVIE (%d)",
        qtdemux->state);
    return ret;
  }
  return ret;
}

/* Seeks to the previous keyframe of the indexed stream and
 * aligns other streams with respect to the keyframe timestamp
 * of indexed stream. Only called in case of Reverse Playback
 */
static GstFlowReturn
gst_qtdemux_seek_to_previous_keyframe (GstQTDemux * qtdemux)
{
  guint8 n = 0;
  guint32 seg_idx = 0, k_index = 0;
  guint32 ref_seg_idx, ref_k_index;
  GstClockTime k_pos = 0, last_stop = 0;
  QtDemuxSegment *seg = NULL;
  QtDemuxStream *ref_str = NULL;
  guint64 seg_media_start_mov;  /* segment media start time in mov format */
  guint64 target_ts;

  /* Now we choose an arbitrary stream, get the previous keyframe timestamp
   * and finally align all the other streams on that timestamp with their
   * respective keyframes */
  for (n = 0; n < qtdemux->n_streams; n++) {
    QtDemuxStream *str = qtdemux->streams[n];

    /* No candidate yet, take the first stream */
    if (!ref_str) {
      ref_str = str;
      continue;
    }

    /* So that stream has a segment, we prefer video streams */
    if (str->subtype == FOURCC_vide) {
      ref_str = str;
      break;
    }
  }

  if (G_UNLIKELY (!ref_str)) {
    GST_DEBUG_OBJECT (qtdemux, "couldn't find any stream");
    goto eos;
  }

  if (G_UNLIKELY (!ref_str->from_sample)) {
    GST_DEBUG_OBJECT (qtdemux, "reached the beginning of the file");
    goto eos;
  }

  /* So that stream has been playing from from_sample to to_sample. We will
   * get the timestamp of the previous sample and search for a keyframe before
   * that. For audio streams we do an arbitrary jump in the past (10 samples) */
  if (ref_str->subtype == FOURCC_vide) {
    k_index = gst_qtdemux_find_keyframe (qtdemux, ref_str,
        ref_str->from_sample - 1);
  } else {
    if (ref_str->from_sample >= 10)
      k_index = ref_str->from_sample - 10;
    else
      k_index = 0;
  }

  target_ts =
      ref_str->samples[k_index].timestamp +
      ref_str->samples[k_index].pts_offset;

  /* get current segment for that stream */
  seg = &ref_str->segments[ref_str->segment_index];
  /* Use segment start in original timescale for comparisons */
  seg_media_start_mov = seg->trak_media_start;

  GST_LOG_OBJECT (qtdemux, "keyframe index %u ts %" G_GUINT64_FORMAT
      " seg start %" G_GUINT64_FORMAT " %" GST_TIME_FORMAT "\n",
      k_index, target_ts, seg_media_start_mov,
      GST_TIME_ARGS (seg->media_start));

  /* Crawl back through segments to find the one containing this I frame */
  while (target_ts < seg_media_start_mov) {
    GST_DEBUG_OBJECT (qtdemux,
        "keyframe position (sample %u) is out of segment %u " " target %"
        G_GUINT64_FORMAT " seg start %" G_GUINT64_FORMAT, k_index,
        ref_str->segment_index, target_ts, seg_media_start_mov);

    if (G_UNLIKELY (!ref_str->segment_index)) {
      /* Reached first segment, let's consider it's EOS */
      goto eos;
    }
    ref_str->segment_index--;
    seg = &ref_str->segments[ref_str->segment_index];
    /* Use segment start in original timescale for comparisons */
    seg_media_start_mov = seg->trak_media_start;
  }
  /* Calculate time position of the keyframe and where we should stop */
  k_pos =
      QTSTREAMTIME_TO_GSTTIME (ref_str,
      target_ts - seg->trak_media_start) + seg->time;
  last_stop =
      QTSTREAMTIME_TO_GSTTIME (ref_str,
      ref_str->samples[ref_str->from_sample].timestamp -
      seg->trak_media_start) + seg->time;

  GST_DEBUG_OBJECT (qtdemux, "preferred stream played from sample %u, "
      "now going to sample %u (pts %" GST_TIME_FORMAT ")", ref_str->from_sample,
      k_index, GST_TIME_ARGS (k_pos));

  /* Set last_stop with the keyframe timestamp we pushed of that stream */
  qtdemux->segment.position = last_stop;
  GST_DEBUG_OBJECT (qtdemux, "last_stop now is %" GST_TIME_FORMAT,
      GST_TIME_ARGS (last_stop));

  if (G_UNLIKELY (last_stop < qtdemux->segment.start)) {
    GST_DEBUG_OBJECT (qtdemux, "reached the beginning of segment");
    goto eos;
  }

  ref_seg_idx = ref_str->segment_index;
  ref_k_index = k_index;

  /* Align them all on this */
  for (n = 0; n < qtdemux->n_streams; n++) {
    guint32 index = 0;
    GstClockTime seg_time = 0;
    QtDemuxStream *str = qtdemux->streams[n];

    /* aligning reference stream again might lead to backing up to yet another
     * keyframe (due to timestamp rounding issues),
     * potentially putting more load on downstream; so let's try to avoid */
    if (str == ref_str) {
      seg_idx = ref_seg_idx;
      seg = &str->segments[seg_idx];
      k_index = ref_k_index;
      GST_DEBUG_OBJECT (qtdemux, "reference stream %d segment %d, "
          "sample at index %d", n, ref_str->segment_index, k_index);
    } else {
      seg_idx = gst_qtdemux_find_segment (qtdemux, str, k_pos);
      GST_DEBUG_OBJECT (qtdemux,
          "stream %d align segment %d for keyframe pos %" GST_TIME_FORMAT, n,
          seg_idx, GST_TIME_ARGS (k_pos));

      /* get segment and time in the segment */
      seg = &str->segments[seg_idx];
      seg_time = k_pos - seg->time;

      /* get the media time in the segment.
       * No adjustment for empty "filler" segments */
      if (seg->media_start != GST_CLOCK_TIME_NONE)
        seg_time += seg->media_start;

      /* get the index of the sample with media time */
      index = gst_qtdemux_find_index_linear (qtdemux, str, seg_time);
      GST_DEBUG_OBJECT (qtdemux,
          "stream %d sample for %" GST_TIME_FORMAT " at %u", n,
          GST_TIME_ARGS (seg_time), index);

      /* find previous keyframe */
      k_index = gst_qtdemux_find_keyframe (qtdemux, str, index);
    }

    /* Remember until where we want to go */
    str->to_sample = str->from_sample - 1;
    /* Define our time position */
    target_ts =
        str->samples[k_index].timestamp + str->samples[k_index].pts_offset;
    str->time_position = QTSTREAMTIME_TO_GSTTIME (str, target_ts) + seg->time;
    if (seg->media_start != GST_CLOCK_TIME_NONE)
      str->time_position -= seg->media_start;

    /* Now seek back in time */
    gst_qtdemux_move_stream (qtdemux, str, k_index);
    GST_DEBUG_OBJECT (qtdemux, "stream %d keyframe at %u, time position %"
        GST_TIME_FORMAT " playing from sample %u to %u", n, k_index,
        GST_TIME_ARGS (str->time_position), str->from_sample, str->to_sample);
  }

  return GST_FLOW_OK;

eos:
  return GST_FLOW_EOS;
}

/*
 * Gets the current qt segment start, stop and position for the
 * given time offset. This is used in update_segment()
 */
static void
gst_qtdemux_stream_segment_get_boundaries (GstQTDemux * qtdemux,
    QtDemuxStream * stream, GstClockTime offset,
    GstClockTime * _start, GstClockTime * _stop, GstClockTime * _time)
{
  GstClockTime seg_time;
  GstClockTime start, stop, time;
  QtDemuxSegment *segment;

  segment = &stream->segments[stream->segment_index];

  /* get time in this segment */
  seg_time = offset - segment->time;

  GST_LOG_OBJECT (stream->pad, "seg_time %" GST_TIME_FORMAT,
      GST_TIME_ARGS (seg_time));

  if (G_UNLIKELY (seg_time > segment->duration)) {
    GST_LOG_OBJECT (stream->pad,
        "seg_time > segment->duration %" GST_TIME_FORMAT,
        GST_TIME_ARGS (segment->duration));
    seg_time = segment->duration;
  }

  /* qtdemux->segment.stop is in outside-time-realm, whereas
   * segment->media_stop is in track-time-realm.
   *
   * In order to compare the two, we need to bring segment.stop
   * into the track-time-realm
   *
   * FIXME - does this comment still hold? Don't see any conversion here */

  stop = qtdemux->segment.stop;
  if (stop == GST_CLOCK_TIME_NONE)
    stop = qtdemux->segment.duration;
  if (stop == GST_CLOCK_TIME_NONE)
    stop = segment->media_stop;
  else
    stop =
        MIN (segment->media_stop, stop - segment->time + segment->media_start);

  if (G_UNLIKELY (QTSEGMENT_IS_EMPTY (segment))) {
    start = segment->time + seg_time;
    time = offset;
    stop = start - seg_time + segment->duration;
  } else if (qtdemux->segment.rate >= 0) {
    start = MIN (segment->media_start + seg_time, stop);
    time = offset;
  } else {
    if (segment->media_start >= qtdemux->segment.start) {
      time = segment->time;
    } else {
      time = segment->time + (qtdemux->segment.start - segment->media_start);
    }

    start = MAX (segment->media_start, qtdemux->segment.start);
    stop = MIN (segment->media_start + seg_time, stop);
  }

  *_start = start;
  *_stop = stop;
  *_time = time;
}

/*
 * Updates the qt segment used for the stream and pushes a new segment event
 * downstream on this stream's pad.
 */
static gboolean
gst_qtdemux_stream_update_segment (GstQTDemux * qtdemux, QtDemuxStream * stream,
    gint seg_idx, GstClockTime offset, GstClockTime * _start,
    GstClockTime * _stop)
{
  QtDemuxSegment *segment;
  GstClockTime start = 0, stop = GST_CLOCK_TIME_NONE, time = 0;
  gdouble rate;
  GstEvent *event;

  /* update the current segment */
  stream->segment_index = seg_idx;

  /* get the segment */
  segment = &stream->segments[seg_idx];

  if (G_UNLIKELY (offset < segment->time)) {
    GST_WARNING_OBJECT (stream->pad, "offset < segment->time %" GST_TIME_FORMAT,
        GST_TIME_ARGS (segment->time));
    return FALSE;
  }

  /* segment lies beyond total indicated duration */
  if (G_UNLIKELY (qtdemux->segment.duration != GST_CLOCK_TIME_NONE &&
          segment->time > qtdemux->segment.duration)) {
    GST_WARNING_OBJECT (stream->pad, "file duration %" GST_TIME_FORMAT
        " < segment->time %" GST_TIME_FORMAT,
        GST_TIME_ARGS (qtdemux->segment.duration),
        GST_TIME_ARGS (segment->time));
    return FALSE;
  }

  gst_qtdemux_stream_segment_get_boundaries (qtdemux, stream, offset,
      &start, &stop, &time);

  GST_DEBUG_OBJECT (stream->pad, "new segment %d from %" GST_TIME_FORMAT
      " to %" GST_TIME_FORMAT ", time %" GST_TIME_FORMAT, seg_idx,
      GST_TIME_ARGS (start), GST_TIME_ARGS (stop), GST_TIME_ARGS (time));

  /* combine global rate with that of the segment */
  rate = segment->rate * qtdemux->segment.rate;

  /* Copy flags from main segment */
  stream->segment.flags = qtdemux->segment.flags;

  /* update the segment values used for clipping */
  stream->segment.offset = qtdemux->segment.offset;
  stream->segment.base = qtdemux->segment.base + stream->accumulated_base;
  stream->segment.applied_rate = qtdemux->segment.applied_rate;
  stream->segment.rate = rate;
  stream->segment.start = start + QTSTREAMTIME_TO_GSTTIME (stream,
      stream->cslg_shift);
  stream->segment.stop = stop + QTSTREAMTIME_TO_GSTTIME (stream,
      stream->cslg_shift);
  stream->segment.time = time;
  stream->segment.position = stream->segment.start;

  GST_DEBUG_OBJECT (stream->pad, "New segment: %" GST_SEGMENT_FORMAT,
      &stream->segment);

  /* now prepare and send the segment */
  if (stream->pad) {
    event = gst_event_new_segment (&stream->segment);
    if (qtdemux->segment_seqnum) {
      gst_event_set_seqnum (event, qtdemux->segment_seqnum);
    }
    gst_pad_push_event (stream->pad, event);
    /* assume we can send more data now */
    GST_PAD_LAST_FLOW_RETURN (stream->pad) = GST_FLOW_OK;
    /* clear to send tags on this pad now */
    gst_qtdemux_push_tags (qtdemux, stream);
  }

  if (_start)
    *_start = start;
  if (_stop)
    *_stop = stop;

  return TRUE;
}

/* activate the given segment number @seg_idx of @stream at time @offset.
 * @offset is an absolute global position over all the segments.
 *
 * This will push out a NEWSEGMENT event with the right values and
 * position the stream index to the first decodable sample before
 * @offset.
 */
static gboolean
gst_qtdemux_activate_segment (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 seg_idx, GstClockTime offset)
{
  QtDemuxSegment *segment;
  guint32 index, kf_index;
  GstClockTime start = 0, stop = GST_CLOCK_TIME_NONE;

  GST_LOG_OBJECT (stream->pad, "activate segment %d, offset %" GST_TIME_FORMAT,
      seg_idx, GST_TIME_ARGS (offset));

  if (!gst_qtdemux_stream_update_segment (qtdemux, stream, seg_idx, offset,
          &start, &stop))
    return FALSE;

  segment = &stream->segments[stream->segment_index];

  /* in the fragmented case, we pick a fragment that starts before our
   * desired position and rely on downstream to wait for a keyframe
   * (FIXME: doesn't seem to work so well with ismv and wmv, as no parser; the
   * tfra entries tells us which trun/sample the key unit is in, but we don't
   * make use of this additional information at the moment) */
  if (qtdemux->fragmented) {
    stream->to_sample = G_MAXUINT32;
    return TRUE;
  }

  /* We don't need to look for a sample in push-based */
  if (!qtdemux->pullbased)
    return TRUE;

  /* and move to the keyframe before the indicated media time of the
   * segment */
  if (G_LIKELY (!QTSEGMENT_IS_EMPTY (segment))) {
    if (qtdemux->segment.rate >= 0) {
      index = gst_qtdemux_find_index_linear (qtdemux, stream, start);
      stream->to_sample = G_MAXUINT32;
      GST_DEBUG_OBJECT (stream->pad,
          "moving data pointer to %" GST_TIME_FORMAT ", index: %u, pts %"
          GST_TIME_FORMAT, GST_TIME_ARGS (start), index,
          GST_TIME_ARGS (QTSAMPLE_PTS (stream, &stream->samples[index])));
    } else {
      index = gst_qtdemux_find_index_linear (qtdemux, stream, stop);
      stream->to_sample = index;
      GST_DEBUG_OBJECT (stream->pad,
          "moving data pointer to %" GST_TIME_FORMAT ", index: %u, pts %"
          GST_TIME_FORMAT, GST_TIME_ARGS (stop), index,
          GST_TIME_ARGS (QTSAMPLE_PTS (stream, &stream->samples[index])));
    }
  } else {
    GST_DEBUG_OBJECT (stream->pad, "No need to look for keyframe, "
        "this is an empty segment");
    return TRUE;
  }

  /* gst_qtdemux_parse_sample () called from gst_qtdemux_find_index_linear ()
   * encountered an error and printed a message so we return appropriately */
  if (index == -1)
    return FALSE;

  /* we're at the right spot */
  if (index == stream->sample_index) {
    GST_DEBUG_OBJECT (stream->pad, "we are at the right index");
    return TRUE;
  }

  /* find keyframe of the target index */
  kf_index = gst_qtdemux_find_keyframe (qtdemux, stream, index);

/* *INDENT-OFF* */
/* indent does stupid stuff with stream->samples[].timestamp */

  /* if we move forwards, we don't have to go back to the previous
   * keyframe since we already sent that. We can also just jump to
   * the keyframe right before the target index if there is one. */
  if (index > stream->sample_index) {
    /* moving forwards check if we move past a keyframe */
    if (kf_index > stream->sample_index) {
      GST_DEBUG_OBJECT (stream->pad,
           "moving forwards to keyframe at %u (pts %" GST_TIME_FORMAT " dts %"GST_TIME_FORMAT" )", kf_index,
           GST_TIME_ARGS (QTSAMPLE_PTS(stream, &stream->samples[kf_index])),
           GST_TIME_ARGS (QTSAMPLE_DTS(stream, &stream->samples[kf_index])));
      gst_qtdemux_move_stream (qtdemux, stream, kf_index);
    } else {
      GST_DEBUG_OBJECT (stream->pad,
          "moving forwards, keyframe at %u (pts %" GST_TIME_FORMAT " dts %"GST_TIME_FORMAT" ) already sent", kf_index,
          GST_TIME_ARGS (QTSAMPLE_PTS (stream, &stream->samples[kf_index])),
          GST_TIME_ARGS (QTSAMPLE_DTS (stream, &stream->samples[kf_index])));
    }
  } else {
    GST_DEBUG_OBJECT (stream->pad,
        "moving backwards to keyframe at %u (pts %" GST_TIME_FORMAT " dts %"GST_TIME_FORMAT" )", kf_index,
        GST_TIME_ARGS (QTSAMPLE_PTS(stream, &stream->samples[kf_index])),
        GST_TIME_ARGS (QTSAMPLE_DTS(stream, &stream->samples[kf_index])));
    gst_qtdemux_move_stream (qtdemux, stream, kf_index);
  }

/* *INDENT-ON* */

  return TRUE;
}

/* prepare to get the current sample of @stream, getting essential values.
 *
 * This function will also prepare and send the segment when needed.
 *
 * Return FALSE if the stream is EOS.
 *
 * PULL-BASED
 */
static gboolean
gst_qtdemux_prepare_current_sample (GstQTDemux * qtdemux,
    QtDemuxStream * stream, gboolean * empty, guint64 * offset, guint * size,
    GstClockTime * dts, GstClockTime * pts, GstClockTime * duration,
    gboolean * keyframe)
{
  QtDemuxSample *sample;
  GstClockTime time_position;
  guint32 seg_idx;

  g_return_val_if_fail (stream != NULL, FALSE);

  time_position = stream->time_position;
  if (G_UNLIKELY (time_position == GST_CLOCK_TIME_NONE))
    goto eos;

  seg_idx = stream->segment_index;
  if (G_UNLIKELY (seg_idx == -1)) {
    /* find segment corresponding to time_position if we are looking
     * for a segment. */
    seg_idx = gst_qtdemux_find_segment (qtdemux, stream, time_position);
  }

  /* different segment, activate it, sample_index will be set. */
  if (G_UNLIKELY (stream->segment_index != seg_idx))
    gst_qtdemux_activate_segment (qtdemux, stream, seg_idx, time_position);

  if (G_UNLIKELY (QTSEGMENT_IS_EMPTY (&stream->segments[stream->
                  segment_index]))) {
    QtDemuxSegment *seg = &stream->segments[stream->segment_index];

    GST_LOG_OBJECT (qtdemux, "Empty segment activated,"
        " prepare empty sample");

    *empty = TRUE;
    *pts = *dts = time_position;
    *duration = seg->duration - (time_position - seg->time);

    return TRUE;
  }

  *empty = FALSE;

  if (stream->sample_index == -1)
    stream->sample_index = 0;

  GST_LOG_OBJECT (qtdemux, "segment active, index = %u of %u",
      stream->sample_index, stream->n_samples);

  if (G_UNLIKELY (stream->sample_index >= stream->n_samples)) {
    if (!qtdemux->fragmented)
      goto eos;

    GST_INFO_OBJECT (qtdemux, "out of samples, trying to add more");
    do {
      GstFlowReturn flow;

      GST_OBJECT_LOCK (qtdemux);
      flow = qtdemux_add_fragmented_samples (qtdemux);
      GST_OBJECT_UNLOCK (qtdemux);

      if (flow != GST_FLOW_OK)
        goto eos;
    }
    while (stream->sample_index >= stream->n_samples);
  }

  if (!qtdemux_parse_samples (qtdemux, stream, stream->sample_index)) {
    GST_LOG_OBJECT (qtdemux, "Parsing of index %u failed!",
        stream->sample_index);
    return FALSE;
  }

  /* now get the info for the sample we're at */
  sample = &stream->samples[stream->sample_index];

  *dts = QTSAMPLE_DTS (stream, sample);
  *pts = QTSAMPLE_PTS (stream, sample);
  *offset = sample->offset;
  *size = sample->size;
  *duration = QTSAMPLE_DUR_DTS (stream, sample, *dts);
  *keyframe = QTSAMPLE_KEYFRAME (stream, sample);

  return TRUE;

  /* special cases */
eos:
  {
    stream->time_position = GST_CLOCK_TIME_NONE;
    return FALSE;
  }
}

/* move to the next sample in @stream.
 *
 * Moves to the next segment when needed.
 */
static void
gst_qtdemux_advance_sample (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
  QtDemuxSample *sample;
  QtDemuxSegment *segment;

  /* get current segment */
  segment = &stream->segments[stream->segment_index];

  if (G_UNLIKELY (QTSEGMENT_IS_EMPTY (segment))) {
    GST_DEBUG_OBJECT (qtdemux, "Empty segment, no samples to advance");
    goto next_segment;
  }

  if (G_UNLIKELY (stream->sample_index >= stream->to_sample)) {
    /* Mark the stream as EOS */
    GST_DEBUG_OBJECT (qtdemux,
        "reached max allowed sample %u, mark EOS", stream->to_sample);
    stream->time_position = GST_CLOCK_TIME_NONE;
    return;
  }

  /* move to next sample */
  stream->sample_index++;
  stream->offset_in_sample = 0;

  /* reached the last sample, we need the next segment */
  if (G_UNLIKELY (stream->sample_index >= stream->n_samples))
    goto next_segment;

  if (!qtdemux_parse_samples (qtdemux, stream, stream->sample_index)) {
    GST_LOG_OBJECT (qtdemux, "Parsing of index %u failed!",
        stream->sample_index);
    return;
  }

  /* get next sample */
  sample = &stream->samples[stream->sample_index];

  /* see if we are past the segment */
  if (G_UNLIKELY (QTSAMPLE_DTS (stream, sample) >= segment->media_stop))
    goto next_segment;

  if (QTSAMPLE_DTS (stream, sample) >= segment->media_start) {
    /* inside the segment, update time_position, looks very familiar to
     * GStreamer segments, doesn't it? */
    stream->time_position =
        QTSAMPLE_DTS (stream, sample) - segment->media_start + segment->time;
  } else {
    /* not yet in segment, time does not yet increment. This means
     * that we are still prerolling keyframes to the decoder so it can
     * decode the first sample of the segment. */
    stream->time_position = segment->time;
  }
  return;

  /* move to the next segment */
next_segment:
  {
    GST_DEBUG_OBJECT (qtdemux, "segment %d ended ", stream->segment_index);

    if (stream->segment_index == stream->n_segments - 1) {
      /* are we at the end of the last segment, we're EOS */
      stream->time_position = GST_CLOCK_TIME_NONE;
    } else {
      /* else we're only at the end of the current segment */
      stream->time_position = segment->stop_time;
    }
    /* make sure we select a new segment */

    /* accumulate previous segments */
    if (GST_CLOCK_TIME_IS_VALID (stream->segment.stop))
      stream->accumulated_base +=
          (stream->segment.stop -
          stream->segment.start) / ABS (stream->segment.rate);

    stream->segment_index = -1;
  }
}

static void
gst_qtdemux_sync_streams (GstQTDemux * demux)
{
  gint i;

  if (demux->n_streams <= 1)
    return;

  for (i = 0; i < demux->n_streams; i++) {
    QtDemuxStream *stream;
    GstClockTime end_time;

    stream = demux->streams[i];

    if (!stream->pad)
      continue;

    /* TODO advance time on subtitle streams here, if any some day */

    /* some clips/trailers may have unbalanced streams at the end,
     * so send EOS on shorter stream to prevent stalling others */

    /* do not mess with EOS if SEGMENT seeking */
    if (demux->segment.flags & GST_SEEK_FLAG_SEGMENT)
      continue;

    if (demux->pullbased) {
      /* loop mode is sample time based */
      if (!STREAM_IS_EOS (stream))
        continue;
    } else {
      /* push mode is byte position based */
      if (stream->n_samples &&
          stream->samples[stream->n_samples - 1].offset >= demux->offset)
        continue;
    }

    if (stream->sent_eos)
      continue;

    /* only act if some gap */
    end_time = stream->segments[stream->n_segments - 1].stop_time;
    GST_LOG_OBJECT (demux, "current position: %" GST_TIME_FORMAT
        ", stream end: %" GST_TIME_FORMAT,
        GST_TIME_ARGS (demux->segment.position), GST_TIME_ARGS (end_time));
    if (GST_CLOCK_TIME_IS_VALID (end_time)
        && (end_time + 2 * GST_SECOND < demux->segment.position)) {
      GstEvent *event;

      GST_DEBUG_OBJECT (demux, "sending EOS for stream %s",
          GST_PAD_NAME (stream->pad));
      stream->sent_eos = TRUE;
      event = gst_event_new_eos ();
      if (demux->segment_seqnum)
        gst_event_set_seqnum (event, demux->segment_seqnum);
      gst_pad_push_event (stream->pad, event);
    }
  }
}

/* EOS and NOT_LINKED need to be combined. This means that we return:
 *
 *  GST_FLOW_NOT_LINKED: when all pads NOT_LINKED.
 *  GST_FLOW_EOS: when all pads EOS or NOT_LINKED.
 */
static GstFlowReturn
gst_qtdemux_combine_flows (GstQTDemux * demux, QtDemuxStream * stream,
    GstFlowReturn ret)
{
  GST_LOG_OBJECT (demux, "flow return: %s", gst_flow_get_name (ret));

  if (stream->pad)
    ret = gst_flow_combiner_update_pad_flow (demux->flowcombiner, stream->pad,
        ret);
  else
    ret = gst_flow_combiner_update_flow (demux->flowcombiner, ret);

  GST_LOG_OBJECT (demux, "combined flow return: %s", gst_flow_get_name (ret));
  return ret;
}

/* the input buffer metadata must be writable. Returns NULL when the buffer is
 * completely clipped
 *
 * Should be used only with raw buffers */
static GstBuffer *
gst_qtdemux_clip_buffer (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstBuffer * buf)
{
  guint64 start, stop, cstart, cstop, diff;
  GstClockTime pts, duration;
  gsize size, osize;
  gint num_rate, denom_rate;
  gint frame_size;
  gboolean clip_data;
  guint offset;

  osize = size = gst_buffer_get_size (buf);
  offset = 0;

  /* depending on the type, setup the clip parameters */
  if (stream->subtype == FOURCC_soun) {
    frame_size = stream->bytes_per_frame;
    num_rate = GST_SECOND;
    denom_rate = (gint) stream->rate;
    clip_data = TRUE;
  } else if (stream->subtype == FOURCC_vide) {
    frame_size = size;
    num_rate = stream->fps_n;
    denom_rate = stream->fps_d;
    clip_data = FALSE;
  } else
    goto wrong_type;

  if (frame_size <= 0)
    goto bad_frame_size;

  /* we can only clip if we have a valid pts */
  pts = GST_BUFFER_PTS (buf);
  if (G_UNLIKELY (!GST_CLOCK_TIME_IS_VALID (pts)))
    goto no_pts;

  duration = GST_BUFFER_DURATION (buf);

  if (G_UNLIKELY (!GST_CLOCK_TIME_IS_VALID (duration))) {
    duration =
        gst_util_uint64_scale_int (size / frame_size, num_rate, denom_rate);
  }

  start = pts;
  stop = start + duration;

  if (G_UNLIKELY (!gst_segment_clip (&stream->segment,
              GST_FORMAT_TIME, start, stop, &cstart, &cstop)))
    goto clipped;

  /* see if some clipping happened */
  diff = cstart - start;
  if (diff > 0) {
    pts += diff;
    duration -= diff;

    if (clip_data) {
      /* bring clipped time to samples and to bytes */
      diff = gst_util_uint64_scale_int (diff, denom_rate, num_rate);
      diff *= frame_size;

      GST_DEBUG_OBJECT (qtdemux,
          "clipping start to %" GST_TIME_FORMAT " %"
          G_GUINT64_FORMAT " bytes", GST_TIME_ARGS (cstart), diff);

      offset = diff;
      size -= diff;
    }
  }
  diff = stop - cstop;
  if (diff > 0) {
    duration -= diff;

    if (clip_data) {
      /* bring clipped time to samples and then to bytes */
      diff = gst_util_uint64_scale_int (diff, denom_rate, num_rate);
      diff *= frame_size;
      GST_DEBUG_OBJECT (qtdemux,
          "clipping stop to %" GST_TIME_FORMAT " %" G_GUINT64_FORMAT
          " bytes", GST_TIME_ARGS (cstop), diff);
      size -= diff;
    }
  }

  if (offset != 0 || size != osize)
    gst_buffer_resize (buf, offset, size);

  GST_BUFFER_DTS (buf) = GST_CLOCK_TIME_NONE;
  GST_BUFFER_PTS (buf) = pts;
  GST_BUFFER_DURATION (buf) = duration;

  return buf;

  /* dropped buffer */
wrong_type:
  {
    GST_DEBUG_OBJECT (qtdemux, "unknown stream type");
    return buf;
  }
bad_frame_size:
  {
    GST_DEBUG_OBJECT (qtdemux, "bad frame size");
    return buf;
  }
no_pts:
  {
    GST_DEBUG_OBJECT (qtdemux, "no pts on buffer");
    return buf;
  }
clipped:
  {
    GST_DEBUG_OBJECT (qtdemux, "clipped buffer");
    gst_buffer_unref (buf);
    return NULL;
  }
}

/* the input buffer metadata must be writable,
 * but time/duration etc not yet set and need not be preserved */
static GstBuffer *
gst_qtdemux_process_buffer (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstBuffer * buf)
{
  GstMapInfo map;
  guint nsize = 0;
  gchar *str;

  /* not many cases for now */
  if (G_UNLIKELY (stream->fourcc == FOURCC_mp4s)) {
    /* send a one time dvd clut event */
    if (stream->pending_event && stream->pad)
      gst_pad_push_event (stream->pad, stream->pending_event);
    stream->pending_event = NULL;
  }

  if (G_UNLIKELY (stream->subtype != FOURCC_text
          && stream->subtype != FOURCC_sbtl &&
          stream->subtype != FOURCC_subp)) {
    return buf;
  }

  gst_buffer_map (buf, &map, GST_MAP_READ);

  /* empty buffer is sent to terminate previous subtitle */
  if (map.size <= 2) {
    gst_buffer_unmap (buf, &map);
    gst_buffer_unref (buf);
    return NULL;
  }
  if (stream->subtype == FOURCC_subp) {
    /* That's all the processing needed for subpictures */
    gst_buffer_unmap (buf, &map);
    return buf;
  }

  nsize = GST_READ_UINT16_BE (map.data);
  nsize = MIN (nsize, map.size - 2);

  GST_LOG_OBJECT (qtdemux, "3GPP timed text subtitle: %d/%" G_GSIZE_FORMAT "",
      nsize, map.size);

  /* takes care of UTF-8 validation or UTF-16 recognition,
   * no other encoding expected */
  str = gst_tag_freeform_string_to_utf8 ((gchar *) map.data + 2, nsize, NULL);
  gst_buffer_unmap (buf, &map);
  if (str) {
    gst_buffer_unref (buf);
    buf = _gst_buffer_new_wrapped (str, strlen (str), g_free);
  } else {
    /* this should not really happen unless the subtitle is corrupted */
    gst_buffer_unref (buf);
    buf = NULL;
  }

  /* FIXME ? convert optional subsequent style info to markup */

  return buf;
}

/* Sets a buffer's attributes properly and pushes it downstream.
 * Also checks for additional actions and custom processing that may
 * need to be done first.
 */
static GstFlowReturn
gst_qtdemux_decorate_and_push_buffer (GstQTDemux * qtdemux,
    QtDemuxStream * stream, GstBuffer * buf,
    GstClockTime dts, GstClockTime pts, GstClockTime duration,
    gboolean keyframe, GstClockTime position, guint64 byte_position)
{
  GstFlowReturn ret = GST_FLOW_OK;

  /* offset the timestamps according to the edit list */

  if (G_UNLIKELY (stream->fourcc == FOURCC_rtsp)) {
    gchar *url;
    GstMapInfo map;

    gst_buffer_map (buf, &map, GST_MAP_READ);
    url = g_strndup ((gchar *) map.data, map.size);
    gst_buffer_unmap (buf, &map);
    if (url != NULL && strlen (url) != 0) {
      /* we have RTSP redirect now */
      gst_element_post_message (GST_ELEMENT_CAST (qtdemux),
          gst_message_new_element (GST_OBJECT_CAST (qtdemux),
              gst_structure_new ("redirect",
                  "new-location", G_TYPE_STRING, url, NULL)));
      qtdemux->posted_redirect = TRUE;
    } else {
      GST_WARNING_OBJECT (qtdemux, "Redirect URI of stream is empty, not "
          "posting");
    }
    g_free (url);
  }

  /* position reporting */
  if (qtdemux->segment.rate >= 0) {
    qtdemux->segment.position = position;
    gst_qtdemux_sync_streams (qtdemux);
  }

  if (G_UNLIKELY (!stream->pad)) {
    GST_DEBUG_OBJECT (qtdemux, "No output pad for stream, ignoring");
    gst_buffer_unref (buf);
    goto exit;
  }

  /* send out pending buffers */
  while (stream->buffers) {
    GstBuffer *buffer = (GstBuffer *) stream->buffers->data;

    if (G_UNLIKELY (stream->discont)) {
      GST_LOG_OBJECT (qtdemux, "marking discont buffer");
      GST_BUFFER_FLAG_SET (buffer, GST_BUFFER_FLAG_DISCONT);
      stream->discont = FALSE;
    } else {
      GST_BUFFER_FLAG_UNSET (buf, GST_BUFFER_FLAG_DISCONT);
    }

    gst_pad_push (stream->pad, buffer);

    stream->buffers = g_slist_delete_link (stream->buffers, stream->buffers);
  }

  /* we're going to modify the metadata */
  buf = gst_buffer_make_writable (buf);

  if (G_UNLIKELY (stream->need_process))
    buf = gst_qtdemux_process_buffer (qtdemux, stream, buf);

  if (!buf) {
    goto exit;
  }

  GST_BUFFER_DTS (buf) = dts;
  GST_BUFFER_PTS (buf) = pts;
  GST_BUFFER_DURATION (buf) = duration;
  GST_BUFFER_OFFSET (buf) = -1;
  GST_BUFFER_OFFSET_END (buf) = -1;

  if (G_UNLIKELY (stream->rgb8_palette))
    gst_buffer_append_memory (buf, gst_memory_ref (stream->rgb8_palette));

  if (G_UNLIKELY (stream->padding)) {
    gst_buffer_resize (buf, stream->padding, -1);
  }
#if 0
  if (G_UNLIKELY (qtdemux->element_index)) {
    GstClockTime stream_time;

    stream_time =
        gst_segment_to_stream_time (&stream->segment, GST_FORMAT_TIME,
        timestamp);
    if (GST_CLOCK_TIME_IS_VALID (stream_time)) {
      GST_LOG_OBJECT (qtdemux,
          "adding association %" GST_TIME_FORMAT "-> %"
          G_GUINT64_FORMAT, GST_TIME_ARGS (stream_time), byte_position);
      gst_index_add_association (qtdemux->element_index,
          qtdemux->index_id,
          keyframe ? GST_ASSOCIATION_FLAG_KEY_UNIT :
          GST_ASSOCIATION_FLAG_DELTA_UNIT, GST_FORMAT_TIME, stream_time,
          GST_FORMAT_BYTES, byte_position, NULL);
    }
  }
#endif

  if (stream->need_clip)
    buf = gst_qtdemux_clip_buffer (qtdemux, stream, buf);

  if (G_UNLIKELY (buf == NULL))
    goto exit;

  if (G_UNLIKELY (stream->discont)) {
    GST_LOG_OBJECT (qtdemux, "marking discont buffer");
    GST_BUFFER_FLAG_SET (buf, GST_BUFFER_FLAG_DISCONT);
    stream->discont = FALSE;
  } else {
    GST_BUFFER_FLAG_UNSET (buf, GST_BUFFER_FLAG_DISCONT);
  }

  if (!keyframe) {
    GST_BUFFER_FLAG_SET (buf, GST_BUFFER_FLAG_DELTA_UNIT);
    stream->on_keyframe = FALSE;
  } else {
    stream->on_keyframe = TRUE;
  }


  GST_LOG_OBJECT (qtdemux,
      "Pushing buffer with dts %" GST_TIME_FORMAT ", pts %" GST_TIME_FORMAT
      ", duration %" GST_TIME_FORMAT " on pad %s", GST_TIME_ARGS (dts),
      GST_TIME_ARGS (pts), GST_TIME_ARGS (duration),
      GST_PAD_NAME (stream->pad));

  if (stream->protected && stream->protection_scheme_type == FOURCC_cenc) {
    GstStructure *crypto_info;
    QtDemuxCencSampleSetInfo *info =
        (QtDemuxCencSampleSetInfo *) stream->protection_scheme_info;
    gint index;
    GstEvent *event;

    while ((event = g_queue_pop_head (&stream->protection_scheme_event_queue))) {
      gst_pad_push_event (stream->pad, event);
    }

    if (qtdemux->cenc_aux_info_offset > 0 && info->crypto_info == NULL) {
      GST_DEBUG_OBJECT (qtdemux, "cenc metadata hasn't been parsed yet");
      gst_buffer_unref (buf);
      goto exit;
    }

    index = stream->sample_index - (stream->n_samples - info->crypto_info->len);
    if (G_LIKELY (index >= 0 && index < info->crypto_info->len)) {
      /* steal structure from array */
      crypto_info = g_ptr_array_index (info->crypto_info, index);
      g_ptr_array_index (info->crypto_info, index) = NULL;
      GST_LOG_OBJECT (qtdemux, "attaching cenc metadata [%u]", index);
      if (!crypto_info || !gst_buffer_add_protection_meta (buf, crypto_info))
        GST_ERROR_OBJECT (qtdemux, "failed to attach cenc metadata to buffer");
    }
  }

  ret = gst_pad_push (stream->pad, buf);

  if (GST_CLOCK_TIME_IS_VALID (pts) && GST_CLOCK_TIME_IS_VALID (duration)) {
    /* mark position in stream, we'll need this to know when to send GAP event */
    stream->segment.position = pts + duration;
  }

exit:
  return ret;
}

static const QtDemuxRandomAccessEntry *
gst_qtdemux_stream_seek_fragment (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GstClockTime pos, gboolean after)
{
  QtDemuxRandomAccessEntry *entries = stream->ra_entries;
  guint n_entries = stream->n_ra_entries;
  guint i;

  /* we assume the table is sorted */
  for (i = 0; i < n_entries; ++i) {
    if (entries[i].ts > pos)
      break;
  }

  /* FIXME: maybe save first moof_offset somewhere instead, but for now it's
   * probably okay to assume that the index lists the very first fragment */
  if (i == 0)
    return &entries[0];

  if (after)
    return &entries[i];
  else
    return &entries[i - 1];
}

static gboolean
gst_qtdemux_do_fragmented_seek (GstQTDemux * qtdemux)
{
  const QtDemuxRandomAccessEntry *best_entry = NULL;
  guint i;

  GST_OBJECT_LOCK (qtdemux);

  g_assert (qtdemux->n_streams > 0);

  for (i = 0; i < qtdemux->n_streams; i++) {
    const QtDemuxRandomAccessEntry *entry;
    QtDemuxStream *stream;
    gboolean is_audio_or_video;

    stream = qtdemux->streams[i];

    g_free (stream->samples);
    stream->samples = NULL;
    stream->n_samples = 0;
    stream->stbl_index = -1;    /* no samples have yet been parsed */
    stream->sample_index = -1;

    if (stream->ra_entries == NULL)
      continue;

    if (stream->subtype == FOURCC_vide || stream->subtype == FOURCC_soun)
      is_audio_or_video = TRUE;
    else
      is_audio_or_video = FALSE;

    entry =
        gst_qtdemux_stream_seek_fragment (qtdemux, stream,
        stream->time_position, !is_audio_or_video);

    GST_INFO_OBJECT (stream->pad, "%" GST_TIME_FORMAT " at offset "
        "%" G_GUINT64_FORMAT, GST_TIME_ARGS (entry->ts), entry->moof_offset);

    stream->pending_seek = entry;

    /* decide position to jump to just based on audio/video tracks, not subs */
    if (!is_audio_or_video)
      continue;

    if (best_entry == NULL || entry->moof_offset < best_entry->moof_offset)
      best_entry = entry;
  }

  if (best_entry == NULL) {
    GST_OBJECT_UNLOCK (qtdemux);
    return FALSE;
  }

  GST_INFO_OBJECT (qtdemux, "seek to %" GST_TIME_FORMAT ", best fragment "
      "moof offset: %" G_GUINT64_FORMAT ", ts %" GST_TIME_FORMAT,
      GST_TIME_ARGS (qtdemux->streams[0]->time_position),
      best_entry->moof_offset, GST_TIME_ARGS (best_entry->ts));

  qtdemux->moof_offset = best_entry->moof_offset;

  qtdemux_add_fragmented_samples (qtdemux);

  GST_OBJECT_UNLOCK (qtdemux);
  return TRUE;
}

static GstFlowReturn
gst_qtdemux_loop_state_movie (GstQTDemux * qtdemux)
{
  GstFlowReturn ret = GST_FLOW_OK;
  GstBuffer *buf = NULL;
  QtDemuxStream *stream;
  GstClockTime min_time;
  guint64 offset = 0;
  GstClockTime dts = GST_CLOCK_TIME_NONE;
  GstClockTime pts = GST_CLOCK_TIME_NONE;
  GstClockTime duration = 0;
  gboolean keyframe = FALSE;
  guint sample_size = 0;
  gboolean empty = 0;
  guint size;
  gint index;
  gint i;

  gst_qtdemux_push_pending_newsegment (qtdemux);

  if (qtdemux->fragmented_seek_pending) {
    GST_INFO_OBJECT (qtdemux, "pending fragmented seek");
    gst_qtdemux_do_fragmented_seek (qtdemux);
    GST_INFO_OBJECT (qtdemux, "fragmented seek done!");
    qtdemux->fragmented_seek_pending = FALSE;
  }

  /* Figure out the next stream sample to output, min_time is expressed in
   * global time and runs over the edit list segments. */
  min_time = G_MAXUINT64;
  index = -1;
  for (i = 0; i < qtdemux->n_streams; i++) {
    GstClockTime position;

    stream = qtdemux->streams[i];
    position = stream->time_position;

    /* position of -1 is EOS */
    if (position != GST_CLOCK_TIME_NONE && position < min_time) {
      min_time = position;
      index = i;
    }
  }
  /* all are EOS */
  if (G_UNLIKELY (index == -1)) {
    GST_DEBUG_OBJECT (qtdemux, "all streams are EOS");
    goto eos;
  }

  /* check for segment end */
  if (G_UNLIKELY (qtdemux->segment.stop != -1
          && ((qtdemux->segment.rate >= 0 && qtdemux->segment.stop <= min_time)
              || (qtdemux->segment.rate < 0
                  && qtdemux->segment.start > min_time))
          && qtdemux->streams[index]->on_keyframe)) {
    GST_DEBUG_OBJECT (qtdemux, "we reached the end of our segment.");
    qtdemux->streams[index]->time_position = GST_CLOCK_TIME_NONE;
    goto eos_stream;
  }

  /* gap events for subtitle streams */
  for (i = 0; i < qtdemux->n_streams; i++) {
    stream = qtdemux->streams[i];
    if (stream->pad && (stream->subtype == FOURCC_subp
            || stream->subtype == FOURCC_text
            || stream->subtype == FOURCC_sbtl)) {
      /* send one second gap events until the stream catches up */
      /* gaps can only be sent after segment is activated (segment.stop is no longer -1) */
      while (GST_CLOCK_TIME_IS_VALID (stream->segment.stop) &&
          GST_CLOCK_TIME_IS_VALID (stream->segment.position) &&
          stream->segment.position + GST_SECOND < min_time) {
        GstEvent *gap =
            gst_event_new_gap (stream->segment.position, GST_SECOND);
        gst_pad_push_event (stream->pad, gap);
        stream->segment.position += GST_SECOND;
      }
    }
  }

  stream = qtdemux->streams[index];
  if (stream->new_caps) {
    gst_qtdemux_configure_stream (qtdemux, stream);
    qtdemux_do_allocation (qtdemux, stream);
  }

  /* fetch info for the current sample of this stream */
  if (G_UNLIKELY (!gst_qtdemux_prepare_current_sample (qtdemux, stream, &empty,
              &offset, &sample_size, &dts, &pts, &duration, &keyframe)))
    goto eos_stream;

  /* If we're doing a keyframe-only trickmode, only push keyframes on video streams */
  if (G_UNLIKELY (qtdemux->
          segment.flags & GST_SEGMENT_FLAG_TRICKMODE_KEY_UNITS)) {
    if (stream->subtype == FOURCC_vide && !keyframe) {
      GST_LOG_OBJECT (qtdemux, "Skipping non-keyframe on stream %d", index);
      goto next;
    }
  }

  GST_DEBUG_OBJECT (qtdemux,
      "pushing from stream %d, empty %d offset %" G_GUINT64_FORMAT
      ", size %d, dts=%" GST_TIME_FORMAT ", pts=%" GST_TIME_FORMAT
      ", duration %" GST_TIME_FORMAT, index, empty, offset, sample_size,
      GST_TIME_ARGS (dts), GST_TIME_ARGS (pts), GST_TIME_ARGS (duration));

  if (G_UNLIKELY (empty)) {
    /* empty segment, push a gap and move to the next one */
    gst_pad_push_event (stream->pad, gst_event_new_gap (pts, duration));
    stream->segment.position = pts + duration;
    goto next;
  }

  /* hmm, empty sample, skip and move to next sample */
  if (G_UNLIKELY (sample_size <= 0))
    goto next;

  /* last pushed sample was out of boundary, goto next sample */
  if (G_UNLIKELY (GST_PAD_LAST_FLOW_RETURN (stream->pad) == GST_FLOW_EOS))
    goto next;

  if (stream->max_buffer_size == 0 || sample_size <= stream->max_buffer_size) {
    size = sample_size;
  } else {
    GST_DEBUG_OBJECT (qtdemux,
        "size %d larger than stream max_buffer_size %d, trimming",
        sample_size, stream->max_buffer_size);
    size =
        MIN (sample_size - stream->offset_in_sample, stream->max_buffer_size);
  }

  if (qtdemux->cenc_aux_info_offset > 0) {
    GstMapInfo map;
    GstByteReader br;
    GstBuffer *aux_info = NULL;

    /* pull the data stored before the sample */
    ret =
        gst_qtdemux_pull_atom (qtdemux, qtdemux->offset,
        offset + stream->offset_in_sample - qtdemux->offset, &aux_info);
    if (G_UNLIKELY (ret != GST_FLOW_OK))
      goto beach;
    gst_buffer_map (aux_info, &map, GST_MAP_READ);
    GST_DEBUG_OBJECT (qtdemux, "parsing cenc auxiliary info");
    gst_byte_reader_init (&br, map.data + 8, map.size);
    if (!qtdemux_parse_cenc_aux_info (qtdemux, stream, &br,
            qtdemux->cenc_aux_info_sizes, qtdemux->cenc_aux_sample_count)) {
      GST_ERROR_OBJECT (qtdemux, "failed to parse cenc auxiliary info");
      gst_buffer_unmap (aux_info, &map);
      gst_buffer_unref (aux_info);
      ret = GST_FLOW_ERROR;
      goto beach;
    }
    gst_buffer_unmap (aux_info, &map);
    gst_buffer_unref (aux_info);
  }

  GST_LOG_OBJECT (qtdemux, "reading %d bytes @ %" G_GUINT64_FORMAT, size,
      offset);

  if (stream->use_allocator) {
    /* if we have a per-stream allocator, use it */
    buf = gst_buffer_new_allocate (stream->allocator, size, &stream->params);
  }

  ret = gst_qtdemux_pull_atom (qtdemux, offset + stream->offset_in_sample,
      size, &buf);
  if (G_UNLIKELY (ret != GST_FLOW_OK))
    goto beach;

  if (size != sample_size) {
    pts += gst_util_uint64_scale_int (GST_SECOND,
        stream->offset_in_sample / stream->bytes_per_frame, stream->timescale);
    dts += gst_util_uint64_scale_int (GST_SECOND,
        stream->offset_in_sample / stream->bytes_per_frame, stream->timescale);
    duration = gst_util_uint64_scale_int (GST_SECOND,
        size / stream->bytes_per_frame, stream->timescale);
  }

  ret = gst_qtdemux_decorate_and_push_buffer (qtdemux, stream, buf,
      dts, pts, duration, keyframe, min_time, offset);

  if (size != sample_size) {
    QtDemuxSample *sample = &stream->samples[stream->sample_index];
    QtDemuxSegment *segment = &stream->segments[stream->segment_index];

    GstClockTime time_position = QTSTREAMTIME_TO_GSTTIME (stream,
        sample->timestamp + stream->offset_in_sample / stream->bytes_per_frame);
    if (time_position >= segment->media_start) {
      /* inside the segment, update time_position, looks very familiar to
       * GStreamer segments, doesn't it? */
      stream->time_position = (time_position - segment->media_start) +
          segment->time;
    } else {
      /* not yet in segment, time does not yet increment. This means
       * that we are still prerolling keyframes to the decoder so it can
       * decode the first sample of the segment. */
      stream->time_position = segment->time;
    }
  }

  /* combine flows */
  ret = gst_qtdemux_combine_flows (qtdemux, stream, ret);
  /* ignore unlinked, we will not push on the pad anymore and we will EOS when
   * we have no more data for the pad to push */
  if (ret == GST_FLOW_EOS)
    ret = GST_FLOW_OK;

  stream->offset_in_sample += size;
  if (stream->offset_in_sample >= sample_size) {
    gst_qtdemux_advance_sample (qtdemux, stream);
  }
  goto beach;

next:
  gst_qtdemux_advance_sample (qtdemux, stream);

beach:
  return ret;

  /* special cases */
eos:
  {
    GST_DEBUG_OBJECT (qtdemux, "No samples left for any streams - EOS");
    ret = GST_FLOW_EOS;
    goto beach;
  }
eos_stream:
  {
    GST_DEBUG_OBJECT (qtdemux, "No samples left for stream");
    /* EOS will be raised if all are EOS */
    ret = GST_FLOW_OK;
    goto beach;
  }
}

static void
gst_qtdemux_loop (GstPad * pad)
{
  GstQTDemux *qtdemux;
  guint64 cur_offset;
  GstFlowReturn ret;

  qtdemux = GST_QTDEMUX (gst_pad_get_parent (pad));

  cur_offset = qtdemux->offset;
  GST_LOG_OBJECT (qtdemux, "loop at position %" G_GUINT64_FORMAT ", state %d",
      cur_offset, qtdemux->state);

  switch (qtdemux->state) {
    case QTDEMUX_STATE_INITIAL:
    case QTDEMUX_STATE_HEADER:
      ret = gst_qtdemux_loop_state_header (qtdemux);
      break;
    case QTDEMUX_STATE_MOVIE:
      ret = gst_qtdemux_loop_state_movie (qtdemux);
      if (qtdemux->segment.rate < 0 && ret == GST_FLOW_EOS) {
        ret = gst_qtdemux_seek_to_previous_keyframe (qtdemux);
      }
      break;
    default:
      /* ouch */
      goto invalid_state;
  }

  /* if something went wrong, pause */
  if (ret != GST_FLOW_OK)
    goto pause;

done:
  gst_object_unref (qtdemux);
  return;

  /* ERRORS */
invalid_state:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, FAILED,
        (NULL), ("streaming stopped, invalid state"));
    gst_pad_pause_task (pad);
    gst_qtdemux_push_event (qtdemux, gst_event_new_eos ());
    goto done;
  }
pause:
  {
    const gchar *reason = gst_flow_get_name (ret);

    GST_LOG_OBJECT (qtdemux, "pausing task, reason %s", reason);

    gst_pad_pause_task (pad);

    /* fatal errors need special actions */
    /* check EOS */
    if (ret == GST_FLOW_EOS) {
      if (qtdemux->n_streams == 0) {
        /* we have no streams, post an error */
        gst_qtdemux_post_no_playable_stream_error (qtdemux);
      }
      if (qtdemux->segment.flags & GST_SEEK_FLAG_SEGMENT) {
        gint64 stop;

        if ((stop = qtdemux->segment.stop) == -1)
          stop = qtdemux->segment.duration;

        if (qtdemux->segment.rate >= 0) {
          GstMessage *message;
          GstEvent *event;

          GST_LOG_OBJECT (qtdemux, "Sending segment done, at end of segment");
          message = gst_message_new_segment_done (GST_OBJECT_CAST (qtdemux),
              GST_FORMAT_TIME, stop);
          event = gst_event_new_segment_done (GST_FORMAT_TIME, stop);
          if (qtdemux->segment_seqnum) {
            gst_message_set_seqnum (message, qtdemux->segment_seqnum);
            gst_event_set_seqnum (event, qtdemux->segment_seqnum);
          }
          gst_element_post_message (GST_ELEMENT_CAST (qtdemux), message);
          gst_qtdemux_push_event (qtdemux, event);
        } else {
          GstMessage *message;
          GstEvent *event;

          /*  For Reverse Playback */
          GST_LOG_OBJECT (qtdemux, "Sending segment done, at start of segment");
          message = gst_message_new_segment_done (GST_OBJECT_CAST (qtdemux),
              GST_FORMAT_TIME, qtdemux->segment.start);
          event = gst_event_new_segment_done (GST_FORMAT_TIME,
              qtdemux->segment.start);
          if (qtdemux->segment_seqnum) {
            gst_message_set_seqnum (message, qtdemux->segment_seqnum);
            gst_event_set_seqnum (event, qtdemux->segment_seqnum);
          }
          gst_element_post_message (GST_ELEMENT_CAST (qtdemux), message);
          gst_qtdemux_push_event (qtdemux, event);
        }
      } else {
        GstEvent *event;

        GST_LOG_OBJECT (qtdemux, "Sending EOS at end of segment");
        event = gst_event_new_eos ();
        if (qtdemux->segment_seqnum)
          gst_event_set_seqnum (event, qtdemux->segment_seqnum);
        gst_qtdemux_push_event (qtdemux, event);
      }
    } else if (ret == GST_FLOW_NOT_LINKED || ret < GST_FLOW_EOS) {
      GST_ELEMENT_ERROR (qtdemux, STREAM, FAILED,
          (NULL), ("streaming stopped, reason %s", reason));
      gst_qtdemux_push_event (qtdemux, gst_event_new_eos ());
    }
    goto done;
  }
}

/*
 * has_next_entry
 *
 * Returns if there are samples to be played.
 */
static gboolean
has_next_entry (GstQTDemux * demux)
{
  QtDemuxStream *stream;
  int i;

  GST_DEBUG_OBJECT (demux, "Checking if there are samples not played yet");

  for (i = 0; i < demux->n_streams; i++) {
    stream = demux->streams[i];

    if (stream->sample_index == -1) {
      stream->sample_index = 0;
      stream->offset_in_sample = 0;
    }

    if (stream->sample_index >= stream->n_samples) {
      GST_LOG_OBJECT (demux, "stream %d samples exhausted", i);
      continue;
    }
    GST_DEBUG_OBJECT (demux, "Found a sample");
    return TRUE;
  }

  GST_DEBUG_OBJECT (demux, "There wasn't any next sample");
  return FALSE;
}

/*
 * next_entry_size
 *
 * Returns the size of the first entry at the current offset.
 * If -1, there are none (which means EOS or empty file).
 */
static guint64
next_entry_size (GstQTDemux * demux)
{
  QtDemuxStream *stream;
  int i;
  int smallidx = -1;
  guint64 smalloffs = (guint64) - 1;
  QtDemuxSample *sample;

  GST_LOG_OBJECT (demux, "Finding entry at offset %" G_GUINT64_FORMAT,
      demux->offset);

  for (i = 0; i < demux->n_streams; i++) {
    stream = demux->streams[i];

    if (stream->sample_index == -1) {
      stream->sample_index = 0;
      stream->offset_in_sample = 0;
    }

    if (stream->sample_index >= stream->n_samples) {
      GST_LOG_OBJECT (demux, "stream %d samples exhausted", i);
      continue;
    }

    if (!qtdemux_parse_samples (demux, stream, stream->sample_index)) {
      GST_LOG_OBJECT (demux, "Parsing of index %u from stbl atom failed!",
          stream->sample_index);
      return -1;
    }

    sample = &stream->samples[stream->sample_index];

    GST_LOG_OBJECT (demux,
        "Checking Stream %d (sample_index:%d / offset:%" G_GUINT64_FORMAT
        " / size:%" G_GUINT32_FORMAT ")", i, stream->sample_index,
        sample->offset, sample->size);

    if (((smalloffs == -1)
            || (sample->offset < smalloffs)) && (sample->size)) {
      smallidx = i;
      smalloffs = sample->offset;
    }
  }

  GST_LOG_OBJECT (demux,
      "stream %d offset %" G_GUINT64_FORMAT " demux->offset :%"
      G_GUINT64_FORMAT, smallidx, smalloffs, demux->offset);

  if (smallidx == -1)
    return -1;

  stream = demux->streams[smallidx];
  sample = &stream->samples[stream->sample_index];

  if (sample->offset >= demux->offset) {
    demux->todrop = sample->offset - demux->offset;
    return sample->size + demux->todrop;
  }

  GST_DEBUG_OBJECT (demux,
      "There wasn't any entry at offset %" G_GUINT64_FORMAT, demux->offset);
  return -1;
}

static void
gst_qtdemux_post_progress (GstQTDemux * demux, gint num, gint denom)
{
  gint perc = (gint) ((gdouble) num * 100.0 / (gdouble) denom);

  gst_element_post_message (GST_ELEMENT_CAST (demux),
      gst_message_new_element (GST_OBJECT_CAST (demux),
          gst_structure_new ("progress", "percent", G_TYPE_INT, perc, NULL)));
}

static gboolean
qtdemux_seek_offset (GstQTDemux * demux, guint64 offset)
{
  GstEvent *event;
  gboolean res = 0;

  GST_DEBUG_OBJECT (demux, "Seeking to %" G_GUINT64_FORMAT, offset);

  event =
      gst_event_new_seek (1.0, GST_FORMAT_BYTES,
      GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_ACCURATE, GST_SEEK_TYPE_SET, offset,
      GST_SEEK_TYPE_NONE, -1);

  /* store seqnum to drop flush events, they don't need to reach downstream */
  demux->offset_seek_seqnum = gst_event_get_seqnum (event);
  res = gst_pad_push_event (demux->sinkpad, event);
  demux->offset_seek_seqnum = 0;

  return res;
}

/* check for seekable upstream, above and beyond a mere query */
static void
gst_qtdemux_check_seekability (GstQTDemux * demux)
{
  GstQuery *query;
  gboolean seekable = FALSE;
  gint64 start = -1, stop = -1;

  if (demux->upstream_size)
    return;

  query = gst_query_new_seeking (GST_FORMAT_BYTES);
  if (!gst_pad_peer_query (demux->sinkpad, query)) {
    GST_DEBUG_OBJECT (demux, "seeking query failed");
    goto done;
  }

  gst_query_parse_seeking (query, NULL, &seekable, &start, &stop);

  /* try harder to query upstream size if we didn't get it the first time */
  if (seekable && stop == -1) {
    GST_DEBUG_OBJECT (demux, "doing duration query to fix up unset stop");
    gst_pad_peer_query_duration (demux->sinkpad, GST_FORMAT_BYTES, &stop);
  }

  /* if upstream doesn't know the size, it's likely that it's not seekable in
   * practice even if it technically may be seekable */
  if (seekable && (start != 0 || stop <= start)) {
    GST_DEBUG_OBJECT (demux, "seekable but unknown start/stop -> disable");
    seekable = FALSE;
  }

done:
  gst_query_unref (query);

  GST_DEBUG_OBJECT (demux, "seekable: %d (%" G_GUINT64_FORMAT " - %"
      G_GUINT64_FORMAT ")", seekable, start, stop);
  demux->upstream_seekable = seekable;
  demux->upstream_size = seekable ? stop : -1;
}

static void
gst_qtdemux_drop_data (GstQTDemux * demux, gint bytes)
{
  g_return_if_fail (bytes <= demux->todrop);

  GST_LOG_OBJECT (demux, "Dropping %d bytes", bytes);
  gst_adapter_flush (demux->adapter, bytes);
  demux->neededbytes -= bytes;
  demux->offset += bytes;
  demux->todrop -= bytes;
}

static void
gst_qtdemux_check_send_pending_segment (GstQTDemux * demux)
{
  if (G_UNLIKELY (demux->pending_newsegment)) {
    gint i;

    gst_qtdemux_push_pending_newsegment (demux);
    /* clear to send tags on all streams */
    for (i = 0; i < demux->n_streams; i++) {
      QtDemuxStream *stream;
      stream = demux->streams[i];
      gst_qtdemux_push_tags (demux, stream);
      if (stream->sparse) {
        GST_INFO_OBJECT (demux, "Sending gap event on stream %d", i);
        gst_pad_push_event (stream->pad,
            gst_event_new_gap (stream->segment.position, GST_CLOCK_TIME_NONE));
      }
    }
  }
}

static void
gst_qtdemux_stream_send_initial_gap_segments (GstQTDemux * demux,
    QtDemuxStream * stream)
{
  gint i;

  /* Push any initial gap segments before proceeding to the
   * 'real' data */
  for (i = 0; i < stream->n_segments; i++) {
    gst_qtdemux_activate_segment (demux, stream, i, stream->time_position);

    if (QTSEGMENT_IS_EMPTY (&stream->segments[i])) {
      GstClockTime ts, dur;
      GstEvent *gap;

      ts = stream->time_position;
      dur =
          stream->segments[i].duration - (stream->time_position -
          stream->segments[i].time);
      gap = gst_event_new_gap (ts, dur);
      stream->time_position += dur;

      GST_DEBUG_OBJECT (stream->pad, "Pushing gap for empty "
          "segment: %" GST_PTR_FORMAT, gap);
      gst_pad_push_event (stream->pad, gap);
    } else {
      /* Only support empty segment at the beginning followed by
       * one non-empty segment, this was checked when parsing the
       * edts atom, arriving here is unexpected */
      g_assert (i + 1 == stream->n_segments);
      break;
    }
  }
}

static GstFlowReturn
gst_qtdemux_chain (GstPad * sinkpad, GstObject * parent, GstBuffer * inbuf)
{
  GstQTDemux *demux;

  demux = GST_QTDEMUX (parent);

  if (GST_BUFFER_FLAG_IS_SET (inbuf, GST_BUFFER_FLAG_DISCONT)) {
    gint i;

    GST_DEBUG_OBJECT (demux, "Got DISCONT, marking all streams as DISCONT");

    for (i = 0; i < demux->n_streams; i++) {
      demux->streams[i]->discont = TRUE;
    }

    /* Reverse fragmented playback, need to flush all we have before
     * consuming a new fragment.
     * The samples array have the timestamps calculated by accumulating the
     * durations but this won't work for reverse playback of fragments as
     * the timestamps of a subsequent fragment should be smaller than the
     * previously received one. */
    if (demux->fragmented && demux->segment.rate < 0) {
      gst_qtdemux_process_adapter (demux, TRUE);
      for (i = 0; i < demux->n_streams; i++)
        gst_qtdemux_stream_flush_samples_data (demux, demux->streams[i]);
    }
  }

  gst_adapter_push (demux->adapter, inbuf);

  GST_DEBUG_OBJECT (demux,
      "pushing in inbuf %p, neededbytes:%u, available:%" G_GSIZE_FORMAT, inbuf,
      demux->neededbytes, gst_adapter_available (demux->adapter));

  return gst_qtdemux_process_adapter (demux, FALSE);
}

static GstFlowReturn
gst_qtdemux_process_adapter (GstQTDemux * demux, gboolean force)
{
  GstFlowReturn ret = GST_FLOW_OK;

  /* we never really mean to buffer that much */
  if (demux->neededbytes == -1) {
    goto eos;
  }

  while (((gst_adapter_available (demux->adapter)) >= demux->neededbytes) &&
      (ret == GST_FLOW_OK || (ret == GST_FLOW_NOT_LINKED && force))) {

    GST_DEBUG_OBJECT (demux,
        "state:%d , demux->neededbytes:%d, demux->offset:%" G_GUINT64_FORMAT,
        demux->state, demux->neededbytes, demux->offset);

    switch (demux->state) {
      case QTDEMUX_STATE_INITIAL:{
        const guint8 *data;
        guint32 fourcc;
        guint64 size;

        gst_qtdemux_check_seekability (demux);

        data = gst_adapter_map (demux->adapter, demux->neededbytes);

        /* get fourcc/length, set neededbytes */
        extract_initial_length_and_fourcc ((guint8 *) data, demux->neededbytes,
            &size, &fourcc);
        gst_adapter_unmap (demux->adapter);
        data = NULL;
        GST_DEBUG_OBJECT (demux, "Peeking found [%" GST_FOURCC_FORMAT "] "
            "size: %" G_GUINT64_FORMAT, GST_FOURCC_ARGS (fourcc), size);
        if (size == 0) {
          GST_ELEMENT_ERROR (demux, STREAM, DEMUX,
              (_("This file is invalid and cannot be played.")),
              ("initial atom '%" GST_FOURCC_FORMAT "' has empty length",
                  GST_FOURCC_ARGS (fourcc)));
          ret = GST_FLOW_ERROR;
          break;
        }
        if (fourcc == FOURCC_mdat) {
          gint next_entry = next_entry_size (demux);
          if (demux->n_streams > 0 && (next_entry != -1 || !demux->fragmented)) {
            /* we have the headers, start playback */
            demux->state = QTDEMUX_STATE_MOVIE;
            demux->neededbytes = next_entry;
            demux->mdatleft = size;
          } else {
            /* no headers yet, try to get them */
            guint bs;
            gboolean res;
            guint64 old, target;

          buffer_data:
            old = demux->offset;
            target = old + size;

            /* try to jump over the atom with a seek */
            /* only bother if it seems worth doing so,
             * and avoids possible upstream/server problems */
            if (demux->upstream_seekable &&
                demux->upstream_size > 4 * (1 << 20)) {
              res = qtdemux_seek_offset (demux, target);
            } else {
              GST_DEBUG_OBJECT (demux, "skipping seek");
              res = FALSE;
            }

            if (res) {
              GST_DEBUG_OBJECT (demux, "seek success");
              /* remember the offset fo the first mdat so we can seek back to it
               * after we have the headers */
              if (fourcc == FOURCC_mdat && demux->first_mdat == -1) {
                demux->first_mdat = old;
                GST_DEBUG_OBJECT (demux, "first mdat at %" G_GUINT64_FORMAT,
                    demux->first_mdat);
              }
              /* seek worked, continue reading */
              demux->offset = target;
              demux->neededbytes = 16;
              demux->state = QTDEMUX_STATE_INITIAL;
            } else {
              /* seek failed, need to buffer */
              demux->offset = old;
              GST_DEBUG_OBJECT (demux, "seek failed/skipped");
              /* there may be multiple mdat (or alike) buffers */
              /* sanity check */
              if (demux->mdatbuffer)
                bs = gst_buffer_get_size (demux->mdatbuffer);
              else
                bs = 0;
              if (size + bs > 10 * (1 << 20))
                goto no_moov;
              demux->state = QTDEMUX_STATE_BUFFER_MDAT;
              demux->neededbytes = size;
              if (!demux->mdatbuffer)
                demux->mdatoffset = demux->offset;
            }
          }
        } else if (G_UNLIKELY (size > QTDEMUX_MAX_ATOM_SIZE)) {
          GST_ELEMENT_ERROR (demux, STREAM, DEMUX,
              (_("This file is invalid and cannot be played.")),
              ("atom %" GST_FOURCC_FORMAT " has bogus size %" G_GUINT64_FORMAT,
                  GST_FOURCC_ARGS (fourcc), size));
          ret = GST_FLOW_ERROR;
          break;
        } else {
          /* this means we already started buffering and still no moov header,
           * let's continue buffering everything till we get moov */
          if (demux->mdatbuffer && !(fourcc == FOURCC_moov
                  || fourcc == FOURCC_moof))
            goto buffer_data;
          demux->neededbytes = size;
          demux->state = QTDEMUX_STATE_HEADER;
        }
        break;
      }
      case QTDEMUX_STATE_HEADER:{
        const guint8 *data;
        guint32 fourcc;

        GST_DEBUG_OBJECT (demux, "In header");

        data = gst_adapter_map (demux->adapter, demux->neededbytes);

        /* parse the header */
        extract_initial_length_and_fourcc (data, demux->neededbytes, NULL,
            &fourcc);
        if (fourcc == FOURCC_moov) {
          gint n;

          /* in usual fragmented setup we could try to scan for more
           * and end up at the the moov (after mdat) again */
          if (demux->got_moov && demux->n_streams > 0 &&
              (!demux->fragmented
                  || demux->last_moov_offset == demux->offset)) {
            GST_DEBUG_OBJECT (demux,
                "Skipping moov atom as we have (this) one already");
          } else {
            GST_DEBUG_OBJECT (demux, "Parsing [moov]");

            if (demux->got_moov && demux->fragmented) {
              GST_DEBUG_OBJECT (demux,
                  "Got a second moov, clean up data from old one");
              if (demux->moov_node)
                g_node_destroy (demux->moov_node);
              demux->moov_node = NULL;
              demux->moov_node_compressed = NULL;
            } else {
              /* prepare newsegment to send when streaming actually starts */
              if (!demux->pending_newsegment) {
                demux->pending_newsegment =
                    gst_event_new_segment (&demux->segment);
                if (demux->segment_seqnum)
                  gst_event_set_seqnum (demux->pending_newsegment,
                      demux->segment_seqnum);
              }
            }

            demux->last_moov_offset = demux->offset;

            qtdemux_parse_moov (demux, data, demux->neededbytes);
            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);
              }
            }

            demux->got_moov = TRUE;
            gst_qtdemux_check_send_pending_segment (demux);

            /* fragmented streams headers shouldn't contain edts atoms */
            if (!demux->fragmented) {
              for (n = 0; n < demux->n_streams; n++) {
                gst_qtdemux_stream_send_initial_gap_segments (demux,
                    demux->streams[n]);
              }
            }

            g_node_destroy (demux->moov_node);
            demux->moov_node = NULL;
            GST_DEBUG_OBJECT (demux, "Finished parsing the header");
          }
        } else if (fourcc == FOURCC_moof) {
          if ((demux->got_moov || demux->media_caps) && demux->fragmented) {
            guint64 dist = 0;
            GstClockTime prev_pts;
            guint64 prev_offset;

            GST_DEBUG_OBJECT (demux, "Parsing [moof]");

            /*
             * The timestamp of the moof buffer is relevant as some scenarios
             * won't have the initial timestamp in the atoms. Whenever a new
             * buffer has started, we get that buffer's PTS and use it as a base
             * timestamp for the trun entries.
             *
             * To keep track of the current buffer timestamp and starting point
             * we use gst_adapter_prev_pts that gives us the PTS and the distance
             * from the beggining of the buffer, with the distance and demux->offset
             * we know if it is still the same buffer or not.
             */
            prev_pts = gst_adapter_prev_pts (demux->adapter, &dist);
            prev_offset = demux->offset - dist;
            if (demux->fragment_start_offset == -1
                || prev_offset > demux->fragment_start_offset) {
              demux->fragment_start_offset = prev_offset;
              demux->fragment_start = prev_pts;
              GST_DEBUG_OBJECT (demux,
                  "New fragment start found at: %" G_GUINT64_FORMAT " : %"
                  GST_TIME_FORMAT, demux->fragment_start_offset,
                  GST_TIME_ARGS (demux->fragment_start));
            }

            demux->moof_offset = demux->offset;
            if (!qtdemux_parse_moof (demux, data, demux->neededbytes,
                    demux->offset, NULL)) {
              gst_adapter_unmap (demux->adapter);
              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) {
                GST_DEBUG_OBJECT (demux, "new pending_newsegment");
                demux->pending_newsegment =
                    gst_event_new_segment (&demux->segment);
                if (demux->segment_seqnum)
                  gst_event_set_seqnum (demux->pending_newsegment,
                      demux->segment_seqnum);
              }
              qtdemux_expose_streams (demux);
            }
          } else {
            GST_DEBUG_OBJECT (demux, "Discarding [moof]");
          }
        } else if (fourcc == FOURCC_ftyp) {
          GST_DEBUG_OBJECT (demux, "Parsing [ftyp]");
          qtdemux_parse_ftyp (demux, data, demux->neededbytes);
        } else if (fourcc == FOURCC_uuid) {
          GST_DEBUG_OBJECT (demux, "Parsing [uuid]");
          qtdemux_parse_uuid (demux, data, demux->neededbytes);
        } else if (fourcc == FOURCC_sidx) {
          GST_DEBUG_OBJECT (demux, "Parsing [sidx]");
          qtdemux_parse_sidx (demux, data, demux->neededbytes);
        } else {
          GST_WARNING_OBJECT (demux,
              "Unknown fourcc while parsing header : %" GST_FOURCC_FORMAT,
              GST_FOURCC_ARGS (fourcc));
          /* Let's jump that one and go back to initial state */
        }
        gst_adapter_unmap (demux->adapter);
        data = NULL;

        if (demux->mdatbuffer && demux->n_streams) {
          gsize remaining_data_size = 0;

          /* the mdat was before the header */
          GST_DEBUG_OBJECT (demux, "We have n_streams:%d and mdatbuffer:%p",
              demux->n_streams, demux->mdatbuffer);
          /* restore our adapter/offset view of things with upstream;
           * put preceding buffered data ahead of current moov data.
           * This should also handle evil mdat, moov, mdat cases and alike */
          gst_adapter_flush (demux->adapter, demux->neededbytes);

          /* Store any remaining data after the mdat for later usage */
          remaining_data_size = gst_adapter_available (demux->adapter);
          if (remaining_data_size > 0) {
            g_assert (demux->restoredata_buffer == NULL);
            demux->restoredata_buffer =
                gst_adapter_take_buffer (demux->adapter, remaining_data_size);
            demux->restoredata_offset = demux->offset + demux->neededbytes;
            GST_DEBUG_OBJECT (demux,
                "Stored %" G_GSIZE_FORMAT " post mdat bytes at offset %"
                G_GUINT64_FORMAT, remaining_data_size,
                demux->restoredata_offset);
          }

          gst_adapter_push (demux->adapter, demux->mdatbuffer);
          demux->mdatbuffer = NULL;
          demux->offset = demux->mdatoffset;
          demux->neededbytes = next_entry_size (demux);
          demux->state = QTDEMUX_STATE_MOVIE;
          demux->mdatleft = gst_adapter_available (demux->adapter);
        } else {
          GST_DEBUG_OBJECT (demux, "Carrying on normally");
          gst_adapter_flush (demux->adapter, demux->neededbytes);

          /* only go back to the mdat if there are samples to play */
          if (demux->got_moov && demux->first_mdat != -1
              && has_next_entry (demux)) {
            gboolean res;

            /* we need to seek back */
            res = qtdemux_seek_offset (demux, demux->first_mdat);
            if (res) {
              demux->offset = demux->first_mdat;
            } else {
              GST_DEBUG_OBJECT (demux, "Seek back failed");
            }
          } else {
            demux->offset += demux->neededbytes;
          }
          demux->neededbytes = 16;
          demux->state = QTDEMUX_STATE_INITIAL;
        }

        break;
      }
      case QTDEMUX_STATE_BUFFER_MDAT:{
        GstBuffer *buf;
        guint8 fourcc[4];

        GST_DEBUG_OBJECT (demux, "Got our buffer at offset %" G_GUINT64_FORMAT,
            demux->offset);
        buf = gst_adapter_take_buffer (demux->adapter, demux->neededbytes);
        gst_buffer_extract (buf, 0, fourcc, 4);
        GST_DEBUG_OBJECT (demux, "mdatbuffer starts with %" GST_FOURCC_FORMAT,
            GST_FOURCC_ARGS (QT_FOURCC (fourcc)));
        if (demux->mdatbuffer)
          demux->mdatbuffer = gst_buffer_append (demux->mdatbuffer, buf);
        else
          demux->mdatbuffer = buf;
        demux->offset += demux->neededbytes;
        demux->neededbytes = 16;
        demux->state = QTDEMUX_STATE_INITIAL;
        gst_qtdemux_post_progress (demux, 1, 1);

        break;
      }
      case QTDEMUX_STATE_MOVIE:{
        QtDemuxStream *stream = NULL;
        QtDemuxSample *sample;
        int i = -1;
        GstClockTime dts, pts, duration;
        gboolean keyframe;

        GST_DEBUG_OBJECT (demux,
            "BEGIN // in MOVIE for offset %" G_GUINT64_FORMAT, demux->offset);

        if (demux->fragmented) {
          GST_DEBUG_OBJECT (demux, "mdat remaining %" G_GUINT64_FORMAT,
              demux->mdatleft);
          if (G_LIKELY (demux->todrop < demux->mdatleft)) {
            /* if needed data starts within this atom,
             * then it should not exceed this atom */
            if (G_UNLIKELY (demux->neededbytes > demux->mdatleft)) {
              GST_ELEMENT_ERROR (demux, STREAM, DEMUX,
                  (_("This file is invalid and cannot be played.")),
                  ("sample data crosses atom boundary"));
              ret = GST_FLOW_ERROR;
              break;
            }
            demux->mdatleft -= demux->neededbytes;
          } else {
            GST_DEBUG_OBJECT (demux, "data atom emptied; resuming atom scan");
            /* so we are dropping more than left in this atom */
            gst_qtdemux_drop_data (demux, demux->mdatleft);
            demux->mdatleft = 0;

            /* need to resume atom parsing so we do not miss any other pieces */
            demux->state = QTDEMUX_STATE_INITIAL;
            demux->neededbytes = 16;

            /* check if there was any stored post mdat data from previous buffers */
            if (demux->restoredata_buffer) {
              g_assert (gst_adapter_available (demux->adapter) == 0);

              gst_adapter_push (demux->adapter, demux->restoredata_buffer);
              demux->restoredata_buffer = NULL;
              demux->offset = demux->restoredata_offset;
            }

            break;
          }
        }

        if (demux->todrop) {
          if (demux->cenc_aux_info_offset > 0) {
            GstByteReader br;
            const guint8 *data;

            GST_DEBUG_OBJECT (demux, "parsing cenc auxiliary info");
            data = gst_adapter_map (demux->adapter, demux->todrop);
            gst_byte_reader_init (&br, data + 8, demux->todrop);
            if (!qtdemux_parse_cenc_aux_info (demux, demux->streams[0], &br,
                    demux->cenc_aux_info_sizes, demux->cenc_aux_sample_count)) {
              GST_ERROR_OBJECT (demux, "failed to parse cenc auxiliary info");
              ret = GST_FLOW_ERROR;
              gst_adapter_unmap (demux->adapter);
              g_free (demux->cenc_aux_info_sizes);
              demux->cenc_aux_info_sizes = NULL;
              goto done;
            }
            demux->cenc_aux_info_offset = 0;
            g_free (demux->cenc_aux_info_sizes);
            demux->cenc_aux_info_sizes = NULL;
            gst_adapter_unmap (demux->adapter);
          }
          gst_qtdemux_drop_data (demux, demux->todrop);
        }

        /* first buffer? */
        /* initial newsegment sent here after having added pads,
         * possible others in sink_event */
        gst_qtdemux_check_send_pending_segment (demux);

        /* Figure out which stream this packet belongs to */
        for (i = 0; i < demux->n_streams; i++) {
          stream = demux->streams[i];
          if (stream->sample_index >= stream->n_samples)
            continue;
          GST_LOG_OBJECT (demux,
              "Checking stream %d (sample_index:%d / offset:%" G_GUINT64_FORMAT
              " / size:%d)", i, stream->sample_index,
              stream->samples[stream->sample_index].offset,
              stream->samples[stream->sample_index].size);

          if (stream->samples[stream->sample_index].offset == demux->offset)
            break;
        }

        if (G_UNLIKELY (stream == NULL || i == demux->n_streams))
          goto unknown_stream;

        if (stream->new_caps) {
          gst_qtdemux_configure_stream (demux, stream);
        }

        /* Put data in a buffer, set timestamps, caps, ... */
        sample = &stream->samples[stream->sample_index];

        if (G_LIKELY (!(STREAM_IS_EOS (stream)))) {
          GST_DEBUG_OBJECT (demux, "stream : %" GST_FOURCC_FORMAT,
              GST_FOURCC_ARGS (stream->fourcc));

          dts = QTSAMPLE_DTS (stream, sample);
          pts = QTSAMPLE_PTS (stream, sample);
          duration = QTSAMPLE_DUR_DTS (stream, sample, dts);
          keyframe = QTSAMPLE_KEYFRAME (stream, sample);

          /* check for segment end */
          if (G_UNLIKELY (demux->segment.stop != -1
                  && demux->segment.stop <= pts && stream->on_keyframe)) {
            GST_DEBUG_OBJECT (demux, "we reached the end of our segment.");
            stream->time_position = GST_CLOCK_TIME_NONE;        /* this means EOS */

            /* skip this data, stream is EOS */
            gst_adapter_flush (demux->adapter, demux->neededbytes);

            /* check if all streams are eos */
            ret = GST_FLOW_EOS;
            for (i = 0; i < demux->n_streams; i++) {
              if (!STREAM_IS_EOS (demux->streams[i])) {
                ret = GST_FLOW_OK;
                break;
              }
            }

            if (ret == GST_FLOW_EOS) {
              GST_DEBUG_OBJECT (demux, "All streams are EOS, signal upstream");
              goto eos;
            }
          } else {
            GstBuffer *outbuf;

            outbuf =
                gst_adapter_take_buffer (demux->adapter, demux->neededbytes);

            /* FIXME: should either be an assert or a plain check */
            g_return_val_if_fail (outbuf != NULL, GST_FLOW_ERROR);

            ret = gst_qtdemux_decorate_and_push_buffer (demux, stream, outbuf,
                dts, pts, duration, keyframe, dts, demux->offset);
          }

          /* combine flows */
          ret = gst_qtdemux_combine_flows (demux, stream, ret);
          if (ret != GST_FLOW_OK && ret != GST_FLOW_NOT_LINKED)
            goto non_ok_unlinked_flow;
        } else {
          /* skip this data, stream is EOS */
          gst_adapter_flush (demux->adapter, demux->neededbytes);
        }

        stream->sample_index++;
        stream->offset_in_sample = 0;

        /* update current offset and figure out size of next buffer */
        GST_LOG_OBJECT (demux, "increasing offset %" G_GUINT64_FORMAT " by %u",
            demux->offset, demux->neededbytes);
        demux->offset += demux->neededbytes;
        GST_LOG_OBJECT (demux, "offset is now %" G_GUINT64_FORMAT,
            demux->offset);

        if ((demux->neededbytes = next_entry_size (demux)) == -1) {
          if (demux->fragmented) {
            GST_DEBUG_OBJECT (demux, "(temporarily) out of fragmented samples");
            /* there may be more to follow, only finish this atom */
            demux->todrop = demux->mdatleft;
            demux->neededbytes = demux->todrop;
            break;
          }
          goto eos;
        }
        break;
      }
      default:
        goto invalid_state;
    }
  }

  /* when buffering movie data, at least show user something is happening */
  if (ret == GST_FLOW_OK && demux->state == QTDEMUX_STATE_BUFFER_MDAT &&
      gst_adapter_available (demux->adapter) <= demux->neededbytes) {
    gst_qtdemux_post_progress (demux, gst_adapter_available (demux->adapter),
        demux->neededbytes);
  }
done:

  return ret;

  /* ERRORS */
non_ok_unlinked_flow:
  {
    GST_DEBUG_OBJECT (demux, "Stopping, combined return flow %s",
        gst_flow_get_name (ret));
    return ret;
  }
unknown_stream:
  {
    GST_ELEMENT_ERROR (demux, STREAM, FAILED, (NULL), ("unknown stream found"));
    ret = GST_FLOW_ERROR;
    goto done;
  }
eos:
  {
    GST_DEBUG_OBJECT (demux, "no next entry, EOS");
    ret = GST_FLOW_EOS;
    goto done;
  }
invalid_state:
  {
    GST_ELEMENT_ERROR (demux, STREAM, FAILED,
        (NULL), ("qtdemuxer invalid state %d", demux->state));
    ret = GST_FLOW_ERROR;
    goto done;
  }
no_moov:
  {
    GST_ELEMENT_ERROR (demux, STREAM, FAILED,
        (NULL), ("no 'moov' atom within the first 10 MB"));
    ret = GST_FLOW_ERROR;
    goto done;
  }
}

static gboolean
qtdemux_sink_activate (GstPad * sinkpad, GstObject * parent)
{
  GstQuery *query;
  gboolean pull_mode;

  query = gst_query_new_scheduling ();

  if (!gst_pad_peer_query (sinkpad, query)) {
    gst_query_unref (query);
    goto activate_push;
  }

  pull_mode = gst_query_has_scheduling_mode_with_flags (query,
      GST_PAD_MODE_PULL, GST_SCHEDULING_FLAG_SEEKABLE);
  gst_query_unref (query);

  if (!pull_mode)
    goto activate_push;

  GST_DEBUG_OBJECT (sinkpad, "activating pull");
  return gst_pad_activate_mode (sinkpad, GST_PAD_MODE_PULL, TRUE);

activate_push:
  {
    GST_DEBUG_OBJECT (sinkpad, "activating push");
    return gst_pad_activate_mode (sinkpad, GST_PAD_MODE_PUSH, TRUE);
  }
}

static gboolean
qtdemux_sink_activate_mode (GstPad * sinkpad, GstObject * parent,
    GstPadMode mode, gboolean active)
{
  gboolean res;
  GstQTDemux *demux = GST_QTDEMUX (parent);

  switch (mode) {
    case GST_PAD_MODE_PUSH:
      demux->pullbased = FALSE;
      res = TRUE;
      break;
    case GST_PAD_MODE_PULL:
      if (active) {
        demux->pullbased = TRUE;
        res = gst_pad_start_task (sinkpad, (GstTaskFunction) gst_qtdemux_loop,
            sinkpad, NULL);
      } else {
        res = gst_pad_stop_task (sinkpad);
      }
      break;
    default:
      res = FALSE;
      break;
  }
  return res;
}

#ifdef HAVE_ZLIB
static void *
qtdemux_zalloc (void *opaque, unsigned int items, unsigned int size)
{
  return g_malloc (items * size);
}

static void
qtdemux_zfree (void *opaque, void *addr)
{
  g_free (addr);
}

static void *
qtdemux_inflate (void *z_buffer, guint z_length, guint length)
{
  guint8 *buffer;
  z_stream *z;
  int ret;

  z = g_new0 (z_stream, 1);
  z->zalloc = qtdemux_zalloc;
  z->zfree = qtdemux_zfree;
  z->opaque = NULL;

  z->next_in = z_buffer;
  z->avail_in = z_length;

  buffer = (guint8 *) g_malloc (length);
  ret = inflateInit (z);
  while (z->avail_in > 0) {
    if (z->avail_out == 0) {
      length += 1024;
      buffer = (guint8 *) g_realloc (buffer, length);
      z->next_out = buffer + z->total_out;
      z->avail_out = 1024;
    }
    ret = inflate (z, Z_SYNC_FLUSH);
    if (ret != Z_OK)
      break;
  }
  if (ret != Z_STREAM_END) {
    g_warning ("inflate() returned %d", ret);
  }

  g_free (z);
  return buffer;
}
#endif /* HAVE_ZLIB */

static gboolean
qtdemux_parse_moov (GstQTDemux * qtdemux, const guint8 * buffer, guint length)
{
  GNode *cmov;

  qtdemux->moov_node = g_node_new ((guint8 *) buffer);

  /* counts as header data */
  qtdemux->header_size += length;

  GST_DEBUG_OBJECT (qtdemux, "parsing 'moov' atom");
  qtdemux_parse_node (qtdemux, qtdemux->moov_node, buffer, length);

  cmov = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_cmov);
  if (cmov) {
    guint32 method;
    GNode *dcom;
    GNode *cmvd;

    dcom = qtdemux_tree_get_child_by_type (cmov, FOURCC_dcom);
    cmvd = qtdemux_tree_get_child_by_type (cmov, FOURCC_cmvd);
    if (dcom == NULL || cmvd == NULL)
      goto invalid_compression;

    method = QT_FOURCC ((guint8 *) dcom->data + 8);
    switch (method) {
#ifdef HAVE_ZLIB
      case FOURCC_zlib:{
        guint uncompressed_length;
        guint compressed_length;
        guint8 *buf;

        uncompressed_length = QT_UINT32 ((guint8 *) cmvd->data + 8);
        compressed_length = QT_UINT32 ((guint8 *) cmvd->data + 4) - 12;
        GST_LOG ("length = %u", uncompressed_length);

        buf =
            (guint8 *) qtdemux_inflate ((guint8 *) cmvd->data + 12,
            compressed_length, uncompressed_length);

        qtdemux->moov_node_compressed = qtdemux->moov_node;
        qtdemux->moov_node = g_node_new (buf);

        qtdemux_parse_node (qtdemux, qtdemux->moov_node, buf,
            uncompressed_length);
        break;
      }
#endif /* HAVE_ZLIB */
      default:
        GST_WARNING_OBJECT (qtdemux, "unknown or unhandled header compression "
            "type %" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (method));
        break;
    }
  }
  return TRUE;

  /* ERRORS */
invalid_compression:
  {
    GST_ERROR_OBJECT (qtdemux, "invalid compressed header");
    return FALSE;
  }
}

static gboolean
qtdemux_parse_container (GstQTDemux * qtdemux, GNode * node, const guint8 * buf,
    const guint8 * end)
{
  while (G_UNLIKELY (buf < end)) {
    GNode *child;
    guint32 len;

    if (G_UNLIKELY (buf + 4 > end)) {
      GST_LOG_OBJECT (qtdemux, "buffer overrun");
      break;
    }
    len = QT_UINT32 (buf);
    if (G_UNLIKELY (len == 0)) {
      GST_LOG_OBJECT (qtdemux, "empty container");
      break;
    }
    if (G_UNLIKELY (len < 8)) {
      GST_WARNING_OBJECT (qtdemux, "length too short (%d < 8)", len);
      break;
    }
    if (G_UNLIKELY (len > (end - buf))) {
      GST_WARNING_OBJECT (qtdemux, "length too long (%d > %d)", len,
          (gint) (end - buf));
      break;
    }

    child = g_node_new ((guint8 *) buf);
    g_node_append (node, child);
    GST_LOG_OBJECT (qtdemux, "adding new node of len %d", len);
    qtdemux_parse_node (qtdemux, child, buf, len);

    buf += len;
  }
  return TRUE;
}

static gboolean
qtdemux_parse_theora_extension (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GNode * xdxt)
{
  int len = QT_UINT32 (xdxt->data);
  guint8 *buf = xdxt->data;
  guint8 *end = buf + len;
  GstBuffer *buffer;

  /* skip size and type */
  buf += 8;
  end -= 8;

  while (buf < end) {
    gint size;
    guint32 type;

    size = QT_UINT32 (buf);
    type = QT_FOURCC (buf + 4);

    GST_LOG_OBJECT (qtdemux, "%p %p", buf, end);

    if (buf + size > end || size <= 0)
      break;

    buf += 8;
    size -= 8;

    GST_WARNING_OBJECT (qtdemux, "have cookie %" GST_FOURCC_FORMAT,
        GST_FOURCC_ARGS (type));

    switch (type) {
      case FOURCC_tCtH:
        buffer = gst_buffer_new_and_alloc (size);
        gst_buffer_fill (buffer, 0, buf, size);
        stream->buffers = g_slist_append (stream->buffers, buffer);
        GST_LOG_OBJECT (qtdemux, "parsing theora header");
        break;
      case FOURCC_tCt_:
        buffer = gst_buffer_new_and_alloc (size);
        gst_buffer_fill (buffer, 0, buf, size);
        stream->buffers = g_slist_append (stream->buffers, buffer);
        GST_LOG_OBJECT (qtdemux, "parsing theora comment");
        break;
      case FOURCC_tCtC:
        buffer = gst_buffer_new_and_alloc (size);
        gst_buffer_fill (buffer, 0, buf, size);
        stream->buffers = g_slist_append (stream->buffers, buffer);
        GST_LOG_OBJECT (qtdemux, "parsing theora codebook");
        break;
      default:
        GST_WARNING_OBJECT (qtdemux,
            "unknown theora cookie %" GST_FOURCC_FORMAT,
            GST_FOURCC_ARGS (type));
        break;
    }
    buf += size;
  }
  return TRUE;
}

static gboolean
qtdemux_parse_node (GstQTDemux * qtdemux, GNode * node, const guint8 * buffer,
    guint length)
{
  guint32 fourcc = 0;
  guint32 node_length = 0;
  const QtNodeType *type;
  const guint8 *end;

  GST_LOG_OBJECT (qtdemux, "qtdemux_parse buffer %p length %u", buffer, length);

  if (G_UNLIKELY (length < 8))
    goto not_enough_data;

  node_length = QT_UINT32 (buffer);
  fourcc = QT_FOURCC (buffer + 4);

  /* ignore empty nodes */
  if (G_UNLIKELY (fourcc == 0 || node_length == 8))
    return TRUE;

  type = qtdemux_type_get (fourcc);

  end = buffer + length;

  GST_LOG_OBJECT (qtdemux,
      "parsing '%" GST_FOURCC_FORMAT "', length=%u, name '%s'",
      GST_FOURCC_ARGS (fourcc), node_length, type->name);

  if (node_length > length)
    goto broken_atom_size;

  if (type->flags & QT_FLAG_CONTAINER) {
    qtdemux_parse_container (qtdemux, node, buffer + 8, end);
  } else {
    switch (fourcc) {
      case FOURCC_stsd:
      {
        if (node_length < 20) {
          GST_LOG_OBJECT (qtdemux, "skipping small stsd box");
          break;
        }
        GST_DEBUG_OBJECT (qtdemux,
            "parsing stsd (sample table, sample description) atom");
        /* Skip over 8 byte atom hdr + 1 byte version, 3 bytes flags, 4 byte num_entries */
        qtdemux_parse_container (qtdemux, node, buffer + 16, end);
        break;
      }
      case FOURCC_mp4a:
      case FOURCC_alac:
      {
        guint32 version;
        guint32 offset;
        guint min_size;

        /* also read alac (or whatever) in stead of mp4a in the following,
         * since a similar layout is used in other cases as well */
        if (fourcc == FOURCC_mp4a)
          min_size = 20;
        else
          min_size = 40;

        /* There are two things we might encounter here: a true mp4a atom, and
           an mp4a entry in an stsd atom. The latter is what we're interested
           in, and it looks like an atom, but isn't really one. The true mp4a
           atom is short, so we detect it based on length here. */
        if (length < min_size) {
          GST_LOG_OBJECT (qtdemux, "skipping small %" GST_FOURCC_FORMAT " box",
              GST_FOURCC_ARGS (fourcc));
          break;
        }

        /* 'version' here is the sound sample description version. Types 0 and
           1 are documented in the QTFF reference, but type 2 is not: it's
           described in Apple header files instead (struct SoundDescriptionV2
           in Movies.h) */
        version = QT_UINT16 (buffer + 16);

        GST_DEBUG_OBJECT (qtdemux, "%" GST_FOURCC_FORMAT " version 0x%08x",
            GST_FOURCC_ARGS (fourcc), version);

        /* parse any esds descriptors */
        switch (version) {
          case 0:
            offset = 0x24;
            break;
          case 1:
            offset = 0x34;
            break;
          case 2:
            offset = 0x48;
            break;
          default:
            GST_WARNING_OBJECT (qtdemux,
                "unhandled %" GST_FOURCC_FORMAT " version 0x%08x",
                GST_FOURCC_ARGS (fourcc), version);
            offset = 0;
            break;
        }
        if (offset)
          qtdemux_parse_container (qtdemux, node, buffer + offset, end);
        break;
      }
      case FOURCC_mp4v:
      case FOURCC_MP4V:
      case FOURCC_fmp4:
      case FOURCC_FMP4:
      case FOURCC_apcs:
      case FOURCC_apch:
      case FOURCC_apcn:
      case FOURCC_apco:
      case FOURCC_ap4h:
      {
        const guint8 *buf;
        guint32 version;
        int tlen;

        /* codec_data is contained inside these atoms, which all have
         * the same format. */

        GST_DEBUG_OBJECT (qtdemux, "parsing in %" GST_FOURCC_FORMAT,
            GST_FOURCC_ARGS (fourcc));
        version = QT_UINT32 (buffer + 16);
        GST_DEBUG_OBJECT (qtdemux, "version %08x", version);
        if (1 || version == 0x00000000) {
          buf = buffer + 0x32;

          /* FIXME Quicktime uses PASCAL string while
           * the iso format uses C strings. Check the file
           * type before attempting to parse the string here. */
          tlen = QT_UINT8 (buf);
          GST_DEBUG_OBJECT (qtdemux, "tlen = %d", tlen);
          buf++;
          GST_DEBUG_OBJECT (qtdemux, "string = %.*s", tlen, (char *) buf);
          /* the string has a reserved space of 32 bytes so skip
           * the remaining 31 */
          buf += 31;
          buf += 4;             /* and 4 bytes reserved */

          GST_MEMDUMP_OBJECT (qtdemux, "mp4v", buf, end - buf);

          qtdemux_parse_container (qtdemux, node, buf, end);
        }
        break;
      }
      case FOURCC_H264:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "H264", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_avc1:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "avc1", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_avc3:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "avc3", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_H265:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "H265", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_hvc1:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "hvc1", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_hev1:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "hev1", buffer, end - buffer);
        qtdemux_parse_container (qtdemux, node, buffer + 0x56, end);
        break;
      }
      case FOURCC_mjp2:
      {
        qtdemux_parse_container (qtdemux, node, buffer + 86, end);
        break;
      }
      case FOURCC_meta:
      {
        GST_DEBUG_OBJECT (qtdemux, "parsing meta atom");
        qtdemux_parse_container (qtdemux, node, buffer + 12, end);
        break;
      }
      case FOURCC_mp4s:
      {
        GST_MEMDUMP_OBJECT (qtdemux, "mp4s", buffer, end - buffer);
        /* Skip 8 byte header, plus 8 byte version + flags + entry_count */
        qtdemux_parse_container (qtdemux, node, buffer + 16, end);
        break;
      }
      case FOURCC_XiTh:
      {
        guint32 version;
        guint32 offset;

        version = QT_UINT32 (buffer + 12);
        GST_DEBUG_OBJECT (qtdemux, "parsing XiTh atom version 0x%08x", version);

        switch (version) {
          case 0x00000001:
            offset = 0x62;
            break;
          default:
            GST_DEBUG_OBJECT (qtdemux, "unknown version 0x%08x", version);
            offset = 0;
            break;
        }
        if (offset)
          qtdemux_parse_container (qtdemux, node, buffer + offset, end);
        break;
      }
      case FOURCC_in24:
      {
        qtdemux_parse_container (qtdemux, node, buffer + 0x34, end);
        break;
      }
      case FOURCC_uuid:
      {
        qtdemux_parse_uuid (qtdemux, buffer, end - buffer);
        break;
      }
      case FOURCC_encv:
      {
        qtdemux_parse_container (qtdemux, node, buffer + 86, end);
        break;
      }
      case FOURCC_enca:
      {
        qtdemux_parse_container (qtdemux, node, buffer + 36, end);
        break;
      }
      default:
        if (!strcmp (type->name, "unknown"))
          GST_MEMDUMP ("Unknown tag", buffer + 4, end - buffer - 4);
        break;
    }
  }
  GST_LOG_OBJECT (qtdemux, "parsed '%" GST_FOURCC_FORMAT "'",
      GST_FOURCC_ARGS (fourcc));
  return TRUE;

/* ERRORS */
not_enough_data:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")),
        ("Not enough data for an atom header, got only %u bytes", length));
    return FALSE;
  }
broken_atom_size:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")),
        ("Atom '%" GST_FOURCC_FORMAT "' has size of %u bytes, but we have only "
            "%u bytes available.", GST_FOURCC_ARGS (fourcc), node_length,
            length));
    return FALSE;
  }
}

static GNode *
qtdemux_tree_get_child_by_type (GNode * node, guint32 fourcc)
{
  GNode *child;
  guint8 *buffer;
  guint32 child_fourcc;

  for (child = g_node_first_child (node); child;
      child = g_node_next_sibling (child)) {
    buffer = (guint8 *) child->data;

    child_fourcc = QT_FOURCC (buffer + 4);

    if (G_UNLIKELY (child_fourcc == fourcc)) {
      return child;
    }
  }
  return NULL;
}

static GNode *
qtdemux_tree_get_child_by_type_full (GNode * node, guint32 fourcc,
    GstByteReader * parser)
{
  GNode *child;
  guint8 *buffer;
  guint32 child_fourcc, child_len;

  for (child = g_node_first_child (node); child;
      child = g_node_next_sibling (child)) {
    buffer = (guint8 *) child->data;

    child_len = QT_UINT32 (buffer);
    child_fourcc = QT_FOURCC (buffer + 4);

    if (G_UNLIKELY (child_fourcc == fourcc)) {
      if (G_UNLIKELY (child_len < (4 + 4)))
        return NULL;
      /* FIXME: must verify if atom length < parent atom length */
      gst_byte_reader_init (parser, buffer + (4 + 4), child_len - (4 + 4));
      return child;
    }
  }
  return NULL;
}

static GNode *
qtdemux_tree_get_sibling_by_type_full (GNode * node, guint32 fourcc,
    GstByteReader * parser)
{
  GNode *child;
  guint8 *buffer;
  guint32 child_fourcc, child_len;

  for (child = g_node_next_sibling (node); child;
      child = g_node_next_sibling (child)) {
    buffer = (guint8 *) child->data;

    child_fourcc = QT_FOURCC (buffer + 4);

    if (child_fourcc == fourcc) {
      if (parser) {
        child_len = QT_UINT32 (buffer);
        if (G_UNLIKELY (child_len < (4 + 4)))
          return NULL;
        /* FIXME: must verify if atom length < parent atom length */
        gst_byte_reader_init (parser, buffer + (4 + 4), child_len - (4 + 4));
      }
      return child;
    }
  }
  return NULL;
}

static GNode *
qtdemux_tree_get_sibling_by_type (GNode * node, guint32 fourcc)
{
  return qtdemux_tree_get_sibling_by_type_full (node, fourcc, NULL);
}

static void
qtdemux_do_allocation (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
/* FIXME: This can only reliably work if demuxers have a
 * separate streaming thread per srcpad. This should be
 * done in a demuxer base class, which integrates parts
 * of multiqueue
 *
 * https://bugzilla.gnome.org/show_bug.cgi?id=701856
 */
#if 0
  GstQuery *query;

  query = gst_query_new_allocation (stream->caps, FALSE);

  if (!gst_pad_peer_query (stream->pad, query)) {
    /* not a problem, just debug a little */
    GST_DEBUG_OBJECT (qtdemux, "peer ALLOCATION query failed");
  }

  if (stream->allocator)
    gst_object_unref (stream->allocator);

  if (gst_query_get_n_allocation_params (query) > 0) {
    /* try the allocator */
    gst_query_parse_nth_allocation_param (query, 0, &stream->allocator,
        &stream->params);
    stream->use_allocator = TRUE;
  } else {
    stream->allocator = NULL;
    gst_allocation_params_init (&stream->params);
    stream->use_allocator = FALSE;
  }
  gst_query_unref (query);
#endif
}

static gboolean
gst_qtdemux_configure_protected_caps (GstQTDemux * qtdemux,
    QtDemuxStream * stream)
{
  GstStructure *s;
  const gchar *selected_system;

  g_return_val_if_fail (qtdemux != NULL, FALSE);
  g_return_val_if_fail (stream != NULL, FALSE);
  g_return_val_if_fail (gst_caps_get_size (stream->caps) == 1, FALSE);

  if (stream->protection_scheme_type != FOURCC_cenc) {
    GST_ERROR_OBJECT (qtdemux, "unsupported protection scheme");
    return FALSE;
  }
  if (qtdemux->protection_system_ids == NULL) {
    GST_ERROR_OBJECT (qtdemux, "stream is protected using cenc, but no "
        "cenc protection system information has been found");
    return FALSE;
  }
  g_ptr_array_add (qtdemux->protection_system_ids, NULL);
  selected_system = gst_protection_select_system ((const gchar **)
      qtdemux->protection_system_ids->pdata);
  g_ptr_array_remove_index (qtdemux->protection_system_ids,
      qtdemux->protection_system_ids->len - 1);
  if (!selected_system) {
    GST_ERROR_OBJECT (qtdemux, "stream is protected, but no "
        "suitable decryptor element has been found");
    return FALSE;
  }

  s = gst_caps_get_structure (stream->caps, 0);
  if (!gst_structure_has_name (s, "application/x-cenc")) {
    gst_structure_set (s,
        "original-media-type", G_TYPE_STRING, gst_structure_get_name (s),
        GST_PROTECTION_SYSTEM_ID_CAPS_FIELD, G_TYPE_STRING, selected_system,
        NULL);
    gst_structure_set_name (s, "application/x-cenc");
  }
  return TRUE;
}

static gboolean
gst_qtdemux_configure_stream (GstQTDemux * qtdemux, QtDemuxStream * stream)
{
  if (stream->subtype == FOURCC_vide) {
    /* fps is calculated base on the duration of the average framerate since
     * qt does not have a fixed framerate. */
    gboolean fps_available = TRUE;

    if ((stream->n_samples == 1) && (stream->first_duration == 0)) {
      /* still frame */
      stream->fps_n = 0;
      stream->fps_d = 1;
    } else {
      if (stream->duration == 0 || stream->n_samples < 2) {
        stream->fps_n = stream->timescale;
        stream->fps_d = 1;
        fps_available = FALSE;
      } else {
        GstClockTime avg_duration;
        guint64 duration;
        guint32 n_samples;

        /* duration and n_samples can be updated for fragmented format
         * so, framerate of fragmented format is calculated using data in a moof */
        if (qtdemux->fragmented && stream->n_samples_moof > 0
            && stream->duration_moof > 0) {
          n_samples = stream->n_samples_moof;
          duration = stream->duration_moof;
        } else {
          n_samples = stream->n_samples;
          duration = stream->duration;
        }

        /* Calculate a framerate, ignoring the first sample which is sometimes truncated */
        /* stream->duration is guint64, timescale, n_samples are guint32 */
        avg_duration =
            gst_util_uint64_scale_round (duration -
            stream->first_duration, GST_SECOND,
            (guint64) (stream->timescale) * (n_samples - 1));

        GST_LOG_OBJECT (qtdemux,
            "Calculating avg sample duration based on stream (or moof) duration %"
            G_GUINT64_FORMAT
            " minus first sample %u, leaving %d samples gives %"
            GST_TIME_FORMAT, duration, stream->first_duration,
            n_samples - 1, GST_TIME_ARGS (avg_duration));

        gst_video_guess_framerate (avg_duration, &stream->fps_n,
            &stream->fps_d);

        GST_DEBUG_OBJECT (qtdemux,
            "Calculating framerate, timescale %u gave fps_n %d fps_d %d",
            stream->timescale, stream->fps_n, stream->fps_d);
      }
    }

    if (stream->caps) {
      stream->caps = gst_caps_make_writable (stream->caps);

      gst_caps_set_simple (stream->caps,
          "width", G_TYPE_INT, stream->width,
          "height", G_TYPE_INT, stream->height, NULL);

      /* set framerate if calculated framerate is reliable */
      if (fps_available) {
        gst_caps_set_simple (stream->caps,
            "framerate", GST_TYPE_FRACTION, stream->fps_n, stream->fps_d, NULL);
      }

      /* calculate pixel-aspect-ratio using display width and height */
      GST_DEBUG_OBJECT (qtdemux,
          "video size %dx%d, target display size %dx%d", stream->width,
          stream->height, stream->display_width, stream->display_height);
      /* qt file might have pasp atom */
      if (stream->par_w > 0 && stream->par_h > 0) {
        GST_DEBUG_OBJECT (qtdemux, "par %d:%d", stream->par_w, stream->par_h);
        gst_caps_set_simple (stream->caps, "pixel-aspect-ratio",
            GST_TYPE_FRACTION, stream->par_w, stream->par_h, NULL);
      } else if (stream->display_width > 0 && stream->display_height > 0 &&
          stream->width > 0 && stream->height > 0) {
        gint n, d;

        /* calculate the pixel aspect ratio using the display and pixel w/h */
        n = stream->display_width * stream->height;
        d = stream->display_height * stream->width;
        if (n == d)
          n = d = 1;
        GST_DEBUG_OBJECT (qtdemux, "setting PAR to %d/%d", n, d);
        stream->par_w = n;
        stream->par_h = d;
        gst_caps_set_simple (stream->caps, "pixel-aspect-ratio",
            GST_TYPE_FRACTION, stream->par_w, stream->par_h, NULL);
      }

      if (stream->multiview_mode != GST_VIDEO_MULTIVIEW_MODE_NONE) {
        guint par_w = 1, par_h = 1;

        if (stream->par_w > 0 && stream->par_h > 0) {
          par_w = stream->par_w;
          par_h = stream->par_h;
        }

        if (gst_video_multiview_guess_half_aspect (stream->multiview_mode,
                stream->width, stream->height, par_w, par_h)) {
          stream->multiview_flags |= GST_VIDEO_MULTIVIEW_FLAGS_HALF_ASPECT;
        }

        gst_caps_set_simple (stream->caps,
            "multiview-mode", G_TYPE_STRING,
            gst_video_multiview_mode_to_caps_string (stream->multiview_mode),
            "multiview-flags", GST_TYPE_VIDEO_MULTIVIEW_FLAGSET,
            stream->multiview_flags, GST_FLAG_SET_MASK_EXACT, NULL);
      }
    }
  }

  else if (stream->subtype == FOURCC_soun) {
    if (stream->caps) {
      stream->caps = gst_caps_make_writable (stream->caps);
      if (stream->rate > 0)
        gst_caps_set_simple (stream->caps,
            "rate", G_TYPE_INT, (int) stream->rate, NULL);
      if (stream->n_channels > 0)
        gst_caps_set_simple (stream->caps,
            "channels", G_TYPE_INT, stream->n_channels, NULL);
      if (stream->n_channels > 2) {
        /* FIXME: Need to parse the 'chan' atom to get channel layouts
         * correctly; this is just the minimum we can do - assume
         * we don't actually have any channel positions. */
        gst_caps_set_simple (stream->caps,
            "channel-mask", GST_TYPE_BITMASK, G_GUINT64_CONSTANT (0), NULL);
      }
    }
  }

  if (stream->pad) {
    GST_PAD_ELEMENT_PRIVATE (stream->pad) = stream;
    gst_pad_set_event_function (stream->pad, gst_qtdemux_handle_src_event);
    gst_pad_set_query_function (stream->pad, gst_qtdemux_handle_src_query);
    gst_pad_set_active (stream->pad, TRUE);

    gst_pad_use_fixed_caps (stream->pad);

    if (stream->protected) {
      if (!gst_qtdemux_configure_protected_caps (qtdemux, stream)) {
        GST_ERROR_OBJECT (qtdemux,
            "Failed to configure protected stream caps.");
        return FALSE;
      }
    }

    GST_DEBUG_OBJECT (qtdemux, "setting caps %" GST_PTR_FORMAT, stream->caps);
    if (stream->new_stream) {
      gchar *stream_id;
      GstEvent *event;
      GstStreamFlags stream_flags;

      event =
          gst_pad_get_sticky_event (qtdemux->sinkpad, GST_EVENT_STREAM_START,
          0);
      if (event) {
        if (gst_event_parse_group_id (event, &qtdemux->group_id))
          qtdemux->have_group_id = TRUE;
        else
          qtdemux->have_group_id = FALSE;
        gst_event_unref (event);
      } else if (!qtdemux->have_group_id) {
        qtdemux->have_group_id = TRUE;
        qtdemux->group_id = gst_util_group_id_next ();
      }

      stream->new_stream = FALSE;
      stream_id =
          gst_pad_create_stream_id_printf (stream->pad,
          GST_ELEMENT_CAST (qtdemux), "%03u", stream->track_id);
      event = gst_event_new_stream_start (stream_id);
      if (qtdemux->have_group_id)
        gst_event_set_group_id (event, qtdemux->group_id);
      stream_flags = GST_STREAM_FLAG_NONE;
      if (stream->disabled)
        stream_flags |= GST_STREAM_FLAG_UNSELECT;
      if (stream->sparse)
        stream_flags |= GST_STREAM_FLAG_SPARSE;
      gst_event_set_stream_flags (event, stream_flags);
      gst_pad_push_event (stream->pad, event);
      g_free (stream_id);
    }
    gst_pad_set_caps (stream->pad, stream->caps);
    stream->new_caps = FALSE;
  }
  return TRUE;
}

static gboolean
gst_qtdemux_add_stream (GstQTDemux * qtdemux,
    QtDemuxStream * stream, GstTagList * list)
{
  gboolean ret = TRUE;
  /* consistent default for push based mode */
  gst_segment_init (&stream->segment, GST_FORMAT_TIME);

  if (stream->subtype == FOURCC_vide) {
    gchar *name = g_strdup_printf ("video_%u", qtdemux->n_video_streams);

    stream->pad =
        gst_pad_new_from_static_template (&gst_qtdemux_videosrc_template, name);
    g_free (name);

    if (!gst_qtdemux_configure_stream (qtdemux, stream)) {
      gst_object_unref (stream->pad);
      stream->pad = NULL;
      ret = FALSE;
      goto done;
    }

    qtdemux->n_video_streams++;
  } else if (stream->subtype == FOURCC_soun) {
    gchar *name = g_strdup_printf ("audio_%u", qtdemux->n_audio_streams);

    stream->pad =
        gst_pad_new_from_static_template (&gst_qtdemux_audiosrc_template, name);
    g_free (name);
    if (!gst_qtdemux_configure_stream (qtdemux, stream)) {
      gst_object_unref (stream->pad);
      stream->pad = NULL;
      ret = FALSE;
      goto done;
    }
    qtdemux->n_audio_streams++;
  } else if (stream->subtype == FOURCC_strm) {
    GST_DEBUG_OBJECT (qtdemux, "stream type, not creating pad");
  } else if (stream->subtype == FOURCC_subp || stream->subtype == FOURCC_text
      || stream->subtype == FOURCC_sbtl || stream->subtype == FOURCC_subt) {
    gchar *name = g_strdup_printf ("subtitle_%u", qtdemux->n_sub_streams);

    stream->pad =
        gst_pad_new_from_static_template (&gst_qtdemux_subsrc_template, name);
    g_free (name);
    if (!gst_qtdemux_configure_stream (qtdemux, stream)) {
      gst_object_unref (stream->pad);
      stream->pad = NULL;
      ret = FALSE;
      goto done;
    }
    qtdemux->n_sub_streams++;
  } else if (stream->caps) {
    gchar *name = g_strdup_printf ("video_%u", qtdemux->n_video_streams);

    stream->pad =
        gst_pad_new_from_static_template (&gst_qtdemux_videosrc_template, name);
    g_free (name);
    if (!gst_qtdemux_configure_stream (qtdemux, stream)) {
      gst_object_unref (stream->pad);
      stream->pad = NULL;
      ret = FALSE;
      goto done;
    }
    qtdemux->n_video_streams++;
  } else {
    GST_DEBUG_OBJECT (qtdemux, "unknown stream type");
    goto done;
  }

  if (stream->pad) {
    GList *l;

    GST_DEBUG_OBJECT (qtdemux, "adding pad %s %p to qtdemux %p",
        GST_OBJECT_NAME (stream->pad), stream->pad, qtdemux);
    gst_element_add_pad (GST_ELEMENT_CAST (qtdemux), stream->pad);
    gst_flow_combiner_add_pad (qtdemux->flowcombiner, stream->pad);

    if (stream->pending_tags)
      gst_tag_list_unref (stream->pending_tags);
    stream->pending_tags = list;
    list = NULL;
    /* global tags go on each pad anyway */
    stream->send_global_tags = TRUE;
    /* send upstream GST_EVENT_PROTECTION events that were received before
       this source pad was created */
    for (l = qtdemux->protection_event_queue.head; l != NULL; l = l->next)
      gst_pad_push_event (stream->pad, gst_event_ref (l->data));
  }
done:
  if (list)
    gst_tag_list_unref (list);
  return ret;
}

/* find next atom with @fourcc starting at @offset */
static GstFlowReturn
qtdemux_find_atom (GstQTDemux * qtdemux, guint64 * offset,
    guint64 * length, guint32 fourcc)
{
  GstFlowReturn ret;
  guint32 lfourcc;
  GstBuffer *buf;

  GST_LOG_OBJECT (qtdemux, "finding fourcc %" GST_FOURCC_FORMAT " at offset %"
      G_GUINT64_FORMAT, GST_FOURCC_ARGS (fourcc), *offset);

  while (TRUE) {
    GstMapInfo map;

    buf = NULL;
    ret = gst_pad_pull_range (qtdemux->sinkpad, *offset, 16, &buf);
    if (G_UNLIKELY (ret != GST_FLOW_OK))
      goto locate_failed;
    if (G_UNLIKELY (gst_buffer_get_size (buf) != 16)) {
      /* likely EOF */
      ret = GST_FLOW_EOS;
      gst_buffer_unref (buf);
      goto locate_failed;
    }
    gst_buffer_map (buf, &map, GST_MAP_READ);
    extract_initial_length_and_fourcc (map.data, 16, length, &lfourcc);
    gst_buffer_unmap (buf, &map);
    gst_buffer_unref (buf);

    if (G_UNLIKELY (*length == 0)) {
      GST_DEBUG_OBJECT (qtdemux, "invalid length 0");
      ret = GST_FLOW_ERROR;
      goto locate_failed;
    }

    if (lfourcc == fourcc) {
      GST_DEBUG_OBJECT (qtdemux, "found fourcc at offset %" G_GUINT64_FORMAT,
          *offset);
      break;
    } else {
      GST_LOG_OBJECT (qtdemux,
          "skipping atom '%" GST_FOURCC_FORMAT "' at %" G_GUINT64_FORMAT,
          GST_FOURCC_ARGS (fourcc), *offset);
      *offset += *length;
    }
  }

  return GST_FLOW_OK;

locate_failed:
  {
    /* might simply have had last one */
    GST_DEBUG_OBJECT (qtdemux, "fourcc not found");
    return ret;
  }
}

/* should only do something in pull mode */
/* call with OBJECT lock */
static GstFlowReturn
qtdemux_add_fragmented_samples (GstQTDemux * qtdemux)
{
  guint64 length, offset;
  GstBuffer *buf = NULL;
  GstFlowReturn ret = GST_FLOW_OK;
  GstFlowReturn res = GST_FLOW_OK;
  GstMapInfo map;

  offset = qtdemux->moof_offset;
  GST_DEBUG_OBJECT (qtdemux, "next moof at offset %" G_GUINT64_FORMAT, offset);

  if (!offset) {
    GST_DEBUG_OBJECT (qtdemux, "no next moof");
    return GST_FLOW_EOS;
  }

  /* best not do pull etc with lock held */
  GST_OBJECT_UNLOCK (qtdemux);

  ret = qtdemux_find_atom (qtdemux, &offset, &length, FOURCC_moof);
  if (ret != GST_FLOW_OK)
    goto flow_failed;

  ret = gst_qtdemux_pull_atom (qtdemux, offset, length, &buf);
  if (G_UNLIKELY (ret != GST_FLOW_OK))
    goto flow_failed;
  gst_buffer_map (buf, &map, GST_MAP_READ);
  if (!qtdemux_parse_moof (qtdemux, map.data, map.size, offset, NULL)) {
    gst_buffer_unmap (buf, &map);
    gst_buffer_unref (buf);
    buf = NULL;
    goto parse_failed;
  }

  gst_buffer_unmap (buf, &map);
  gst_buffer_unref (buf);
  buf = NULL;

  offset += length;
  /* look for next moof */
  ret = qtdemux_find_atom (qtdemux, &offset, &length, FOURCC_moof);
  if (G_UNLIKELY (ret != GST_FLOW_OK))
    goto flow_failed;

exit:
  GST_OBJECT_LOCK (qtdemux);

  qtdemux->moof_offset = offset;

  return res;

parse_failed:
  {
    GST_DEBUG_OBJECT (qtdemux, "failed to parse moof");
    offset = 0;
    res = GST_FLOW_ERROR;
    goto exit;
  }
flow_failed:
  {
    /* maybe upstream temporarily flushing */
    if (ret != GST_FLOW_FLUSHING) {
      GST_DEBUG_OBJECT (qtdemux, "no next moof");
      offset = 0;
    } else {
      GST_DEBUG_OBJECT (qtdemux, "upstream WRONG_STATE");
      /* resume at current position next time */
    }
    res = ret;
    goto exit;
  }
}

/* initialise bytereaders for stbl sub-atoms */
static gboolean
qtdemux_stbl_init (GstQTDemux * qtdemux, QtDemuxStream * stream, GNode * stbl)
{
  stream->stbl_index = -1;      /* no samples have yet been parsed */
  stream->sample_index = -1;

  /* time-to-sample atom */
  if (!qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stts, &stream->stts))
    goto corrupt_file;

  /* copy atom data into a new buffer for later use */
  stream->stts.data = g_memdup (stream->stts.data, stream->stts.size);

  /* skip version + flags */
  if (!gst_byte_reader_skip (&stream->stts, 1 + 3) ||
      !gst_byte_reader_get_uint32_be (&stream->stts, &stream->n_sample_times))
    goto corrupt_file;
  GST_LOG_OBJECT (qtdemux, "%u timestamp blocks", stream->n_sample_times);

  /* make sure there's enough data */
  if (!qt_atom_parser_has_chunks (&stream->stts, stream->n_sample_times, 8)) {
    stream->n_sample_times = gst_byte_reader_get_remaining (&stream->stts) / 8;
    GST_LOG_OBJECT (qtdemux, "overriding to %u timestamp blocks",
        stream->n_sample_times);
    if (!stream->n_sample_times)
      goto corrupt_file;
  }

  /* sync sample atom */
  stream->stps_present = FALSE;
  if ((stream->stss_present =
          ! !qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stss,
              &stream->stss) ? TRUE : FALSE) == TRUE) {
    /* copy atom data into a new buffer for later use */
    stream->stss.data = g_memdup (stream->stss.data, stream->stss.size);

    /* skip version + flags */
    if (!gst_byte_reader_skip (&stream->stss, 1 + 3) ||
        !gst_byte_reader_get_uint32_be (&stream->stss, &stream->n_sample_syncs))
      goto corrupt_file;

    if (stream->n_sample_syncs) {
      /* make sure there's enough data */
      if (!qt_atom_parser_has_chunks (&stream->stss, stream->n_sample_syncs, 4))
        goto corrupt_file;
    }

    /* partial sync sample atom */
    if ((stream->stps_present =
            ! !qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stps,
                &stream->stps) ? TRUE : FALSE) == TRUE) {
      /* copy atom data into a new buffer for later use */
      stream->stps.data = g_memdup (stream->stps.data, stream->stps.size);

      /* skip version + flags */
      if (!gst_byte_reader_skip (&stream->stps, 1 + 3) ||
          !gst_byte_reader_get_uint32_be (&stream->stps,
              &stream->n_sample_partial_syncs))
        goto corrupt_file;

      /* if there are no entries, the stss table contains the real
       * sync samples */
      if (stream->n_sample_partial_syncs) {
        /* make sure there's enough data */
        if (!qt_atom_parser_has_chunks (&stream->stps,
                stream->n_sample_partial_syncs, 4))
          goto corrupt_file;
      }
    }
  }

  /* sample size */
  if (!qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stsz, &stream->stsz))
    goto no_samples;

  /* copy atom data into a new buffer for later use */
  stream->stsz.data = g_memdup (stream->stsz.data, stream->stsz.size);

  /* skip version + flags */
  if (!gst_byte_reader_skip (&stream->stsz, 1 + 3) ||
      !gst_byte_reader_get_uint32_be (&stream->stsz, &stream->sample_size))
    goto corrupt_file;

  if (!gst_byte_reader_get_uint32_be (&stream->stsz, &stream->n_samples))
    goto corrupt_file;

  if (!stream->n_samples)
    goto no_samples;

  /* sample-to-chunk atom */
  if (!qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stsc, &stream->stsc))
    goto corrupt_file;

  /* copy atom data into a new buffer for later use */
  stream->stsc.data = g_memdup (stream->stsc.data, stream->stsc.size);

  /* skip version + flags */
  if (!gst_byte_reader_skip (&stream->stsc, 1 + 3) ||
      !gst_byte_reader_get_uint32_be (&stream->stsc,
          &stream->n_samples_per_chunk))
    goto corrupt_file;

  GST_DEBUG_OBJECT (qtdemux, "n_samples_per_chunk %u",
      stream->n_samples_per_chunk);

  /* make sure there's enough data */
  if (!qt_atom_parser_has_chunks (&stream->stsc, stream->n_samples_per_chunk,
          12))
    goto corrupt_file;


  /* chunk offset */
  if (qtdemux_tree_get_child_by_type_full (stbl, FOURCC_stco, &stream->stco))
    stream->co_size = sizeof (guint32);
  else if (qtdemux_tree_get_child_by_type_full (stbl, FOURCC_co64,
          &stream->stco))
    stream->co_size = sizeof (guint64);
  else
    goto corrupt_file;

  /* copy atom data into a new buffer for later use */
  stream->stco.data = g_memdup (stream->stco.data, stream->stco.size);

  /* skip version + flags */
  if (!gst_byte_reader_skip (&stream->stco, 1 + 3))
    goto corrupt_file;

  /* chunks_are_samples == TRUE means treat chunks as samples */
  stream->chunks_are_samples = stream->sample_size && !stream->sampled;
  if (stream->chunks_are_samples) {
    /* treat chunks as samples */
    if (!gst_byte_reader_get_uint32_be (&stream->stco, &stream->n_samples))
      goto corrupt_file;
  } else {
    /* skip number of entries */
    if (!gst_byte_reader_skip (&stream->stco, 4))
      goto corrupt_file;

    /* make sure there are enough data in the stsz atom */
    if (!stream->sample_size) {
      /* different sizes for each sample */
      if (!qt_atom_parser_has_chunks (&stream->stsz, stream->n_samples, 4))
        goto corrupt_file;
    }
  }

  GST_DEBUG_OBJECT (qtdemux, "allocating n_samples %u * %u (%.2f MB)",
      stream->n_samples, (guint) sizeof (QtDemuxSample),
      stream->n_samples * sizeof (QtDemuxSample) / (1024.0 * 1024.0));

  if (stream->n_samples >=
      QTDEMUX_MAX_SAMPLE_INDEX_SIZE / sizeof (QtDemuxSample)) {
    GST_WARNING_OBJECT (qtdemux, "not allocating index of %d samples, would "
        "be larger than %uMB (broken file?)", stream->n_samples,
        QTDEMUX_MAX_SAMPLE_INDEX_SIZE >> 20);
    return FALSE;
  }

  g_assert (stream->samples == NULL);
  stream->samples = g_try_new0 (QtDemuxSample, stream->n_samples);
  if (!stream->samples) {
    GST_WARNING_OBJECT (qtdemux, "failed to allocate %d samples",
        stream->n_samples);
    return FALSE;
  }

  /* composition time-to-sample */
  if ((stream->ctts_present =
          ! !qtdemux_tree_get_child_by_type_full (stbl, FOURCC_ctts,
              &stream->ctts) ? TRUE : FALSE) == TRUE) {
    GstByteReader cslg = GST_BYTE_READER_INIT (NULL, 0);

    /* copy atom data into a new buffer for later use */
    stream->ctts.data = g_memdup (stream->ctts.data, stream->ctts.size);

    /* skip version + flags */
    if (!gst_byte_reader_skip (&stream->ctts, 1 + 3)
        || !gst_byte_reader_get_uint32_be (&stream->ctts,
            &stream->n_composition_times))
      goto corrupt_file;

    /* make sure there's enough data */
    if (!qt_atom_parser_has_chunks (&stream->ctts, stream->n_composition_times,
            4 + 4))
      goto corrupt_file;

    /* This is optional, if missing we iterate the ctts */
    if (qtdemux_tree_get_child_by_type_full (stbl, FOURCC_cslg, &cslg)) {
      if (!gst_byte_reader_skip (&cslg, 1 + 3)
          || !gst_byte_reader_get_uint32_be (&cslg, &stream->cslg_shift)) {
        g_free ((gpointer) cslg.data);
        goto corrupt_file;
      }
    } else {
      gint32 cslg_least = 0;
      guint num_entries, pos;
      gint i;

      pos = gst_byte_reader_get_pos (&stream->ctts);
      num_entries = stream->n_composition_times;

      stream->cslg_shift = 0;

      for (i = 0; i < num_entries; i++) {
        gint32 offset;

        gst_byte_reader_skip_unchecked (&stream->ctts, 4);
        offset = gst_byte_reader_get_int32_be_unchecked (&stream->ctts);

        if (offset < cslg_least)
          cslg_least = offset;
      }

      if (cslg_least < 0)
        stream->cslg_shift = ABS (cslg_least);
      else
        stream->cslg_shift = 0;

      /* reset the reader so we can generate sample table */
      gst_byte_reader_set_pos (&stream->ctts, pos);
    }
  } else {
    /* Ensure the cslg_shift value is consistent so we can use it
     * unconditionnally to produce TS and Segment */
    stream->cslg_shift = 0;
  }

  return TRUE;

corrupt_file:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")), (NULL));
    return FALSE;
  }
no_samples:
  {
    gst_qtdemux_stbl_free (stream);
    if (!qtdemux->fragmented) {
      /* not quite good */
      GST_WARNING_OBJECT (qtdemux, "stream has no samples");
      return FALSE;
    } else {
      /* may pick up samples elsewhere */
      return TRUE;
    }
  }
}

/* collect samples from the next sample to be parsed up to sample @n for @stream
 * by reading the info from @stbl
 *
 * This code can be executed from both the streaming thread and the seeking
 * thread so it takes the object lock to protect itself
 */
static gboolean
qtdemux_parse_samples (GstQTDemux * qtdemux, QtDemuxStream * stream, guint32 n)
{
  gint i, j, k;
  QtDemuxSample *samples, *first, *cur, *last;
  guint32 n_samples_per_chunk;
  guint32 n_samples;

  GST_LOG_OBJECT (qtdemux, "parsing samples for stream fourcc %"
      GST_FOURCC_FORMAT ", pad %s", GST_FOURCC_ARGS (stream->fourcc),
      stream->pad ? GST_PAD_NAME (stream->pad) : "(NULL)");

  n_samples = stream->n_samples;

  if (n >= n_samples)
    goto out_of_samples;

  GST_OBJECT_LOCK (qtdemux);
  if (n <= stream->stbl_index)
    goto already_parsed;

  GST_DEBUG_OBJECT (qtdemux, "parsing up to sample %u", n);

  if (!stream->stsz.data) {
    /* so we already parsed and passed all the moov samples;
     * onto fragmented ones */
    g_assert (qtdemux->fragmented);
    goto done;
  }

  /* pointer to the sample table */
  samples = stream->samples;

  /* starts from -1, moves to the next sample index to parse */
  stream->stbl_index++;

  /* keep track of the first and last sample to fill */
  first = &samples[stream->stbl_index];
  last = &samples[n];

  if (!stream->chunks_are_samples) {
    /* set the sample sizes */
    if (stream->sample_size == 0) {
      /* different sizes for each sample */
      for (cur = first; cur <= last; cur++) {
        cur->size = gst_byte_reader_get_uint32_be_unchecked (&stream->stsz);
        GST_LOG_OBJECT (qtdemux, "sample %d has size %u",
            (guint) (cur - samples), cur->size);
      }
    } else {
      /* samples have the same size */
      GST_LOG_OBJECT (qtdemux, "all samples have size %u", stream->sample_size);
      for (cur = first; cur <= last; cur++)
        cur->size = stream->sample_size;
    }
  }

  n_samples_per_chunk = stream->n_samples_per_chunk;
  cur = first;

  for (i = stream->stsc_index; i < n_samples_per_chunk; i++) {
    guint32 last_chunk;

    if (stream->stsc_chunk_index >= stream->last_chunk
        || stream->stsc_chunk_index < stream->first_chunk) {
      stream->first_chunk =
          gst_byte_reader_get_uint32_be_unchecked (&stream->stsc);
      stream->samples_per_chunk =
          gst_byte_reader_get_uint32_be_unchecked (&stream->stsc);
      gst_byte_reader_skip_unchecked (&stream->stsc, 4);

      /* chunk numbers are counted from 1 it seems */
      if (G_UNLIKELY (stream->first_chunk == 0))
        goto corrupt_file;

      --stream->first_chunk;

      /* the last chunk of each entry is calculated by taking the first chunk
       * of the next entry; except if there is no next, where we fake it with
       * INT_MAX */
      if (G_UNLIKELY (i == (stream->n_samples_per_chunk - 1))) {
        stream->last_chunk = G_MAXUINT32;
      } else {
        stream->last_chunk =
            gst_byte_reader_peek_uint32_be_unchecked (&stream->stsc);
        if (G_UNLIKELY (stream->last_chunk == 0))
          goto corrupt_file;

        --stream->last_chunk;
      }

      GST_LOG_OBJECT (qtdemux,
          "entry %d has first_chunk %d, last_chunk %d, samples_per_chunk %d", i,
          stream->first_chunk, stream->last_chunk, stream->samples_per_chunk);

      if (G_UNLIKELY (stream->last_chunk < stream->first_chunk))
        goto corrupt_file;

      if (stream->last_chunk != G_MAXUINT32) {
        if (!qt_atom_parser_peek_sub (&stream->stco,
                stream->first_chunk * stream->co_size,
                (stream->last_chunk - stream->first_chunk) * stream->co_size,
                &stream->co_chunk))
          goto corrupt_file;

      } else {
        stream->co_chunk = stream->stco;
        if (!gst_byte_reader_skip (&stream->co_chunk,
                stream->first_chunk * stream->co_size))
          goto corrupt_file;
      }

      stream->stsc_chunk_index = stream->first_chunk;
    }

    last_chunk = stream->last_chunk;

    if (stream->chunks_are_samples) {
      cur = &samples[stream->stsc_chunk_index];

      for (j = stream->stsc_chunk_index; j < last_chunk; j++) {
        if (j > n) {
          /* save state */
          stream->stsc_chunk_index = j;
          goto done;
        }

        cur->offset =
            qt_atom_parser_get_offset_unchecked (&stream->co_chunk,
            stream->co_size);

        GST_LOG_OBJECT (qtdemux, "Created entry %d with offset "
            "%" G_GUINT64_FORMAT, j, cur->offset);

        if (stream->samples_per_frame * stream->bytes_per_frame) {
          cur->size =
              (stream->samples_per_chunk * stream->n_channels) /
              stream->samples_per_frame * stream->bytes_per_frame;
        } else {
          cur->size = stream->samples_per_chunk;
        }

        GST_DEBUG_OBJECT (qtdemux,
            "keyframe sample %d: timestamp %" GST_TIME_FORMAT ", size %u",
            j, GST_TIME_ARGS (QTSTREAMTIME_TO_GSTTIME (stream,
                    stream->stco_sample_index)), cur->size);

        cur->timestamp = stream->stco_sample_index;
        cur->duration = stream->samples_per_chunk;
        cur->keyframe = TRUE;
        cur++;

        stream->stco_sample_index += stream->samples_per_chunk;
      }
      stream->stsc_chunk_index = j;
    } else {
      for (j = stream->stsc_chunk_index; j < last_chunk; j++) {
        guint32 samples_per_chunk;
        guint64 chunk_offset;

        if (!stream->stsc_sample_index
            && !qt_atom_parser_get_offset (&stream->co_chunk, stream->co_size,
                &stream->chunk_offset))
          goto corrupt_file;

        samples_per_chunk = stream->samples_per_chunk;
        chunk_offset = stream->chunk_offset;

        for (k = stream->stsc_sample_index; k < samples_per_chunk; k++) {
          GST_LOG_OBJECT (qtdemux, "creating entry %d with offset %"
              G_GUINT64_FORMAT " and size %d",
              (guint) (cur - samples), chunk_offset, cur->size);

          cur->offset = chunk_offset;
          chunk_offset += cur->size;
          cur++;

          if (G_UNLIKELY (cur > last)) {
            /* save state */
            stream->stsc_sample_index = k + 1;
            stream->chunk_offset = chunk_offset;
            stream->stsc_chunk_index = j;
            goto done2;
          }
        }
        stream->stsc_sample_index = 0;
      }
      stream->stsc_chunk_index = j;
    }
    stream->stsc_index++;
  }

  if (stream->chunks_are_samples)
    goto ctts;
done2:
  {
    guint32 n_sample_times;

    n_sample_times = stream->n_sample_times;
    cur = first;

    for (i = stream->stts_index; i < n_sample_times; i++) {
      guint32 stts_samples;
      gint32 stts_duration;
      gint64 stts_time;

      if (stream->stts_sample_index >= stream->stts_samples
          || !stream->stts_sample_index) {

        stream->stts_samples =
            gst_byte_reader_get_uint32_be_unchecked (&stream->stts);
        stream->stts_duration =
            gst_byte_reader_get_uint32_be_unchecked (&stream->stts);

        GST_LOG_OBJECT (qtdemux, "block %d, %u timestamps, duration %u",
            i, stream->stts_samples, stream->stts_duration);

        stream->stts_sample_index = 0;
      }

      stts_samples = stream->stts_samples;
      stts_duration = stream->stts_duration;
      stts_time = stream->stts_time;

      for (j = stream->stts_sample_index; j < stts_samples; j++) {
        GST_DEBUG_OBJECT (qtdemux,
            "sample %d: index %d, timestamp %" GST_TIME_FORMAT,
            (guint) (cur - samples), j,
            GST_TIME_ARGS (QTSTREAMTIME_TO_GSTTIME (stream, stts_time)));

        cur->timestamp = stts_time;
        cur->duration = stts_duration;

        /* avoid 32-bit wrap-around,
         * but still mind possible 'negative' duration */
        stts_time += (gint64) stts_duration;
        cur++;

        if (G_UNLIKELY (cur > last)) {
          /* save values */
          stream->stts_time = stts_time;
          stream->stts_sample_index = j + 1;
          goto done3;
        }
      }
      stream->stts_sample_index = 0;
      stream->stts_time = stts_time;
      stream->stts_index++;
    }
    /* fill up empty timestamps with the last timestamp, this can happen when
     * the last samples do not decode and so we don't have timestamps for them.
     * We however look at the last timestamp to estimate the track length so we
     * need something in here. */
    for (; cur < last; cur++) {
      GST_DEBUG_OBJECT (qtdemux,
          "fill sample %d: timestamp %" GST_TIME_FORMAT,
          (guint) (cur - samples),
          GST_TIME_ARGS (QTSTREAMTIME_TO_GSTTIME (stream, stream->stts_time)));
      cur->timestamp = stream->stts_time;
      cur->duration = -1;
    }
  }
done3:
  {
    /* sample sync, can be NULL */
    if (stream->stss_present == TRUE) {
      guint32 n_sample_syncs;

      n_sample_syncs = stream->n_sample_syncs;

      if (!n_sample_syncs) {
        GST_DEBUG_OBJECT (qtdemux, "all samples are keyframes");
        stream->all_keyframe = TRUE;
      } else {
        for (i = stream->stss_index; i < n_sample_syncs; i++) {
          /* note that the first sample is index 1, not 0 */
          guint32 index;

          index = gst_byte_reader_get_uint32_be_unchecked (&stream->stss);

          if (G_LIKELY (index > 0 && index <= n_samples)) {
            index -= 1;
            samples[index].keyframe = TRUE;
            GST_DEBUG_OBJECT (qtdemux, "samples at %u is keyframe", index);
            /* and exit if we have enough samples */
            if (G_UNLIKELY (index >= n)) {
              i++;
              break;
            }
          }
        }
        /* save state */
        stream->stss_index = i;
      }

      /* stps marks partial sync frames like open GOP I-Frames */
      if (stream->stps_present == TRUE) {
        guint32 n_sample_partial_syncs;

        n_sample_partial_syncs = stream->n_sample_partial_syncs;

        /* if there are no entries, the stss table contains the real
         * sync samples */
        if (n_sample_partial_syncs) {
          for (i = stream->stps_index; i < n_sample_partial_syncs; i++) {
            /* note that the first sample is index 1, not 0 */
            guint32 index;

            index = gst_byte_reader_get_uint32_be_unchecked (&stream->stps);

            if (G_LIKELY (index > 0 && index <= n_samples)) {
              index -= 1;
              samples[index].keyframe = TRUE;
              GST_DEBUG_OBJECT (qtdemux, "samples at %u is keyframe", index);
              /* and exit if we have enough samples */
              if (G_UNLIKELY (index >= n)) {
                i++;
                break;
              }
            }
          }
          /* save state */
          stream->stps_index = i;
        }
      }
    } else {
      /* no stss, all samples are keyframes */
      stream->all_keyframe = TRUE;
      GST_DEBUG_OBJECT (qtdemux, "setting all keyframes");
    }
  }

ctts:
  /* composition time to sample */
  if (stream->ctts_present == TRUE) {
    guint32 n_composition_times;
    guint32 ctts_count;
    gint32 ctts_soffset;

    /* Fill in the pts_offsets */
    cur = first;
    n_composition_times = stream->n_composition_times;

    for (i = stream->ctts_index; i < n_composition_times; i++) {
      if (stream->ctts_sample_index >= stream->ctts_count
          || !stream->ctts_sample_index) {
        stream->ctts_count =
            gst_byte_reader_get_uint32_be_unchecked (&stream->ctts);
        stream->ctts_soffset =
            gst_byte_reader_get_int32_be_unchecked (&stream->ctts);
        stream->ctts_sample_index = 0;
      }

      ctts_count = stream->ctts_count;
      ctts_soffset = stream->ctts_soffset;

      for (j = stream->ctts_sample_index; j < ctts_count; j++) {
        cur->pts_offset = ctts_soffset;
        cur++;

        if (G_UNLIKELY (cur > last)) {
          /* save state */
          stream->ctts_sample_index = j + 1;
          goto done;
        }
      }
      stream->ctts_sample_index = 0;
      stream->ctts_index++;
    }
  }
done:
  stream->stbl_index = n;
  /* if index has been completely parsed, free data that is no-longer needed */
  if (n + 1 == stream->n_samples) {
    gst_qtdemux_stbl_free (stream);
    GST_DEBUG_OBJECT (qtdemux, "parsed all available samples;");
    if (qtdemux->pullbased) {
      GST_DEBUG_OBJECT (qtdemux, "checking for more samples");
      while (n + 1 == stream->n_samples)
        if (qtdemux_add_fragmented_samples (qtdemux) != GST_FLOW_OK)
          break;
    }
  }
  GST_OBJECT_UNLOCK (qtdemux);

  return TRUE;

  /* SUCCESS */
already_parsed:
  {
    GST_LOG_OBJECT (qtdemux,
        "Tried to parse up to sample %u but this sample has already been parsed",
        n);
    /* if fragmented, there may be more */
    if (qtdemux->fragmented && n == stream->stbl_index)
      goto done;
    GST_OBJECT_UNLOCK (qtdemux);
    return TRUE;
  }
  /* ERRORS */
out_of_samples:
  {
    GST_LOG_OBJECT (qtdemux,
        "Tried to parse up to sample %u but there are only %u samples", n + 1,
        stream->n_samples);
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")), (NULL));
    return FALSE;
  }
corrupt_file:
  {
    GST_OBJECT_UNLOCK (qtdemux);
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")), (NULL));
    return FALSE;
  }
}

/* collect all segment info for @stream.
 */
static gboolean
qtdemux_parse_segments (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GNode * trak)
{
  GNode *edts;
  /* accept edts if they contain gaps at start and there is only
   * one media segment */
  gboolean allow_pushbased_edts = TRUE;
  gint media_segments_count = 0;

  /* parse and prepare segment info from the edit list */
  GST_DEBUG_OBJECT (qtdemux, "looking for edit list container");
  stream->n_segments = 0;
  stream->segments = NULL;
  if ((edts = qtdemux_tree_get_child_by_type (trak, FOURCC_edts))) {
    GNode *elst;
    gint n_segments;
    gint i, count, entry_size;
    guint64 time;
    GstClockTime stime;
    guint8 *buffer;
    guint8 version;

    GST_DEBUG_OBJECT (qtdemux, "looking for edit list");
    if (!(elst = qtdemux_tree_get_child_by_type (edts, FOURCC_elst)))
      goto done;

    buffer = elst->data;

    version = QT_UINT8 (buffer + 8);
    entry_size = (version == 1) ? 20 : 12;

    n_segments = QT_UINT32 (buffer + 12);

    /* we might allocate a bit too much, at least allocate 1 segment */
    stream->segments = g_new (QtDemuxSegment, MAX (n_segments, 1));

    /* segments always start from 0 */
    time = 0;
    stime = 0;
    count = 0;
    for (i = 0; i < n_segments; i++) {
      guint64 duration;
      guint64 media_time;
      gboolean time_valid = TRUE;
      QtDemuxSegment *segment;
      guint32 rate_int;
      GstClockTime media_start = GST_CLOCK_TIME_NONE;

      if (version == 1) {
        media_time = QT_UINT64 (buffer + 24 + i * entry_size);
        duration = QT_UINT64 (buffer + 16 + i * entry_size);
        if (media_time == G_MAXUINT64)
          time_valid = FALSE;
      } else {
        media_time = QT_UINT32 (buffer + 20 + i * entry_size);
        duration = QT_UINT32 (buffer + 16 + i * entry_size);
        if (media_time == G_MAXUINT32)
          time_valid = FALSE;
      }

      if (time_valid)
        media_start = QTSTREAMTIME_TO_GSTTIME (stream, media_time);

      segment = &stream->segments[count++];

      /* time and duration expressed in global timescale */
      segment->time = stime;
      /* add non scaled values so we don't cause roundoff errors */
      if (duration || media_start == GST_CLOCK_TIME_NONE) {
        time += duration;
        stime = QTTIME_TO_GSTTIME (qtdemux, time);
        segment->duration = stime - segment->time;
      } else {
        /* zero duration does not imply media_start == media_stop
         * but, only specify media_start.*/
        stime = QTTIME_TO_GSTTIME (qtdemux, qtdemux->duration);
        if (GST_CLOCK_TIME_IS_VALID (stime) && time_valid
            && stime >= media_start) {
          segment->duration = stime - media_start;
        } else {
          segment->duration = GST_CLOCK_TIME_NONE;
        }
      }
      segment->stop_time = stime;

      segment->trak_media_start = media_time;
      /* media_time expressed in stream timescale */
      if (time_valid) {
        segment->media_start = media_start;
        segment->media_stop = segment->media_start + segment->duration;
        media_segments_count++;
      } else {
        segment->media_start = GST_CLOCK_TIME_NONE;
        segment->media_stop = GST_CLOCK_TIME_NONE;
      }
      rate_int =
          QT_UINT32 (buffer + ((version == 1) ? 32 : 24) + i * entry_size);

      if (rate_int <= 1) {
        /* 0 is not allowed, some programs write 1 instead of the floating point
         * value */
        GST_WARNING_OBJECT (qtdemux, "found suspicious rate %" G_GUINT32_FORMAT,
            rate_int);
        segment->rate = 1;
      } else {
        segment->rate = rate_int / 65536.0;
      }

      GST_DEBUG_OBJECT (qtdemux, "created segment %d time %" GST_TIME_FORMAT
          ", duration %" GST_TIME_FORMAT ", media_start %" GST_TIME_FORMAT
          " (%" G_GUINT64_FORMAT ") , media_stop %" GST_TIME_FORMAT
          " stop_time %" GST_TIME_FORMAT " rate %g, (%d) timescale %u",
          i, GST_TIME_ARGS (segment->time),
          GST_TIME_ARGS (segment->duration),
          GST_TIME_ARGS (segment->media_start), media_time,
          GST_TIME_ARGS (segment->media_stop),
          GST_TIME_ARGS (segment->stop_time), segment->rate, rate_int,
          stream->timescale);
      if (segment->stop_time > qtdemux->segment.stop) {
        GST_WARNING_OBJECT (qtdemux, "Segment %d "
            " extends to %" GST_TIME_FORMAT
            " past the end of the file duration %" GST_TIME_FORMAT
            " it will be truncated", i, GST_TIME_ARGS (segment->stop_time),
            GST_TIME_ARGS (qtdemux->segment.stop));
        qtdemux->segment.stop = segment->stop_time;
      }
    }
    GST_DEBUG_OBJECT (qtdemux, "found %d segments", count);
    stream->n_segments = count;
    if (media_segments_count != 1)
      allow_pushbased_edts = FALSE;
  }
done:

  /* push based does not handle segments, so act accordingly here,
   * and warn if applicable */
  if (!qtdemux->pullbased && !allow_pushbased_edts) {
    GST_WARNING_OBJECT (qtdemux, "streaming; discarding edit list segments");
    /* remove and use default one below, we stream like it anyway */
    g_free (stream->segments);
    stream->segments = NULL;
    stream->n_segments = 0;
  }

  /* no segments, create one to play the complete trak */
  if (stream->n_segments == 0) {
    GstClockTime stream_duration =
        QTSTREAMTIME_TO_GSTTIME (stream, stream->duration);

    if (stream->segments == NULL)
      stream->segments = g_new (QtDemuxSegment, 1);

    /* represent unknown our way */
    if (stream_duration == 0)
      stream_duration = GST_CLOCK_TIME_NONE;

    stream->segments[0].time = 0;
    stream->segments[0].stop_time = stream_duration;
    stream->segments[0].duration = stream_duration;
    stream->segments[0].media_start = 0;
    stream->segments[0].media_stop = stream_duration;
    stream->segments[0].rate = 1.0;
    stream->segments[0].trak_media_start = 0;

    GST_DEBUG_OBJECT (qtdemux, "created dummy segment %" GST_TIME_FORMAT,
        GST_TIME_ARGS (stream_duration));
    stream->n_segments = 1;
    stream->dummy_segment = TRUE;
  }
  GST_DEBUG_OBJECT (qtdemux, "using %d segments", stream->n_segments);

  return TRUE;
}

/*
 * Parses the stsd atom of a svq3 trak looking for
 * the SMI and gama atoms.
 */
static void
qtdemux_parse_svq3_stsd_data (GstQTDemux * qtdemux, GNode * stsd,
    guint8 ** gamma, GstBuffer ** seqh)
{
  guint8 *_gamma = NULL;
  GstBuffer *_seqh = NULL;
  guint8 *stsd_data = stsd->data;
  guint32 length = QT_UINT32 (stsd_data);
  guint16 version;

  if (length < 32) {
    GST_WARNING_OBJECT (qtdemux, "stsd too short");
    goto end;
  }

  stsd_data += 32;
  length -= 32;
  version = QT_UINT16 (stsd_data);
  if (version == 3) {
    if (length >= 70) {
      length -= 70;
      stsd_data += 70;
      while (length > 8) {
        guint32 fourcc, size;
        guint8 *data;
        size = QT_UINT32 (stsd_data);
        fourcc = QT_FOURCC (stsd_data + 4);
        data = stsd_data + 8;

        if (size == 0) {
          GST_WARNING_OBJECT (qtdemux, "Atom of size 0 found, aborting "
              "svq3 atom parsing");
          goto end;
        }

        switch (fourcc) {
          case FOURCC_gama:{
            if (size == 12) {
              _gamma = data;
            } else {
              GST_WARNING_OBJECT (qtdemux, "Unexpected size %" G_GUINT32_FORMAT
                  " for gama atom, expected 12", size);
            }
            break;
          }
          case FOURCC_SMI_:{
            if (size > 16 && QT_FOURCC (data) == FOURCC_SEQH) {
              guint32 seqh_size;
              if (_seqh != NULL) {
                GST_WARNING_OBJECT (qtdemux, "Unexpected second SEQH SMI atom "
                    " found, ignoring");
              } else {
                seqh_size = QT_UINT32 (data + 4);
                if (seqh_size > 0) {
                  _seqh = gst_buffer_new_and_alloc (seqh_size);
                  gst_buffer_fill (_seqh, 0, data + 8, seqh_size);
                }
              }
            }
            break;
          }
          default:{
            GST_WARNING_OBJECT (qtdemux, "Unhandled atom %" GST_FOURCC_FORMAT
                " in SVQ3 entry in stsd atom", GST_FOURCC_ARGS (fourcc));
          }
        }

        if (size <= length) {
          length -= size;
          stsd_data += size;
        }
      }
    } else {
      GST_WARNING_OBJECT (qtdemux, "SVQ3 entry too short in stsd atom");
    }
  } else {
    GST_WARNING_OBJECT (qtdemux, "Unexpected version for SVQ3 entry %"
        G_GUINT16_FORMAT, version);
    goto end;
  }

end:
  if (gamma) {
    *gamma = _gamma;
  }
  if (seqh) {
    *seqh = _seqh;
  } else if (_seqh) {
    gst_buffer_unref (_seqh);
  }
}

static gchar *
qtdemux_get_rtsp_uri_from_hndl (GstQTDemux * qtdemux, GNode * minf)
{
  GNode *dinf;
  GstByteReader dref;
  gchar *uri = NULL;

  /*
   * Get 'dinf', to get its child 'dref', that might contain a 'hndl'
   * atom that might contain a 'data' atom with the rtsp uri.
   * This case was reported in bug #597497, some info about
   * the hndl atom can be found in TN1195
   */
  dinf = qtdemux_tree_get_child_by_type (minf, FOURCC_dinf);
  GST_DEBUG_OBJECT (qtdemux, "Trying to obtain rtsp URI for stream trak");

  if (dinf) {
    guint32 dref_num_entries = 0;
    if (qtdemux_tree_get_child_by_type_full (dinf, FOURCC_dref, &dref) &&
        gst_byte_reader_skip (&dref, 4) &&
        gst_byte_reader_get_uint32_be (&dref, &dref_num_entries)) {
      gint i;

      /* search dref entries for hndl atom */
      for (i = 0; i < dref_num_entries; i++) {
        guint32 size = 0, type;
        guint8 string_len = 0;
        if (gst_byte_reader_get_uint32_be (&dref, &size) &&
            qt_atom_parser_get_fourcc (&dref, &type)) {
          if (type == FOURCC_hndl) {
            GST_DEBUG_OBJECT (qtdemux, "Found hndl atom");

            /* skip data reference handle bytes and the
             * following pascal string and some extra 4
             * bytes I have no idea what are */
            if (!gst_byte_reader_skip (&dref, 4) ||
                !gst_byte_reader_get_uint8 (&dref, &string_len) ||
                !gst_byte_reader_skip (&dref, string_len + 4)) {
              GST_WARNING_OBJECT (qtdemux, "Failed to parse hndl atom");
              break;
            }

            /* iterate over the atoms to find the data atom */
            while (gst_byte_reader_get_remaining (&dref) >= 8) {
              guint32 atom_size;
              guint32 atom_type;

              if (gst_byte_reader_get_uint32_be (&dref, &atom_size) &&
                  qt_atom_parser_get_fourcc (&dref, &atom_type)) {
                if (atom_type == FOURCC_data) {
                  const guint8 *uri_aux = NULL;

                  /* found the data atom that might contain the rtsp uri */
                  GST_DEBUG_OBJECT (qtdemux, "Found data atom inside "
                      "hndl atom, interpreting it as an URI");
                  if (gst_byte_reader_peek_data (&dref, atom_size - 8,
                          &uri_aux)) {
                    if (g_strstr_len ((gchar *) uri_aux, 7, "rtsp://") != NULL)
                      uri = g_strndup ((gchar *) uri_aux, atom_size - 8);
                    else
                      GST_WARNING_OBJECT (qtdemux, "Data atom in hndl atom "
                          "didn't contain a rtsp address");
                  } else {
                    GST_WARNING_OBJECT (qtdemux, "Failed to get the data "
                        "atom contents");
                  }
                  break;
                }
                /* skipping to the next entry */
                if (!gst_byte_reader_skip (&dref, atom_size - 8))
                  break;
              } else {
                GST_WARNING_OBJECT (qtdemux, "Failed to parse hndl child "
                    "atom header");
                break;
              }
            }
            break;
          }
          /* skip to the next entry */
          if (!gst_byte_reader_skip (&dref, size - 8))
            break;
        } else {
          GST_WARNING_OBJECT (qtdemux, "Error parsing dref atom");
        }
      }
      GST_DEBUG_OBJECT (qtdemux, "Finished parsing dref atom");
    }
  }
  return uri;
}

#define AMR_NB_ALL_MODES        0x81ff
#define AMR_WB_ALL_MODES        0x83ff
static guint
qtdemux_parse_amr_bitrate (GstBuffer * buf, gboolean wb)
{
  /* The 'damr' atom is of the form:
   *
   * | vendor | decoder_ver | mode_set | mode_change_period | frames/sample |
   *    32 b       8 b          16 b           8 b                 8 b
   *
   * The highest set bit of the first 7 (AMR-NB) or 8 (AMR-WB) bits of mode_set
   * represents the highest mode used in the stream (and thus the maximum
   * bitrate), with a couple of special cases as seen below.
   */

  /* Map of frame type ID -> bitrate */
  static const guint nb_bitrates[] = {
    4750, 5150, 5900, 6700, 7400, 7950, 10200, 12200
  };
  static const guint wb_bitrates[] = {
    6600, 8850, 12650, 14250, 15850, 18250, 19850, 23050, 23850
  };
  GstMapInfo map;
  gsize max_mode;
  guint16 mode_set;

  gst_buffer_map (buf, &map, GST_MAP_READ);

  if (map.size != 0x11) {
    GST_DEBUG ("Atom should have size 0x11, not %" G_GSIZE_FORMAT, map.size);
    goto bad_data;
  }

  if (QT_FOURCC (map.data + 4) != FOURCC_damr) {
    GST_DEBUG ("Unknown atom in %" GST_FOURCC_FORMAT,
        GST_FOURCC_ARGS (QT_UINT32 (map.data + 4)));
    goto bad_data;
  }

  mode_set = QT_UINT16 (map.data + 13);

  if (mode_set == (wb ? AMR_WB_ALL_MODES : AMR_NB_ALL_MODES))
    max_mode = 7 + (wb ? 1 : 0);
  else
    /* AMR-NB modes fo from 0-7, and AMR-WB modes go from 0-8 */
    max_mode = g_bit_nth_msf ((gulong) mode_set & (wb ? 0x1ff : 0xff), -1);

  if (max_mode == -1) {
    GST_DEBUG ("No mode indication was found (mode set) = %x",
        (guint) mode_set);
    goto bad_data;
  }

  gst_buffer_unmap (buf, &map);
  return wb ? wb_bitrates[max_mode] : nb_bitrates[max_mode];

bad_data:
  gst_buffer_unmap (buf, &map);
  return 0;
}

static gboolean
qtdemux_parse_transformation_matrix (GstQTDemux * qtdemux,
    GstByteReader * reader, guint32 * matrix, const gchar * atom)
{
  /*
   * 9 values of 32 bits (fixed point 16.16, except 2 5 and 8 that are 2.30)
   * [0 1 2]
   * [3 4 5]
   * [6 7 8]
   */

  if (gst_byte_reader_get_remaining (reader) < 36)
    return FALSE;

  matrix[0] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[1] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[2] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[3] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[4] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[5] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[6] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[7] = gst_byte_reader_get_uint32_be_unchecked (reader);
  matrix[8] = gst_byte_reader_get_uint32_be_unchecked (reader);

  GST_DEBUG_OBJECT (qtdemux, "Transformation matrix from atom %s", atom);
  GST_DEBUG_OBJECT (qtdemux, "%u.%u %u.%u %u.%u", matrix[0] >> 16,
      matrix[0] & 0xFFFF, matrix[1] >> 16, matrix[1] & 0xFF, matrix[2] >> 16,
      matrix[2] & 0xFF);
  GST_DEBUG_OBJECT (qtdemux, "%u.%u %u.%u %u.%u", matrix[3] >> 16,
      matrix[3] & 0xFFFF, matrix[4] >> 16, matrix[4] & 0xFF, matrix[5] >> 16,
      matrix[5] & 0xFF);
  GST_DEBUG_OBJECT (qtdemux, "%u.%u %u.%u %u.%u", matrix[6] >> 16,
      matrix[6] & 0xFFFF, matrix[7] >> 16, matrix[7] & 0xFF, matrix[8] >> 16,
      matrix[8] & 0xFF);

  return TRUE;
}

static void
qtdemux_inspect_transformation_matrix (GstQTDemux * qtdemux,
    QtDemuxStream * stream, guint32 * matrix, GstTagList ** taglist)
{

/* [a b c]
 * [d e f]
 * [g h i]
 *
 * This macro will only compare value abdegh, it expects cfi to have already
 * been checked
 */
#define QTCHECK_MATRIX(m,a,b,d,e) ((m)[0] == (a << 16) && (m)[1] == (b << 16) && \
                                   (m)[3] == (d << 16) && (m)[4] == (e << 16))

  /* only handle the cases where the last column has standard values */
  if (matrix[2] == 0 && matrix[5] == 0 && matrix[8] == 1 << 30) {
    const gchar *rotation_tag = NULL;

    /* no rotation needed */
    if (QTCHECK_MATRIX (matrix, 1, 0, 0, 1)) {
      /* NOP */
    } else if (QTCHECK_MATRIX (matrix, 0, 1, G_MAXUINT16, 0)) {
      rotation_tag = "rotate-90";
    } else if (QTCHECK_MATRIX (matrix, G_MAXUINT16, 0, 0, G_MAXUINT16)) {
      rotation_tag = "rotate-180";
    } else if (QTCHECK_MATRIX (matrix, 0, G_MAXUINT16, 1, 0)) {
      rotation_tag = "rotate-270";
    } else {
      GST_FIXME_OBJECT (qtdemux, "Unhandled transformation matrix values");
    }

    GST_DEBUG_OBJECT (qtdemux, "Transformation matrix rotation %s",
        rotation_tag);
    if (rotation_tag != NULL) {
      if (*taglist == NULL)
        *taglist = gst_tag_list_new_empty ();
      gst_tag_list_add (*taglist, GST_TAG_MERGE_REPLACE,
          GST_TAG_IMAGE_ORIENTATION, rotation_tag, NULL);
    }
  } else {
    GST_FIXME_OBJECT (qtdemux, "Unhandled transformation matrix values");
  }
}

/* Parses the boxes defined in ISO/IEC 14496-12 that enable support for
 * protected streams (sinf, frma, schm and schi); if the protection scheme is
 * Common Encryption (cenc), the function will also parse the tenc box (defined
 * in ISO/IEC 23001-7). @container points to the node that contains these boxes
 * (typically an enc[v|a|t|s] sample entry); the function will set
 * @original_fmt to the fourcc of the original unencrypted stream format.
 * Returns TRUE if successful; FALSE otherwise. */
static gboolean
qtdemux_parse_protection_scheme_info (GstQTDemux * qtdemux,
    QtDemuxStream * stream, GNode * container, guint32 * original_fmt)
{
  GNode *sinf;
  GNode *frma;
  GNode *schm;
  GNode *schi;

  g_return_val_if_fail (qtdemux != NULL, FALSE);
  g_return_val_if_fail (stream != NULL, FALSE);
  g_return_val_if_fail (container != NULL, FALSE);
  g_return_val_if_fail (original_fmt != NULL, FALSE);

  sinf = qtdemux_tree_get_child_by_type (container, FOURCC_sinf);
  if (G_UNLIKELY (!sinf)) {
    if (stream->protection_scheme_type == FOURCC_cenc) {
      GST_ERROR_OBJECT (qtdemux, "sinf box does not contain schi box, which is "
          "mandatory for Common Encryption");
      return FALSE;
    }
    return TRUE;
  }

  frma = qtdemux_tree_get_child_by_type (sinf, FOURCC_frma);
  if (G_UNLIKELY (!frma)) {
    GST_ERROR_OBJECT (qtdemux, "sinf box does not contain mandatory frma box");
    return FALSE;
  }

  *original_fmt = QT_FOURCC ((const guint8 *) frma->data + 8);
  GST_DEBUG_OBJECT (qtdemux, "original stream format: '%" GST_FOURCC_FORMAT "'",
      GST_FOURCC_ARGS (*original_fmt));

  schm = qtdemux_tree_get_child_by_type (sinf, FOURCC_schm);
  if (!schm) {
    GST_DEBUG_OBJECT (qtdemux, "sinf box does not contain schm box");
    return FALSE;
  }
  stream->protection_scheme_type = QT_FOURCC ((const guint8 *) schm->data + 12);
  stream->protection_scheme_version =
      QT_UINT32 ((const guint8 *) schm->data + 16);

  GST_DEBUG_OBJECT (qtdemux,
      "protection_scheme_type: %" GST_FOURCC_FORMAT ", "
      "protection_scheme_version: %#010x",
      GST_FOURCC_ARGS (stream->protection_scheme_type),
      stream->protection_scheme_version);

  schi = qtdemux_tree_get_child_by_type (sinf, FOURCC_schi);
  if (!schi) {
    GST_DEBUG_OBJECT (qtdemux, "sinf box does not contain schi box");
    return FALSE;
  }
  if (stream->protection_scheme_type == FOURCC_cenc) {
    QtDemuxCencSampleSetInfo *info;
    GNode *tenc;
    const guint8 *tenc_data;
    guint32 isEncrypted;
    guint8 iv_size;
    const guint8 *default_kid;
    GstBuffer *kid_buf;

    if (G_UNLIKELY (!stream->protection_scheme_info))
      stream->protection_scheme_info =
          g_malloc0 (sizeof (QtDemuxCencSampleSetInfo));

    info = (QtDemuxCencSampleSetInfo *) stream->protection_scheme_info;

    tenc = qtdemux_tree_get_child_by_type (schi, FOURCC_tenc);
    if (!tenc) {
      GST_ERROR_OBJECT (qtdemux, "schi box does not contain tenc box, "
          "which is mandatory for Common Encryption");
      return FALSE;
    }
    tenc_data = (const guint8 *) tenc->data + 12;
    isEncrypted = QT_UINT24 (tenc_data);
    iv_size = QT_UINT8 (tenc_data + 3);
    default_kid = (tenc_data + 4);
    kid_buf = gst_buffer_new_allocate (NULL, 16, NULL);
    gst_buffer_fill (kid_buf, 0, default_kid, 16);
    if (info->default_properties)
      gst_structure_free (info->default_properties);
    info->default_properties =
        gst_structure_new ("application/x-cenc",
        "iv_size", G_TYPE_UINT, iv_size,
        "encrypted", G_TYPE_BOOLEAN, (isEncrypted == 1),
        "kid", GST_TYPE_BUFFER, kid_buf, NULL);
    GST_DEBUG_OBJECT (qtdemux, "default sample properties: "
        "is_encrypted=%u, iv_size=%u", isEncrypted, iv_size);
    gst_buffer_unref (kid_buf);
  }
  return TRUE;
}

/* parse the traks.
 * With each track we associate a new QtDemuxStream that contains all the info
 * about the trak.
 * traks that do not decode to something (like strm traks) will not have a pad.
 */
static gboolean
qtdemux_parse_trak (GstQTDemux * qtdemux, GNode * trak)
{
  GstByteReader tkhd;
  int offset;
  GNode *mdia;
  GNode *mdhd;
  GNode *hdlr;
  GNode *minf;
  GNode *stbl;
  GNode *stsd;
  GNode *mp4a;
  GNode *mp4v;
  GNode *wave;
  GNode *esds;
  GNode *pasp;
  GNode *tref;
  GNode *udta;
  GNode *svmi;

  QtDemuxStream *stream = NULL;
  gboolean new_stream = FALSE;
  gchar *codec = NULL;
  const guint8 *stsd_data;
  guint16 lang_code;            /* quicktime lang code or packed iso code */
  guint32 version;
  guint32 tkhd_flags = 0;
  guint8 tkhd_version = 0;
  guint32 fourcc;
  guint value_size, stsd_len, len;
  guint32 track_id;
  guint32 dummy;

  GST_DEBUG_OBJECT (qtdemux, "parse_trak");

  if (!qtdemux_tree_get_child_by_type_full (trak, FOURCC_tkhd, &tkhd)
      || !gst_byte_reader_get_uint8 (&tkhd, &tkhd_version)
      || !gst_byte_reader_get_uint24_be (&tkhd, &tkhd_flags))
    goto corrupt_file;

  /* pick between 64 or 32 bits */
  value_size = tkhd_version == 1 ? 8 : 4;
  if (!gst_byte_reader_skip (&tkhd, value_size * 2) ||
      !gst_byte_reader_get_uint32_be (&tkhd, &track_id))
    goto corrupt_file;

  if (!qtdemux->got_moov) {
    if (qtdemux_find_stream (qtdemux, track_id))
      goto existing_stream;
    stream = _create_stream ();
    stream->track_id = track_id;
    new_stream = TRUE;
  } else {
    stream = qtdemux_find_stream (qtdemux, track_id);
    if (!stream) {
      GST_WARNING_OBJECT (qtdemux, "Stream not found, going to ignore it");
      goto skip_track;
    }

    /* flush samples data from this track from previous moov */
    gst_qtdemux_stream_flush_segments_data (qtdemux, stream);
    gst_qtdemux_stream_flush_samples_data (qtdemux, stream);
  }
  /* need defaults for fragments */
  qtdemux_parse_trex (qtdemux, stream, &dummy, &dummy, &dummy);

  if (stream->pending_tags == NULL)
    stream->pending_tags = gst_tag_list_new_empty ();

  if ((tkhd_flags & 1) == 0)
    stream->disabled = TRUE;

  GST_LOG_OBJECT (qtdemux, "track[tkhd] version/flags/id: 0x%02x/%06x/%u",
      tkhd_version, tkhd_flags, stream->track_id);

  if (!(mdia = qtdemux_tree_get_child_by_type (trak, FOURCC_mdia)))
    goto corrupt_file;

  if (!(mdhd = qtdemux_tree_get_child_by_type (mdia, FOURCC_mdhd))) {
    /* be nice for some crooked mjp2 files that use mhdr for mdhd */
    if (qtdemux->major_brand != FOURCC_mjp2 ||
        !(mdhd = qtdemux_tree_get_child_by_type (mdia, FOURCC_mhdr)))
      goto corrupt_file;
  }

  len = QT_UINT32 ((guint8 *) mdhd->data);
  version = QT_UINT32 ((guint8 *) mdhd->data + 8);
  GST_LOG_OBJECT (qtdemux, "track version/flags: %08x", version);
  if (version == 0x01000000) {
    if (len < 38)
      goto corrupt_file;
    stream->timescale = QT_UINT32 ((guint8 *) mdhd->data + 28);
    stream->duration = QT_UINT64 ((guint8 *) mdhd->data + 32);
    lang_code = QT_UINT16 ((guint8 *) mdhd->data + 36);
  } else {
    if (len < 30)
      goto corrupt_file;
    stream->timescale = QT_UINT32 ((guint8 *) mdhd->data + 20);
    stream->duration = QT_UINT32 ((guint8 *) mdhd->data + 24);
    lang_code = QT_UINT16 ((guint8 *) mdhd->data + 28);
  }

  if (lang_code < 0x400) {
    qtdemux_lang_map_qt_code_to_iso (stream->lang_id, lang_code);
  } else if (lang_code == 0x7fff) {
    stream->lang_id[0] = 0;     /* unspecified */
  } else {
    stream->lang_id[0] = 0x60 + ((lang_code >> 10) & 0x1F);
    stream->lang_id[1] = 0x60 + ((lang_code >> 5) & 0x1F);
    stream->lang_id[2] = 0x60 + (lang_code & 0x1F);
    stream->lang_id[3] = 0;
  }

  GST_LOG_OBJECT (qtdemux, "track timescale: %" G_GUINT32_FORMAT,
      stream->timescale);
  GST_LOG_OBJECT (qtdemux, "track duration: %" G_GUINT64_FORMAT,
      stream->duration);
  GST_LOG_OBJECT (qtdemux, "track language code/id: 0x%04x/%s",
      lang_code, stream->lang_id);

  if (G_UNLIKELY (stream->timescale == 0 || qtdemux->timescale == 0))
    goto corrupt_file;

  if ((tref = qtdemux_tree_get_child_by_type (trak, FOURCC_tref))) {
    /* chapters track reference */
    GNode *chap = qtdemux_tree_get_child_by_type (tref, FOURCC_chap);
    if (chap) {
      gsize length = GST_READ_UINT32_BE (chap->data);
      if (qtdemux->chapters_track_id)
        GST_FIXME_OBJECT (qtdemux, "Multiple CHAP tracks");

      if (length >= 12) {
        qtdemux->chapters_track_id =
            GST_READ_UINT32_BE ((gint8 *) chap->data + 8);
      }
    }
  }

  /* fragmented files may have bogus duration in moov */
  if (!qtdemux->fragmented &&
      qtdemux->duration != G_MAXINT64 && stream->duration != G_MAXINT32) {
    guint64 tdur1, tdur2;

    /* don't overflow */
    tdur1 = stream->timescale * (guint64) qtdemux->duration;
    tdur2 = qtdemux->timescale * (guint64) stream->duration;

    /* HACK:
     * some of those trailers, nowadays, have prologue images that are
     * themselves vide tracks as well. I haven't really found a way to
     * identify those yet, except for just looking at their duration. */
    if (tdur1 != 0 && (tdur2 * 10 / tdur1) < 2) {
      GST_WARNING_OBJECT (qtdemux,
          "Track shorter than 20%% (%" G_GUINT64_FORMAT "/%" G_GUINT32_FORMAT
          " vs. %" G_GUINT64_FORMAT "/%" G_GUINT32_FORMAT ") of the stream "
          "found, assuming preview image or something; skipping track",
          stream->duration, stream->timescale, qtdemux->duration,
          qtdemux->timescale);
      if (new_stream)
        gst_qtdemux_stream_free (qtdemux, stream);
      return TRUE;
    }
  }

  if (!(hdlr = qtdemux_tree_get_child_by_type (mdia, FOURCC_hdlr)))
    goto corrupt_file;

  GST_LOG_OBJECT (qtdemux, "track type: %" GST_FOURCC_FORMAT,
      GST_FOURCC_ARGS (QT_FOURCC ((guint8 *) hdlr->data + 12)));

  len = QT_UINT32 ((guint8 *) hdlr->data);
  if (len >= 20)
    stream->subtype = QT_FOURCC ((guint8 *) hdlr->data + 16);
  GST_LOG_OBJECT (qtdemux, "track subtype: %" GST_FOURCC_FORMAT,
      GST_FOURCC_ARGS (stream->subtype));

  if (!(minf = qtdemux_tree_get_child_by_type (mdia, FOURCC_minf)))
    goto corrupt_file;

  if (!(stbl = qtdemux_tree_get_child_by_type (minf, FOURCC_stbl)))
    goto corrupt_file;

  /*parse svmi header if existing */
  svmi = qtdemux_tree_get_child_by_type (stbl, FOURCC_svmi);
  if (svmi) {
    len = QT_UINT32 ((guint8 *) svmi->data);
    version = QT_UINT32 ((guint8 *) svmi->data + 8);
    if (!version) {
      GstVideoMultiviewMode mode = GST_VIDEO_MULTIVIEW_MODE_NONE;
      GstVideoMultiviewFlags flags = GST_VIDEO_MULTIVIEW_FLAGS_NONE;
      guint8 frame_type, frame_layout;

      /* MPEG-A stereo video */
      if (qtdemux->major_brand == FOURCC_ss02)
        flags |= GST_VIDEO_MULTIVIEW_FLAGS_MIXED_MONO;

      frame_type = QT_UINT8 ((guint8 *) svmi->data + 12);
      frame_layout = QT_UINT8 ((guint8 *) svmi->data + 13) & 0x01;
      switch (frame_type) {
        case 0:
          mode = GST_VIDEO_MULTIVIEW_MODE_SIDE_BY_SIDE;
          break;
        case 1:
          mode = GST_VIDEO_MULTIVIEW_MODE_ROW_INTERLEAVED;
          break;
        case 2:
          mode = GST_VIDEO_MULTIVIEW_MODE_FRAME_BY_FRAME;
          break;
        case 3:
          /* mode 3 is primary/secondary view sequence, ie
           * left/right views in separate tracks. See section 7.2
           * of ISO/IEC 23000-11:2009 */
          GST_FIXME_OBJECT (qtdemux,
              "Implement stereo video in separate streams");
      }

      if ((frame_layout & 0x1) == 0)
        flags |= GST_VIDEO_MULTIVIEW_FLAGS_RIGHT_VIEW_FIRST;

      GST_LOG_OBJECT (qtdemux,
          "StereoVideo: composition type: %u, is_left_first: %u",
          frame_type, frame_layout);
      stream->multiview_mode = mode;
      stream->multiview_flags = flags;
    }
  }

  /* parse stsd */
  if (!(stsd = qtdemux_tree_get_child_by_type (stbl, FOURCC_stsd)))
    goto corrupt_file;
  stsd_data = (const guint8 *) stsd->data;

  /* stsd should at least have one entry */
  stsd_len = QT_UINT32 (stsd_data);
  if (stsd_len < 24) {
    /* .. but skip stream with empty stsd produced by some Vivotek cameras */
    if (stream->subtype == FOURCC_vivo) {
      if (new_stream)
        gst_qtdemux_stream_free (qtdemux, stream);
      return TRUE;
    } else {
      goto corrupt_file;
    }
  }

  GST_LOG_OBJECT (qtdemux, "stsd len:           %d", stsd_len);

  /* and that entry should fit within stsd */
  len = QT_UINT32 (stsd_data + 16);
  if (len > stsd_len + 16)
    goto corrupt_file;

  stream->fourcc = fourcc = QT_FOURCC (stsd_data + 16 + 4);
  GST_LOG_OBJECT (qtdemux, "stsd type:          %" GST_FOURCC_FORMAT,
      GST_FOURCC_ARGS (stream->fourcc));
  GST_LOG_OBJECT (qtdemux, "stsd type len:      %d", len);

  if ((fourcc == FOURCC_drms) || (fourcc == FOURCC_drmi))
    goto error_encrypted;

  if (fourcc == FOURCC_encv || fourcc == FOURCC_enca) {
    GNode *enc = qtdemux_tree_get_child_by_type (stsd, fourcc);
    stream->protected = TRUE;
    if (!qtdemux_parse_protection_scheme_info (qtdemux, stream, enc, &fourcc))
      GST_ERROR_OBJECT (qtdemux, "Failed to parse protection scheme info");
  }

  if (stream->subtype == FOURCC_vide) {
    guint32 w = 0, h = 0;
    gboolean gray;
    gint depth, palette_size, palette_count;
    guint32 matrix[9];
    guint32 *palette_data = NULL;

    stream->sampled = TRUE;

    /* version 1 uses some 64-bit ints */
    if (!gst_byte_reader_skip (&tkhd, 20 + value_size))
      goto corrupt_file;

    if (!qtdemux_parse_transformation_matrix (qtdemux, &tkhd, matrix, "tkhd"))
      goto corrupt_file;

    if (!gst_byte_reader_get_uint32_be (&tkhd, &w)
        || !gst_byte_reader_get_uint32_be (&tkhd, &h))
      goto corrupt_file;

    stream->display_width = w >> 16;
    stream->display_height = h >> 16;

    qtdemux_inspect_transformation_matrix (qtdemux, stream, matrix,
        &stream->pending_tags);

    offset = 16;
    if (len < 86)
      goto corrupt_file;

    stream->width = QT_UINT16 (stsd_data + offset + 32);
    stream->height = QT_UINT16 (stsd_data + offset + 34);
    stream->fps_n = 0;          /* this is filled in later */
    stream->fps_d = 0;          /* this is filled in later */
    stream->bits_per_sample = QT_UINT16 (stsd_data + offset + 82);
    stream->color_table_id = QT_UINT16 (stsd_data + offset + 84);

    /* if color_table_id is 0, ctab atom must follow; however some files
     * produced by TMPEGEnc have color_table_id = 0 and no ctab atom, so
     * if color table is not present we'll correct the value */
    if (stream->color_table_id == 0 &&
        (len < 90 || QT_FOURCC (stsd_data + offset + 86) != FOURCC_ctab)) {
      stream->color_table_id = -1;
    }

    GST_LOG_OBJECT (qtdemux, "width %d, height %d, bps %d, color table id %d",
        stream->width, stream->height, stream->bits_per_sample,
        stream->color_table_id);

    depth = stream->bits_per_sample;

    /* more than 32 bits means grayscale */
    gray = (depth > 32);
    /* low 32 bits specify the depth  */
    depth &= 0x1F;

    /* different number of palette entries is determined by depth. */
    palette_count = 0;
    if ((depth == 1) || (depth == 2) || (depth == 4) || (depth == 8))
      palette_count = (1 << depth);
    palette_size = palette_count * 4;

    if (stream->color_table_id) {
      switch (palette_count) {
        case 0:
          break;
        case 2:
          palette_data = g_memdup (ff_qt_default_palette_2, palette_size);
          break;
        case 4:
          palette_data = g_memdup (ff_qt_default_palette_4, palette_size);
          break;
        case 16:
          if (gray)
            palette_data = g_memdup (ff_qt_grayscale_palette_16, palette_size);
          else
            palette_data = g_memdup (ff_qt_default_palette_16, palette_size);
          break;
        case 256:
          if (gray)
            palette_data = g_memdup (ff_qt_grayscale_palette_256, palette_size);
          else
            palette_data = g_memdup (ff_qt_default_palette_256, palette_size);
          break;
        default:
          GST_ELEMENT_WARNING (qtdemux, STREAM, DEMUX,
              (_("The video in this file might not play correctly.")),
              ("unsupported palette depth %d", depth));
          break;
      }
    } else {
      gint i, j, start, end;

      if (len < 94)
        goto corrupt_file;

      /* read table */
      start = QT_UINT32 (stsd_data + offset + 86);
      palette_count = QT_UINT16 (stsd_data + offset + 90);
      end = QT_UINT16 (stsd_data + offset + 92);

      GST_LOG_OBJECT (qtdemux, "start %d, end %d, palette_count %d",
          start, end, palette_count);

      if (end > 255)
        end = 255;
      if (start > end)
        start = end;

      if (len < 94 + (end - start) * 8)
        goto corrupt_file;

      /* palette is always the same size */
      palette_data = g_malloc0 (256 * 4);
      palette_size = 256 * 4;

      for (j = 0, i = start; i <= end; j++, i++) {
        guint32 a, r, g, b;

        a = QT_UINT16 (stsd_data + offset + 94 + (j * 8));
        r = QT_UINT16 (stsd_data + offset + 96 + (j * 8));
        g = QT_UINT16 (stsd_data + offset + 98 + (j * 8));
        b = QT_UINT16 (stsd_data + offset + 100 + (j * 8));

        palette_data[i] = ((a & 0xff00) << 16) | ((r & 0xff00) << 8) |
            (g & 0xff00) | (b >> 8);
      }
    }

    if (stream->caps)
      gst_caps_unref (stream->caps);

    stream->caps =
        qtdemux_video_caps (qtdemux, stream, fourcc, stsd_data, &codec);
    if (G_UNLIKELY (!stream->caps)) {
      g_free (palette_data);
      goto unknown_stream;
    }

    if (codec) {
      gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
          GST_TAG_VIDEO_CODEC, codec, NULL);
      g_free (codec);
      codec = NULL;
    }


    if (palette_data) {
      GstStructure *s;

      if (stream->rgb8_palette)
        gst_memory_unref (stream->rgb8_palette);
      stream->rgb8_palette = gst_memory_new_wrapped (GST_MEMORY_FLAG_READONLY,
          palette_data, palette_size, 0, palette_size, palette_data, g_free);

      s = gst_caps_get_structure (stream->caps, 0);

      /* non-raw video has a palette_data property. raw video has the palette as
       * an extra plane that we append to the output buffers before we push
       * them*/
      if (!gst_structure_has_name (s, "video/x-raw")) {
        GstBuffer *palette;

        palette = gst_buffer_new ();
        gst_buffer_append_memory (palette, stream->rgb8_palette);
        stream->rgb8_palette = NULL;

        gst_caps_set_simple (stream->caps, "palette_data",
            GST_TYPE_BUFFER, palette, NULL);
        gst_buffer_unref (palette);
      }
    } else if (palette_count != 0) {
      GST_ELEMENT_WARNING (qtdemux, STREAM, NOT_IMPLEMENTED,
          (NULL), ("Unsupported palette depth %d", depth));
    }

    GST_LOG_OBJECT (qtdemux, "frame count:   %u",
        QT_UINT16 (stsd_data + offset + 48));

    esds = NULL;
    pasp = NULL;
    /* pick 'the' stsd child */
    if (!stream->protected)
      mp4v = qtdemux_tree_get_child_by_type (stsd, fourcc);
    else
      mp4v = qtdemux_tree_get_child_by_type (stsd, FOURCC_encv);

    if (mp4v) {
      esds = qtdemux_tree_get_child_by_type (mp4v, FOURCC_esds);
      pasp = qtdemux_tree_get_child_by_type (mp4v, FOURCC_pasp);
    }

    if (pasp) {
      const guint8 *pasp_data = (const guint8 *) pasp->data;

      stream->par_w = QT_UINT32 (pasp_data + 8);
      stream->par_h = QT_UINT32 (pasp_data + 12);
    } else {
      stream->par_w = 0;
      stream->par_h = 0;
    }

    if (esds) {
      gst_qtdemux_handle_esds (qtdemux, stream, esds, stream->pending_tags);
    } else {
      switch (fourcc) {
        case FOURCC_H264:
        case FOURCC_avc1:
        case FOURCC_avc3:
        {
          gint len = QT_UINT32 (stsd_data) - 0x66;
          const guint8 *avc_data = stsd_data + 0x66;

          /* find avcC */
          while (len >= 0x8) {
            gint size;

            if (QT_UINT32 (avc_data) <= len)
              size = QT_UINT32 (avc_data) - 0x8;
            else
              size = len - 0x8;

            if (size < 1)
              /* No real data, so break out */
              break;

            switch (QT_FOURCC (avc_data + 0x4)) {
              case FOURCC_avcC:
              {
                /* parse, if found */
                GstBuffer *buf;

                GST_DEBUG_OBJECT (qtdemux, "found avcC codec_data in stsd");

                /* First 4 bytes are the length of the atom, the next 4 bytes
                 * are the fourcc, the next 1 byte is the version, and the
                 * subsequent bytes are profile_tier_level structure like data. */
                gst_codec_utils_h264_caps_set_level_and_profile (stream->caps,
                    avc_data + 8 + 1, size - 1);
                buf = gst_buffer_new_and_alloc (size);
                gst_buffer_fill (buf, 0, avc_data + 0x8, size);
                gst_caps_set_simple (stream->caps,
                    "codec_data", GST_TYPE_BUFFER, buf, NULL);
                gst_buffer_unref (buf);

                break;
              }
              case FOURCC_strf:
              {
                GstBuffer *buf;

                GST_DEBUG_OBJECT (qtdemux, "found strf codec_data in stsd");

                /* First 4 bytes are the length of the atom, the next 4 bytes
                 * are the fourcc, next 40 bytes are BITMAPINFOHEADER,
                 * next 1 byte is the version, and the
                 * subsequent bytes are sequence parameter set like data. */

                size -= 40;     /* we'll be skipping BITMAPINFOHEADER */
                if (size > 1) {
                  gst_codec_utils_h264_caps_set_level_and_profile (stream->caps,
                      avc_data + 8 + 40 + 1, size - 1);

                  buf = gst_buffer_new_and_alloc (size);
                  gst_buffer_fill (buf, 0, avc_data + 8 + 40, size);
                  gst_caps_set_simple (stream->caps,
                      "codec_data", GST_TYPE_BUFFER, buf, NULL);
                  gst_buffer_unref (buf);
                }
                break;
              }
              case FOURCC_btrt:
              {
                guint avg_bitrate, max_bitrate;

                /* bufferSizeDB, maxBitrate and avgBitrate - 4 bytes each */
                if (size < 12)
                  break;

                max_bitrate = QT_UINT32 (avc_data + 0xc);
                avg_bitrate = QT_UINT32 (avc_data + 0x10);

                if (!max_bitrate && !avg_bitrate)
                  break;

                /* Some muxers seem to swap the average and maximum bitrates
                 * (I'm looking at you, YouTube), so we swap for sanity. */
                if (max_bitrate > 0 && max_bitrate < avg_bitrate) {
                  guint temp = avg_bitrate;

                  avg_bitrate = max_bitrate;
                  max_bitrate = temp;
                }

                if (max_bitrate > 0 && max_bitrate < G_MAXUINT32) {
                  gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
                      GST_TAG_MAXIMUM_BITRATE, max_bitrate, NULL);
                }
                if (avg_bitrate > 0 && avg_bitrate < G_MAXUINT32) {
                  gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
                      GST_TAG_BITRATE, avg_bitrate, NULL);
                }

                break;
              }

              default:
                break;
            }

            len -= size + 8;
            avc_data += size + 8;
          }

          break;
        }
        case FOURCC_H265:
        case FOURCC_hvc1:
        case FOURCC_hev1:
        {
          gint len = QT_UINT32 (stsd_data) - 0x66;
          const guint8 *hevc_data = stsd_data + 0x66;

          /* find hevc */
          while (len >= 0x8) {
            gint size;

            if (QT_UINT32 (hevc_data) <= len)
              size = QT_UINT32 (hevc_data) - 0x8;
            else
              size = len - 0x8;

            if (size < 1)
              /* No real data, so break out */
              break;

            switch (QT_FOURCC (hevc_data + 0x4)) {
              case FOURCC_hvcC:
              {
                /* parse, if found */
                GstBuffer *buf;

                GST_DEBUG_OBJECT (qtdemux, "found avcC codec_data in stsd");

                /* First 4 bytes are the length of the atom, the next 4 bytes
                 * are the fourcc, the next 1 byte is the version, and the
                 * subsequent bytes are sequence parameter set like data. */
                gst_codec_utils_h265_caps_set_level_tier_and_profile
                    (stream->caps, hevc_data + 8 + 1, size - 1);

                buf = gst_buffer_new_and_alloc (size);
                gst_buffer_fill (buf, 0, hevc_data + 0x8, size);
                gst_caps_set_simple (stream->caps,
                    "codec_data", GST_TYPE_BUFFER, buf, NULL);
                gst_buffer_unref (buf);
                break;
              }
              default:
                break;
            }
            len -= size + 8;
            hevc_data += size + 8;
          }
          break;
        }
        case FOURCC_mp4v:
        case FOURCC_MP4V:
        case FOURCC_fmp4:
        case FOURCC_FMP4:
        {
          GNode *glbl;

          GST_DEBUG_OBJECT (qtdemux, "found %" GST_FOURCC_FORMAT,
              GST_FOURCC_ARGS (fourcc));

          /* codec data might be in glbl extension atom */
          glbl = mp4v ?
              qtdemux_tree_get_child_by_type (mp4v, FOURCC_glbl) : NULL;
          if (glbl) {
            guint8 *data;
            GstBuffer *buf;
            gint len;

            GST_DEBUG_OBJECT (qtdemux, "found glbl data in stsd");
            data = glbl->data;
            len = QT_UINT32 (data);
            if (len > 0x8) {
              len -= 0x8;
              buf = gst_buffer_new_and_alloc (len);
              gst_buffer_fill (buf, 0, data + 8, len);
              gst_caps_set_simple (stream->caps,
                  "codec_data", GST_TYPE_BUFFER, buf, NULL);
              gst_buffer_unref (buf);
            }
          }
          break;
        }
        case FOURCC_mjp2:
        {
          /* see annex I of the jpeg2000 spec */
          GNode *jp2h, *ihdr, *colr, *mjp2, *field, *prefix, *cmap, *cdef;
          const guint8 *data;
          const gchar *colorspace = NULL;
          gint ncomp = 0;
          guint32 ncomp_map = 0;
          gint32 *comp_map = NULL;
          guint32 nchan_def = 0;
          gint32 *chan_def = NULL;

          GST_DEBUG_OBJECT (qtdemux, "found mjp2");
          /* some required atoms */
          mjp2 = qtdemux_tree_get_child_by_type (stsd, FOURCC_mjp2);
          if (!mjp2)
            break;
          jp2h = qtdemux_tree_get_child_by_type (mjp2, FOURCC_jp2h);
          if (!jp2h)
            break;

          /* number of components; redundant with info in codestream, but useful
             to a muxer */
          ihdr = qtdemux_tree_get_child_by_type (jp2h, FOURCC_ihdr);
          if (!ihdr || QT_UINT32 (ihdr->data) != 22)
            break;
          ncomp = QT_UINT16 (((guint8 *) ihdr->data) + 16);

          colr = qtdemux_tree_get_child_by_type (jp2h, FOURCC_colr);
          if (!colr)
            break;
          GST_DEBUG_OBJECT (qtdemux, "found colr");
          /* extract colour space info */
          if (QT_UINT8 ((guint8 *) colr->data + 8) == 1) {
            switch (QT_UINT32 ((guint8 *) colr->data + 11)) {
              case 16:
                colorspace = "sRGB";
                break;
              case 17:
                colorspace = "GRAY";
                break;
              case 18:
                colorspace = "sYUV";
                break;
              default:
                colorspace = NULL;
                break;
            }
          }
          if (!colorspace)
            /* colr is required, and only values 16, 17, and 18 are specified,
               so error if we have no colorspace */
            break;

          /* extract component mapping */
          cmap = qtdemux_tree_get_child_by_type (jp2h, FOURCC_cmap);
          if (cmap) {
            guint32 cmap_len = 0;
            int i;
            cmap_len = QT_UINT32 (cmap->data);
            if (cmap_len >= 8) {
              /* normal box, subtract off header */
              cmap_len -= 8;
              /* cmap: { u16 cmp; u8 mtyp; u8 pcol; }* */
              if (cmap_len % 4 == 0) {
                ncomp_map = (cmap_len / 4);
                comp_map = g_new0 (gint32, ncomp_map);
                for (i = 0; i < ncomp_map; i++) {
                  guint16 cmp;
                  guint8 mtyp, pcol;
                  cmp = QT_UINT16 (((guint8 *) cmap->data) + 8 + i * 4);
                  mtyp = QT_UINT8 (((guint8 *) cmap->data) + 8 + i * 4 + 2);
                  pcol = QT_UINT8 (((guint8 *) cmap->data) + 8 + i * 4 + 3);
                  comp_map[i] = (mtyp << 24) | (pcol << 16) | cmp;
                }
              }
            }
          }
          /* extract channel definitions */
          cdef = qtdemux_tree_get_child_by_type (jp2h, FOURCC_cdef);
          if (cdef) {
            guint32 cdef_len = 0;
            int i;
            cdef_len = QT_UINT32 (cdef->data);
            if (cdef_len >= 10) {
              /* normal box, subtract off header and len */
              cdef_len -= 10;
              /* cdef: u16 n; { u16 cn; u16 typ; u16 asoc; }* */
              if (cdef_len % 6 == 0) {
                nchan_def = (cdef_len / 6);
                chan_def = g_new0 (gint32, nchan_def);
                for (i = 0; i < nchan_def; i++)
                  chan_def[i] = -1;
                for (i = 0; i < nchan_def; i++) {
                  guint16 cn, typ, asoc;
                  cn = QT_UINT16 (((guint8 *) cdef->data) + 10 + i * 6);
                  typ = QT_UINT16 (((guint8 *) cdef->data) + 10 + i * 6 + 2);
                  asoc = QT_UINT16 (((guint8 *) cdef->data) + 10 + i * 6 + 4);
                  if (cn < nchan_def) {
                    switch (typ) {
                      case 0:
                        chan_def[cn] = asoc;
                        break;
                      case 1:
                        chan_def[cn] = 0;       /* alpha */
                        break;
                      default:
                        chan_def[cn] = -typ;
                    }
                  }
                }
              }
            }
          }

          gst_caps_set_simple (stream->caps,
              "num-components", G_TYPE_INT, ncomp, NULL);
          gst_caps_set_simple (stream->caps,
              "colorspace", G_TYPE_STRING, colorspace, NULL);

          if (comp_map) {
            GValue arr = { 0, };
            GValue elt = { 0, };
            int i;
            g_value_init (&arr, GST_TYPE_ARRAY);
            g_value_init (&elt, G_TYPE_INT);
            for (i = 0; i < ncomp_map; i++) {
              g_value_set_int (&elt, comp_map[i]);
              gst_value_array_append_value (&arr, &elt);
            }
            gst_structure_set_value (gst_caps_get_structure (stream->caps, 0),
                "component-map", &arr);
            g_value_unset (&elt);
            g_value_unset (&arr);
            g_free (comp_map);
          }

          if (chan_def) {
            GValue arr = { 0, };
            GValue elt = { 0, };
            int i;
            g_value_init (&arr, GST_TYPE_ARRAY);
            g_value_init (&elt, G_TYPE_INT);
            for (i = 0; i < nchan_def; i++) {
              g_value_set_int (&elt, chan_def[i]);
              gst_value_array_append_value (&arr, &elt);
            }
            gst_structure_set_value (gst_caps_get_structure (stream->caps, 0),
                "channel-definitions", &arr);
            g_value_unset (&elt);
            g_value_unset (&arr);
            g_free (chan_def);
          }

          /* some optional atoms */
          field = qtdemux_tree_get_child_by_type (mjp2, FOURCC_fiel);
          prefix = qtdemux_tree_get_child_by_type (mjp2, FOURCC_jp2x);

          /* indicate possible fields in caps */
          if (field) {
            data = (guint8 *) field->data + 8;
            if (*data != 1)
              gst_caps_set_simple (stream->caps, "fields", G_TYPE_INT,
                  (gint) * data, NULL);
          }
          /* add codec_data if provided */
          if (prefix) {
            GstBuffer *buf;
            gint len;

            GST_DEBUG_OBJECT (qtdemux, "found prefix data in stsd");
            data = prefix->data;
            len = QT_UINT32 (data);
            if (len > 0x8) {
              len -= 0x8;
              buf = gst_buffer_new_and_alloc (len);
              gst_buffer_fill (buf, 0, data + 8, len);
              gst_caps_set_simple (stream->caps,
                  "codec_data", GST_TYPE_BUFFER, buf, NULL);
              gst_buffer_unref (buf);
            }
          }
          break;
        }
        case FOURCC_SVQ3:
        case FOURCC_VP31:
        {
          GstBuffer *buf;
          GstBuffer *seqh = NULL;
          guint8 *gamma_data = NULL;
          gint len = QT_UINT32 (stsd_data);

          qtdemux_parse_svq3_stsd_data (qtdemux, stsd, &gamma_data, &seqh);
          if (gamma_data) {
            gst_caps_set_simple (stream->caps, "applied-gamma", G_TYPE_DOUBLE,
                QT_FP32 (gamma_data), NULL);
          }
          if (seqh) {
            /* sorry for the bad name, but we don't know what this is, other
             * than its own fourcc */
            gst_caps_set_simple (stream->caps, "seqh", GST_TYPE_BUFFER, seqh,
                NULL);
          }

          GST_DEBUG_OBJECT (qtdemux, "found codec_data in stsd");
          buf = gst_buffer_new_and_alloc (len);
          gst_buffer_fill (buf, 0, stsd_data, len);
          gst_caps_set_simple (stream->caps,
              "codec_data", GST_TYPE_BUFFER, buf, NULL);
          gst_buffer_unref (buf);
          break;
        }
        case FOURCC_rle_:
        case FOURCC_WRLE:
        {
          gst_caps_set_simple (stream->caps,
              "depth", G_TYPE_INT, QT_UINT16 (stsd_data + offset + 82), NULL);
          break;
        }
        case FOURCC_XiTh:
        {
          GNode *xith, *xdxt;

          GST_DEBUG_OBJECT (qtdemux, "found XiTh");
          xith = qtdemux_tree_get_child_by_type (stsd, FOURCC_XiTh);
          if (!xith)
            break;

          xdxt = qtdemux_tree_get_child_by_type (xith, FOURCC_XdxT);
          if (!xdxt)
            break;

          GST_DEBUG_OBJECT (qtdemux, "found XdxT node");
          /* collect the headers and store them in a stream list so that we can
           * send them out first */
          qtdemux_parse_theora_extension (qtdemux, stream, xdxt);
          break;
        }
        case FOURCC_ovc1:
        {
          GNode *ovc1;
          guint8 *ovc1_data;
          guint ovc1_len;
          GstBuffer *buf;

          GST_DEBUG_OBJECT (qtdemux, "parse ovc1 header");
          ovc1 = qtdemux_tree_get_child_by_type (stsd, FOURCC_ovc1);
          if (!ovc1)
            break;
          ovc1_data = ovc1->data;
          ovc1_len = QT_UINT32 (ovc1_data);
          if (ovc1_len <= 198) {
            GST_WARNING_OBJECT (qtdemux, "Too small ovc1 header, skipping");
            break;
          }
          buf = gst_buffer_new_and_alloc (ovc1_len - 198);
          gst_buffer_fill (buf, 0, ovc1_data + 198, ovc1_len - 198);
          gst_caps_set_simple (stream->caps,
              "codec_data", GST_TYPE_BUFFER, buf, NULL);
          gst_buffer_unref (buf);
          break;
        }
        case FOURCC_vc_1:
        {
          gint len = QT_UINT32 (stsd_data) - 0x66;
          const guint8 *vc1_data = stsd_data + 0x66;

          /* find dvc1 */
          while (len >= 8) {
            gint size;

            if (QT_UINT32 (vc1_data) <= len)
              size = QT_UINT32 (vc1_data) - 8;
            else
              size = len - 8;

            if (size < 1)
              /* No real data, so break out */
              break;

            switch (QT_FOURCC (vc1_data + 0x4)) {
              case GST_MAKE_FOURCC ('d', 'v', 'c', '1'):
              {
                GstBuffer *buf;

                GST_DEBUG_OBJECT (qtdemux, "found dvc1 codec_data in stsd");
                buf = gst_buffer_new_and_alloc (size);
                gst_buffer_fill (buf, 0, vc1_data + 8, size);
                gst_caps_set_simple (stream->caps,
                    "codec_data", GST_TYPE_BUFFER, buf, NULL);
                gst_buffer_unref (buf);
                break;
              }
              default:
                break;
            }
            len -= size + 8;
            vc1_data += size + 8;
          }
          break;
        }
        default:
          break;
      }
    }

    GST_INFO_OBJECT (qtdemux,
        "type %" GST_FOURCC_FORMAT " caps %" GST_PTR_FORMAT,
        GST_FOURCC_ARGS (fourcc), stream->caps);

  } else if (stream->subtype == FOURCC_soun) {
    int version, samplesize;
    guint16 compression_id;
    gboolean amrwb = FALSE;

    offset = 32;
    /* sample description entry (16) + sound sample description v0 (20) */
    if (len < 36)
      goto corrupt_file;

    version = QT_UINT32 (stsd_data + offset);
    stream->n_channels = QT_UINT16 (stsd_data + offset + 8);
    samplesize = QT_UINT16 (stsd_data + offset + 10);
    compression_id = QT_UINT16 (stsd_data + offset + 12);
    stream->rate = QT_FP32 (stsd_data + offset + 16);

    GST_LOG_OBJECT (qtdemux, "version/rev:      %08x", version);
    GST_LOG_OBJECT (qtdemux, "vendor:           %08x",
        QT_UINT32 (stsd_data + offset + 4));
    GST_LOG_OBJECT (qtdemux, "n_channels:       %d", stream->n_channels);
    GST_LOG_OBJECT (qtdemux, "sample_size:      %d", samplesize);
    GST_LOG_OBJECT (qtdemux, "compression_id:   %d", compression_id);
    GST_LOG_OBJECT (qtdemux, "packet size:      %d",
        QT_UINT16 (stsd_data + offset + 14));
    GST_LOG_OBJECT (qtdemux, "sample rate:      %g", stream->rate);

    if (compression_id == 0xfffe)
      stream->sampled = TRUE;

    /* first assume uncompressed audio */
    stream->bytes_per_sample = samplesize / 8;
    stream->samples_per_frame = stream->n_channels;
    stream->bytes_per_frame = stream->n_channels * stream->bytes_per_sample;
    stream->samples_per_packet = stream->samples_per_frame;
    stream->bytes_per_packet = stream->bytes_per_sample;

    offset = 52;
    switch (fourcc) {
        /* Yes, these have to be hard-coded */
      case FOURCC_MAC6:
      {
        stream->samples_per_packet = 6;
        stream->bytes_per_packet = 1;
        stream->bytes_per_frame = 1 * stream->n_channels;
        stream->bytes_per_sample = 1;
        stream->samples_per_frame = 6 * stream->n_channels;
        break;
      }
      case FOURCC_MAC3:
      {
        stream->samples_per_packet = 3;
        stream->bytes_per_packet = 1;
        stream->bytes_per_frame = 1 * stream->n_channels;
        stream->bytes_per_sample = 1;
        stream->samples_per_frame = 3 * stream->n_channels;
        break;
      }
      case FOURCC_ima4:
      {
        stream->samples_per_packet = 64;
        stream->bytes_per_packet = 34;
        stream->bytes_per_frame = 34 * stream->n_channels;
        stream->bytes_per_sample = 2;
        stream->samples_per_frame = 64 * stream->n_channels;
        break;
      }
      case FOURCC_ulaw:
      case FOURCC_alaw:
      {
        stream->samples_per_packet = 1;
        stream->bytes_per_packet = 1;
        stream->bytes_per_frame = 1 * stream->n_channels;
        stream->bytes_per_sample = 1;
        stream->samples_per_frame = 1 * stream->n_channels;
        break;
      }
      case FOURCC_agsm:
      {
        stream->samples_per_packet = 160;
        stream->bytes_per_packet = 33;
        stream->bytes_per_frame = 33 * stream->n_channels;
        stream->bytes_per_sample = 2;
        stream->samples_per_frame = 160 * stream->n_channels;
        break;
      }
      default:
        break;
    }

    if (version == 0x00010000) {
      /* sample description entry (16) + sound sample description v1 (20+16) */
      if (len < 52)
        goto corrupt_file;

      switch (fourcc) {
        case FOURCC_twos:
        case FOURCC_sowt:
        case FOURCC_raw_:
          break;
        default:
        {
          /* only parse extra decoding config for non-pcm audio */
          stream->samples_per_packet = QT_UINT32 (stsd_data + offset);
          stream->bytes_per_packet = QT_UINT32 (stsd_data + offset + 4);
          stream->bytes_per_frame = QT_UINT32 (stsd_data + offset + 8);
          stream->bytes_per_sample = QT_UINT32 (stsd_data + offset + 12);

          GST_LOG_OBJECT (qtdemux, "samples/packet:   %d",
              stream->samples_per_packet);
          GST_LOG_OBJECT (qtdemux, "bytes/packet:     %d",
              stream->bytes_per_packet);
          GST_LOG_OBJECT (qtdemux, "bytes/frame:      %d",
              stream->bytes_per_frame);
          GST_LOG_OBJECT (qtdemux, "bytes/sample:     %d",
              stream->bytes_per_sample);

          if (!stream->sampled && stream->bytes_per_packet) {
            stream->samples_per_frame = (stream->bytes_per_frame /
                stream->bytes_per_packet) * stream->samples_per_packet;
            GST_LOG_OBJECT (qtdemux, "samples/frame:    %d",
                stream->samples_per_frame);
          }
          break;
        }
      }
    } else if (version == 0x00020000) {
      union
      {
        gdouble fp;
        guint64 val;
      } qtfp;

      /* sample description entry (16) + sound sample description v2 (56) */
      if (len < 72)
        goto corrupt_file;

      qtfp.val = QT_UINT64 (stsd_data + offset + 4);
      stream->rate = qtfp.fp;
      stream->n_channels = QT_UINT32 (stsd_data + offset + 12);

      GST_LOG_OBJECT (qtdemux, "Sound sample description Version 2");
      GST_LOG_OBJECT (qtdemux, "sample rate:        %g", stream->rate);
      GST_LOG_OBJECT (qtdemux, "n_channels:         %d", stream->n_channels);
      GST_LOG_OBJECT (qtdemux, "bits/channel:       %d",
          QT_UINT32 (stsd_data + offset + 20));
      GST_LOG_OBJECT (qtdemux, "format flags:       %X",
          QT_UINT32 (stsd_data + offset + 24));
      GST_LOG_OBJECT (qtdemux, "bytes/packet:       %d",
          QT_UINT32 (stsd_data + offset + 28));
      GST_LOG_OBJECT (qtdemux, "LPCM frames/packet: %d",
          QT_UINT32 (stsd_data + offset + 32));
    } else if (version != 0x00000) {
      GST_WARNING_OBJECT (qtdemux, "unknown audio STSD version %08x", version);
    }

    if (stream->caps)
      gst_caps_unref (stream->caps);

    stream->caps = qtdemux_audio_caps (qtdemux, stream, fourcc,
        stsd_data + 32, len - 16, &codec);

    switch (fourcc) {
      case FOURCC_in24:
      {
        GNode *enda;
        GNode *in24;

        in24 = qtdemux_tree_get_child_by_type (stsd, FOURCC_in24);

        enda = qtdemux_tree_get_child_by_type (in24, FOURCC_enda);
        if (!enda) {
          wave = qtdemux_tree_get_child_by_type (in24, FOURCC_wave);
          if (wave)
            enda = qtdemux_tree_get_child_by_type (wave, FOURCC_enda);
        }
        if (enda) {
          int enda_value = QT_UINT16 ((guint8 *) enda->data + 8);
          gst_caps_set_simple (stream->caps,
              "format", G_TYPE_STRING, (enda_value) ? "S24LE" : "S24BE", NULL);
        }
        break;
      }
      case FOURCC_owma:
      {
        GNode *owma;
        const guint8 *owma_data;
        const gchar *codec_name = NULL;
        guint owma_len;
        GstBuffer *buf;
        gint version = 1;
        /* from http://msdn.microsoft.com/en-us/library/dd757720(VS.85).aspx */
        /* FIXME this should also be gst_riff_strf_auds,
         * but the latter one is actually missing bits-per-sample :( */
        typedef struct
        {
          gint16 wFormatTag;
          gint16 nChannels;
          gint32 nSamplesPerSec;
          gint32 nAvgBytesPerSec;
          gint16 nBlockAlign;
          gint16 wBitsPerSample;
          gint16 cbSize;
        } WAVEFORMATEX;
        WAVEFORMATEX *wfex;

        GST_DEBUG_OBJECT (qtdemux, "parse owma");
        owma = qtdemux_tree_get_child_by_type (stsd, FOURCC_owma);
        if (!owma)
          break;
        owma_data = owma->data;
        owma_len = QT_UINT32 (owma_data);
        if (owma_len <= 54) {
          GST_WARNING_OBJECT (qtdemux, "Too small owma header, skipping");
          break;
        }
        wfex = (WAVEFORMATEX *) (owma_data + 36);
        buf = gst_buffer_new_and_alloc (owma_len - 54);
        gst_buffer_fill (buf, 0, owma_data + 54, owma_len - 54);
        if (wfex->wFormatTag == 0x0161) {
          codec_name = "Windows Media Audio";
          version = 2;
        } else if (wfex->wFormatTag == 0x0162) {
          codec_name = "Windows Media Audio 9 Pro";
          version = 3;
        } else if (wfex->wFormatTag == 0x0163) {
          codec_name = "Windows Media Audio 9 Lossless";
          /* is that correct? gstffmpegcodecmap.c is missing it, but
           * fluendo codec seems to support it */
          version = 4;
        }

        gst_caps_set_simple (stream->caps,
            "codec_data", GST_TYPE_BUFFER, buf,
            "wmaversion", G_TYPE_INT, version,
            "block_align", G_TYPE_INT, GST_READ_UINT16_LE (&wfex->nBlockAlign),
            "bitrate", G_TYPE_INT, GST_READ_UINT32_LE (&wfex->nAvgBytesPerSec),
            "width", G_TYPE_INT, GST_READ_UINT16_LE (&wfex->wBitsPerSample),
            "depth", G_TYPE_INT, GST_READ_UINT16_LE (&wfex->wBitsPerSample),
            NULL);
        gst_buffer_unref (buf);

        if (codec_name) {
          g_free (codec);
          codec = g_strdup (codec_name);
        }
        break;
      }
      case FOURCC_wma_:
      {
        gint len = QT_UINT32 (stsd_data) - offset;
        const guint8 *wfex_data = stsd_data + offset;
        const gchar *codec_name = NULL;
        gint version = 1;
        /* from http://msdn.microsoft.com/en-us/library/dd757720(VS.85).aspx */
        /* FIXME this should also be gst_riff_strf_auds,
         * but the latter one is actually missing bits-per-sample :( */
        typedef struct
        {
          gint16 wFormatTag;
          gint16 nChannels;
          gint32 nSamplesPerSec;
          gint32 nAvgBytesPerSec;
          gint16 nBlockAlign;
          gint16 wBitsPerSample;
          gint16 cbSize;
        } WAVEFORMATEX;
        WAVEFORMATEX wfex;

        /* FIXME: unify with similar wavformatex parsing code above */
        GST_DEBUG_OBJECT (qtdemux, "parse wma, looking for wfex");

        /* find wfex */
        while (len >= 8) {
          gint size;

          if (QT_UINT32 (wfex_data) <= len)
            size = QT_UINT32 (wfex_data) - 8;
          else
            size = len - 8;

          if (size < 1)
            /* No real data, so break out */
            break;

          switch (QT_FOURCC (wfex_data + 4)) {
            case GST_MAKE_FOURCC ('w', 'f', 'e', 'x'):
            {
              GST_DEBUG_OBJECT (qtdemux, "found wfex in stsd");

              if (size < 8 + 18)
                break;

              wfex.wFormatTag = GST_READ_UINT16_LE (wfex_data + 8 + 0);
              wfex.nChannels = GST_READ_UINT16_LE (wfex_data + 8 + 2);
              wfex.nSamplesPerSec = GST_READ_UINT32_LE (wfex_data + 8 + 4);
              wfex.nAvgBytesPerSec = GST_READ_UINT32_LE (wfex_data + 8 + 8);
              wfex.nBlockAlign = GST_READ_UINT16_LE (wfex_data + 8 + 12);
              wfex.wBitsPerSample = GST_READ_UINT16_LE (wfex_data + 8 + 14);
              wfex.cbSize = GST_READ_UINT16_LE (wfex_data + 8 + 16);

              GST_LOG_OBJECT (qtdemux, "Found wfex box in stsd:");
              GST_LOG_OBJECT (qtdemux, "FormatTag = 0x%04x, Channels = %u, "
                  "SamplesPerSec = %u, AvgBytesPerSec = %u, BlockAlign = %u, "
                  "BitsPerSample = %u, Size = %u", wfex.wFormatTag,
                  wfex.nChannels, wfex.nSamplesPerSec, wfex.nAvgBytesPerSec,
                  wfex.nBlockAlign, wfex.wBitsPerSample, wfex.cbSize);

              if (wfex.wFormatTag == 0x0161) {
                codec_name = "Windows Media Audio";
                version = 2;
              } else if (wfex.wFormatTag == 0x0162) {
                codec_name = "Windows Media Audio 9 Pro";
                version = 3;
              } else if (wfex.wFormatTag == 0x0163) {
                codec_name = "Windows Media Audio 9 Lossless";
                /* is that correct? gstffmpegcodecmap.c is missing it, but
                 * fluendo codec seems to support it */
                version = 4;
              }

              gst_caps_set_simple (stream->caps,
                  "wmaversion", G_TYPE_INT, version,
                  "block_align", G_TYPE_INT, wfex.nBlockAlign,
                  "bitrate", G_TYPE_INT, wfex.nAvgBytesPerSec,
                  "width", G_TYPE_INT, wfex.wBitsPerSample,
                  "depth", G_TYPE_INT, wfex.wBitsPerSample, NULL);

              if (size > wfex.cbSize) {
                GstBuffer *buf;

                buf = gst_buffer_new_and_alloc (size - wfex.cbSize);
                gst_buffer_fill (buf, 0, wfex_data + 8 + wfex.cbSize,
                    size - wfex.cbSize);
                gst_caps_set_simple (stream->caps,
                    "codec_data", GST_TYPE_BUFFER, buf, NULL);
                gst_buffer_unref (buf);
              } else {
                GST_WARNING_OBJECT (qtdemux, "no codec data");
              }

              if (codec_name) {
                g_free (codec);
                codec = g_strdup (codec_name);
              }
              break;
            }
            default:
              break;
          }
          len -= size + 8;
          wfex_data += size + 8;
        }
        break;
      }
      case FOURCC_opus:
      {
        GNode *opus;
        const guint8 *opus_data;
        guint8 *channel_mapping = NULL;
        guint32 rate;
        guint8 channels;
        guint8 channel_mapping_family;
        guint8 stream_count;
        guint8 coupled_count;
        guint8 i;

        opus = qtdemux_tree_get_child_by_type (stsd, FOURCC_opus);
        opus_data = opus->data;

        channels = GST_READ_UINT8 (opus_data + 45);
        rate = GST_READ_UINT32_LE (opus_data + 48);
        channel_mapping_family = GST_READ_UINT8 (opus_data + 54);
        stream_count = GST_READ_UINT8 (opus_data + 55);
        coupled_count = GST_READ_UINT8 (opus_data + 56);

        if (channels > 0) {
          channel_mapping = g_malloc (channels * sizeof (guint8));
          for (i = 0; i < channels; i++)
            channel_mapping[i] = GST_READ_UINT8 (opus_data + i + 57);
        }

        stream->caps = gst_codec_utils_opus_create_caps (rate, channels,
            channel_mapping_family, stream_count, coupled_count,
            channel_mapping);
        break;
      }
      default:
        break;
    }

    if (codec) {
      GstStructure *s;
      gint bitrate = 0;

      gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
          GST_TAG_AUDIO_CODEC, codec, NULL);
      g_free (codec);
      codec = NULL;

      /* some bitrate info may have ended up in caps */
      s = gst_caps_get_structure (stream->caps, 0);
      gst_structure_get_int (s, "bitrate", &bitrate);
      if (bitrate > 0)
        gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
            GST_TAG_BITRATE, bitrate, NULL);
    }

    if (stream->protected && fourcc == FOURCC_mp4a)
      mp4a = qtdemux_tree_get_child_by_type (stsd, FOURCC_enca);
    else
      mp4a = qtdemux_tree_get_child_by_type (stsd, FOURCC_mp4a);

    wave = NULL;
    esds = NULL;
    if (mp4a) {
      wave = qtdemux_tree_get_child_by_type (mp4a, FOURCC_wave);
      if (wave)
        esds = qtdemux_tree_get_child_by_type (wave, FOURCC_esds);
      if (!esds)
        esds = qtdemux_tree_get_child_by_type (mp4a, FOURCC_esds);
    }


    /* If the fourcc's bottom 16 bits gives 'sm', then the top
       16 bits is a byte-swapped wave-style codec identifier,
       and we can find a WAVE header internally to a 'wave' atom here.
       This can more clearly be thought of as 'ms' as the top 16 bits, and a
       codec id as the bottom 16 bits - but byte-swapped to store in QT (which
       is big-endian).
     */
    if ((fourcc & 0xffff) == (('s' << 8) | 'm')) {
      if (len < offset + 20) {
        GST_WARNING_OBJECT (qtdemux, "No wave atom in MS-style audio");
      } else {
        guint32 datalen = QT_UINT32 (stsd_data + offset + 16);
        const guint8 *data = stsd_data + offset + 16;
        GNode *wavenode;
        GNode *waveheadernode;

        wavenode = g_node_new ((guint8 *) data);
        if (qtdemux_parse_node (qtdemux, wavenode, data, datalen)) {
          const guint8 *waveheader;
          guint32 headerlen;

          waveheadernode = qtdemux_tree_get_child_by_type (wavenode, fourcc);
          if (waveheadernode) {
            waveheader = (const guint8 *) waveheadernode->data;
            headerlen = QT_UINT32 (waveheader);

            if (headerlen > 8) {
              gst_riff_strf_auds *header = NULL;
              GstBuffer *headerbuf;
              GstBuffer *extra;

              waveheader += 8;
              headerlen -= 8;

              headerbuf = gst_buffer_new_and_alloc (headerlen);
              gst_buffer_fill (headerbuf, 0, waveheader, headerlen);

              if (gst_riff_parse_strf_auds (GST_ELEMENT_CAST (qtdemux),
                      headerbuf, &header, &extra)) {
                gst_caps_unref (stream->caps);
                /* FIXME: Need to do something with the channel reorder map */
                stream->caps = gst_riff_create_audio_caps (header->format, NULL,
                    header, extra, NULL, NULL, NULL);

                if (extra)
                  gst_buffer_unref (extra);
                g_free (header);
              }
            }
          } else
            GST_DEBUG ("Didn't find waveheadernode for this codec");
        }
        g_node_destroy (wavenode);
      }
    } else if (esds) {
      gst_qtdemux_handle_esds (qtdemux, stream, esds, stream->pending_tags);
    } else {
      switch (fourcc) {
#if 0
          /* FIXME: what is in the chunk? */
        case FOURCC_QDMC:
        {
          gint len = QT_UINT32 (stsd_data);

          /* seems to be always = 116 = 0x74 */
          break;
        }
#endif
        case FOURCC_QDM2:
        {
          gint len = QT_UINT32 (stsd_data);

          if (len > 0x4C) {
            GstBuffer *buf = gst_buffer_new_and_alloc (len - 0x4C);

            gst_buffer_fill (buf, 0, stsd_data + 0x4C, len - 0x4C);
            gst_caps_set_simple (stream->caps,
                "codec_data", GST_TYPE_BUFFER, buf, NULL);
            gst_buffer_unref (buf);
          }
          gst_caps_set_simple (stream->caps,
              "samplesize", G_TYPE_INT, samplesize, NULL);
          break;
        }
        case FOURCC_alac:
        {
          GNode *alac, *wave = NULL;

          /* apparently, m4a has this atom appended directly in the stsd entry,
           * while mov has it in a wave atom */
          alac = qtdemux_tree_get_child_by_type (stsd, FOURCC_alac);
          if (alac) {
            /* alac now refers to stsd entry atom */
            wave = qtdemux_tree_get_child_by_type (alac, FOURCC_wave);
            if (wave)
              alac = qtdemux_tree_get_child_by_type (wave, FOURCC_alac);
            else
              alac = qtdemux_tree_get_child_by_type (alac, FOURCC_alac);
          }
          if (alac) {
            const guint8 *alac_data = alac->data;
            gint len = QT_UINT32 (alac->data);
            GstBuffer *buf;

            if (len < 36) {
              GST_DEBUG_OBJECT (qtdemux,
                  "discarding alac atom with unexpected len %d", len);
            } else {
              /* codec-data contains alac atom size and prefix,
               * ffmpeg likes it that way, not quite gst-ish though ...*/
              buf = gst_buffer_new_and_alloc (len);
              gst_buffer_fill (buf, 0, alac->data, len);
              gst_caps_set_simple (stream->caps,
                  "codec_data", GST_TYPE_BUFFER, buf, NULL);
              gst_buffer_unref (buf);

              stream->bytes_per_frame = QT_UINT32 (alac_data + 12);
              stream->n_channels = QT_UINT8 (alac_data + 21);
              stream->rate = QT_UINT32 (alac_data + 32);
            }
          }
          gst_caps_set_simple (stream->caps,
              "samplesize", G_TYPE_INT, samplesize, NULL);
          break;
        }
        case FOURCC_sawb:
          /* Fallthrough! */
          amrwb = TRUE;
        case FOURCC_samr:
        {
          gint len = QT_UINT32 (stsd_data);

          if (len > 0x34) {
            GstBuffer *buf = gst_buffer_new_and_alloc (len - 0x34);
            guint bitrate;

            gst_buffer_fill (buf, 0, stsd_data + 0x34, len - 0x34);

            /* If we have enough data, let's try to get the 'damr' atom. See
             * the 3GPP container spec (26.244) for more details. */
            if ((len - 0x34) > 8 &&
                (bitrate = qtdemux_parse_amr_bitrate (buf, amrwb))) {
              gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
                  GST_TAG_MAXIMUM_BITRATE, bitrate, NULL);
            }

            gst_caps_set_simple (stream->caps,
                "codec_data", GST_TYPE_BUFFER, buf, NULL);
            gst_buffer_unref (buf);
          }
          break;
        }
        case FOURCC_mp4a:
        {
          /* mp4a atom withtout ESDS; Attempt to build codec data from atom */
          gint len = QT_UINT32 (stsd_data);

          if (len >= 50) {
            guint16 sound_version = QT_UINT16 (stsd_data + 32);

            if (sound_version == 1) {
              guint16 channels = QT_UINT16 (stsd_data + 40);
              guint32 time_scale = QT_UINT32 (stsd_data + 46);
              guint8 codec_data[2];
              GstBuffer *buf;
              gint profile = 2; /* FIXME: Can this be determined somehow? There doesn't seem to be anything in mp4a atom that specifis compression */

              gint sample_rate_index =
                  gst_codec_utils_aac_get_index_from_sample_rate (time_scale);

              /* build AAC codec data */
              codec_data[0] = profile << 3;
              codec_data[0] |= ((sample_rate_index >> 1) & 0x7);
              codec_data[1] = (sample_rate_index & 0x01) << 7;
              codec_data[1] |= (channels & 0xF) << 3;

              buf = gst_buffer_new_and_alloc (2);
              gst_buffer_fill (buf, 0, codec_data, 2);
              gst_caps_set_simple (stream->caps,
                  "codec_data", GST_TYPE_BUFFER, buf, NULL);
              gst_buffer_unref (buf);
            }
          }
          break;
        }
        default:
          GST_INFO_OBJECT (qtdemux,
              "unhandled type %" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));
          break;
      }
    }
    GST_INFO_OBJECT (qtdemux,
        "type %" GST_FOURCC_FORMAT " caps %" GST_PTR_FORMAT,
        GST_FOURCC_ARGS (fourcc), stream->caps);

  } else if (stream->subtype == FOURCC_strm) {
    if (fourcc == FOURCC_rtsp) {
      stream->redirect_uri = qtdemux_get_rtsp_uri_from_hndl (qtdemux, minf);
    } else {
      GST_INFO_OBJECT (qtdemux, "unhandled stream type %" GST_FOURCC_FORMAT,
          GST_FOURCC_ARGS (fourcc));
      goto unknown_stream;
    }
    stream->sampled = TRUE;
  } else if (stream->subtype == FOURCC_subp || stream->subtype == FOURCC_text
      || stream->subtype == FOURCC_sbtl || stream->subtype == FOURCC_subt) {

    stream->sampled = TRUE;
    stream->sparse = TRUE;

    stream->caps =
        qtdemux_sub_caps (qtdemux, stream, fourcc, stsd_data, &codec);
    if (codec) {
      gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
          GST_TAG_SUBTITLE_CODEC, codec, NULL);
      g_free (codec);
      codec = NULL;
    }

    /* hunt for sort-of codec data */
    switch (fourcc) {
      case FOURCC_mp4s:
      {
        GNode *mp4s = NULL;
        GNode *esds = NULL;

        /* look for palette in a stsd->mp4s->esds sub-atom */
        mp4s = qtdemux_tree_get_child_by_type (stsd, FOURCC_mp4s);
        if (mp4s)
          esds = qtdemux_tree_get_child_by_type (mp4s, FOURCC_esds);
        if (esds == NULL) {
          /* Invalid STSD */
          GST_LOG_OBJECT (qtdemux, "Skipping invalid stsd: no esds child");
          break;
        }

        gst_qtdemux_handle_esds (qtdemux, stream, esds, stream->pending_tags);
        break;
      }
      default:
        GST_INFO_OBJECT (qtdemux,
            "unhandled type %" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));
        break;
    }
    GST_INFO_OBJECT (qtdemux,
        "type %" GST_FOURCC_FORMAT " caps %" GST_PTR_FORMAT,
        GST_FOURCC_ARGS (fourcc), stream->caps);
  } else {
    /* everything in 1 sample */
    stream->sampled = TRUE;

    stream->caps =
        qtdemux_generic_caps (qtdemux, stream, fourcc, stsd_data, &codec);

    if (stream->caps == NULL)
      goto unknown_stream;

    if (codec) {
      gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
          GST_TAG_SUBTITLE_CODEC, codec, NULL);
      g_free (codec);
      codec = NULL;
    }
  }

  /* promote to sampled format */
  if (stream->fourcc == FOURCC_samr) {
    /* force mono 8000 Hz for AMR */
    stream->sampled = TRUE;
    stream->n_channels = 1;
    stream->rate = 8000;
  } else if (stream->fourcc == FOURCC_sawb) {
    /* force mono 16000 Hz for AMR-WB */
    stream->sampled = TRUE;
    stream->n_channels = 1;
    stream->rate = 16000;
  } else if (stream->fourcc == FOURCC_mp4a) {
    stream->sampled = TRUE;
  }

  /* collect sample information */
  if (!qtdemux_stbl_init (qtdemux, stream, stbl))
    goto samples_failed;

  if (qtdemux->fragmented) {
    guint64 offset;

    /* need all moov samples as basis; probably not many if any at all */
    /* prevent moof parsing taking of at this time */
    offset = qtdemux->moof_offset;
    qtdemux->moof_offset = 0;
    if (stream->n_samples &&
        !qtdemux_parse_samples (qtdemux, stream, stream->n_samples - 1)) {
      qtdemux->moof_offset = offset;
      goto samples_failed;
    }
    qtdemux->moof_offset = 0;
    /* movie duration more reliable in this case (e.g. mehd) */
    if (qtdemux->segment.duration &&
        GST_CLOCK_TIME_IS_VALID (qtdemux->segment.duration))
      stream->duration =
          GSTTIME_TO_QTSTREAMTIME (stream, qtdemux->segment.duration);
  }

  /* configure segments */
  if (!qtdemux_parse_segments (qtdemux, stream, trak))
    goto segments_failed;

  /* add some language tag, if useful */
  if (stream->lang_id[0] != '\0' && strcmp (stream->lang_id, "unk") &&
      strcmp (stream->lang_id, "und")) {
    const gchar *lang_code;

    /* convert ISO 639-2 code to ISO 639-1 */
    lang_code = gst_tag_get_language_code (stream->lang_id);
    gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
        GST_TAG_LANGUAGE_CODE, (lang_code) ? lang_code : stream->lang_id, NULL);
  }

  /* Check for UDTA tags */
  if ((udta = qtdemux_tree_get_child_by_type (trak, FOURCC_udta))) {
    qtdemux_parse_udta (qtdemux, stream->pending_tags, udta);
  }

  /* now we are ready to add the stream */
  if (qtdemux->n_streams >= GST_QTDEMUX_MAX_STREAMS)
    goto too_many_streams;

  if (!qtdemux->got_moov) {
    qtdemux->streams[qtdemux->n_streams] = stream;
    qtdemux->n_streams++;
    GST_DEBUG_OBJECT (qtdemux, "n_streams is now %d", qtdemux->n_streams);
  }

  return TRUE;

/* ERRORS */
skip_track:
  {
    GST_INFO_OBJECT (qtdemux, "skip disabled track");
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return TRUE;
  }
corrupt_file:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DEMUX,
        (_("This file is corrupt and cannot be played.")), (NULL));
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return FALSE;
  }
error_encrypted:
  {
    GST_ELEMENT_ERROR (qtdemux, STREAM, DECRYPT, (NULL), (NULL));
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return FALSE;
  }
samples_failed:
segments_failed:
  {
    /* we posted an error already */
    /* free stbl sub-atoms */
    gst_qtdemux_stbl_free (stream);
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return FALSE;
  }
existing_stream:
  {
    GST_INFO_OBJECT (qtdemux, "stream with track id %i already exists",
        track_id);
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return TRUE;
  }
unknown_stream:
  {
    GST_INFO_OBJECT (qtdemux, "unknown subtype %" GST_FOURCC_FORMAT,
        GST_FOURCC_ARGS (stream->subtype));
    if (new_stream)
      gst_qtdemux_stream_free (qtdemux, stream);
    return TRUE;
  }
too_many_streams:
  {
    GST_ELEMENT_WARNING (qtdemux, STREAM, DEMUX,
        (_("This file contains too many streams. Only playing first %d"),
            GST_QTDEMUX_MAX_STREAMS), (NULL));
    return TRUE;
  }
}

/* If we can estimate the overall bitrate, and don't have information about the
 * stream bitrate for exactly one stream, this guesses the stream bitrate as
 * the overall bitrate minus the sum of the bitrates of all other streams. This
 * should be useful for the common case where we have one audio and one video
 * stream and can estimate the bitrate of one, but not the other. */
static void
gst_qtdemux_guess_bitrate (GstQTDemux * qtdemux)
{
  QtDemuxStream *stream = NULL;
  gint64 size, sys_bitrate, sum_bitrate = 0;
  GstClockTime duration;
  gint i;
  guint bitrate;

  if (qtdemux->fragmented)
    return;

  GST_DEBUG_OBJECT (qtdemux, "Looking for streams with unknown bitrate");

  if (!gst_pad_peer_query_duration (qtdemux->sinkpad, GST_FORMAT_BYTES, &size)
      || size <= 0) {
    GST_DEBUG_OBJECT (qtdemux,
        "Size in bytes of the stream not known - bailing");
    return;
  }

  /* Subtract the header size */
  GST_DEBUG_OBJECT (qtdemux, "Total size %" G_GINT64_FORMAT ", header size %u",
      size, qtdemux->header_size);

  if (size < qtdemux->header_size)
    return;

  size = size - qtdemux->header_size;

  if (!gst_qtdemux_get_duration (qtdemux, &duration) ||
      duration == GST_CLOCK_TIME_NONE) {
    GST_DEBUG_OBJECT (qtdemux, "Stream duration not known - bailing");
    return;
  }

  for (i = 0; i < qtdemux->n_streams; i++) {
    switch (qtdemux->streams[i]->subtype) {
      case FOURCC_soun:
      case FOURCC_vide:
        GST_DEBUG_OBJECT (qtdemux, "checking bitrate for %" GST_PTR_FORMAT,
            qtdemux->streams[i]->caps);
        /* retrieve bitrate, prefer avg then max */
        bitrate = 0;
        if (qtdemux->streams[i]->pending_tags) {
          gst_tag_list_get_uint (qtdemux->streams[i]->pending_tags,
              GST_TAG_MAXIMUM_BITRATE, &bitrate);
          GST_DEBUG_OBJECT (qtdemux, "max-bitrate: %u", bitrate);
          gst_tag_list_get_uint (qtdemux->streams[i]->pending_tags,
              GST_TAG_NOMINAL_BITRATE, &bitrate);
          GST_DEBUG_OBJECT (qtdemux, "nominal-bitrate: %u", bitrate);
          gst_tag_list_get_uint (qtdemux->streams[i]->pending_tags,
              GST_TAG_BITRATE, &bitrate);
          GST_DEBUG_OBJECT (qtdemux, "bitrate: %u", bitrate);
        }
        if (bitrate)
          sum_bitrate += bitrate;
        else {
          if (stream) {
            GST_DEBUG_OBJECT (qtdemux,
                ">1 stream with unknown bitrate - bailing");
            return;
          } else
            stream = qtdemux->streams[i];
        }

      default:
        /* For other subtypes, we assume no significant impact on bitrate */
        break;
    }
  }

  if (!stream) {
    GST_DEBUG_OBJECT (qtdemux, "All stream bitrates are known");
    return;
  }

  sys_bitrate = gst_util_uint64_scale (size, GST_SECOND * 8, duration);

  if (sys_bitrate < sum_bitrate) {
    /* This can happen, since sum_bitrate might be derived from maximum
     * bitrates and not average bitrates */
    GST_DEBUG_OBJECT (qtdemux,
        "System bitrate less than sum bitrate - bailing");
    return;
  }

  bitrate = sys_bitrate - sum_bitrate;
  GST_DEBUG_OBJECT (qtdemux, "System bitrate = %" G_GINT64_FORMAT
      ", Stream bitrate = %u", sys_bitrate, bitrate);

  if (!stream->pending_tags)
    stream->pending_tags = gst_tag_list_new_empty ();

  gst_tag_list_add (stream->pending_tags, GST_TAG_MERGE_REPLACE,
      GST_TAG_BITRATE, bitrate, NULL);
}

static GstFlowReturn
qtdemux_prepare_streams (GstQTDemux * qtdemux)
{
  gint i;
  GstFlowReturn ret = GST_FLOW_OK;

  GST_DEBUG_OBJECT (qtdemux, "prepare streams");

  for (i = 0; ret == GST_FLOW_OK && i < qtdemux->n_streams; i++) {
    QtDemuxStream *stream = qtdemux->streams[i];
    guint32 sample_num = 0;

    GST_DEBUG_OBJECT (qtdemux, "stream %d, id %d, fourcc %" GST_FOURCC_FORMAT,
        i, stream->track_id, GST_FOURCC_ARGS (stream->fourcc));

    if (qtdemux->fragmented) {
      /* need all moov samples first */
      GST_OBJECT_LOCK (qtdemux);
      while (stream->n_samples == 0)
        if ((ret = qtdemux_add_fragmented_samples (qtdemux)) != GST_FLOW_OK)
          break;
      GST_OBJECT_UNLOCK (qtdemux);
    } else {
      /* discard any stray moof */
      qtdemux->moof_offset = 0;
    }

    /* prepare braking */
    if (ret != GST_FLOW_ERROR)
      ret = GST_FLOW_OK;

    /* in pull mode, we should have parsed some sample info by now;
     * and quite some code will not handle no samples.
     * in push mode, we'll just have to deal with it */
    if (G_UNLIKELY (qtdemux->pullbased && !stream->n_samples)) {
      GST_DEBUG_OBJECT (qtdemux, "no samples for stream; discarding");
      gst_qtdemux_remove_stream (qtdemux, i);
      i--;
      continue;
    }

    /* parse the initial sample for use in setting the frame rate cap */
    while (sample_num == 0 && sample_num < stream->n_samples) {
      if (!qtdemux_parse_samples (qtdemux, stream, sample_num))
        break;
      ++sample_num;
    }
    if (stream->n_samples > 0 && stream->stbl_index >= 0) {
      stream->first_duration = stream->samples[0].duration;
      GST_LOG_OBJECT (qtdemux, "stream %d first duration %u",
          stream->track_id, stream->first_duration);
    }
  }

  return ret;
}

static GstFlowReturn
qtdemux_expose_streams (GstQTDemux * qtdemux)
{
  gint i;
  GstFlowReturn ret = GST_FLOW_OK;
  GSList *oldpads = NULL;
  GSList *iter;

  GST_DEBUG_OBJECT (qtdemux, "exposing streams");

  for (i = 0; ret == GST_FLOW_OK && i < qtdemux->n_streams; i++) {
    QtDemuxStream *stream = qtdemux->streams[i];
    GstPad *oldpad = stream->pad;
    GstTagList *list;

    GST_DEBUG_OBJECT (qtdemux, "stream %d, id %d, fourcc %" GST_FOURCC_FORMAT,
        i, stream->track_id, GST_FOURCC_ARGS (stream->fourcc));

    if ((stream->subtype == FOURCC_text || stream->subtype == FOURCC_sbtl) &&
        stream->track_id == qtdemux->chapters_track_id) {
      /* TODO - parse chapters track and expose it as GstToc; For now just ignore it
         so that it doesn't look like a subtitle track */
      gst_qtdemux_remove_stream (qtdemux, i);
      i--;
      continue;
    }

    /* now we have all info and can expose */
    list = stream->pending_tags;
    stream->pending_tags = NULL;
    if (oldpad)
      oldpads = g_slist_prepend (oldpads, oldpad);
    if (!gst_qtdemux_add_stream (qtdemux, stream, list))
      return GST_FLOW_ERROR;
  }

  gst_qtdemux_guess_bitrate (qtdemux);

  gst_element_no_more_pads (GST_ELEMENT_CAST (qtdemux));

  for (iter = oldpads; iter; iter = g_slist_next (iter)) {
    GstPad *oldpad = iter->data;
    GstEvent *event;

    event = gst_event_new_eos ();
    if (qtdemux->segment_seqnum)
      gst_event_set_seqnum (event, qtdemux->segment_seqnum);

    gst_pad_push_event (oldpad, event);
    gst_pad_set_active (oldpad, FALSE);
    gst_element_remove_pad (GST_ELEMENT (qtdemux), oldpad);
    gst_flow_combiner_remove_pad (qtdemux->flowcombiner, oldpad);
    gst_object_unref (oldpad);
  }

  /* check if we should post a redirect in case there is a single trak
   * and it is a redirecting trak */
  if (qtdemux->n_streams == 1 && qtdemux->streams[0]->redirect_uri != NULL) {
    GstMessage *m;

    GST_INFO_OBJECT (qtdemux, "Issuing a redirect due to a single track with "
        "an external content");
    m = gst_message_new_element (GST_OBJECT_CAST (qtdemux),
        gst_structure_new ("redirect",
            "new-location", G_TYPE_STRING, qtdemux->streams[0]->redirect_uri,
            NULL));
    gst_element_post_message (GST_ELEMENT_CAST (qtdemux), m);
    qtdemux->posted_redirect = TRUE;
  }

  for (i = 0; i < qtdemux->n_streams; i++) {
    QtDemuxStream *stream = qtdemux->streams[i];

    qtdemux_do_allocation (qtdemux, stream);
  }

  qtdemux->exposed = TRUE;
  return ret;
}

/* check if major or compatible brand is 3GP */
static inline gboolean
qtdemux_is_brand_3gp (GstQTDemux * qtdemux, gboolean major)
{
  if (major) {
    return ((qtdemux->major_brand & GST_MAKE_FOURCC (255, 255, 0, 0)) ==
        FOURCC_3g__);
  } else if (qtdemux->comp_brands != NULL) {
    GstMapInfo map;
    guint8 *data;
    gsize size;
    gboolean res = FALSE;

    gst_buffer_map (qtdemux->comp_brands, &map, GST_MAP_READ);
    data = map.data;
    size = map.size;
    while (size >= 4) {
      res = res || ((QT_FOURCC (data) & GST_MAKE_FOURCC (255, 255, 0, 0)) ==
          FOURCC_3g__);
      data += 4;
      size -= 4;
    }
    gst_buffer_unmap (qtdemux->comp_brands, &map);
    return res;
  } else {
    return FALSE;
  }
}

/* check if tag is a spec'ed 3GP tag keyword storing a string */
static inline gboolean
qtdemux_is_string_tag_3gp (GstQTDemux * qtdemux, guint32 fourcc)
{
  return fourcc == FOURCC_cprt || fourcc == FOURCC_gnre || fourcc == FOURCC_titl
      || fourcc == FOURCC_dscp || fourcc == FOURCC_perf || fourcc == FOURCC_auth
      || fourcc == FOURCC_albm;
}

static void
qtdemux_tag_add_location (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  const gchar *env_vars[] = { "GST_QT_TAG_ENCODING", "GST_TAG_ENCODING", NULL };
  int offset;
  char *name;
  gchar *data;
  gdouble longitude, latitude, altitude;
  gint len;

  len = QT_UINT32 (node->data);
  if (len <= 14)
    goto short_read;

  data = node->data;
  offset = 14;

  /* TODO: language code skipped */

  name = gst_tag_freeform_string_to_utf8 (data + offset, -1, env_vars);

  if (!name) {
    /* do not alarm in trivial case, but bail out otherwise */
    if (*(data + offset) != 0) {
      GST_DEBUG_OBJECT (qtdemux, "failed to convert %s tag to UTF-8, "
          "giving up", tag);
    }
  } else {
    gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE,
        GST_TAG_GEO_LOCATION_NAME, name, NULL);
    offset += strlen (name);
    g_free (name);
  }

  if (len < offset + 2 + 4 + 4 + 4)
    goto short_read;

  /* +1 +1 = skip null-terminator and location role byte */
  offset += 1 + 1;
  /* table in spec says unsigned, semantics say negative has meaning ... */
  longitude = QT_SFP32 (data + offset);

  offset += 4;
  latitude = QT_SFP32 (data + offset);

  offset += 4;
  altitude = QT_SFP32 (data + offset);

  /* one invalid means all are invalid */
  if (longitude >= -180.0 && longitude <= 180.0 &&
      latitude >= -90.0 && latitude <= 90.0) {
    gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE,
        GST_TAG_GEO_LOCATION_LATITUDE, latitude,
        GST_TAG_GEO_LOCATION_LONGITUDE, longitude,
        GST_TAG_GEO_LOCATION_ELEVATION, altitude, NULL);
  }

  /* TODO: no GST_TAG_, so astronomical body and additional notes skipped */

  return;

  /* ERRORS */
short_read:
  {
    GST_DEBUG_OBJECT (qtdemux, "short read parsing 3GP location");
    return;
  }
}


static void
qtdemux_tag_add_year (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  guint16 y;
  GDate *date;
  gint len;

  len = QT_UINT32 (node->data);
  if (len < 14)
    return;

  y = QT_UINT16 ((guint8 *) node->data + 12);
  if (y == 0) {
    GST_DEBUG_OBJECT (qtdemux, "year: %u is not a valid year", y);
    return;
  }
  GST_DEBUG_OBJECT (qtdemux, "year: %u", y);

  date = g_date_new_dmy (1, 1, y);
  gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, date, NULL);
  g_date_free (date);
}

static void
qtdemux_tag_add_classification (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  int offset;
  char *tag_str = NULL;
  guint8 *entity;
  guint16 table;
  gint len;

  len = QT_UINT32 (node->data);
  if (len <= 20)
    goto short_read;

  offset = 12;
  entity = (guint8 *) node->data + offset;
  if (entity[0] == 0 || entity[1] == 0 || entity[2] == 0 || entity[3] == 0) {
    GST_DEBUG_OBJECT (qtdemux,
        "classification info: %c%c%c%c invalid classification entity",
        entity[0], entity[1], entity[2], entity[3]);
    return;
  }

  offset += 4;
  table = QT_UINT16 ((guint8 *) node->data + offset);

  /* Language code skipped */

  offset += 4;

  /* Tag format: "XXXX://Y[YYYY]/classification info string"
   * XXXX: classification entity, fixed length 4 chars.
   * Y[YYYY]: classification table, max 5 chars.
   */
  tag_str = g_strdup_printf ("----://%u/%s",
      table, (char *) node->data + offset);

  /* memcpy To be sure we're preserving byte order */
  memcpy (tag_str, entity, 4);
  GST_DEBUG_OBJECT (qtdemux, "classification info: %s", tag_str);

  gst_tag_list_add (taglist, GST_TAG_MERGE_APPEND, tag, tag_str, NULL);

  g_free (tag_str);

  return;

  /* ERRORS */
short_read:
  {
    GST_DEBUG_OBJECT (qtdemux, "short read parsing 3GP classification");
    return;
  }
}

static gboolean
qtdemux_tag_add_str_full (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  const gchar *env_vars[] = { "GST_QT_TAG_ENCODING", "GST_TAG_ENCODING", NULL };
  GNode *data;
  char *s;
  int len;
  guint32 type;
  int offset;
  gboolean ret = TRUE;
  const gchar *charset = NULL;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    if (type == 0x00000001 && len > 16) {
      s = gst_tag_freeform_string_to_utf8 ((char *) data->data + 16, len - 16,
          env_vars);
      if (s) {
        GST_DEBUG_OBJECT (qtdemux, "adding tag %s", GST_STR_NULL (s));
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, s, NULL);
        g_free (s);
      } else {
        GST_DEBUG_OBJECT (qtdemux, "failed to convert %s tag to UTF-8", tag);
      }
    }
  } else {
    len = QT_UINT32 (node->data);
    type = QT_UINT32 ((guint8 *) node->data + 4);
    if ((type >> 24) == 0xa9) {
      gint str_len;
      gint lang_code;

      /* Type starts with the (C) symbol, so the next data is a list
       * of (string size(16), language code(16), string) */

      str_len = QT_UINT16 ((guint8 *) node->data + 8);
      lang_code = QT_UINT16 ((guint8 *) node->data + 10);

      /* the string + fourcc + size + 2 16bit fields,
       * means that there are more tags in this atom */
      if (len > str_len + 8 + 4) {
        /* TODO how to represent the same tag in different languages? */
        GST_WARNING_OBJECT (qtdemux, "Ignoring metadata entry with multiple "
            "text alternatives, reading only first one");
      }

      offset = 12;
      len = str_len + 8 + 4;    /* remove trailing strings that we don't use */
      GST_DEBUG_OBJECT (qtdemux, "found international text tag");

      if (lang_code < 0x800) {  /* MAC encoded string */
        charset = "mac";
      }
    } else if (len > 14 && qtdemux_is_string_tag_3gp (qtdemux,
            QT_FOURCC ((guint8 *) node->data + 4))) {
      guint32 type = QT_UINT32 ((guint8 *) node->data + 8);

      /* we go for 3GP style encoding if major brands claims so,
       * or if no hope for data be ok UTF-8, and compatible 3GP brand present */
      if (qtdemux_is_brand_3gp (qtdemux, TRUE) ||
          (qtdemux_is_brand_3gp (qtdemux, FALSE) &&
              ((type & 0x00FFFFFF) == 0x0) && (type >> 24 <= 0xF))) {
        offset = 14;
        /* 16-bit Language code is ignored here as well */
        GST_DEBUG_OBJECT (qtdemux, "found 3gpp text tag");
      } else {
        goto normal;
      }
    } else {
    normal:
      offset = 8;
      GST_DEBUG_OBJECT (qtdemux, "found normal text tag");
      ret = FALSE;              /* may have to fallback */
    }
    if (charset) {
      GError *err = NULL;

      s = g_convert ((gchar *) node->data + offset, len - offset, "utf8",
          charset, NULL, NULL, &err);
      if (err) {
        GST_DEBUG_OBJECT (qtdemux, "Failed to convert string from charset %s:"
            " %s(%d): %s", charset, g_quark_to_string (err->domain), err->code,
            err->message);
        g_error_free (err);
      }
    } else {
      s = gst_tag_freeform_string_to_utf8 ((char *) node->data + offset,
          len - offset, env_vars);
    }
    if (s) {
      GST_DEBUG_OBJECT (qtdemux, "adding tag %s", GST_STR_NULL (s));
      gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, s, NULL);
      g_free (s);
      ret = TRUE;
    } else {
      GST_DEBUG_OBJECT (qtdemux, "failed to convert %s tag to UTF-8", tag);
    }
  }
  return ret;
}

static void
qtdemux_tag_add_str (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  qtdemux_tag_add_str_full (qtdemux, taglist, tag, dummy, node);
}

static void
qtdemux_tag_add_keywords (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  const gchar *env_vars[] = { "GST_QT_TAG_ENCODING", "GST_TAG_ENCODING", NULL };
  guint8 *data;
  char *s, *t, *k = NULL;
  int len;
  int offset;
  int count;

  /* first try normal string tag if major brand not 3GP */
  if (!qtdemux_is_brand_3gp (qtdemux, TRUE)) {
    if (!qtdemux_tag_add_str_full (qtdemux, taglist, tag, dummy, node)) {
      /* hm, that did not work, maybe 3gpp storage in non-3gpp major brand;
       * let's try it 3gpp way after minor safety check */
      data = node->data;
      if (QT_UINT32 (data) < 15 || !qtdemux_is_brand_3gp (qtdemux, FALSE))
        return;
    } else
      return;
  }

  GST_DEBUG_OBJECT (qtdemux, "found 3gpp keyword tag");

  data = node->data;

  len = QT_UINT32 (data);
  if (len < 15)
    goto short_read;

  count = QT_UINT8 (data + 14);
  offset = 15;
  for (; count; count--) {
    gint slen;

    if (offset + 1 > len)
      goto short_read;
    slen = QT_UINT8 (data + offset);
    offset += 1;
    if (offset + slen > len)
      goto short_read;
    s = gst_tag_freeform_string_to_utf8 ((char *) node->data + offset,
        slen, env_vars);
    if (s) {
      GST_DEBUG_OBJECT (qtdemux, "adding keyword %s", GST_STR_NULL (s));
      if (k) {
        t = g_strjoin (",", k, s, NULL);
        g_free (s);
        g_free (k);
        k = t;
      } else {
        k = s;
      }
    } else {
      GST_DEBUG_OBJECT (qtdemux, "failed to convert keyword to UTF-8");
    }
    offset += slen;
  }

done:
  if (k) {
    GST_DEBUG_OBJECT (qtdemux, "adding tag %s", GST_STR_NULL (k));
    gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, k, NULL);
  }
  g_free (k);

  return;

  /* ERRORS */
short_read:
  {
    GST_DEBUG_OBJECT (qtdemux, "short read parsing 3GP keywords");
    goto done;
  }
}

static void
qtdemux_tag_add_num (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag1, const char *tag2, GNode * node)
{
  GNode *data;
  int len;
  int type;
  int n1, n2;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    if (type == 0x00000000 && len >= 22) {
      n1 = QT_UINT16 ((guint8 *) data->data + 18);
      n2 = QT_UINT16 ((guint8 *) data->data + 20);
      if (n1 > 0) {
        GST_DEBUG_OBJECT (qtdemux, "adding tag %s=%d", tag1, n1);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag1, n1, NULL);
      }
      if (n2 > 0) {
        GST_DEBUG_OBJECT (qtdemux, "adding tag %s=%d", tag2, n2);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag2, n2, NULL);
      }
    }
  }
}

static void
qtdemux_tag_add_tmpo (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag1, const char *dummy, GNode * node)
{
  GNode *data;
  int len;
  int type;
  int n1;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    GST_DEBUG_OBJECT (qtdemux, "have tempo tag, type=%d,len=%d", type, len);
    /* some files wrongly have a type 0x0f=15, but it should be 0x15 */
    if ((type == 0x00000015 || type == 0x0000000f) && len >= 18) {
      n1 = QT_UINT16 ((guint8 *) data->data + 16);
      if (n1) {
        /* do not add bpm=0 */
        GST_DEBUG_OBJECT (qtdemux, "adding tag %d", n1);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag1, (gdouble) n1,
            NULL);
      }
    }
  }
}

static void
qtdemux_tag_add_uint32 (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag1, const char *dummy, GNode * node)
{
  GNode *data;
  int len;
  int type;
  guint32 num;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    GST_DEBUG_OBJECT (qtdemux, "have %s tag, type=%d,len=%d", tag1, type, len);
    /* some files wrongly have a type 0x0f=15, but it should be 0x15 */
    if ((type == 0x00000015 || type == 0x0000000f) && len >= 20) {
      num = QT_UINT32 ((guint8 *) data->data + 16);
      if (num) {
        /* do not add num=0 */
        GST_DEBUG_OBJECT (qtdemux, "adding tag %d", num);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag1, num, NULL);
      }
    }
  }
}

static void
qtdemux_tag_add_covr (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag1, const char *dummy, GNode * node)
{
  GNode *data;
  int len;
  int type;
  GstSample *sample;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    GST_DEBUG_OBJECT (qtdemux, "have covr tag, type=%d,len=%d", type, len);
    if ((type == 0x0000000d || type == 0x0000000e) && len > 16) {
      if ((sample =
              gst_tag_image_data_to_image_sample ((guint8 *) data->data + 16,
                  len - 16, GST_TAG_IMAGE_TYPE_NONE))) {
        GST_DEBUG_OBJECT (qtdemux, "adding tag size %d", len - 16);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag1, sample, NULL);
        gst_sample_unref (sample);
      }
    }
  }
}

static void
qtdemux_tag_add_date (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  GNode *data;
  char *s;
  int len;
  int type;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (data) {
    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    if (type == 0x00000001 && len > 16) {
      guint y, m = 1, d = 1;
      gint ret;

      s = g_strndup ((char *) data->data + 16, len - 16);
      GST_DEBUG_OBJECT (qtdemux, "adding date '%s'", s);
      ret = sscanf (s, "%u-%u-%u", &y, &m, &d);
      if (ret >= 1 && y > 1500 && y < 3000) {
        GDate *date;

        date = g_date_new_dmy (d, m, y);
        gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, date, NULL);
        g_date_free (date);
      } else {
        GST_DEBUG_OBJECT (qtdemux, "could not parse date string '%s'", s);
      }
      g_free (s);
    }
  }
}

static void
qtdemux_tag_add_gnre (GstQTDemux * qtdemux, GstTagList * taglist,
    const char *tag, const char *dummy, GNode * node)
{
  GNode *data;

  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);

  /* re-route to normal string tag if major brand says so
   * or no data atom and compatible brand suggests so */
  if (qtdemux_is_brand_3gp (qtdemux, TRUE) ||
      (qtdemux_is_brand_3gp (qtdemux, FALSE) && !data)) {
    qtdemux_tag_add_str (qtdemux, taglist, tag, dummy, node);
    return;
  }

  if (data) {
    guint len, type, n;

    len = QT_UINT32 (data->data);
    type = QT_UINT32 ((guint8 *) data->data + 8);
    if (type == 0x00000000 && len >= 18) {
      n = QT_UINT16 ((guint8 *) data->data + 16);
      if (n > 0) {
        const gchar *genre;

        genre = gst_tag_id3_genre_get (n - 1);
        if (genre != NULL) {
          GST_DEBUG_OBJECT (qtdemux, "adding %d [%s]", n, genre);
          gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, genre, NULL);
        }
      }
    }
  }
}

static void
qtdemux_add_double_tag_from_str (GstQTDemux * demux, GstTagList * taglist,
    const gchar * tag, guint8 * data, guint32 datasize)
{
  gdouble value;
  gchar *datacopy;

  /* make a copy to have \0 at the end */
  datacopy = g_strndup ((gchar *) data, datasize);

  /* convert the str to double */
  if (sscanf (datacopy, "%lf", &value) == 1) {
    GST_DEBUG_OBJECT (demux, "adding tag: %s [%s]", tag, datacopy);
    gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, tag, value, NULL);
  } else {
    GST_WARNING_OBJECT (demux, "Failed to parse double from string: %s",
        datacopy);
  }
  g_free (datacopy);
}


static void
qtdemux_tag_add_revdns (GstQTDemux * demux, GstTagList * taglist,
    const char *tag, const char *tag_bis, GNode * node)
{
  GNode *mean;
  GNode *name;
  GNode *data;
  guint32 meansize;
  guint32 namesize;
  guint32 datatype;
  guint32 datasize;
  const gchar *meanstr;
  const gchar *namestr;

  /* checking the whole ---- atom size for consistency */
  if (QT_UINT32 (node->data) <= 4 + 12 + 12 + 16) {
    GST_WARNING_OBJECT (demux, "Tag ---- atom is too small, ignoring");
    return;
  }

  mean = qtdemux_tree_get_child_by_type (node, FOURCC_mean);
  if (!mean) {
    GST_WARNING_OBJECT (demux, "No 'mean' atom found");
    return;
  }

  meansize = QT_UINT32 (mean->data);
  if (meansize <= 12) {
    GST_WARNING_OBJECT (demux, "Small mean atom, ignoring the whole tag");
    return;
  }
  meanstr = ((gchar *) mean->data) + 12;
  meansize -= 12;

  name = qtdemux_tree_get_child_by_type (node, FOURCC_name);
  if (!name) {
    GST_WARNING_OBJECT (demux, "'name' atom not found, ignoring tag");
    return;
  }

  namesize = QT_UINT32 (name->data);
  if (namesize <= 12) {
    GST_WARNING_OBJECT (demux, "'name' atom is too small, ignoring tag");
    return;
  }
  namestr = ((gchar *) name->data) + 12;
  namesize -= 12;

  /*
   * Data atom is:
   * uint32 - size
   * uint32 - name
   * uint8  - version
   * uint24 - data type
   * uint32 - all 0
   * rest   - the data
   */
  data = qtdemux_tree_get_child_by_type (node, FOURCC_data);
  if (!data) {
    GST_WARNING_OBJECT (demux, "No data atom in this tag");
    return;
  }
  datasize = QT_UINT32 (data->data);
  if (datasize <= 16) {
    GST_WARNING_OBJECT (demux, "Data atom too small");
    return;
  }
  datatype = QT_UINT32 (((gchar *) data->data) + 8) & 0xFFFFFF;

  if ((strncmp (meanstr, "com.apple.iTunes", meansize) == 0) ||
      (strncmp (meanstr, "org.hydrogenaudio.replaygain", meansize) == 0)) {
    static const struct
    {
      const gchar name[28];
      const gchar tag[28];
    } tags[] = {
      {
      "replaygain_track_gain", GST_TAG_TRACK_GAIN}, {
      "replaygain_track_peak", GST_TAG_TRACK_PEAK}, {
      "replaygain_album_gain", GST_TAG_ALBUM_GAIN}, {
      "replaygain_album_peak", GST_TAG_ALBUM_PEAK}, {
      "MusicBrainz Track Id", GST_TAG_MUSICBRAINZ_TRACKID}, {
      "MusicBrainz Artist Id", GST_TAG_MUSICBRAINZ_ARTISTID}, {
      "MusicBrainz Album Id", GST_TAG_MUSICBRAINZ_ALBUMID}, {
      "MusicBrainz Album Artist Id", GST_TAG_MUSICBRAINZ_ALBUMARTISTID}
    };
    int i;

    for (i = 0; i < G_N_ELEMENTS (tags); ++i) {
      if (!g_ascii_strncasecmp (tags[i].name, namestr, namesize)) {
        switch (gst_tag_get_type (tags[i].tag)) {
          case G_TYPE_DOUBLE:
            qtdemux_add_double_tag_from_str (demux, taglist, tags[i].tag,
                ((guint8 *) data->data) + 16, datasize - 16);
            break;
          case G_TYPE_STRING:
            qtdemux_tag_add_str (demux, taglist, tags[i].tag, NULL, node);
            break;
          default:
            /* not reached */
            break;
        }
        break;
      }
    }
    if (i == G_N_ELEMENTS (tags))
      goto unknown_tag;
  } else {
    goto unknown_tag;
  }

  return;

/* errors */
unknown_tag:
#ifndef GST_DISABLE_GST_DEBUG
  {
    gchar *namestr_dbg;
    gchar *meanstr_dbg;

    meanstr_dbg = g_strndup (meanstr, meansize);
    namestr_dbg = g_strndup (namestr, namesize);

    GST_WARNING_OBJECT (demux, "This tag %s:%s type:%u is not mapped, "
        "file a bug at bugzilla.gnome.org", meanstr_dbg, namestr_dbg, datatype);

    g_free (namestr_dbg);
    g_free (meanstr_dbg);
  }
#endif
  return;
}

static void
qtdemux_tag_add_id32 (GstQTDemux * demux, GstTagList * taglist, const char *tag,
    const char *tag_bis, GNode * node)
{
  guint8 *data;
  GstBuffer *buf;
  guint len;
  GstTagList *id32_taglist = NULL;

  GST_LOG_OBJECT (demux, "parsing ID32");

  data = node->data;
  len = GST_READ_UINT32_BE (data);

  /* need at least full box and language tag */
  if (len < 12 + 2)
    return;

  buf = gst_buffer_new_allocate (NULL, len - 14, NULL);
  gst_buffer_fill (buf, 0, data + 14, len - 14);

  id32_taglist = gst_tag_list_from_id3v2_tag (buf);
  if (id32_taglist) {
    GST_LOG_OBJECT (demux, "parsing ok");
    gst_tag_list_insert (taglist, id32_taglist, GST_TAG_MERGE_KEEP);
    gst_tag_list_unref (id32_taglist);
  } else {
    GST_LOG_OBJECT (demux, "parsing failed");
  }

  gst_buffer_unref (buf);
}

typedef void (*GstQTDemuxAddTagFunc) (GstQTDemux * demux, GstTagList * taglist,
    const char *tag, const char *tag_bis, GNode * node);

/* unmapped tags
FOURCC_pcst -> if media is a podcast -> bool
FOURCC_cpil -> if media is part of a compilation -> bool
FOURCC_pgap -> if media is part of a gapless context -> bool
FOURCC_tven -> the tv episode id e.g. S01E23 -> str
*/

static const struct
{
  guint32 fourcc;
  const gchar *gst_tag;
  const gchar *gst_tag_bis;
  const GstQTDemuxAddTagFunc func;
} add_funcs[] = {
  {
  FOURCC__nam, GST_TAG_TITLE, NULL, qtdemux_tag_add_str}, {
  FOURCC_titl, GST_TAG_TITLE, NULL, qtdemux_tag_add_str}, {
  FOURCC__grp, GST_TAG_GROUPING, NULL, qtdemux_tag_add_str}, {
  FOURCC__wrt, GST_TAG_COMPOSER, NULL, qtdemux_tag_add_str}, {
  FOURCC__ART, GST_TAG_ARTIST, NULL, qtdemux_tag_add_str}, {
  FOURCC_aART, GST_TAG_ALBUM_ARTIST, NULL, qtdemux_tag_add_str}, {
  FOURCC_perf, GST_TAG_ARTIST, NULL, qtdemux_tag_add_str}, {
  FOURCC_auth, GST_TAG_COMPOSER, NULL, qtdemux_tag_add_str}, {
  FOURCC__alb, GST_TAG_ALBUM, NULL, qtdemux_tag_add_str}, {
  FOURCC_albm, GST_TAG_ALBUM, NULL, qtdemux_tag_add_str}, {
  FOURCC_cprt, GST_TAG_COPYRIGHT, NULL, qtdemux_tag_add_str}, {
  FOURCC__cpy, GST_TAG_COPYRIGHT, NULL, qtdemux_tag_add_str}, {
  FOURCC__cmt, GST_TAG_COMMENT, NULL, qtdemux_tag_add_str}, {
  FOURCC__des, GST_TAG_DESCRIPTION, NULL, qtdemux_tag_add_str}, {
  FOURCC_desc, GST_TAG_DESCRIPTION, NULL, qtdemux_tag_add_str}, {
  FOURCC_dscp, GST_TAG_DESCRIPTION, NULL, qtdemux_tag_add_str}, {
  FOURCC__lyr, GST_TAG_LYRICS, NULL, qtdemux_tag_add_str}, {
  FOURCC__day, GST_TAG_DATE, NULL, qtdemux_tag_add_date}, {
  FOURCC_yrrc, GST_TAG_DATE, NULL, qtdemux_tag_add_year}, {
  FOURCC__too, GST_TAG_ENCODER, NULL, qtdemux_tag_add_str}, {
  FOURCC__inf, GST_TAG_COMMENT, NULL, qtdemux_tag_add_str}, {
  FOURCC_trkn, GST_TAG_TRACK_NUMBER, GST_TAG_TRACK_COUNT, qtdemux_tag_add_num}, {
  FOURCC_disk, GST_TAG_ALBUM_VOLUME_NUMBER, GST_TAG_ALBUM_VOLUME_COUNT,
        qtdemux_tag_add_num}, {
  FOURCC_disc, GST_TAG_ALBUM_VOLUME_NUMBER, GST_TAG_ALBUM_VOLUME_COUNT,
        qtdemux_tag_add_num}, {
  FOURCC__gen, GST_TAG_GENRE, NULL, qtdemux_tag_add_str}, {
  FOURCC_gnre, GST_TAG_GENRE, NULL, qtdemux_tag_add_gnre}, {
  FOURCC_tmpo, GST_TAG_BEATS_PER_MINUTE, NULL, qtdemux_tag_add_tmpo}, {
  FOURCC_covr, GST_TAG_PREVIEW_IMAGE, NULL, qtdemux_tag_add_covr}, {
  FOURCC_sonm, GST_TAG_TITLE_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_soal, GST_TAG_ALBUM_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_soar, GST_TAG_ARTIST_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_soaa, GST_TAG_ALBUM_ARTIST_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_soco, GST_TAG_COMPOSER_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_sosn, GST_TAG_SHOW_SORTNAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_tvsh, GST_TAG_SHOW_NAME, NULL, qtdemux_tag_add_str}, {
  FOURCC_tvsn, GST_TAG_SHOW_SEASON_NUMBER, NULL, qtdemux_tag_add_uint32}, {
  FOURCC_tves, GST_TAG_SHOW_EPISODE_NUMBER, NULL, qtdemux_tag_add_uint32}, {
  FOURCC_kywd, GST_TAG_KEYWORDS, NULL, qtdemux_tag_add_keywords}, {
  FOURCC_keyw, GST_TAG_KEYWORDS, NULL, qtdemux_tag_add_str}, {
  FOURCC__enc, GST_TAG_ENCODER, NULL, qtdemux_tag_add_str}, {
  FOURCC_loci, GST_TAG_GEO_LOCATION_NAME, NULL, qtdemux_tag_add_location}, {
  FOURCC_clsf, GST_QT_DEMUX_CLASSIFICATION_TAG, NULL,
        qtdemux_tag_add_classification}, {
  FOURCC__mak, GST_TAG_DEVICE_MANUFACTURER, NULL, qtdemux_tag_add_str}, {
  FOURCC__mod, GST_TAG_DEVICE_MODEL, NULL, qtdemux_tag_add_str}, {
  FOURCC__swr, GST_TAG_APPLICATION_NAME, NULL, qtdemux_tag_add_str}, {

    /* This is a special case, some tags are stored in this
     * 'reverse dns naming', according to:
     * http://atomicparsley.sourceforge.net/mpeg-4files.html and
     * bug #614471
     */
  FOURCC_____, "", NULL, qtdemux_tag_add_revdns}, {
    /* see http://www.mp4ra.org/specs.html for ID32 in meta box */
  FOURCC_ID32, "", NULL, qtdemux_tag_add_id32}
};

struct _GstQtDemuxTagList
{
  GstQTDemux *demux;
  GstTagList *taglist;
};
typedef struct _GstQtDemuxTagList GstQtDemuxTagList;

static void
qtdemux_tag_add_blob (GNode * node, GstQtDemuxTagList * qtdemuxtaglist)
{
  gint len;
  guint8 *data;
  GstBuffer *buf;
  gchar *media_type;
  const gchar *style;
  GstSample *sample;
  GstStructure *s;
  guint i;
  guint8 ndata[4];
  GstQTDemux *demux = qtdemuxtaglist->demux;
  GstTagList *taglist = qtdemuxtaglist->taglist;

  data = node->data;
  len = QT_UINT32 (data);
  buf = gst_buffer_new_and_alloc (len);
  gst_buffer_fill (buf, 0, data, len);

  /* heuristic to determine style of tag */
  if (QT_FOURCC (data + 4) == FOURCC_____ ||
      (len > 8 + 12 && QT_FOURCC (data + 12) == FOURCC_data))
    style = "itunes";
  else if (demux->major_brand == FOURCC_qt__)
    style = "quicktime";
  /* fall back to assuming iso/3gp tag style */
  else
    style = "iso";

  /* santize the name for the caps. */
  for (i = 0; i < 4; i++) {
    guint8 d = data[4 + i];
    if (g_ascii_isalnum (d))
      ndata[i] = g_ascii_tolower (d);
    else
      ndata[i] = '_';
  }

  media_type = g_strdup_printf ("application/x-gst-qt-%c%c%c%c-tag",
      ndata[0], ndata[1], ndata[2], ndata[3]);
  GST_DEBUG_OBJECT (demux, "media type %s", media_type);

  s = gst_structure_new (media_type, "style", G_TYPE_STRING, style, NULL);
  sample = gst_sample_new (buf, NULL, NULL, s);
  gst_buffer_unref (buf);
  g_free (media_type);

  GST_DEBUG_OBJECT (demux, "adding private tag; size %d, info %" GST_PTR_FORMAT,
      len, s);

  gst_tag_list_add (taglist, GST_TAG_MERGE_APPEND,
      GST_QT_DEMUX_PRIVATE_TAG, sample, NULL);

  gst_sample_unref (sample);
}

static void
qtdemux_parse_udta (GstQTDemux * qtdemux, GstTagList * taglist, GNode * udta)
{
  GNode *meta;
  GNode *ilst;
  GNode *xmp_;
  GNode *node;
  gint i;
  GstQtDemuxTagList demuxtaglist;

  demuxtaglist.demux = qtdemux;
  demuxtaglist.taglist = taglist;

  meta = qtdemux_tree_get_child_by_type (udta, FOURCC_meta);
  if (meta != NULL) {
    ilst = qtdemux_tree_get_child_by_type (meta, FOURCC_ilst);
    if (ilst == NULL) {
      GST_LOG_OBJECT (qtdemux, "no ilst");
      return;
    }
  } else {
    ilst = udta;
    GST_LOG_OBJECT (qtdemux, "no meta so using udta itself");
  }

  i = 0;
  while (i < G_N_ELEMENTS (add_funcs)) {
    node = qtdemux_tree_get_child_by_type (ilst, add_funcs[i].fourcc);
    if (node) {
      gint len;

      len = QT_UINT32 (node->data);
      if (len < 12) {
        GST_DEBUG_OBJECT (qtdemux, "too small tag atom %" GST_FOURCC_FORMAT,
            GST_FOURCC_ARGS (add_funcs[i].fourcc));
      } else {
        add_funcs[i].func (qtdemux, taglist, add_funcs[i].gst_tag,
            add_funcs[i].gst_tag_bis, node);
      }
      g_node_destroy (node);
    } else {
      i++;
    }
  }

  /* parsed nodes have been removed, pass along remainder as blob */
  g_node_children_foreach (ilst, G_TRAVERSE_ALL,
      (GNodeForeachFunc) qtdemux_tag_add_blob, &demuxtaglist);

  /* parse up XMP_ node if existing */
  xmp_ = qtdemux_tree_get_child_by_type (udta, FOURCC_XMP_);
  if (xmp_ != NULL) {
    GstBuffer *buf;
    GstTagList *xmptaglist;

    buf = _gst_buffer_new_wrapped (((guint8 *) xmp_->data) + 8,
        QT_UINT32 ((guint8 *) xmp_->data) - 8, NULL);
    xmptaglist = gst_tag_list_from_xmp_buffer (buf);
    gst_buffer_unref (buf);

    qtdemux_handle_xmp_taglist (qtdemux, taglist, xmptaglist);
  } else {
    GST_DEBUG_OBJECT (qtdemux, "No XMP_ node found");
  }
}

typedef struct
{
  GstStructure *structure;      /* helper for sort function */
  gchar *location;
  guint min_req_bitrate;
  guint min_req_qt_version;
} GstQtReference;

static gint
qtdemux_redirects_sort_func (gconstpointer a, gconstpointer b)
{
  GstQtReference *ref_a = (GstQtReference *) a;
  GstQtReference *ref_b = (GstQtReference *) b;

  if (ref_b->min_req_qt_version != ref_a->min_req_qt_version)
    return ref_b->min_req_qt_version - ref_a->min_req_qt_version;

  /* known bitrates go before unknown; higher bitrates go first */
  return ref_b->min_req_bitrate - ref_a->min_req_bitrate;
}

/* sort the redirects and post a message for the application.
 */
static void
qtdemux_process_redirects (GstQTDemux * qtdemux, GList * references)
{
  GstQtReference *best;
  GstStructure *s;
  GstMessage *msg;
  GValue list_val = { 0, };
  GList *l;

  g_assert (references != NULL);

  references = g_list_sort (references, qtdemux_redirects_sort_func);

  best = (GstQtReference *) references->data;

  g_value_init (&list_val, GST_TYPE_LIST);

  for (l = references; l != NULL; l = l->next) {
    GstQtReference *ref = (GstQtReference *) l->data;
    GValue struct_val = { 0, };

    ref->structure = gst_structure_new ("redirect",
        "new-location", G_TYPE_STRING, ref->location, NULL);

    if (ref->min_req_bitrate > 0) {
      gst_structure_set (ref->structure, "minimum-bitrate", G_TYPE_INT,
          ref->min_req_bitrate, NULL);
    }

    g_value_init (&struct_val, GST_TYPE_STRUCTURE);
    g_value_set_boxed (&struct_val, ref->structure);
    gst_value_list_append_value (&list_val, &struct_val);
    g_value_unset (&struct_val);
    /* don't free anything here yet, since we need best->structure below */
  }

  g_assert (best != NULL);
  s = gst_structure_copy (best->structure);

  if (g_list_length (references) > 1) {
    gst_structure_set_value (s, "locations", &list_val);
  }

  g_value_unset (&list_val);

  for (l = references; l != NULL; l = l->next) {
    GstQtReference *ref = (GstQtReference *) l->data;

    gst_structure_free (ref->structure);
    g_free (ref->location);
    g_free (ref);
  }
  g_list_free (references);

  GST_INFO_OBJECT (qtdemux, "posting redirect message: %" GST_PTR_FORMAT, s);
  msg = gst_message_new_element (GST_OBJECT_CAST (qtdemux), s);
  gst_element_post_message (GST_ELEMENT_CAST (qtdemux), msg);
  qtdemux->posted_redirect = TRUE;
}

/* look for redirect nodes, collect all redirect information and
 * process it.
 */
static gboolean
qtdemux_parse_redirects (GstQTDemux * qtdemux)
{
  GNode *rmra, *rmda, *rdrf;

  rmra = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_rmra);
  if (rmra) {
    GList *redirects = NULL;

    rmda = qtdemux_tree_get_child_by_type (rmra, FOURCC_rmda);
    while (rmda) {
      GstQtReference ref = { NULL, NULL, 0, 0 };
      GNode *rmdr, *rmvc;

      if ((rmdr = qtdemux_tree_get_child_by_type (rmda, FOURCC_rmdr))) {
        ref.min_req_bitrate = QT_UINT32 ((guint8 *) rmdr->data + 12);
        GST_LOG_OBJECT (qtdemux, "data rate atom, required bitrate = %u",
            ref.min_req_bitrate);
      }

      if ((rmvc = qtdemux_tree_get_child_by_type (rmda, FOURCC_rmvc))) {
        guint32 package = QT_FOURCC ((guint8 *) rmvc->data + 12);
        guint version = QT_UINT32 ((guint8 *) rmvc->data + 16);

#ifndef GST_DISABLE_GST_DEBUG
        guint bitmask = QT_UINT32 ((guint8 *) rmvc->data + 20);
#endif
        guint check_type = QT_UINT16 ((guint8 *) rmvc->data + 24);

        GST_LOG_OBJECT (qtdemux,
            "version check atom [%" GST_FOURCC_FORMAT "], version=0x%08x"
            ", mask=%08x, check_type=%u", GST_FOURCC_ARGS (package), version,
            bitmask, check_type);
        if (package == FOURCC_qtim && check_type == 0) {
          ref.min_req_qt_version = version;
        }
      }

      rdrf = qtdemux_tree_get_child_by_type (rmda, FOURCC_rdrf);
      if (rdrf) {
        guint32 ref_type;
        guint8 *ref_data;
        guint ref_len;

        ref_len = QT_UINT32 ((guint8 *) rdrf->data);
        if (ref_len > 20) {
          ref_type = QT_FOURCC ((guint8 *) rdrf->data + 12);
          ref_data = (guint8 *) rdrf->data + 20;
          if (ref_type == FOURCC_alis) {
            guint record_len, record_version, fn_len;

            if (ref_len > 70) {
              /* MacOSX alias record, google for alias-layout.txt */
              record_len = QT_UINT16 (ref_data + 4);
              record_version = QT_UINT16 (ref_data + 4 + 2);
              fn_len = QT_UINT8 (ref_data + 50);
              if (record_len > 50 && record_version == 2 && fn_len > 0) {
                ref.location = g_strndup ((gchar *) ref_data + 51, fn_len);
              }
            } else {
              GST_WARNING_OBJECT (qtdemux, "Invalid rdrf/alis size (%u < 70)",
                  ref_len);
            }
          } else if (ref_type == FOURCC_url_) {
            ref.location = g_strndup ((gchar *) ref_data, ref_len - 8);
          } else {
            GST_DEBUG_OBJECT (qtdemux,
                "unknown rdrf reference type %" GST_FOURCC_FORMAT,
                GST_FOURCC_ARGS (ref_type));
          }
          if (ref.location != NULL) {
            GST_INFO_OBJECT (qtdemux, "New location: %s", ref.location);
            redirects =
                g_list_prepend (redirects, g_memdup (&ref, sizeof (ref)));
          } else {
            GST_WARNING_OBJECT (qtdemux,
                "Failed to extract redirect location from rdrf atom");
          }
        } else {
          GST_WARNING_OBJECT (qtdemux, "Invalid rdrf size (%u < 20)", ref_len);
        }
      }

      /* look for others */
      rmda = qtdemux_tree_get_sibling_by_type (rmda, FOURCC_rmda);
    }

    if (redirects != NULL) {
      qtdemux_process_redirects (qtdemux, redirects);
    }
  }
  return TRUE;
}

static GstTagList *
qtdemux_add_container_format (GstQTDemux * qtdemux, GstTagList * tags)
{
  const gchar *fmt;

  if (tags == NULL) {
    tags = gst_tag_list_new_empty ();
    gst_tag_list_set_scope (tags, GST_TAG_SCOPE_GLOBAL);
  }

  if (qtdemux->major_brand == FOURCC_mjp2)
    fmt = "Motion JPEG 2000";
  else if ((qtdemux->major_brand & 0xffff) == FOURCC_3g__)
    fmt = "3GP";
  else if (qtdemux->major_brand == FOURCC_qt__)
    fmt = "Quicktime";
  else if (qtdemux->fragmented)
    fmt = "ISO fMP4";
  else
    fmt = "ISO MP4/M4A";

  GST_LOG_OBJECT (qtdemux, "mapped %" GST_FOURCC_FORMAT " to '%s'",
      GST_FOURCC_ARGS (qtdemux->major_brand), fmt);

  gst_tag_list_add (tags, GST_TAG_MERGE_REPLACE, GST_TAG_CONTAINER_FORMAT,
      fmt, NULL);

  return tags;
}

/* we have read th complete moov node now.
 * This function parses all of the relevant info, creates the traks and
 * prepares all data structures for playback
 */
static gboolean
qtdemux_parse_tree (GstQTDemux * qtdemux)
{
  GNode *mvhd;
  GNode *trak;
  GNode *udta;
  GNode *mvex;
  GstClockTime duration;
  GNode *pssh;
  guint64 creation_time;
  GstDateTime *datetime = NULL;
  gint version;

  /* make sure we have a usable taglist */
  if (!qtdemux->tag_list) {
    qtdemux->tag_list = gst_tag_list_new_empty ();
    gst_tag_list_set_scope (qtdemux->tag_list, GST_TAG_SCOPE_GLOBAL);
  } else {
    qtdemux->tag_list = gst_tag_list_make_writable (qtdemux->tag_list);
  }

  mvhd = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_mvhd);
  if (mvhd == NULL) {
    GST_LOG_OBJECT (qtdemux, "No mvhd node found, looking for redirects.");
    return qtdemux_parse_redirects (qtdemux);
  }

  version = QT_UINT8 ((guint8 *) mvhd->data + 8);
  if (version == 1) {
    creation_time = QT_UINT64 ((guint8 *) mvhd->data + 12);
    qtdemux->timescale = QT_UINT32 ((guint8 *) mvhd->data + 28);
    qtdemux->duration = QT_UINT64 ((guint8 *) mvhd->data + 32);
  } else if (version == 0) {
    creation_time = QT_UINT32 ((guint8 *) mvhd->data + 12);
    qtdemux->timescale = QT_UINT32 ((guint8 *) mvhd->data + 20);
    qtdemux->duration = QT_UINT32 ((guint8 *) mvhd->data + 24);
  } else {
    GST_WARNING_OBJECT (qtdemux, "Unhandled mvhd version %d", version);
    return FALSE;
  }

  /* Moving qt creation time (secs since 1904) to unix time */
  if (creation_time != 0) {
    /* Try to use epoch first as it should be faster and more commonly found */
    if (creation_time >= QTDEMUX_SECONDS_FROM_1904_TO_1970) {
      GTimeVal now;

      creation_time -= QTDEMUX_SECONDS_FROM_1904_TO_1970;
      /* some data cleansing sanity */
      g_get_current_time (&now);
      if (now.tv_sec + 24 * 3600 < creation_time) {
        GST_DEBUG_OBJECT (qtdemux, "discarding bogus future creation time");
      } else {
        datetime = gst_date_time_new_from_unix_epoch_utc (creation_time);
      }
    } else {
      GDateTime *base_dt = g_date_time_new_utc (1904, 1, 1, 0, 0, 0);
      GDateTime *dt, *dt_local;

      dt = g_date_time_add_seconds (base_dt, creation_time);
      dt_local = g_date_time_to_local (dt);
      datetime = gst_date_time_new_from_g_date_time (dt_local);

      g_date_time_unref (base_dt);
      g_date_time_unref (dt);
    }
  }
  if (datetime) {
    /* Use KEEP as explicit tags should have a higher priority than mvhd tag */
    gst_tag_list_add (qtdemux->tag_list, GST_TAG_MERGE_KEEP, GST_TAG_DATE_TIME,
        datetime, NULL);
    gst_date_time_unref (datetime);
  }

  GST_INFO_OBJECT (qtdemux, "timescale: %u", qtdemux->timescale);
  GST_INFO_OBJECT (qtdemux, "duration: %" G_GUINT64_FORMAT, qtdemux->duration);

  /* check for fragmented file and get some (default) data */
  mvex = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_mvex);
  if (mvex) {
    GNode *mehd;
    GstByteReader mehd_data;

    /* let track parsing or anyone know weird stuff might happen ... */
    qtdemux->fragmented = TRUE;

    /* compensate for total duration */
    mehd = qtdemux_tree_get_child_by_type_full (mvex, FOURCC_mehd, &mehd_data);
    if (mehd)
      qtdemux_parse_mehd (qtdemux, &mehd_data);
  }

  /* set duration in the segment info */
  gst_qtdemux_get_duration (qtdemux, &duration);
  if (duration) {
    qtdemux->segment.duration = duration;
    /* also do not exceed duration; stop is set that way post seek anyway,
     * and segment activation falls back to duration,
     * whereas loop only checks stop, so let's align this here as well */
    qtdemux->segment.stop = duration;
  }

  /* parse all traks */
  trak = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_trak);
  while (trak) {
    qtdemux_parse_trak (qtdemux, trak);
    /* iterate all siblings */
    trak = qtdemux_tree_get_sibling_by_type (trak, FOURCC_trak);
  }

  if (!qtdemux->tag_list) {
    GST_DEBUG_OBJECT (qtdemux, "new tag list");
    qtdemux->tag_list = gst_tag_list_new_empty ();
    gst_tag_list_set_scope (qtdemux->tag_list, GST_TAG_SCOPE_GLOBAL);
  } else {
    qtdemux->tag_list = gst_tag_list_make_writable (qtdemux->tag_list);
  }

  /* find tags */
  udta = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_udta);
  if (udta) {
    qtdemux_parse_udta (qtdemux, qtdemux->tag_list, udta);
  } else {
    GST_LOG_OBJECT (qtdemux, "No udta node found.");
  }

  /* maybe also some tags in meta box */
  udta = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_meta);
  if (udta) {
    GST_DEBUG_OBJECT (qtdemux, "Parsing meta box for tags.");
    qtdemux_parse_udta (qtdemux, qtdemux->tag_list, udta);
  } else {
    GST_LOG_OBJECT (qtdemux, "No meta node found.");
  }

  /* parse any protection system info */
  pssh = qtdemux_tree_get_child_by_type (qtdemux->moov_node, FOURCC_pssh);
  while (pssh) {
    GST_LOG_OBJECT (qtdemux, "Parsing pssh box.");
    qtdemux_parse_pssh (qtdemux, pssh);
    pssh = qtdemux_tree_get_sibling_by_type (pssh, FOURCC_pssh);
  }

  qtdemux->tag_list = qtdemux_add_container_format (qtdemux, qtdemux->tag_list);

  return TRUE;
}

/* taken from ffmpeg */
static int
read_descr_size (guint8 * ptr, guint8 * end, guint8 ** end_out)
{
  int count = 4;
  int len = 0;

  while (count--) {
    int c;

    if (ptr >= end)
      return -1;

    c = *ptr++;
    len = (len << 7) | (c & 0x7f);
    if (!(c & 0x80))
      break;
  }
  *end_out = ptr;
  return len;
}

/* this can change the codec originally present in @list */
static void
gst_qtdemux_handle_esds (GstQTDemux * qtdemux, QtDemuxStream * stream,
    GNode * esds, GstTagList * list)
{
  int len = QT_UINT32 (esds->data);
  guint8 *ptr = esds->data;
  guint8 *end = ptr + len;
  int tag;
  guint8 *data_ptr = NULL;
  int data_len = 0;
  guint8 object_type_id = 0;
  const char *codec_name = NULL;
  GstCaps *caps = NULL;

  GST_MEMDUMP_OBJECT (qtdemux, "esds", ptr, len);
  ptr += 8;
  GST_DEBUG_OBJECT (qtdemux, "version/flags = %08x", QT_UINT32 (ptr));
  ptr += 4;
  while (ptr + 1 < end) {
    tag = QT_UINT8 (ptr);
    GST_DEBUG_OBJECT (qtdemux, "tag = %02x", tag);
    ptr++;
    len = read_descr_size (ptr, end, &ptr);
    GST_DEBUG_OBJECT (qtdemux, "len = %d", len);

    /* Check the stated amount of data is available for reading */
    if (len < 0 || ptr + len > end)
      break;

    switch (tag) {
      case ES_DESCRIPTOR_TAG:
        GST_DEBUG_OBJECT (qtdemux, "ID %04x", QT_UINT16 (ptr));
        GST_DEBUG_OBJECT (qtdemux, "priority %04x", QT_UINT8 (ptr + 2));
        ptr += 3;
        break;
      case DECODER_CONFIG_DESC_TAG:{
        guint max_bitrate, avg_bitrate;

        object_type_id = QT_UINT8 (ptr);
        max_bitrate = QT_UINT32 (ptr + 5);
        avg_bitrate = QT_UINT32 (ptr + 9);
        GST_DEBUG_OBJECT (qtdemux, "object_type_id %02x", object_type_id);
        GST_DEBUG_OBJECT (qtdemux, "stream_type %02x", QT_UINT8 (ptr + 1));
        GST_DEBUG_OBJECT (qtdemux, "buffer_size_db %02x", QT_UINT24 (ptr + 2));
        GST_DEBUG_OBJECT (qtdemux, "max bitrate %u", max_bitrate);
        GST_DEBUG_OBJECT (qtdemux, "avg bitrate %u", avg_bitrate);
        if (max_bitrate > 0 && max_bitrate < G_MAXUINT32) {
          gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
              GST_TAG_MAXIMUM_BITRATE, max_bitrate, NULL);
        }
        if (avg_bitrate > 0 && avg_bitrate < G_MAXUINT32) {
          gst_tag_list_add (list, GST_TAG_MERGE_REPLACE, GST_TAG_BITRATE,
              avg_bitrate, NULL);
        }
        ptr += 13;
        break;
      }
      case DECODER_SPECIFIC_INFO_TAG:
        GST_MEMDUMP_OBJECT (qtdemux, "data", ptr, len);
        if (object_type_id == 0xe0 && len == 0x40) {
          guint8 *data;
          GstStructure *s;
          guint32 clut[16];
          gint i;

          GST_DEBUG_OBJECT (qtdemux,
              "Have VOBSUB palette. Creating palette event");
          /* move to decConfigDescr data and read palette */
          data = ptr;
          for (i = 0; i < 16; i++) {
            clut[i] = QT_UINT32 (data);
            data += 4;
          }

          s = gst_structure_new ("application/x-gst-dvd", "event",
              G_TYPE_STRING, "dvd-spu-clut-change",
              "clut00", G_TYPE_INT, clut[0], "clut01", G_TYPE_INT, clut[1],
              "clut02", G_TYPE_INT, clut[2], "clut03", G_TYPE_INT, clut[3],
              "clut04", G_TYPE_INT, clut[4], "clut05", G_TYPE_INT, clut[5],
              "clut06", G_TYPE_INT, clut[6], "clut07", G_TYPE_INT, clut[7],
              "clut08", G_TYPE_INT, clut[8], "clut09", G_TYPE_INT, clut[9],
              "clut10", G_TYPE_INT, clut[10], "clut11", G_TYPE_INT, clut[11],
              "clut12", G_TYPE_INT, clut[12], "clut13", G_TYPE_INT, clut[13],
              "clut14", G_TYPE_INT, clut[14], "clut15", G_TYPE_INT, clut[15],
              NULL);

          /* store event and trigger custom processing */
          stream->pending_event =
              gst_event_new_custom (GST_EVENT_CUSTOM_DOWNSTREAM, s);
        } else {
          /* Generic codec_data handler puts it on the caps */
          data_ptr = ptr;
          data_len = len;
        }

        ptr += len;
        break;
      case SL_CONFIG_DESC_TAG:
        GST_DEBUG_OBJECT (qtdemux, "data %02x", QT_UINT8 (ptr));
        ptr += 1;
        break;
      default:
        GST_DEBUG_OBJECT (qtdemux, "Unknown/unhandled descriptor tag %02x",
            tag);
        GST_MEMDUMP_OBJECT (qtdemux, "descriptor data", ptr, len);
        ptr += len;
        break;
    }
  }

  /* object_type_id in the esds atom in mp4a and mp4v tells us which codec is
   * in use, and should also be used to override some other parameters for some
   * codecs. */
  switch (object_type_id) {
    case 0x20:                 /* MPEG-4 */
      /* 4 bytes for the visual_object_sequence_start_code and 1 byte for the
       * profile_and_level_indication */
      if (data_ptr != NULL && data_len >= 5 &&
          GST_READ_UINT32_BE (data_ptr) == 0x000001b0) {
        gst_codec_utils_mpeg4video_caps_set_level_and_profile (stream->caps,
            data_ptr + 4, data_len - 4);
      }
      break;                    /* Nothing special needed here */
    case 0x21:                 /* H.264 */
      codec_name = "H.264 / AVC";
      caps = gst_caps_new_simple ("video/x-h264",
          "stream-format", G_TYPE_STRING, "avc",
          "alignment", G_TYPE_STRING, "au", NULL);
      break;
    case 0x40:                 /* AAC (any) */
    case 0x66:                 /* AAC Main */
    case 0x67:                 /* AAC LC */
    case 0x68:                 /* AAC SSR */
      /* Override channels and rate based on the codec_data, as it's often
       * wrong. */
      /* Only do so for basic setup without HE-AAC extension */
      if (data_ptr && data_len == 2) {
        guint channels, rateindex, rate;

        /* FIXME: add gst_codec_utils_aac_get_{channels|sample_rate}()? */
        channels = (data_ptr[1] & 0x7f) >> 3;
        if (channels > 0 && channels < 7) {
          stream->n_channels = channels;
        } else if (channels == 7) {
          stream->n_channels = 8;
        }

        rateindex = ((data_ptr[0] & 0x7) << 1) | ((data_ptr[1] & 0x80) >> 7);
        rate = gst_codec_utils_aac_get_sample_rate_from_index (rateindex);
        if (rate > 0)
          stream->rate = rate;
      }

      /* Set level and profile if possible */
      if (data_ptr != NULL && data_len >= 2) {
        gst_codec_utils_aac_caps_set_level_and_profile (stream->caps,
            data_ptr, data_len);
      }
      break;
    case 0x60:                 /* MPEG-2, various profiles */
    case 0x61:
    case 0x62:
    case 0x63:
    case 0x64:
    case 0x65:
      codec_name = "MPEG-2 video";
      caps = gst_caps_new_simple ("video/mpeg",
          "mpegversion", G_TYPE_INT, 2,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case 0x69:                 /* MPEG-2 BC audio */
    case 0x6B:                 /* MPEG-1 audio */
      caps = gst_caps_new_simple ("audio/mpeg",
          "mpegversion", G_TYPE_INT, 1, "parsed", G_TYPE_BOOLEAN, TRUE, NULL);
      codec_name = "MPEG-1 audio";
      break;
    case 0x6A:                 /* MPEG-1 */
      codec_name = "MPEG-1 video";
      caps = gst_caps_new_simple ("video/mpeg",
          "mpegversion", G_TYPE_INT, 1,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case 0x6C:                 /* MJPEG */
      caps =
          gst_caps_new_simple ("image/jpeg", "parsed", G_TYPE_BOOLEAN, TRUE,
          NULL);
      codec_name = "Motion-JPEG";
      break;
    case 0x6D:                 /* PNG */
      caps =
          gst_caps_new_simple ("image/png", "parsed", G_TYPE_BOOLEAN, TRUE,
          NULL);
      codec_name = "PNG still images";
      break;
    case 0x6E:                 /* JPEG2000 */
      codec_name = "JPEG-2000";
      caps = gst_caps_new_simple ("image/x-j2c", "fields", G_TYPE_INT, 1, NULL);
      break;
    case 0xA4:                 /* Dirac */
      codec_name = "Dirac";
      caps = gst_caps_new_empty_simple ("video/x-dirac");
      break;
    case 0xA5:                 /* AC3 */
      codec_name = "AC-3 audio";
      caps = gst_caps_new_simple ("audio/x-ac3",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      break;
    case 0xA9:                 /* AC3 */
      codec_name = "DTS audio";
      caps = gst_caps_new_simple ("audio/x-dts",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      break;
    case 0xE1:                 /* QCELP */
      /* QCELP, the codec_data is a riff tag (little endian) with
       * more info (http://ftp.3gpp2.org/TSGC/Working/2003/2003-05-SanDiego/TSG-C-2003-05-San%20Diego/WG1/SWG12/C12-20030512-006%20=%20C12-20030217-015_Draft_Baseline%20Text%20of%20FFMS_R2.doc). */
      caps = gst_caps_new_empty_simple ("audio/qcelp");
      codec_name = "QCELP";
      break;
    default:
      break;
  }

  /* If we have a replacement caps, then change our caps for this stream */
  if (caps) {
    gst_caps_unref (stream->caps);
    stream->caps = caps;
  }

  if (codec_name && list)
    gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
        GST_TAG_AUDIO_CODEC, codec_name, NULL);

  /* Add the codec_data attribute to caps, if we have it */
  if (data_ptr) {
    GstBuffer *buffer;

    buffer = gst_buffer_new_and_alloc (data_len);
    gst_buffer_fill (buffer, 0, data_ptr, data_len);

    GST_DEBUG_OBJECT (qtdemux, "setting codec_data from esds");
    GST_MEMDUMP_OBJECT (qtdemux, "codec_data from esds", data_ptr, data_len);

    gst_caps_set_simple (stream->caps, "codec_data", GST_TYPE_BUFFER,
        buffer, NULL);
    gst_buffer_unref (buffer);
  }

}

#define _codec(name) \
  do { \
    if (codec_name) { \
      *codec_name = g_strdup (name); \
    } \
  } while (0)

static GstCaps *
qtdemux_video_caps (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 fourcc, const guint8 * stsd_data, gchar ** codec_name)
{
  GstCaps *caps = NULL;
  GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;

  switch (fourcc) {
    case GST_MAKE_FOURCC ('p', 'n', 'g', ' '):
      _codec ("PNG still images");
      caps = gst_caps_new_empty_simple ("image/png");
      break;
    case FOURCC_jpeg:
      _codec ("JPEG still images");
      caps =
          gst_caps_new_simple ("image/jpeg", "parsed", G_TYPE_BOOLEAN, TRUE,
          NULL);
      break;
    case GST_MAKE_FOURCC ('m', 'j', 'p', 'a'):
    case GST_MAKE_FOURCC ('A', 'V', 'D', 'J'):
    case GST_MAKE_FOURCC ('M', 'J', 'P', 'G'):
    case GST_MAKE_FOURCC ('d', 'm', 'b', '1'):
      _codec ("Motion-JPEG");
      caps =
          gst_caps_new_simple ("image/jpeg", "parsed", G_TYPE_BOOLEAN, TRUE,
          NULL);
      break;
    case GST_MAKE_FOURCC ('m', 'j', 'p', 'b'):
      _codec ("Motion-JPEG format B");
      caps = gst_caps_new_empty_simple ("video/x-mjpeg-b");
      break;
    case FOURCC_mjp2:
      _codec ("JPEG-2000");
      /* override to what it should be according to spec, avoid palette_data */
      stream->bits_per_sample = 24;
      caps = gst_caps_new_simple ("image/x-j2c", "fields", G_TYPE_INT, 1, NULL);
      break;
    case FOURCC_SVQ3:
      _codec ("Sorensen video v.3");
      caps = gst_caps_new_simple ("video/x-svq",
          "svqversion", G_TYPE_INT, 3, NULL);
      break;
    case GST_MAKE_FOURCC ('s', 'v', 'q', 'i'):
    case GST_MAKE_FOURCC ('S', 'V', 'Q', '1'):
      _codec ("Sorensen video v.1");
      caps = gst_caps_new_simple ("video/x-svq",
          "svqversion", G_TYPE_INT, 1, NULL);
      break;
    case GST_MAKE_FOURCC ('W', 'R', 'A', 'W'):
      caps = gst_caps_new_empty_simple ("video/x-raw");
      gst_caps_set_simple (caps, "format", G_TYPE_STRING, "RGB8P", NULL);
      _codec ("Windows Raw RGB");
      break;
    case FOURCC_raw_:
    {
      guint16 bps;

      bps = QT_UINT16 (stsd_data + 98);
      switch (bps) {
        case 15:
          format = GST_VIDEO_FORMAT_RGB15;
          break;
        case 16:
          format = GST_VIDEO_FORMAT_RGB16;
          break;
        case 24:
          format = GST_VIDEO_FORMAT_RGB;
          break;
        case 32:
          format = GST_VIDEO_FORMAT_ARGB;
          break;
        default:
          /* unknown */
          break;
      }
      break;
    }
    case GST_MAKE_FOURCC ('y', 'v', '1', '2'):
      format = GST_VIDEO_FORMAT_I420;
      break;
    case GST_MAKE_FOURCC ('y', 'u', 'v', '2'):
    case GST_MAKE_FOURCC ('Y', 'u', 'v', '2'):
      format = GST_VIDEO_FORMAT_I420;
      break;
    case FOURCC_2vuy:
    case GST_MAKE_FOURCC ('2', 'V', 'u', 'y'):
      format = GST_VIDEO_FORMAT_UYVY;
      break;
    case GST_MAKE_FOURCC ('v', '3', '0', '8'):
      format = GST_VIDEO_FORMAT_v308;
      break;
    case GST_MAKE_FOURCC ('v', '2', '1', '6'):
      format = GST_VIDEO_FORMAT_v216;
      break;
    case FOURCC_v210:
      format = GST_VIDEO_FORMAT_v210;
      break;
    case GST_MAKE_FOURCC ('r', '2', '1', '0'):
      format = GST_VIDEO_FORMAT_r210;
      break;
      /* Packed YUV 4:4:4 10 bit in 32 bits, complex
         case GST_MAKE_FOURCC ('v', '4', '1', '0'):
         format = GST_VIDEO_FORMAT_v410;
         break;
       */
      /* Packed YUV 4:4:4:4 8 bit in 32 bits
       * but different order than AYUV
       case GST_MAKE_FOURCC ('v', '4', '0', '8'):
       format = GST_VIDEO_FORMAT_v408;
       break;
       */
    case GST_MAKE_FOURCC ('m', 'p', 'e', 'g'):
    case GST_MAKE_FOURCC ('m', 'p', 'g', '1'):
      _codec ("MPEG-1 video");
      caps = gst_caps_new_simple ("video/mpeg", "mpegversion", G_TYPE_INT, 1,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case GST_MAKE_FOURCC ('h', 'd', 'v', '1'): /* HDV 720p30 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '2'): /* HDV 1080i60 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '3'): /* HDV 1080i50 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '4'): /* HDV 720p24 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '5'): /* HDV 720p25 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '6'): /* HDV 1080p24 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '7'): /* HDV 1080p25 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '8'): /* HDV 1080p30 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', '9'): /* HDV 720p60 */
    case GST_MAKE_FOURCC ('h', 'd', 'v', 'a'): /* HDV 720p50 */
    case GST_MAKE_FOURCC ('m', 'x', '5', 'n'): /* MPEG2 IMX NTSC 525/60 50mb/s produced by FCP */
    case GST_MAKE_FOURCC ('m', 'x', '5', 'p'): /* MPEG2 IMX PAL 625/60 50mb/s produced by FCP */
    case GST_MAKE_FOURCC ('m', 'x', '4', 'n'): /* MPEG2 IMX NTSC 525/60 40mb/s produced by FCP */
    case GST_MAKE_FOURCC ('m', 'x', '4', 'p'): /* MPEG2 IMX PAL 625/60 40mb/s produced by FCP */
    case GST_MAKE_FOURCC ('m', 'x', '3', 'n'): /* MPEG2 IMX NTSC 525/60 30mb/s produced by FCP */
    case GST_MAKE_FOURCC ('m', 'x', '3', 'p'): /* MPEG2 IMX PAL 625/50 30mb/s produced by FCP */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '1'): /* XDCAM HD 720p30 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '2'): /* XDCAM HD 1080i60 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '3'): /* XDCAM HD 1080i50 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '4'): /* XDCAM HD 720p24 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '5'): /* XDCAM HD 720p25 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '6'): /* XDCAM HD 1080p24 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '7'): /* XDCAM HD 1080p25 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '8'): /* XDCAM HD 1080p30 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', '9'): /* XDCAM HD 720p60 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'a'): /* XDCAM HD 720p50 35Mb/s */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'b'): /* XDCAM EX 1080i60 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'c'): /* XDCAM EX 1080i50 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'd'): /* XDCAM HD 1080p24 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'e'): /* XDCAM HD 1080p25 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', 'v', 'f'): /* XDCAM HD 1080p30 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', '1'): /* XDCAM HD422 720p30 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', '4'): /* XDCAM HD422 720p24 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', '5'): /* XDCAM HD422 720p25 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', '9'): /* XDCAM HD422 720p60 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'a'): /* XDCAM HD422 720p50 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'b'): /* XDCAM HD422 1080i50 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'c'): /* XDCAM HD422 1080i50 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'd'): /* XDCAM HD422 1080p24 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'e'): /* XDCAM HD422 1080p25 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', '5', 'f'): /* XDCAM HD422 1080p30 50Mb/s CBR */
    case GST_MAKE_FOURCC ('x', 'd', 'h', 'd'): /* XDCAM HD 540p */
    case GST_MAKE_FOURCC ('x', 'd', 'h', '2'): /* XDCAM HD422 540p */
    case GST_MAKE_FOURCC ('A', 'V', 'm', 'p'): /* AVID IMX PAL */
    case GST_MAKE_FOURCC ('m', 'p', 'g', '2'): /* AVID IMX PAL */
    case GST_MAKE_FOURCC ('m', 'p', '2', 'v'): /* AVID IMX PAL */
      _codec ("MPEG-2 video");
      caps = gst_caps_new_simple ("video/mpeg", "mpegversion", G_TYPE_INT, 2,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case GST_MAKE_FOURCC ('g', 'i', 'f', ' '):
      _codec ("GIF still images");
      caps = gst_caps_new_empty_simple ("image/gif");
      break;
    case FOURCC_h263:
    case GST_MAKE_FOURCC ('H', '2', '6', '3'):
    case FOURCC_s263:
    case GST_MAKE_FOURCC ('U', '2', '6', '3'):
      _codec ("H.263");
      /* ffmpeg uses the height/width props, don't know why */
      caps = gst_caps_new_simple ("video/x-h263",
          "variant", G_TYPE_STRING, "itu", NULL);
      break;
    case FOURCC_mp4v:
    case FOURCC_MP4V:
      _codec ("MPEG-4 video");
      caps = gst_caps_new_simple ("video/mpeg", "mpegversion", G_TYPE_INT, 4,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case GST_MAKE_FOURCC ('3', 'i', 'v', 'd'):
    case GST_MAKE_FOURCC ('3', 'I', 'V', 'D'):
      _codec ("Microsoft MPEG-4 4.3");  /* FIXME? */
      caps = gst_caps_new_simple ("video/x-msmpeg",
          "msmpegversion", G_TYPE_INT, 43, NULL);
      break;
    case GST_MAKE_FOURCC ('D', 'I', 'V', '3'):
      _codec ("DivX 3");
      caps = gst_caps_new_simple ("video/x-divx",
          "divxversion", G_TYPE_INT, 3, NULL);
      break;
    case GST_MAKE_FOURCC ('D', 'I', 'V', 'X'):
    case GST_MAKE_FOURCC ('d', 'i', 'v', 'x'):
      _codec ("DivX 4");
      caps = gst_caps_new_simple ("video/x-divx",
          "divxversion", G_TYPE_INT, 4, NULL);
      break;
    case GST_MAKE_FOURCC ('D', 'X', '5', '0'):
      _codec ("DivX 5");
      caps = gst_caps_new_simple ("video/x-divx",
          "divxversion", G_TYPE_INT, 5, NULL);
      break;

    case GST_MAKE_FOURCC ('F', 'F', 'V', '1'):
      _codec ("FFV1");
      caps = gst_caps_new_simple ("video/x-ffv",
          "ffvversion", G_TYPE_INT, 1, NULL);
      break;

    case GST_MAKE_FOURCC ('3', 'I', 'V', '1'):
    case GST_MAKE_FOURCC ('3', 'I', 'V', '2'):
    case GST_MAKE_FOURCC ('X', 'V', 'I', 'D'):
    case GST_MAKE_FOURCC ('x', 'v', 'i', 'd'):
    case FOURCC_FMP4:
    case GST_MAKE_FOURCC ('U', 'M', 'P', '4'):
      caps = gst_caps_new_simple ("video/mpeg",
          "mpegversion", G_TYPE_INT, 4, NULL);
      _codec ("MPEG-4");
      break;

    case GST_MAKE_FOURCC ('c', 'v', 'i', 'd'):
      _codec ("Cinepak");
      caps = gst_caps_new_empty_simple ("video/x-cinepak");
      break;
    case GST_MAKE_FOURCC ('q', 'd', 'r', 'w'):
      _codec ("Apple QuickDraw");
      caps = gst_caps_new_empty_simple ("video/x-qdrw");
      break;
    case GST_MAKE_FOURCC ('r', 'p', 'z', 'a'):
      _codec ("Apple video");
      caps = gst_caps_new_empty_simple ("video/x-apple-video");
      break;
    case FOURCC_H264:
    case FOURCC_avc1:
      _codec ("H.264 / AVC");
      caps = gst_caps_new_simple ("video/x-h264",
          "stream-format", G_TYPE_STRING, "avc",
          "alignment", G_TYPE_STRING, "au", NULL);
      break;
    case FOURCC_avc3:
      _codec ("H.264 / AVC");
      caps = gst_caps_new_simple ("video/x-h264",
          "stream-format", G_TYPE_STRING, "avc3",
          "alignment", G_TYPE_STRING, "au", NULL);
      break;
    case FOURCC_H265:
    case FOURCC_hvc1:
      _codec ("H.265 / HEVC");
      caps = gst_caps_new_simple ("video/x-h265",
          "stream-format", G_TYPE_STRING, "hvc1",
          "alignment", G_TYPE_STRING, "au", NULL);
      break;
    case FOURCC_hev1:
      _codec ("H.265 / HEVC");
      caps = gst_caps_new_simple ("video/x-h265",
          "stream-format", G_TYPE_STRING, "hev1",
          "alignment", G_TYPE_STRING, "au", NULL);
      break;
    case FOURCC_rle_:
      _codec ("Run-length encoding");
      caps = gst_caps_new_simple ("video/x-rle",
          "layout", G_TYPE_STRING, "quicktime", NULL);
      break;
    case FOURCC_WRLE:
      _codec ("Run-length encoding");
      caps = gst_caps_new_simple ("video/x-rle",
          "layout", G_TYPE_STRING, "microsoft", NULL);
      break;
    case GST_MAKE_FOURCC ('I', 'V', '3', '2'):
    case GST_MAKE_FOURCC ('i', 'v', '3', '2'):
      _codec ("Indeo Video 3");
      caps = gst_caps_new_simple ("video/x-indeo",
          "indeoversion", G_TYPE_INT, 3, NULL);
      break;
    case GST_MAKE_FOURCC ('I', 'V', '4', '1'):
    case GST_MAKE_FOURCC ('i', 'v', '4', '1'):
      _codec ("Intel Video 4");
      caps = gst_caps_new_simple ("video/x-indeo",
          "indeoversion", G_TYPE_INT, 4, NULL);
      break;
    case FOURCC_dvcp:
    case FOURCC_dvc_:
    case GST_MAKE_FOURCC ('d', 'v', 's', 'd'):
    case GST_MAKE_FOURCC ('D', 'V', 'S', 'D'):
    case GST_MAKE_FOURCC ('d', 'v', 'c', 's'):
    case GST_MAKE_FOURCC ('D', 'V', 'C', 'S'):
    case GST_MAKE_FOURCC ('d', 'v', '2', '5'):
    case GST_MAKE_FOURCC ('d', 'v', 'p', 'p'):
      _codec ("DV Video");
      caps = gst_caps_new_simple ("video/x-dv", "dvversion", G_TYPE_INT, 25,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case FOURCC_dv5n:          /* DVCPRO50 NTSC */
    case FOURCC_dv5p:          /* DVCPRO50 PAL */
      _codec ("DVCPro50 Video");
      caps = gst_caps_new_simple ("video/x-dv", "dvversion", G_TYPE_INT, 50,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case GST_MAKE_FOURCC ('d', 'v', 'h', '5'): /* DVCPRO HD 50i produced by FCP */
    case GST_MAKE_FOURCC ('d', 'v', 'h', '6'): /* DVCPRO HD 60i produced by FCP */
      _codec ("DVCProHD Video");
      caps = gst_caps_new_simple ("video/x-dv", "dvversion", G_TYPE_INT, 100,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    case GST_MAKE_FOURCC ('s', 'm', 'c', ' '):
      _codec ("Apple Graphics (SMC)");
      caps = gst_caps_new_empty_simple ("video/x-smc");
      break;
    case GST_MAKE_FOURCC ('V', 'P', '3', '1'):
      _codec ("VP3");
      caps = gst_caps_new_empty_simple ("video/x-vp3");
      break;
    case GST_MAKE_FOURCC ('V', 'P', '6', 'F'):
      _codec ("VP6 Flash");
      caps = gst_caps_new_empty_simple ("video/x-vp6-flash");
      break;
    case FOURCC_XiTh:
      _codec ("Theora");
      caps = gst_caps_new_empty_simple ("video/x-theora");
      /* theora uses one byte of padding in the data stream because it does not
       * allow 0 sized packets while theora does */
      stream->padding = 1;
      break;
    case FOURCC_drac:
      _codec ("Dirac");
      caps = gst_caps_new_empty_simple ("video/x-dirac");
      break;
    case GST_MAKE_FOURCC ('t', 'i', 'f', 'f'):
      _codec ("TIFF still images");
      caps = gst_caps_new_empty_simple ("image/tiff");
      break;
    case GST_MAKE_FOURCC ('i', 'c', 'o', 'd'):
      _codec ("Apple Intermediate Codec");
      caps = gst_caps_from_string ("video/x-apple-intermediate-codec");
      break;
    case GST_MAKE_FOURCC ('A', 'V', 'd', 'n'):
      _codec ("AVID DNxHD");
      caps = gst_caps_from_string ("video/x-dnxhd");
      break;
    case FOURCC_VP80:
      _codec ("On2 VP8");
      caps = gst_caps_from_string ("video/x-vp8");
      break;
    case FOURCC_apcs:
      _codec ("Apple ProRes LT");
      caps =
          gst_caps_new_simple ("video/x-prores", "variant", G_TYPE_STRING, "lt",
          NULL);
      break;
    case FOURCC_apch:
      _codec ("Apple ProRes HQ");
      caps =
          gst_caps_new_simple ("video/x-prores", "variant", G_TYPE_STRING, "hq",
          NULL);
      break;
    case FOURCC_apcn:
      _codec ("Apple ProRes");
      caps =
          gst_caps_new_simple ("video/x-prores", "variant", G_TYPE_STRING,
          "standard", NULL);
      break;
    case FOURCC_apco:
      _codec ("Apple ProRes Proxy");
      caps =
          gst_caps_new_simple ("video/x-prores", "variant", G_TYPE_STRING,
          "proxy", NULL);
      break;
    case FOURCC_ap4h:
      _codec ("Apple ProRes 4444");
      caps =
          gst_caps_new_simple ("video/x-prores", "variant", G_TYPE_STRING,
          "4444", NULL);
      break;
    case FOURCC_vc_1:
    case FOURCC_ovc1:
      _codec ("VC-1");
      caps = gst_caps_new_simple ("video/x-wmv",
          "wmvversion", G_TYPE_INT, 3, "format", G_TYPE_STRING, "WVC1", NULL);
      break;
    case GST_MAKE_FOURCC ('k', 'p', 'c', 'd'):
    default:
    {
      char *s, fourstr[5];

      g_snprintf (fourstr, 5, "%" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));
      s = g_strdup_printf ("video/x-gst-fourcc-%s", g_strstrip (fourstr));
      caps = gst_caps_new_empty_simple (s);
      g_free (s);
      break;
    }
  }

  if (format != GST_VIDEO_FORMAT_UNKNOWN) {
    GstVideoInfo info;

    gst_video_info_init (&info);
    gst_video_info_set_format (&info, format, stream->width, stream->height);

    caps = gst_video_info_to_caps (&info);
    *codec_name = gst_pb_utils_get_codec_description (caps);

    /* enable clipping for raw video streams */
    stream->need_clip = TRUE;
  }

  return caps;
}

static GstCaps *
qtdemux_audio_caps (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 fourcc, const guint8 * data, int len, gchar ** codec_name)
{
  GstCaps *caps;
  const GstStructure *s;
  const gchar *name;
  gint endian = 0;
  GstAudioFormat format = 0;
  gint depth;

  GST_DEBUG_OBJECT (qtdemux, "resolve fourcc 0x%08x", GUINT32_TO_BE (fourcc));

  depth = stream->bytes_per_packet * 8;

  switch (fourcc) {
    case GST_MAKE_FOURCC ('N', 'O', 'N', 'E'):
    case FOURCC_raw_:
      /* 8-bit audio is unsigned */
      if (depth == 8)
        format = GST_AUDIO_FORMAT_U8;
      /* otherwise it's signed and big-endian just like 'twos' */
    case FOURCC_twos:
      endian = G_BIG_ENDIAN;
      /* fall-through */
    case FOURCC_sowt:
    {
      gchar *str;

      if (!endian)
        endian = G_LITTLE_ENDIAN;

      if (!format)
        format = gst_audio_format_build_integer (TRUE, endian, depth, depth);

      str = g_strdup_printf ("Raw %d-bit PCM audio", depth);
      _codec (str);
      g_free (str);

      caps = gst_caps_new_simple ("audio/x-raw",
          "format", G_TYPE_STRING, gst_audio_format_to_string (format),
          "layout", G_TYPE_STRING, "interleaved", NULL);
      break;
    }
    case GST_MAKE_FOURCC ('f', 'l', '6', '4'):
      _codec ("Raw 64-bit floating-point audio");
      caps = gst_caps_new_simple ("audio/x-raw",
          "format", G_TYPE_STRING, "F64BE",
          "layout", G_TYPE_STRING, "interleaved", NULL);
      break;
    case GST_MAKE_FOURCC ('f', 'l', '3', '2'):
      _codec ("Raw 32-bit floating-point audio");
      caps = gst_caps_new_simple ("audio/x-raw",
          "format", G_TYPE_STRING, "F32BE",
          "layout", G_TYPE_STRING, "interleaved", NULL);
      break;
    case FOURCC_in24:
      _codec ("Raw 24-bit PCM audio");
      /* we assume BIG ENDIAN, an enda box will tell us to change this to little
       * endian later */
      caps = gst_caps_new_simple ("audio/x-raw",
          "format", G_TYPE_STRING, "S24BE",
          "layout", G_TYPE_STRING, "interleaved", NULL);
      break;
    case GST_MAKE_FOURCC ('i', 'n', '3', '2'):
      _codec ("Raw 32-bit PCM audio");
      caps = gst_caps_new_simple ("audio/x-raw",
          "format", G_TYPE_STRING, "S32BE",
          "layout", G_TYPE_STRING, "interleaved", NULL);
      break;
    case FOURCC_ulaw:
      _codec ("Mu-law audio");
      caps = gst_caps_new_empty_simple ("audio/x-mulaw");
      break;
    case FOURCC_alaw:
      _codec ("A-law audio");
      caps = gst_caps_new_empty_simple ("audio/x-alaw");
      break;
    case 0x0200736d:
    case 0x6d730002:
      _codec ("Microsoft ADPCM");
      /* Microsoft ADPCM-ACM code 2 */
      caps = gst_caps_new_simple ("audio/x-adpcm",
          "layout", G_TYPE_STRING, "microsoft", NULL);
      break;
    case 0x1100736d:
    case 0x6d730011:
      _codec ("DVI/IMA ADPCM");
      caps = gst_caps_new_simple ("audio/x-adpcm",
          "layout", G_TYPE_STRING, "dvi", NULL);
      break;
    case 0x1700736d:
    case 0x6d730017:
      _codec ("DVI/Intel IMA ADPCM");
      /* FIXME DVI/Intel IMA ADPCM/ACM code 17 */
      caps = gst_caps_new_simple ("audio/x-adpcm",
          "layout", G_TYPE_STRING, "quicktime", NULL);
      break;
    case 0x5500736d:
    case 0x6d730055:
      /* MPEG layer 3, CBR only (pre QT4.1) */
    case FOURCC__mp3:
      _codec ("MPEG-1 layer 3");
      /* MPEG layer 3, CBR & VBR (QT4.1 and later) */
      caps = gst_caps_new_simple ("audio/mpeg", "layer", G_TYPE_INT, 3,
          "mpegversion", G_TYPE_INT, 1, NULL);
      break;
    case 0x20736d:
    case GST_MAKE_FOURCC ('e', 'c', '-', '3'):
      _codec ("EAC-3 audio");
      caps = gst_caps_new_simple ("audio/x-eac3",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      stream->sampled = TRUE;
      break;
    case GST_MAKE_FOURCC ('s', 'a', 'c', '3'): // Nero Recode
    case FOURCC_ac_3:
      _codec ("AC-3 audio");
      caps = gst_caps_new_simple ("audio/x-ac3",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      stream->sampled = TRUE;
      break;
    case GST_MAKE_FOURCC ('d', 't', 's', 'c'):
    case GST_MAKE_FOURCC ('D', 'T', 'S', ' '):
      _codec ("DTS audio");
      caps = gst_caps_new_simple ("audio/x-dts",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      stream->sampled = TRUE;
      break;
    case GST_MAKE_FOURCC ('d', 't', 's', 'h'): // DTS-HD
    case GST_MAKE_FOURCC ('d', 't', 's', 'l'): // DTS-HD Lossless
      _codec ("DTS-HD audio");
      caps = gst_caps_new_simple ("audio/x-dts",
          "framed", G_TYPE_BOOLEAN, TRUE, NULL);
      stream->sampled = TRUE;
      break;
    case FOURCC_MAC3:
      _codec ("MACE-3");
      caps = gst_caps_new_simple ("audio/x-mace",
          "maceversion", G_TYPE_INT, 3, NULL);
      break;
    case FOURCC_MAC6:
      _codec ("MACE-6");
      caps = gst_caps_new_simple ("audio/x-mace",
          "maceversion", G_TYPE_INT, 6, NULL);
      break;
    case GST_MAKE_FOURCC ('O', 'g', 'g', 'V'):
      /* ogg/vorbis */
      caps = gst_caps_new_empty_simple ("application/ogg");
      break;
    case GST_MAKE_FOURCC ('d', 'v', 'c', 'a'):
      _codec ("DV audio");
      caps = gst_caps_new_empty_simple ("audio/x-dv");
      break;
    case FOURCC_mp4a:
      _codec ("MPEG-4 AAC audio");
      caps = gst_caps_new_simple ("audio/mpeg",
          "mpegversion", G_TYPE_INT, 4, "framed", G_TYPE_BOOLEAN, TRUE,
          "stream-format", G_TYPE_STRING, "raw", NULL);
      break;
    case GST_MAKE_FOURCC ('Q', 'D', 'M', 'C'):
      _codec ("QDesign Music");
      caps = gst_caps_new_empty_simple ("audio/x-qdm");
      break;
    case FOURCC_QDM2:
      _codec ("QDesign Music v.2");
      /* FIXME: QDesign music version 2 (no constant) */
      if (FALSE && data) {
        caps = gst_caps_new_simple ("audio/x-qdm2",
            "framesize", G_TYPE_INT, QT_UINT32 (data + 52),
            "bitrate", G_TYPE_INT, QT_UINT32 (data + 40),
            "blocksize", G_TYPE_INT, QT_UINT32 (data + 44), NULL);
      } else {
        caps = gst_caps_new_empty_simple ("audio/x-qdm2");
      }
      break;
    case FOURCC_agsm:
      _codec ("GSM audio");
      caps = gst_caps_new_empty_simple ("audio/x-gsm");
      break;
    case FOURCC_samr:
      _codec ("AMR audio");
      caps = gst_caps_new_empty_simple ("audio/AMR");
      break;
    case FOURCC_sawb:
      _codec ("AMR-WB audio");
      caps = gst_caps_new_empty_simple ("audio/AMR-WB");
      break;
    case FOURCC_ima4:
      _codec ("Quicktime IMA ADPCM");
      caps = gst_caps_new_simple ("audio/x-adpcm",
          "layout", G_TYPE_STRING, "quicktime", NULL);
      break;
    case FOURCC_alac:
      _codec ("Apple lossless audio");
      caps = gst_caps_new_empty_simple ("audio/x-alac");
      break;
    case GST_MAKE_FOURCC ('Q', 'c', 'l', 'p'):
      _codec ("QualComm PureVoice");
      caps = gst_caps_from_string ("audio/qcelp");
      break;
    case FOURCC_wma_:
    case FOURCC_owma:
      _codec ("WMA");
      caps = gst_caps_new_empty_simple ("audio/x-wma");
      break;
    case FOURCC_opus:
      _codec ("Opus");
      caps = gst_caps_new_empty_simple ("audio/x-opus");
      break;
    case GST_MAKE_FOURCC ('l', 'p', 'c', 'm'):
    {
      guint32 flags = 0;
      guint32 depth = 0;
      guint32 width = 0;
      GstAudioFormat format;
      enum
      {
        FLAG_IS_FLOAT = 0x1,
        FLAG_IS_BIG_ENDIAN = 0x2,
        FLAG_IS_SIGNED = 0x4,
        FLAG_IS_PACKED = 0x8,
        FLAG_IS_ALIGNED_HIGH = 0x10,
        FLAG_IS_NON_INTERLEAVED = 0x20
      };
      _codec ("Raw LPCM audio");

      if (data && len >= 56) {
        depth = QT_UINT32 (data + 40);
        flags = QT_UINT32 (data + 44);
        width = QT_UINT32 (data + 48) * 8 / stream->n_channels;
      }
      if ((flags & FLAG_IS_FLOAT) == 0) {
        if (depth == 0)
          depth = 16;
        if (width == 0)
          width = 16;
        format = gst_audio_format_build_integer ((flags & FLAG_IS_SIGNED) ?
            TRUE : FALSE, (flags & FLAG_IS_BIG_ENDIAN) ?
            G_BIG_ENDIAN : G_LITTLE_ENDIAN, width, depth);
        caps = gst_caps_new_simple ("audio/x-raw",
            "format", G_TYPE_STRING, gst_audio_format_to_string (format),
            "layout", G_TYPE_STRING, (flags & FLAG_IS_NON_INTERLEAVED) ?
            "non-interleaved" : "interleaved", NULL);
      } else {
        if (width == 0)
          width = 32;
        if (width == 64) {
          if (flags & FLAG_IS_BIG_ENDIAN)
            format = GST_AUDIO_FORMAT_F64BE;
          else
            format = GST_AUDIO_FORMAT_F64LE;
        } else {
          if (flags & FLAG_IS_BIG_ENDIAN)
            format = GST_AUDIO_FORMAT_F32BE;
          else
            format = GST_AUDIO_FORMAT_F32LE;
        }
        caps = gst_caps_new_simple ("audio/x-raw",
            "format", G_TYPE_STRING, gst_audio_format_to_string (format),
            "layout", G_TYPE_STRING, (flags & FLAG_IS_NON_INTERLEAVED) ?
            "non-interleaved" : "interleaved", NULL);
      }
      break;
    }
    case GST_MAKE_FOURCC ('q', 't', 'v', 'r'):
      /* ? */
    default:
    {
      char *s, fourstr[5];

      g_snprintf (fourstr, 5, "%" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));
      s = g_strdup_printf ("audio/x-gst-fourcc-%s", g_strstrip (fourstr));
      caps = gst_caps_new_empty_simple (s);
      g_free (s);
      break;
    }
  }

  if (caps) {
    GstCaps *templ_caps =
        gst_static_pad_template_get_caps (&gst_qtdemux_audiosrc_template);
    GstCaps *intersection = gst_caps_intersect (caps, templ_caps);
    gst_caps_unref (caps);
    gst_caps_unref (templ_caps);
    caps = intersection;
  }

  /* enable clipping for raw audio streams */
  s = gst_caps_get_structure (caps, 0);
  name = gst_structure_get_name (s);
  if (g_str_has_prefix (name, "audio/x-raw")) {
    stream->need_clip = TRUE;
    stream->max_buffer_size = 4096 * stream->bytes_per_frame;
    GST_DEBUG ("setting max buffer size to %d", stream->max_buffer_size);
  }
  return caps;
}

static GstCaps *
qtdemux_sub_caps (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 fourcc, const guint8 * stsd_data, gchar ** codec_name)
{
  GstCaps *caps;

  GST_DEBUG_OBJECT (qtdemux, "resolve fourcc 0x%08x", GUINT32_TO_BE (fourcc));

  switch (fourcc) {
    case FOURCC_mp4s:
      _codec ("DVD subtitle");
      caps = gst_caps_new_empty_simple ("subpicture/x-dvd");
      stream->need_process = TRUE;
      break;
    case FOURCC_text:
      _codec ("Quicktime timed text");
      goto text;
    case FOURCC_tx3g:
      _codec ("3GPP timed text");
    text:
      caps = gst_caps_new_simple ("text/x-raw", "format", G_TYPE_STRING,
          "utf8", NULL);
      /* actual text piece needs to be extracted */
      stream->need_process = TRUE;
      break;
    case FOURCC_stpp:
      _codec ("XML subtitles");
      caps = gst_caps_new_empty_simple ("application/ttml+xml");
      break;
    default:
    {
      char *s, fourstr[5];

      g_snprintf (fourstr, 5, "%" GST_FOURCC_FORMAT, GST_FOURCC_ARGS (fourcc));
      s = g_strdup_printf ("text/x-gst-fourcc-%s", g_strstrip (fourstr));
      caps = gst_caps_new_empty_simple (s);
      g_free (s);
      break;
    }
  }
  return caps;
}

static GstCaps *
qtdemux_generic_caps (GstQTDemux * qtdemux, QtDemuxStream * stream,
    guint32 fourcc, const guint8 * stsd_data, gchar ** codec_name)
{
  GstCaps *caps;

  switch (fourcc) {
    case FOURCC_m1v:
      _codec ("MPEG 1 video");
      caps = gst_caps_new_simple ("video/mpeg", "mpegversion", G_TYPE_INT, 1,
          "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
      break;
    default:
      caps = NULL;
      break;
  }
  return caps;
}

static void
gst_qtdemux_append_protection_system_id (GstQTDemux * qtdemux,
    const gchar * system_id)
{
  gint i;

  if (!qtdemux->protection_system_ids)
    qtdemux->protection_system_ids =
        g_ptr_array_new_with_free_func ((GDestroyNotify) g_free);
  /* Check whether we already have an entry for this system ID. */
  for (i = 0; i < qtdemux->protection_system_ids->len; ++i) {
    const gchar *id = g_ptr_array_index (qtdemux->protection_system_ids, i);
    if (g_ascii_strcasecmp (system_id, id) == 0) {
      return;
    }
  }
  GST_DEBUG_OBJECT (qtdemux, "Adding cenc protection system ID %s", system_id);
  g_ptr_array_add (qtdemux->protection_system_ids, g_ascii_strdown (system_id,
          -1));
}
