matroska: Adds support to muxing/demuxing WMA
[platform/upstream/gst-plugins-good.git] / gst / matroska / matroska-demux.c
1 /* GStreamer Matroska muxer/demuxer
2  * (c) 2003 Ronald Bultje <rbultje@ronald.bitfreak.net>
3  * (c) 2006 Tim-Philipp Müller <tim centricular net>
4  * (c) 2008 Sebastian Dröge <slomo@circular-chaos.org>
5  *
6  * matroska-demux.c: matroska file/stream demuxer
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Library General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Library General Public License for more details.
17  *
18  * You should have received a copy of the GNU Library General Public
19  * License along with this library; if not, write to the
20  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21  * Boston, MA 02111-1307, USA.
22  */
23
24 /* TODO: check CRC32 if present
25  * TODO: there can be a segment after the first segment. Handle like
26  *       chained oggs. Fixes #334082
27  * TODO: Test samples: http://www.matroska.org/samples/matrix/index.html
28  *                     http://samples.mplayerhq.hu/Matroska/
29  * TODO: check if demuxing is done correct for all codecs according to spec
30  * TODO: seeking with incomplete or without CUE
31  */
32
33 /**
34  * SECTION:element-matroskademux
35  *
36  * matroskademux demuxes a Matroska file into the different contained streams.
37  *
38  * <refsect2>
39  * <title>Example launch line</title>
40  * |[
41  * gst-launch -v filesrc location=/path/to/mkv ! matroskademux ! vorbisdec ! audioconvert ! audioresample ! autoaudiosink
42  * ]| This pipeline demuxes a Matroska file and outputs the contained Vorbis audio.
43  * </refsect2>
44  */
45
46
47 #ifdef HAVE_CONFIG_H
48 #include "config.h"
49 #endif
50
51 #include <math.h>
52 #include <string.h>
53
54 /* For AVI compatibility mode
55    and for fourcc stuff */
56 #include <gst/riff/riff-read.h>
57 #include <gst/riff/riff-ids.h>
58 #include <gst/riff/riff-media.h>
59
60 #include <gst/tag/tag.h>
61
62 #include <gst/base/gsttypefindhelper.h>
63
64 #ifdef HAVE_ZLIB
65 #include <zlib.h>
66 #endif
67
68 #ifdef HAVE_BZ2
69 #include <bzlib.h>
70 #endif
71
72 #include "lzo.h"
73
74 #include "matroska-demux.h"
75 #include "matroska-ids.h"
76
77 GST_DEBUG_CATEGORY_STATIC (matroskademux_debug);
78 #define GST_CAT_DEFAULT matroskademux_debug
79
80 #define DEBUG_ELEMENT_START(demux, ebml, element) \
81     GST_DEBUG_OBJECT (demux, "Parsing " element " element at offset %" \
82         G_GUINT64_FORMAT, ebml->offset)
83
84 #define DEBUG_ELEMENT_STOP(demux, ebml, element, ret) \
85     GST_DEBUG_OBJECT (demux, "Parsing " element " element at offset %" \
86         G_GUINT64_FORMAT " finished with '%s'", ebml->offset, \
87         gst_flow_get_name (ret))
88
89 enum
90 {
91   ARG_0,
92   ARG_METADATA,
93   ARG_STREAMINFO
94 };
95
96 static GstStaticPadTemplate sink_templ = GST_STATIC_PAD_TEMPLATE ("sink",
97     GST_PAD_SINK,
98     GST_PAD_ALWAYS,
99     GST_STATIC_CAPS ("video/x-matroska")
100     );
101
102 /* TODO: fill in caps! */
103
104 static GstStaticPadTemplate audio_src_templ =
105 GST_STATIC_PAD_TEMPLATE ("audio_%02d",
106     GST_PAD_SRC,
107     GST_PAD_SOMETIMES,
108     GST_STATIC_CAPS ("ANY")
109     );
110
111 static GstStaticPadTemplate video_src_templ =
112 GST_STATIC_PAD_TEMPLATE ("video_%02d",
113     GST_PAD_SRC,
114     GST_PAD_SOMETIMES,
115     GST_STATIC_CAPS ("ANY")
116     );
117
118 static GstStaticPadTemplate subtitle_src_templ =
119     GST_STATIC_PAD_TEMPLATE ("subtitle_%02d",
120     GST_PAD_SRC,
121     GST_PAD_SOMETIMES,
122     GST_STATIC_CAPS ("text/plain; application/x-ssa; application/x-ass; "
123         "application/x-usf; video/x-dvd-subpicture; "
124         "subpicture/x-pgs; subtitle/x-kate; "
125         "application/x-subtitle-unknown")
126     );
127
128 static GstFlowReturn gst_matroska_demux_parse_contents (GstMatroskaDemux *
129     demux);
130
131 /* element functions */
132 static void gst_matroska_demux_loop (GstPad * pad);
133
134 static gboolean gst_matroska_demux_element_send_event (GstElement * element,
135     GstEvent * event);
136 static gboolean gst_matroska_demux_element_query (GstElement * element,
137     GstQuery * query);
138
139 /* pad functions */
140 static gboolean gst_matroska_demux_sink_activate_pull (GstPad * sinkpad,
141     gboolean active);
142 static gboolean gst_matroska_demux_sink_activate (GstPad * sinkpad);
143
144 static gboolean gst_matroska_demux_handle_seek_event (GstMatroskaDemux * demux,
145     GstPad * pad, GstEvent * event);
146 static gboolean gst_matroska_demux_handle_src_event (GstPad * pad,
147     GstEvent * event);
148 static const GstQueryType *gst_matroska_demux_get_src_query_types (GstPad *
149     pad);
150 static gboolean gst_matroska_demux_handle_src_query (GstPad * pad,
151     GstQuery * query);
152
153 static GstStateChangeReturn
154 gst_matroska_demux_change_state (GstElement * element,
155     GstStateChange transition);
156 static void
157 gst_matroska_demux_set_index (GstElement * element, GstIndex * index);
158 static GstIndex *gst_matroska_demux_get_index (GstElement * element);
159
160 /* caps functions */
161 static GstCaps *gst_matroska_demux_video_caps (GstMatroskaTrackVideoContext
162     * videocontext,
163     const gchar * codec_id, guint8 * data, guint size, gchar ** codec_name);
164 static GstCaps *gst_matroska_demux_audio_caps (GstMatroskaTrackAudioContext
165     * audiocontext,
166     const gchar * codec_id, guint8 * data, guint size, gchar ** codec_name);
167 static GstCaps
168     * gst_matroska_demux_subtitle_caps (GstMatroskaTrackSubtitleContext *
169     subtitlecontext, const gchar * codec_id, gpointer data, guint size);
170
171 /* stream methods */
172 static void gst_matroska_demux_reset (GstElement * element);
173
174 GST_BOILERPLATE (GstMatroskaDemux, gst_matroska_demux, GstEbmlRead,
175     GST_TYPE_EBML_READ);
176
177 static void
178 gst_matroska_demux_base_init (gpointer klass)
179 {
180   GstElementClass *element_class = GST_ELEMENT_CLASS (klass);
181
182   gst_element_class_add_pad_template (element_class,
183       gst_static_pad_template_get (&video_src_templ));
184   gst_element_class_add_pad_template (element_class,
185       gst_static_pad_template_get (&audio_src_templ));
186   gst_element_class_add_pad_template (element_class,
187       gst_static_pad_template_get (&subtitle_src_templ));
188   gst_element_class_add_pad_template (element_class,
189       gst_static_pad_template_get (&sink_templ));
190
191   gst_element_class_set_details_simple (element_class, "Matroska demuxer",
192       "Codec/Demuxer",
193       "Demuxes a Matroska Stream into video/audio/subtitles",
194       "Ronald Bultje <rbultje@ronald.bitfreak.net>");
195 }
196
197 static void
198 gst_matroska_demux_finalize (GObject * object)
199 {
200   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (object);
201
202   if (demux->src) {
203     g_ptr_array_free (demux->src, TRUE);
204     demux->src = NULL;
205   }
206
207   G_OBJECT_CLASS (parent_class)->finalize (object);
208 }
209
210 static void
211 gst_matroska_demux_class_init (GstMatroskaDemuxClass * klass)
212 {
213   GObjectClass *gobject_class = (GObjectClass *) klass;
214   GstElementClass *gstelement_class = (GstElementClass *) klass;
215
216   GST_DEBUG_CATEGORY_INIT (matroskademux_debug, "matroskademux", 0,
217       "Matroska demuxer");
218
219   gobject_class->finalize = gst_matroska_demux_finalize;
220
221   gstelement_class->change_state =
222       GST_DEBUG_FUNCPTR (gst_matroska_demux_change_state);
223   gstelement_class->send_event =
224       GST_DEBUG_FUNCPTR (gst_matroska_demux_element_send_event);
225   gstelement_class->query =
226       GST_DEBUG_FUNCPTR (gst_matroska_demux_element_query);
227
228   gstelement_class->set_index =
229       GST_DEBUG_FUNCPTR (gst_matroska_demux_set_index);
230   gstelement_class->get_index =
231       GST_DEBUG_FUNCPTR (gst_matroska_demux_get_index);
232 }
233
234 static void
235 gst_matroska_demux_init (GstMatroskaDemux * demux,
236     GstMatroskaDemuxClass * klass)
237 {
238   demux->sinkpad = gst_pad_new_from_static_template (&sink_templ, "sink");
239   gst_pad_set_activate_function (demux->sinkpad,
240       GST_DEBUG_FUNCPTR (gst_matroska_demux_sink_activate));
241   gst_pad_set_activatepull_function (demux->sinkpad,
242       GST_DEBUG_FUNCPTR (gst_matroska_demux_sink_activate_pull));
243   gst_element_add_pad (GST_ELEMENT (demux), demux->sinkpad);
244   GST_EBML_READ (demux)->sinkpad = demux->sinkpad;
245
246   /* initial stream no. */
247   demux->src = NULL;
248
249   demux->writing_app = NULL;
250   demux->muxing_app = NULL;
251   demux->index = NULL;
252
253   /* finish off */
254   gst_matroska_demux_reset (GST_ELEMENT (demux));
255 }
256
257 static void
258 gst_matroska_track_free (GstMatroskaTrackContext * track)
259 {
260   g_free (track->codec_id);
261   g_free (track->codec_name);
262   g_free (track->name);
263   g_free (track->language);
264   g_free (track->codec_priv);
265   g_free (track->codec_state);
266
267   if (track->encodings != NULL) {
268     int i;
269
270     for (i = 0; i < track->encodings->len; ++i) {
271       GstMatroskaTrackEncoding *enc = &g_array_index (track->encodings,
272           GstMatroskaTrackEncoding,
273           i);
274
275       g_free (enc->comp_settings);
276     }
277     g_array_free (track->encodings, TRUE);
278   }
279
280   if (track->pending_tags)
281     gst_tag_list_free (track->pending_tags);
282
283   if (track->index_table)
284     g_array_free (track->index_table, TRUE);
285
286   g_free (track);
287 }
288
289 /*
290  * Returns the aggregated GstFlowReturn.
291  */
292 static GstFlowReturn
293 gst_matroska_demux_combine_flows (GstMatroskaDemux * demux,
294     GstMatroskaTrackContext * track, GstFlowReturn ret)
295 {
296   guint i;
297
298   /* store the value */
299   track->last_flow = ret;
300
301   /* any other error that is not-linked can be returned right away */
302   if (ret != GST_FLOW_NOT_LINKED)
303     goto done;
304
305   /* only return NOT_LINKED if all other pads returned NOT_LINKED */
306   g_assert (demux->src->len == demux->num_streams);
307   for (i = 0; i < demux->src->len; i++) {
308     GstMatroskaTrackContext *ostream = g_ptr_array_index (demux->src, i);
309
310     if (ostream == NULL)
311       continue;
312
313     ret = ostream->last_flow;
314     /* some other return value (must be SUCCESS but we can return
315      * other values as well) */
316     if (ret != GST_FLOW_NOT_LINKED)
317       goto done;
318   }
319   /* if we get here, all other pads were unlinked and we return
320    * NOT_LINKED then */
321 done:
322   GST_LOG_OBJECT (demux, "combined return %s", gst_flow_get_name (ret));
323   return ret;
324 }
325
326 static void
327 gst_matroska_demux_reset (GstElement * element)
328 {
329   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
330   guint i;
331
332   GST_DEBUG_OBJECT (demux, "Resetting state");
333
334   /* reset input */
335   demux->state = GST_MATROSKA_DEMUX_STATE_START;
336
337   /* clean up existing streams */
338   if (demux->src) {
339     g_assert (demux->src->len == demux->num_streams);
340     for (i = 0; i < demux->src->len; i++) {
341       GstMatroskaTrackContext *context = g_ptr_array_index (demux->src, i);
342
343       if (context->pad != NULL)
344         gst_element_remove_pad (GST_ELEMENT (demux), context->pad);
345
346       gst_caps_replace (&context->caps, NULL);
347       gst_matroska_track_free (context);
348     }
349     g_ptr_array_free (demux->src, TRUE);
350   }
351   demux->src = g_ptr_array_new ();
352
353   demux->num_streams = 0;
354   demux->num_a_streams = 0;
355   demux->num_t_streams = 0;
356   demux->num_v_streams = 0;
357
358   /* reset media info */
359   g_free (demux->writing_app);
360   demux->writing_app = NULL;
361   g_free (demux->muxing_app);
362   demux->muxing_app = NULL;
363
364   /* reset indexes */
365   if (demux->index) {
366     g_array_free (demux->index, TRUE);
367     demux->index = NULL;
368   }
369
370   /* reset timers */
371   demux->clock = NULL;
372   demux->time_scale = 1000000;
373   demux->created = G_MININT64;
374
375   demux->index_parsed = FALSE;
376   demux->tracks_parsed = FALSE;
377   demux->segmentinfo_parsed = FALSE;
378   demux->attachments_parsed = FALSE;
379
380   g_list_foreach (demux->tags_parsed, (GFunc) gst_ebml_level_free, NULL);
381   g_list_free (demux->tags_parsed);
382   demux->tags_parsed = NULL;
383
384   gst_segment_init (&demux->segment, GST_FORMAT_TIME);
385   demux->duration = -1;
386
387   if (demux->close_segment) {
388     gst_event_unref (demux->close_segment);
389     demux->close_segment = NULL;
390   }
391
392   if (demux->new_segment) {
393     gst_event_unref (demux->new_segment);
394     demux->new_segment = NULL;
395   }
396
397   if (demux->element_index) {
398     gst_object_unref (demux->element_index);
399     demux->element_index = NULL;
400   }
401   demux->element_index_writer_id = -1;
402 }
403
404 static gint
405 gst_matroska_demux_stream_from_num (GstMatroskaDemux * demux, guint track_num)
406 {
407   guint n;
408
409   g_assert (demux->src->len == demux->num_streams);
410   for (n = 0; n < demux->src->len; n++) {
411     GstMatroskaTrackContext *context = g_ptr_array_index (demux->src, n);
412
413     if (context->num == track_num) {
414       return n;
415     }
416   }
417
418   if (n == demux->num_streams)
419     GST_WARNING_OBJECT (demux,
420         "Failed to find corresponding pad for tracknum %d", track_num);
421
422   return -1;
423 }
424
425 static gint
426 gst_matroska_demux_encoding_cmp (GstMatroskaTrackEncoding * a,
427     GstMatroskaTrackEncoding * b)
428 {
429   if (b->order > a->order)
430     return 1;
431   else if (b->order < a->order)
432     return -1;
433   else
434     return 0;
435 }
436
437 static gboolean
438 gst_matroska_demux_encoding_order_unique (GArray * encodings, guint64 order)
439 {
440   gint i;
441
442   if (encodings == NULL || encodings->len == 0)
443     return TRUE;
444
445   for (i = 0; i < encodings->len; i++)
446     if (g_array_index (encodings, GstMatroskaTrackEncoding, i).order == order)
447       return FALSE;
448
449   return TRUE;
450 }
451
452 static GstFlowReturn
453 gst_matroska_demux_read_track_encoding (GstMatroskaDemux * demux,
454     GstMatroskaTrackContext * context)
455 {
456   GstMatroskaTrackEncoding enc = { 0, };
457   GstEbmlRead *ebml = GST_EBML_READ (demux);
458   GstFlowReturn ret;
459   guint32 id;
460
461   DEBUG_ELEMENT_START (demux, ebml, "ContentEncoding");
462   /* Set default values */
463   enc.scope = 1;
464   /* All other default values are 0 */
465
466   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
467     DEBUG_ELEMENT_STOP (demux, ebml, "ContentEncoding", ret);
468     return ret;
469   }
470
471   while (ret == GST_FLOW_OK) {
472     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
473       break;
474
475     if (demux->level_up) {
476       demux->level_up--;
477       break;
478     }
479
480     switch (id) {
481       case GST_MATROSKA_ID_CONTENTENCODINGORDER:{
482         guint64 num;
483
484         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
485           break;
486
487         if (!gst_matroska_demux_encoding_order_unique (context->encodings, num)) {
488           GST_ERROR_OBJECT (demux, "ContentEncodingOrder %" G_GUINT64_FORMAT
489               "is not unique for track %d", num, context->num);
490           ret = GST_FLOW_ERROR;
491           break;
492         }
493
494         GST_DEBUG_OBJECT (demux, "ContentEncodingOrder: %" G_GUINT64_FORMAT,
495             num);
496         enc.order = num;
497         break;
498       }
499       case GST_MATROSKA_ID_CONTENTENCODINGSCOPE:{
500         guint64 num;
501
502         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
503           break;
504
505         if (num > 7 && num == 0) {
506           GST_ERROR_OBJECT (demux, "Invalid ContentEncodingScope %"
507               G_GUINT64_FORMAT, num);
508           ret = GST_FLOW_ERROR;
509           break;
510         }
511
512         GST_DEBUG_OBJECT (demux, "ContentEncodingScope: %" G_GUINT64_FORMAT,
513             num);
514         enc.scope = num;
515
516         break;
517       }
518       case GST_MATROSKA_ID_CONTENTENCODINGTYPE:{
519         guint64 num;
520
521         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
522           break;
523
524         if (num > 1) {
525           GST_ERROR_OBJECT (demux, "Invalid ContentEncodingType %"
526               G_GUINT64_FORMAT, num);
527           ret = GST_FLOW_ERROR;
528           break;
529         } else if (num != 0) {
530           GST_ERROR_OBJECT (demux, "Encrypted tracks are not supported yet");
531           ret = GST_FLOW_ERROR;
532           break;
533         }
534         GST_DEBUG_OBJECT (demux, "ContentEncodingType: %" G_GUINT64_FORMAT,
535             num);
536         enc.type = num;
537         break;
538       }
539       case GST_MATROSKA_ID_CONTENTCOMPRESSION:{
540
541         DEBUG_ELEMENT_START (demux, ebml, "ContentCompression");
542
543         if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK)
544           break;
545
546         while (ret == GST_FLOW_OK) {
547           if ((ret = gst_ebml_peek_id (ebml, &demux->level_up,
548                       &id)) != GST_FLOW_OK)
549             break;
550
551           if (demux->level_up) {
552             demux->level_up--;
553             break;
554           }
555
556           switch (id) {
557             case GST_MATROSKA_ID_CONTENTCOMPALGO:{
558               guint64 num;
559
560               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK) {
561                 break;
562               }
563               if (num > 3) {
564                 GST_ERROR_OBJECT (demux, "Invalid ContentCompAlgo %"
565                     G_GUINT64_FORMAT, num);
566                 ret = GST_FLOW_ERROR;
567                 break;
568               }
569               GST_DEBUG_OBJECT (demux, "ContentCompAlgo: %" G_GUINT64_FORMAT,
570                   num);
571               enc.comp_algo = num;
572
573               break;
574             }
575             case GST_MATROSKA_ID_CONTENTCOMPSETTINGS:{
576               guint8 *data;
577               guint64 size;
578
579               if ((ret =
580                       gst_ebml_read_binary (ebml, &id, &data,
581                           &size)) != GST_FLOW_OK) {
582                 break;
583               }
584               enc.comp_settings = data;
585               enc.comp_settings_length = size;
586               GST_DEBUG_OBJECT (demux,
587                   "ContentCompSettings of size %" G_GUINT64_FORMAT, size);
588               break;
589             }
590             default:
591               GST_WARNING_OBJECT (demux,
592                   "Unknown ContentCompression subelement 0x%x - ignoring", id);
593               ret = gst_ebml_read_skip (ebml);
594               break;
595           }
596
597           if (demux->level_up) {
598             demux->level_up--;
599             break;
600           }
601         }
602         DEBUG_ELEMENT_STOP (demux, ebml, "ContentCompression", ret);
603         break;
604       }
605
606       case GST_MATROSKA_ID_CONTENTENCRYPTION:
607         GST_ERROR_OBJECT (demux, "Encrypted tracks not yet supported");
608         gst_ebml_read_skip (ebml);
609         ret = GST_FLOW_ERROR;
610         break;
611       default:
612         GST_WARNING_OBJECT (demux,
613             "Unknown ContentEncoding subelement 0x%x - ignoring", id);
614         ret = gst_ebml_read_skip (ebml);
615         break;
616     }
617
618     if (demux->level_up) {
619       demux->level_up--;
620       break;
621     }
622   }
623
624   DEBUG_ELEMENT_STOP (demux, ebml, "ContentEncoding", ret);
625   if (ret != GST_FLOW_OK && ret != GST_FLOW_UNEXPECTED)
626     return ret;
627
628   /* TODO: Check if the combination of values is valid */
629
630   g_array_append_val (context->encodings, enc);
631
632   return ret;
633 }
634
635 static gboolean
636 gst_matroska_decompress_data (GstMatroskaTrackEncoding * enc,
637     guint8 ** data_out, guint * size_out,
638     GstMatroskaTrackCompressionAlgorithm algo)
639 {
640   guint8 *new_data = NULL;
641   guint new_size = 0;
642
643   guint8 *data = *data_out;
644   guint size = *size_out;
645
646   gboolean ret = TRUE;
647
648   if (algo == GST_MATROSKA_TRACK_COMPRESSION_ALGORITHM_ZLIB) {
649 #ifdef HAVE_ZLIB
650     /* zlib encoded data */
651     z_stream zstream;
652     guint orig_size;
653     int result;
654
655     orig_size = size;
656     zstream.zalloc = (alloc_func) 0;
657     zstream.zfree = (free_func) 0;
658     zstream.opaque = (voidpf) 0;
659     if (inflateInit (&zstream) != Z_OK) {
660       GST_WARNING ("zlib initialization failed.");
661       ret = FALSE;
662       goto out;
663     }
664     zstream.next_in = (Bytef *) data;
665     zstream.avail_in = orig_size;
666     new_size = orig_size;
667     new_data = g_malloc (new_size);
668     zstream.avail_out = new_size;
669     zstream.next_out = (Bytef *) new_data;
670
671     do {
672       result = inflate (&zstream, Z_NO_FLUSH);
673       if (result != Z_OK && result != Z_STREAM_END) {
674         GST_WARNING ("zlib decompression failed.");
675         g_free (new_data);
676         inflateEnd (&zstream);
677         break;
678       }
679       new_size += 4000;
680       new_data = g_realloc (new_data, new_size);
681       zstream.next_out = (Bytef *) (new_data + zstream.total_out);
682       zstream.avail_out += 4000;
683     } while (zstream.avail_in != 0 && result != Z_STREAM_END);
684
685     if (result != Z_STREAM_END) {
686       ret = FALSE;
687       goto out;
688     } else {
689       new_size = zstream.total_out;
690       inflateEnd (&zstream);
691     }
692 #else
693     GST_WARNING ("zlib encoded tracks not supported.");
694     ret = FALSE;
695     goto out;
696 #endif
697   } else if (algo == GST_MATROSKA_TRACK_COMPRESSION_ALGORITHM_BZLIB) {
698 #ifdef HAVE_BZ2
699     /* bzip2 encoded data */
700     bz_stream bzstream;
701     guint orig_size;
702     int result;
703
704     bzstream.bzalloc = NULL;
705     bzstream.bzfree = NULL;
706     bzstream.opaque = NULL;
707     orig_size = size;
708
709     if ((result = BZ2_bzDecompressInit (&bzstream, 0, 0)) != BZ_OK) {
710       GST_WARNING ("bzip2 initialization failed.");
711       ret = FALSE;
712       goto out;
713     }
714
715     bzstream.next_in = (char *) data;
716     bzstream.avail_in = orig_size;
717     new_size = orig_size;
718     new_data = g_malloc (new_size);
719     bzstream.avail_out = new_size;
720     bzstream.next_out = (char *) new_data;
721
722     do {
723       result = BZ2_bzDecompress (&bzstream);
724       if (result != BZ_OK && result != BZ_STREAM_END) {
725         GST_WARNING ("bzip2 decompression failed.");
726         g_free (new_data);
727         BZ2_bzDecompressEnd (&bzstream);
728         break;
729       }
730       new_size += 4000;
731       new_data = g_realloc (new_data, new_size);
732       bzstream.next_out = (char *) (new_data + bzstream.total_out_lo32);
733       bzstream.avail_out += 4000;
734     } while (bzstream.avail_in != 0 && result != BZ_STREAM_END);
735
736     if (result != BZ_STREAM_END) {
737       ret = FALSE;
738       goto out;
739     } else {
740       new_size = bzstream.total_out_lo32;
741       BZ2_bzDecompressEnd (&bzstream);
742     }
743 #else
744     GST_WARNING ("bzip2 encoded tracks not supported.");
745     ret = FALSE;
746     goto out;
747 #endif
748   } else if (algo == GST_MATROSKA_TRACK_COMPRESSION_ALGORITHM_LZO1X) {
749     /* lzo encoded data */
750     int result;
751     int orig_size, out_size;
752
753     orig_size = size;
754     out_size = size;
755     new_size = size;
756     new_data = g_malloc (new_size);
757
758     do {
759       orig_size = size;
760       out_size = new_size;
761
762       result = lzo1x_decode (new_data, &out_size, data, &orig_size);
763
764       if (orig_size > 0) {
765         new_size += 4000;
766         new_data = g_realloc (new_data, new_size);
767       }
768     } while (orig_size > 0 && result == LZO_OUTPUT_FULL);
769
770     new_size -= out_size;
771
772     if (result != LZO_OUTPUT_FULL) {
773       GST_WARNING ("lzo decompression failed");
774       g_free (new_data);
775
776       ret = FALSE;
777       goto out;
778     }
779
780   } else if (algo == GST_MATROSKA_TRACK_COMPRESSION_ALGORITHM_HEADERSTRIP) {
781     /* header stripped encoded data */
782     if (enc->comp_settings_length > 0) {
783       new_data = g_malloc (size + enc->comp_settings_length);
784       new_size = size + enc->comp_settings_length;
785
786       memcpy (new_data, enc->comp_settings, enc->comp_settings_length);
787       memcpy (new_data + enc->comp_settings_length, data, size);
788     }
789   } else {
790     g_assert_not_reached ();
791   }
792
793 out:
794
795   if (!ret) {
796     *data_out = NULL;
797     *size_out = 0;
798   } else {
799     *data_out = new_data;
800     *size_out = new_size;
801   }
802
803   return ret;
804 }
805
806 static gboolean
807 gst_matroska_decode_data (GArray * encodings, guint8 ** data_out,
808     guint * size_out, GstMatroskaTrackEncodingScope scope, gboolean free)
809 {
810   guint8 *data;
811   guint size;
812   gboolean ret = TRUE;
813   gint i;
814
815   g_return_val_if_fail (encodings != NULL, FALSE);
816   g_return_val_if_fail (data_out != NULL && *data_out != NULL, FALSE);
817   g_return_val_if_fail (size_out != NULL, FALSE);
818
819   data = *data_out;
820   size = *size_out;
821
822   for (i = 0; i < encodings->len; i++) {
823     GstMatroskaTrackEncoding *enc =
824         &g_array_index (encodings, GstMatroskaTrackEncoding, i);
825     guint8 *new_data = NULL;
826     guint new_size = 0;
827
828     if ((enc->scope & scope) == 0)
829       continue;
830
831     /* Encryption not supported yet */
832     if (enc->type != 0) {
833       ret = FALSE;
834       break;
835     }
836
837     new_data = data;
838     new_size = size;
839
840     ret =
841         gst_matroska_decompress_data (enc, &new_data, &new_size,
842         enc->comp_algo);
843
844     if (!ret)
845       break;
846
847     if ((data == *data_out && free) || (data != *data_out))
848       g_free (data);
849
850     data = new_data;
851     size = new_size;
852   }
853
854   if (!ret) {
855     if ((data == *data_out && free) || (data != *data_out))
856       g_free (data);
857
858     *data_out = NULL;
859     *size_out = 0;
860   } else {
861     *data_out = data;
862     *size_out = size;
863   }
864
865   return ret;
866 }
867
868 static GstBuffer *
869 gst_matroska_decode_buffer (GstMatroskaTrackContext * context, GstBuffer * buf)
870 {
871   guint8 *data;
872   guint size;
873   GstBuffer *new_buf;
874
875   g_return_val_if_fail (GST_IS_BUFFER (buf), NULL);
876
877   GST_DEBUG ("decoding buffer %p", buf);
878
879   data = GST_BUFFER_DATA (buf);
880   size = GST_BUFFER_SIZE (buf);
881
882   g_return_val_if_fail (data != NULL && size > 0, buf);
883
884   if (gst_matroska_decode_data (context->encodings, &data, &size,
885           GST_MATROSKA_TRACK_ENCODING_SCOPE_FRAME, FALSE)) {
886     new_buf = gst_buffer_new ();
887     GST_BUFFER_MALLOCDATA (new_buf) = (guint8 *) data;
888     GST_BUFFER_DATA (new_buf) = (guint8 *) data;
889     GST_BUFFER_SIZE (new_buf) = size;
890
891     gst_buffer_unref (buf);
892     buf = new_buf;
893
894     return buf;
895   } else {
896     GST_DEBUG ("decode data failed");
897     gst_buffer_unref (buf);
898     return NULL;
899   }
900 }
901
902 static GstFlowReturn
903 gst_matroska_decode_content_encodings (GArray * encodings)
904 {
905   gint i;
906
907   if (encodings == NULL)
908     return GST_FLOW_OK;
909
910   for (i = 0; i < encodings->len; i++) {
911     GstMatroskaTrackEncoding *enc =
912         &g_array_index (encodings, GstMatroskaTrackEncoding, i);
913     GstMatroskaTrackEncoding *enc2;
914     guint8 *data = NULL;
915     guint size;
916
917     if ((enc->scope & GST_MATROSKA_TRACK_ENCODING_SCOPE_NEXT_CONTENT_ENCODING)
918         == 0)
919       continue;
920
921     /* Encryption not supported yet */
922     if (enc->type != 0)
923       return GST_FLOW_ERROR;
924
925     if (i + 1 >= encodings->len)
926       return GST_FLOW_ERROR;
927
928     enc2 = &g_array_index (encodings, GstMatroskaTrackEncoding, i + 1);
929
930     if (enc->comp_settings_length == 0)
931       continue;
932
933     data = enc->comp_settings;
934     size = enc->comp_settings_length;
935
936     if (!gst_matroska_decompress_data (enc, &data, &size, enc->comp_algo))
937       return GST_FLOW_ERROR;
938
939     g_free (enc->comp_settings);
940
941     enc->comp_settings = data;
942     enc->comp_settings_length = size;
943   }
944
945   return GST_FLOW_OK;
946 }
947
948 static GstFlowReturn
949 gst_matroska_demux_read_track_encodings (GstMatroskaDemux * demux,
950     GstMatroskaTrackContext * context)
951 {
952   GstFlowReturn ret;
953   GstEbmlRead *ebml = GST_EBML_READ (demux);
954   guint32 id;
955
956   DEBUG_ELEMENT_START (demux, ebml, "ContentEncodings");
957
958   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
959     DEBUG_ELEMENT_STOP (demux, ebml, "ContentEncodings", ret);
960     return ret;
961   }
962
963   context->encodings =
964       g_array_sized_new (FALSE, FALSE, sizeof (GstMatroskaTrackEncoding), 1);
965
966   while (ret == GST_FLOW_OK) {
967     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
968       break;
969
970     if (demux->level_up) {
971       demux->level_up--;
972       break;
973     }
974
975     switch (id) {
976       case GST_MATROSKA_ID_CONTENTENCODING:
977         ret = gst_matroska_demux_read_track_encoding (demux, context);
978         break;
979       default:
980         GST_WARNING_OBJECT (demux,
981             "Unknown ContentEncodings subelement 0x%x - ignoring", id);
982         ret = gst_ebml_read_skip (ebml);
983         break;
984     }
985
986     if (demux->level_up) {
987       demux->level_up--;
988       break;
989     }
990   }
991
992   DEBUG_ELEMENT_STOP (demux, ebml, "ContentEncodings", ret);
993   if (ret != GST_FLOW_OK && ret != GST_FLOW_UNEXPECTED)
994     return ret;
995
996   /* Sort encodings according to their order */
997   g_array_sort (context->encodings,
998       (GCompareFunc) gst_matroska_demux_encoding_cmp);
999
1000   return gst_matroska_decode_content_encodings (context->encodings);
1001 }
1002
1003 static gboolean
1004 gst_matroska_demux_tracknumber_unique (GstMatroskaDemux * demux, guint64 num)
1005 {
1006   gint i;
1007
1008   g_assert (demux->src->len == demux->num_streams);
1009   for (i = 0; i < demux->src->len; i++) {
1010     GstMatroskaTrackContext *context = g_ptr_array_index (demux->src, i);
1011
1012     if (context->num == num)
1013       return FALSE;
1014   }
1015
1016   return TRUE;
1017 }
1018
1019 static GstFlowReturn
1020 gst_matroska_demux_add_stream (GstMatroskaDemux * demux)
1021 {
1022   GstElementClass *klass = GST_ELEMENT_GET_CLASS (demux);
1023   GstEbmlRead *ebml = GST_EBML_READ (demux);
1024   GstMatroskaTrackContext *context;
1025   GstPadTemplate *templ = NULL;
1026   GstCaps *caps = NULL;
1027   gchar *padname = NULL;
1028   GstFlowReturn ret;
1029   guint32 id;
1030   GstTagList *list = NULL;
1031   gchar *codec = NULL;
1032
1033   DEBUG_ELEMENT_START (demux, ebml, "TrackEntry");
1034
1035   /* start with the master */
1036   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
1037     DEBUG_ELEMENT_STOP (demux, ebml, "TrackEntry", ret);
1038     return ret;
1039   }
1040
1041   /* allocate generic... if we know the type, we'll g_renew()
1042    * with the precise type */
1043   context = g_new0 (GstMatroskaTrackContext, 1);
1044   g_ptr_array_add (demux->src, context);
1045   context->index = demux->num_streams;
1046   context->index_writer_id = -1;
1047   context->type = 0;            /* no type yet */
1048   context->default_duration = 0;
1049   context->pos = 0;
1050   context->set_discont = TRUE;
1051   context->timecodescale = 1.0;
1052   context->flags =
1053       GST_MATROSKA_TRACK_ENABLED | GST_MATROSKA_TRACK_DEFAULT |
1054       GST_MATROSKA_TRACK_LACING;
1055   context->last_flow = GST_FLOW_OK;
1056   demux->num_streams++;
1057   g_assert (demux->src->len == demux->num_streams);
1058
1059   GST_DEBUG_OBJECT (demux, "Stream number %d", context->index);
1060
1061   /* try reading the trackentry headers */
1062   while (ret == GST_FLOW_OK) {
1063     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
1064       break;
1065
1066     if (demux->level_up) {
1067       demux->level_up--;
1068       break;
1069     }
1070
1071     switch (id) {
1072         /* track number (unique stream ID) */
1073       case GST_MATROSKA_ID_TRACKNUMBER:{
1074         guint64 num;
1075
1076         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1077           break;
1078
1079         if (num == 0) {
1080           GST_ERROR_OBJECT (demux, "Invalid TrackNumber 0");
1081           ret = GST_FLOW_ERROR;
1082           break;
1083         } else if (!gst_matroska_demux_tracknumber_unique (demux, num)) {
1084           GST_ERROR_OBJECT (demux, "TrackNumber %" G_GUINT64_FORMAT
1085               " is not unique", num);
1086           ret = GST_FLOW_ERROR;
1087           break;
1088         }
1089
1090         GST_DEBUG_OBJECT (demux, "TrackNumber: %" G_GUINT64_FORMAT, num);
1091         context->num = num;
1092         break;
1093       }
1094         /* track UID (unique identifier) */
1095       case GST_MATROSKA_ID_TRACKUID:{
1096         guint64 num;
1097
1098         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1099           break;
1100
1101         if (num == 0) {
1102           GST_ERROR_OBJECT (demux, "Invalid TrackUID 0");
1103           ret = GST_FLOW_ERROR;
1104           break;
1105         }
1106
1107         GST_DEBUG_OBJECT (demux, "TrackUID: %" G_GUINT64_FORMAT, num);
1108         context->uid = num;
1109         break;
1110       }
1111
1112         /* track type (video, audio, combined, subtitle, etc.) */
1113       case GST_MATROSKA_ID_TRACKTYPE:{
1114         guint64 track_type;
1115
1116         if ((ret = gst_ebml_read_uint (ebml, &id, &track_type)) != GST_FLOW_OK) {
1117           break;
1118         }
1119
1120         if (context->type != 0 && context->type != track_type) {
1121           GST_WARNING_OBJECT (demux,
1122               "More than one tracktype defined in a TrackEntry - skipping");
1123           break;
1124         } else if (track_type < 1 || track_type > 254) {
1125           GST_WARNING_OBJECT (demux, "Invalid TrackType %" G_GUINT64_FORMAT,
1126               track_type);
1127           break;
1128         }
1129
1130         GST_DEBUG_OBJECT (demux, "TrackType: %" G_GUINT64_FORMAT, track_type);
1131
1132         /* ok, so we're actually going to reallocate this thing */
1133         switch (track_type) {
1134           case GST_MATROSKA_TRACK_TYPE_VIDEO:
1135             gst_matroska_track_init_video_context (&context);
1136             break;
1137           case GST_MATROSKA_TRACK_TYPE_AUDIO:
1138             gst_matroska_track_init_audio_context (&context);
1139             break;
1140           case GST_MATROSKA_TRACK_TYPE_SUBTITLE:
1141             gst_matroska_track_init_subtitle_context (&context);
1142             break;
1143           case GST_MATROSKA_TRACK_TYPE_COMPLEX:
1144           case GST_MATROSKA_TRACK_TYPE_LOGO:
1145           case GST_MATROSKA_TRACK_TYPE_BUTTONS:
1146           case GST_MATROSKA_TRACK_TYPE_CONTROL:
1147           default:
1148             GST_WARNING_OBJECT (demux,
1149                 "Unknown or unsupported TrackType %" G_GUINT64_FORMAT,
1150                 track_type);
1151             context->type = 0;
1152             break;
1153         }
1154         g_ptr_array_index (demux->src, demux->num_streams - 1) = context;
1155         break;
1156       }
1157
1158         /* tracktype specific stuff for video */
1159       case GST_MATROSKA_ID_TRACKVIDEO:{
1160         GstMatroskaTrackVideoContext *videocontext;
1161
1162         DEBUG_ELEMENT_START (demux, ebml, "TrackVideo");
1163
1164         if (!gst_matroska_track_init_video_context (&context)) {
1165           GST_WARNING_OBJECT (demux,
1166               "TrackVideo element in non-video track - ignoring track");
1167           ret = GST_FLOW_ERROR;
1168           break;
1169         } else if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
1170           break;
1171         }
1172         videocontext = (GstMatroskaTrackVideoContext *) context;
1173         g_ptr_array_index (demux->src, demux->num_streams - 1) = context;
1174
1175         while (ret == GST_FLOW_OK) {
1176           if ((ret =
1177                   gst_ebml_peek_id (ebml, &demux->level_up,
1178                       &id)) != GST_FLOW_OK)
1179             break;
1180
1181           if (demux->level_up) {
1182             demux->level_up--;
1183             break;
1184           }
1185
1186           switch (id) {
1187               /* Should be one level up but some broken muxers write it here. */
1188             case GST_MATROSKA_ID_TRACKDEFAULTDURATION:{
1189               guint64 num;
1190
1191               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1192                 break;
1193
1194               if (num == 0) {
1195                 GST_WARNING_OBJECT (demux, "Invalid TrackDefaultDuration 0");
1196                 break;
1197               }
1198
1199               GST_DEBUG_OBJECT (demux,
1200                   "TrackDefaultDuration: %" G_GUINT64_FORMAT, num);
1201               context->default_duration = num;
1202               break;
1203             }
1204
1205               /* video framerate */
1206               /* NOTE: This one is here only for backward compatibility.
1207                * Use _TRACKDEFAULDURATION one level up. */
1208             case GST_MATROSKA_ID_VIDEOFRAMERATE:{
1209               gdouble num;
1210
1211               if ((ret = gst_ebml_read_float (ebml, &id, &num)) != GST_FLOW_OK)
1212                 break;
1213
1214               if (num <= 0.0) {
1215                 GST_WARNING_OBJECT (demux, "Invalid TrackVideoFPS %lf", num);
1216                 break;
1217               }
1218
1219               GST_DEBUG_OBJECT (demux, "TrackVideoFrameRate: %lf", num);
1220               if (context->default_duration == 0)
1221                 context->default_duration =
1222                     gst_gdouble_to_guint64 ((gdouble) GST_SECOND * (1.0 / num));
1223               videocontext->default_fps = num;
1224               break;
1225             }
1226
1227               /* width of the size to display the video at */
1228             case GST_MATROSKA_ID_VIDEODISPLAYWIDTH:{
1229               guint64 num;
1230
1231               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1232                 break;
1233
1234               if (num == 0) {
1235                 GST_WARNING_OBJECT (demux, "Invalid TrackVideoDisplayWidth 0");
1236                 break;
1237               }
1238
1239               GST_DEBUG_OBJECT (demux,
1240                   "TrackVideoDisplayWidth: %" G_GUINT64_FORMAT, num);
1241               videocontext->display_width = num;
1242               break;
1243             }
1244
1245               /* height of the size to display the video at */
1246             case GST_MATROSKA_ID_VIDEODISPLAYHEIGHT:{
1247               guint64 num;
1248
1249               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1250                 break;
1251
1252               if (num == 0) {
1253                 GST_WARNING_OBJECT (demux, "Invalid TrackVideoDisplayHeight 0");
1254                 break;
1255               }
1256
1257               GST_DEBUG_OBJECT (demux,
1258                   "TrackVideoDisplayHeight: %" G_GUINT64_FORMAT, num);
1259               videocontext->display_height = num;
1260               break;
1261             }
1262
1263               /* width of the video in the file */
1264             case GST_MATROSKA_ID_VIDEOPIXELWIDTH:{
1265               guint64 num;
1266
1267               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1268                 break;
1269
1270               if (num == 0) {
1271                 GST_WARNING_OBJECT (demux, "Invalid TrackVideoPixelWidth 0");
1272                 break;
1273               }
1274
1275               GST_DEBUG_OBJECT (demux,
1276                   "TrackVideoPixelWidth: %" G_GUINT64_FORMAT, num);
1277               videocontext->pixel_width = num;
1278               break;
1279             }
1280
1281               /* height of the video in the file */
1282             case GST_MATROSKA_ID_VIDEOPIXELHEIGHT:{
1283               guint64 num;
1284
1285               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1286                 break;
1287
1288               if (num == 0) {
1289                 GST_WARNING_OBJECT (demux, "Invalid TrackVideoPixelHeight 0");
1290                 break;
1291               }
1292
1293               GST_DEBUG_OBJECT (demux,
1294                   "TrackVideoPixelHeight: %" G_GUINT64_FORMAT, num);
1295               videocontext->pixel_height = num;
1296               break;
1297             }
1298
1299               /* whether the video is interlaced */
1300             case GST_MATROSKA_ID_VIDEOFLAGINTERLACED:{
1301               guint64 num;
1302
1303               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1304                 break;
1305
1306               if (num)
1307                 context->flags |= GST_MATROSKA_VIDEOTRACK_INTERLACED;
1308               else
1309                 context->flags &= ~GST_MATROSKA_VIDEOTRACK_INTERLACED;
1310               GST_DEBUG_OBJECT (demux, "TrackVideoInterlaced: %d",
1311                   (context->flags & GST_MATROSKA_VIDEOTRACK_INTERLACED) ? 1 :
1312                   0);
1313               break;
1314             }
1315
1316               /* aspect ratio behaviour */
1317             case GST_MATROSKA_ID_VIDEOASPECTRATIOTYPE:{
1318               guint64 num;
1319
1320               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1321                 break;
1322
1323               if (num != GST_MATROSKA_ASPECT_RATIO_MODE_FREE &&
1324                   num != GST_MATROSKA_ASPECT_RATIO_MODE_KEEP &&
1325                   num != GST_MATROSKA_ASPECT_RATIO_MODE_FIXED) {
1326                 GST_WARNING_OBJECT (demux,
1327                     "Unknown TrackVideoAspectRatioType 0x%x", (guint) num);
1328                 break;
1329               }
1330               GST_DEBUG_OBJECT (demux,
1331                   "TrackVideoAspectRatioType: %" G_GUINT64_FORMAT, num);
1332               videocontext->asr_mode = num;
1333               break;
1334             }
1335
1336               /* colourspace (only matters for raw video) fourcc */
1337             case GST_MATROSKA_ID_VIDEOCOLOURSPACE:{
1338               guint8 *data;
1339               guint64 datalen;
1340
1341               if ((ret =
1342                       gst_ebml_read_binary (ebml, &id, &data,
1343                           &datalen)) != GST_FLOW_OK)
1344                 break;
1345
1346               if (datalen != 4) {
1347                 g_free (data);
1348                 GST_WARNING_OBJECT (demux,
1349                     "Invalid TrackVideoColourSpace length %" G_GUINT64_FORMAT,
1350                     datalen);
1351                 break;
1352               }
1353
1354               memcpy (&videocontext->fourcc, data, 4);
1355               GST_DEBUG_OBJECT (demux,
1356                   "TrackVideoColourSpace: %" GST_FOURCC_FORMAT,
1357                   GST_FOURCC_ARGS (videocontext->fourcc));
1358               g_free (data);
1359               break;
1360             }
1361
1362             default:
1363               GST_WARNING_OBJECT (demux,
1364                   "Unknown TrackVideo subelement 0x%x - ignoring", id);
1365               /* fall through */
1366             case GST_MATROSKA_ID_VIDEOSTEREOMODE:
1367             case GST_MATROSKA_ID_VIDEODISPLAYUNIT:
1368             case GST_MATROSKA_ID_VIDEOPIXELCROPBOTTOM:
1369             case GST_MATROSKA_ID_VIDEOPIXELCROPTOP:
1370             case GST_MATROSKA_ID_VIDEOPIXELCROPLEFT:
1371             case GST_MATROSKA_ID_VIDEOPIXELCROPRIGHT:
1372             case GST_MATROSKA_ID_VIDEOGAMMAVALUE:
1373               ret = gst_ebml_read_skip (ebml);
1374               break;
1375           }
1376
1377           if (demux->level_up) {
1378             demux->level_up--;
1379             break;
1380           }
1381         }
1382
1383         DEBUG_ELEMENT_STOP (demux, ebml, "TrackVideo", ret);
1384         break;
1385       }
1386
1387         /* tracktype specific stuff for audio */
1388       case GST_MATROSKA_ID_TRACKAUDIO:{
1389         GstMatroskaTrackAudioContext *audiocontext;
1390
1391         DEBUG_ELEMENT_START (demux, ebml, "TrackAudio");
1392
1393         if (!gst_matroska_track_init_audio_context (&context)) {
1394           GST_WARNING_OBJECT (demux,
1395               "TrackAudio element in non-audio track - ignoring track");
1396           ret = GST_FLOW_ERROR;
1397           break;
1398         }
1399
1400         if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK)
1401           break;
1402
1403         audiocontext = (GstMatroskaTrackAudioContext *) context;
1404         g_ptr_array_index (demux->src, demux->num_streams - 1) = context;
1405
1406         while (ret == GST_FLOW_OK) {
1407           if ((ret =
1408                   gst_ebml_peek_id (ebml, &demux->level_up,
1409                       &id)) != GST_FLOW_OK)
1410             break;
1411
1412           if (demux->level_up) {
1413             demux->level_up--;
1414             break;
1415           }
1416
1417           switch (id) {
1418               /* samplerate */
1419             case GST_MATROSKA_ID_AUDIOSAMPLINGFREQ:{
1420               gdouble num;
1421
1422               if ((ret = gst_ebml_read_float (ebml, &id, &num)) != GST_FLOW_OK)
1423                 break;
1424
1425
1426               if (num <= 0.0) {
1427                 GST_WARNING_OBJECT (demux,
1428                     "Invalid TrackAudioSamplingFrequency %lf", num);
1429                 break;
1430               }
1431
1432               GST_DEBUG_OBJECT (demux, "TrackAudioSamplingFrequency: %lf", num);
1433               audiocontext->samplerate = num;
1434               break;
1435             }
1436
1437               /* bitdepth */
1438             case GST_MATROSKA_ID_AUDIOBITDEPTH:{
1439               guint64 num;
1440
1441               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1442                 break;
1443
1444               if (num == 0) {
1445                 GST_WARNING_OBJECT (demux, "Invalid TrackAudioBitDepth 0");
1446                 break;
1447               }
1448
1449               GST_DEBUG_OBJECT (demux, "TrackAudioBitDepth: %" G_GUINT64_FORMAT,
1450                   num);
1451               audiocontext->bitdepth = num;
1452               break;
1453             }
1454
1455               /* channels */
1456             case GST_MATROSKA_ID_AUDIOCHANNELS:{
1457               guint64 num;
1458
1459               if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1460                 break;
1461
1462               if (num == 0) {
1463                 GST_WARNING_OBJECT (demux, "Invalid TrackAudioChannels 0");
1464                 break;
1465               }
1466
1467               GST_DEBUG_OBJECT (demux, "TrackAudioChannels: %" G_GUINT64_FORMAT,
1468                   num);
1469               audiocontext->channels = num;
1470               break;
1471             }
1472
1473             default:
1474               GST_WARNING_OBJECT (demux,
1475                   "Unknown TrackAudio subelement 0x%x - ignoring", id);
1476               /* fall through */
1477             case GST_MATROSKA_ID_AUDIOCHANNELPOSITIONS:
1478             case GST_MATROSKA_ID_AUDIOOUTPUTSAMPLINGFREQ:
1479               ret = gst_ebml_read_skip (ebml);
1480               break;
1481           }
1482
1483           if (demux->level_up) {
1484             demux->level_up--;
1485             break;
1486           }
1487         }
1488
1489         DEBUG_ELEMENT_STOP (demux, ebml, "TrackAudio", ret);
1490
1491         break;
1492       }
1493
1494         /* codec identifier */
1495       case GST_MATROSKA_ID_CODECID:{
1496         gchar *text;
1497
1498         if ((ret = gst_ebml_read_ascii (ebml, &id, &text)) != GST_FLOW_OK)
1499           break;
1500
1501         GST_DEBUG_OBJECT (demux, "CodecID: %s", GST_STR_NULL (text));
1502         context->codec_id = text;
1503         break;
1504       }
1505
1506         /* codec private data */
1507       case GST_MATROSKA_ID_CODECPRIVATE:{
1508         guint8 *data;
1509         guint64 size;
1510
1511         if ((ret =
1512                 gst_ebml_read_binary (ebml, &id, &data, &size)) != GST_FLOW_OK)
1513           break;
1514
1515         context->codec_priv = data;
1516         context->codec_priv_size = size;
1517
1518         GST_DEBUG_OBJECT (demux, "CodecPrivate of size %" G_GUINT64_FORMAT,
1519             size);
1520         break;
1521       }
1522
1523         /* name of the codec */
1524       case GST_MATROSKA_ID_CODECNAME:{
1525         gchar *text;
1526
1527         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
1528           break;
1529
1530         GST_DEBUG_OBJECT (demux, "CodecName: %s", GST_STR_NULL (text));
1531         context->codec_name = text;
1532         break;
1533       }
1534
1535         /* name of this track */
1536       case GST_MATROSKA_ID_TRACKNAME:{
1537         gchar *text;
1538
1539         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
1540           break;
1541
1542         context->name = text;
1543         GST_DEBUG_OBJECT (demux, "TrackName: %s", GST_STR_NULL (text));
1544         break;
1545       }
1546
1547         /* language (matters for audio/subtitles, mostly) */
1548       case GST_MATROSKA_ID_TRACKLANGUAGE:{
1549         gchar *text;
1550
1551         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
1552           break;
1553
1554
1555         context->language = text;
1556
1557         /* fre-ca => fre */
1558         if (strlen (context->language) >= 4 && context->language[3] == '-')
1559           context->language[3] = '\0';
1560
1561         GST_DEBUG_OBJECT (demux, "TrackLanguage: %s",
1562             GST_STR_NULL (context->language));
1563         break;
1564       }
1565
1566         /* whether this is actually used */
1567       case GST_MATROSKA_ID_TRACKFLAGENABLED:{
1568         guint64 num;
1569
1570         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1571           break;
1572
1573         if (num)
1574           context->flags |= GST_MATROSKA_TRACK_ENABLED;
1575         else
1576           context->flags &= ~GST_MATROSKA_TRACK_ENABLED;
1577
1578         GST_DEBUG_OBJECT (demux, "TrackEnabled: %d",
1579             (context->flags & GST_MATROSKA_TRACK_ENABLED) ? 1 : 0);
1580         break;
1581       }
1582
1583         /* whether it's the default for this track type */
1584       case GST_MATROSKA_ID_TRACKFLAGDEFAULT:{
1585         guint64 num;
1586
1587         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1588           break;
1589
1590         if (num)
1591           context->flags |= GST_MATROSKA_TRACK_DEFAULT;
1592         else
1593           context->flags &= ~GST_MATROSKA_TRACK_DEFAULT;
1594
1595         GST_DEBUG_OBJECT (demux, "TrackDefault: %d",
1596             (context->flags & GST_MATROSKA_TRACK_ENABLED) ? 1 : 0);
1597         break;
1598       }
1599
1600         /* whether the track must be used during playback */
1601       case GST_MATROSKA_ID_TRACKFLAGFORCED:{
1602         guint64 num;
1603
1604         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1605           break;
1606
1607         if (num)
1608           context->flags |= GST_MATROSKA_TRACK_FORCED;
1609         else
1610           context->flags &= ~GST_MATROSKA_TRACK_FORCED;
1611
1612         GST_DEBUG_OBJECT (demux, "TrackForced: %d",
1613             (context->flags & GST_MATROSKA_TRACK_ENABLED) ? 1 : 0);
1614         break;
1615       }
1616
1617         /* lacing (like MPEG, where blocks don't end/start on frame
1618          * boundaries) */
1619       case GST_MATROSKA_ID_TRACKFLAGLACING:{
1620         guint64 num;
1621
1622         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1623           break;
1624
1625         if (num)
1626           context->flags |= GST_MATROSKA_TRACK_LACING;
1627         else
1628           context->flags &= ~GST_MATROSKA_TRACK_LACING;
1629
1630         GST_DEBUG_OBJECT (demux, "TrackLacing: %d",
1631             (context->flags & GST_MATROSKA_TRACK_ENABLED) ? 1 : 0);
1632         break;
1633       }
1634
1635         /* default length (in time) of one data block in this track */
1636       case GST_MATROSKA_ID_TRACKDEFAULTDURATION:{
1637         guint64 num;
1638
1639         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
1640           break;
1641
1642
1643         if (num == 0) {
1644           GST_WARNING_OBJECT (demux, "Invalid TrackDefaultDuration 0");
1645           break;
1646         }
1647
1648         GST_DEBUG_OBJECT (demux, "TrackDefaultDuration: %" G_GUINT64_FORMAT,
1649             num);
1650         context->default_duration = num;
1651         break;
1652       }
1653
1654       case GST_MATROSKA_ID_CONTENTENCODINGS:{
1655         ret = gst_matroska_demux_read_track_encodings (demux, context);
1656         break;
1657       }
1658
1659       case GST_MATROSKA_ID_TRACKTIMECODESCALE:{
1660         gdouble num;
1661
1662         if ((ret = gst_ebml_read_float (ebml, &id, &num)) != GST_FLOW_OK)
1663           break;
1664
1665         if (num <= 0.0) {
1666           GST_WARNING_OBJECT (demux, "Invalid TrackTimeCodeScale %lf", num);
1667           break;
1668         }
1669
1670         GST_DEBUG_OBJECT (demux, "TrackTimeCodeScale: %lf", num);
1671         context->timecodescale = num;
1672         break;
1673       }
1674
1675       default:
1676         GST_WARNING ("Unknown TrackEntry subelement 0x%x - ignoring", id);
1677         /* pass-through */
1678
1679         /* we ignore these because they're nothing useful (i.e. crap)
1680          * or simply not implemented yet. */
1681       case GST_MATROSKA_ID_TRACKMINCACHE:
1682       case GST_MATROSKA_ID_TRACKMAXCACHE:
1683       case GST_MATROSKA_ID_MAXBLOCKADDITIONID:
1684       case GST_MATROSKA_ID_TRACKATTACHMENTLINK:
1685       case GST_MATROSKA_ID_TRACKOVERLAY:
1686       case GST_MATROSKA_ID_TRACKTRANSLATE:
1687       case GST_MATROSKA_ID_TRACKOFFSET:
1688       case GST_MATROSKA_ID_CODECSETTINGS:
1689       case GST_MATROSKA_ID_CODECINFOURL:
1690       case GST_MATROSKA_ID_CODECDOWNLOADURL:
1691       case GST_MATROSKA_ID_CODECDECODEALL:
1692         ret = gst_ebml_read_skip (ebml);
1693         break;
1694     }
1695
1696     if (demux->level_up) {
1697       demux->level_up--;
1698       break;
1699     }
1700   }
1701
1702   DEBUG_ELEMENT_STOP (demux, ebml, "TrackEntry", ret);
1703
1704   /* Decode codec private data if necessary */
1705   if (context->encodings && context->encodings->len > 0 && context->codec_priv
1706       && context->codec_priv_size > 0) {
1707     if (!gst_matroska_decode_data (context->encodings,
1708             &context->codec_priv, &context->codec_priv_size,
1709             GST_MATROSKA_TRACK_ENCODING_SCOPE_CODEC_DATA, TRUE)) {
1710       GST_WARNING_OBJECT (demux, "Decoding codec private data failed");
1711       ret = GST_FLOW_ERROR;
1712     }
1713   }
1714
1715   if (context->type == 0 || context->codec_id == NULL || (ret != GST_FLOW_OK
1716           && ret != GST_FLOW_UNEXPECTED)) {
1717     if (ret == GST_FLOW_OK || ret == GST_FLOW_UNEXPECTED)
1718       GST_WARNING_OBJECT (ebml, "Unknown stream/codec in track entry header");
1719
1720     demux->num_streams--;
1721     g_ptr_array_remove_index (demux->src, demux->num_streams);
1722     g_assert (demux->src->len == demux->num_streams);
1723     if (context) {
1724       gst_matroska_track_free (context);
1725     }
1726
1727     return ret;
1728   }
1729
1730   /* now create the GStreamer connectivity */
1731   switch (context->type) {
1732     case GST_MATROSKA_TRACK_TYPE_VIDEO:{
1733       GstMatroskaTrackVideoContext *videocontext =
1734           (GstMatroskaTrackVideoContext *) context;
1735
1736       padname = g_strdup_printf ("video_%02d", demux->num_v_streams++);
1737       templ = gst_element_class_get_pad_template (klass, "video_%02d");
1738       caps = gst_matroska_demux_video_caps (videocontext,
1739           context->codec_id,
1740           (guint8 *) context->codec_priv, context->codec_priv_size, &codec);
1741       if (codec) {
1742         list = gst_tag_list_new ();
1743         gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
1744             GST_TAG_VIDEO_CODEC, codec, NULL);
1745         g_free (codec);
1746       }
1747       break;
1748     }
1749
1750     case GST_MATROSKA_TRACK_TYPE_AUDIO:{
1751       GstMatroskaTrackAudioContext *audiocontext =
1752           (GstMatroskaTrackAudioContext *) context;
1753
1754       padname = g_strdup_printf ("audio_%02d", demux->num_a_streams++);
1755       templ = gst_element_class_get_pad_template (klass, "audio_%02d");
1756       caps = gst_matroska_demux_audio_caps (audiocontext,
1757           context->codec_id,
1758           context->codec_priv, context->codec_priv_size, &codec);
1759       if (codec) {
1760         list = gst_tag_list_new ();
1761         gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
1762             GST_TAG_AUDIO_CODEC, codec, NULL);
1763         g_free (codec);
1764       }
1765       break;
1766     }
1767
1768     case GST_MATROSKA_TRACK_TYPE_SUBTITLE:{
1769       GstMatroskaTrackSubtitleContext *subtitlecontext =
1770           (GstMatroskaTrackSubtitleContext *) context;
1771
1772       padname = g_strdup_printf ("subtitle_%02d", demux->num_t_streams++);
1773       templ = gst_element_class_get_pad_template (klass, "subtitle_%02d");
1774       caps = gst_matroska_demux_subtitle_caps (subtitlecontext,
1775           context->codec_id, context->codec_priv, context->codec_priv_size);
1776       break;
1777     }
1778
1779     case GST_MATROSKA_TRACK_TYPE_COMPLEX:
1780     case GST_MATROSKA_TRACK_TYPE_LOGO:
1781     case GST_MATROSKA_TRACK_TYPE_BUTTONS:
1782     case GST_MATROSKA_TRACK_TYPE_CONTROL:
1783     default:
1784       /* we should already have quit by now */
1785       g_assert_not_reached ();
1786   }
1787
1788   if ((context->language == NULL || *context->language == '\0') &&
1789       (context->type == GST_MATROSKA_TRACK_TYPE_AUDIO ||
1790           context->type == GST_MATROSKA_TRACK_TYPE_SUBTITLE)) {
1791     GST_LOG ("stream %d: language=eng (assuming default)", context->index);
1792     context->language = g_strdup ("eng");
1793   }
1794
1795   if (context->language) {
1796     if (!list)
1797       list = gst_tag_list_new ();
1798     gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
1799         GST_TAG_LANGUAGE_CODE, context->language, NULL);
1800   }
1801
1802   if (caps == NULL) {
1803     GST_WARNING_OBJECT (demux, "could not determine caps for stream with "
1804         "codec_id='%s'", context->codec_id);
1805     switch (context->type) {
1806       case GST_MATROSKA_TRACK_TYPE_VIDEO:
1807         caps = gst_caps_new_simple ("video/x-unknown", NULL);
1808         break;
1809       case GST_MATROSKA_TRACK_TYPE_AUDIO:
1810         caps = gst_caps_new_simple ("audio/x-unknown", NULL);
1811         break;
1812       case GST_MATROSKA_TRACK_TYPE_SUBTITLE:
1813         caps = gst_caps_new_simple ("application/x-subtitle-unknown", NULL);
1814         break;
1815       case GST_MATROSKA_TRACK_TYPE_COMPLEX:
1816       default:
1817         caps = gst_caps_new_simple ("application/x-matroska-unknown", NULL);
1818         break;
1819     }
1820     gst_caps_set_simple (caps, "codec-id", G_TYPE_STRING, context->codec_id,
1821         NULL);
1822   }
1823
1824   /* the pad in here */
1825   context->pad = gst_pad_new_from_template (templ, padname);
1826   context->caps = caps;
1827
1828   gst_pad_set_event_function (context->pad,
1829       GST_DEBUG_FUNCPTR (gst_matroska_demux_handle_src_event));
1830   gst_pad_set_query_type_function (context->pad,
1831       GST_DEBUG_FUNCPTR (gst_matroska_demux_get_src_query_types));
1832   gst_pad_set_query_function (context->pad,
1833       GST_DEBUG_FUNCPTR (gst_matroska_demux_handle_src_query));
1834
1835   GST_INFO_OBJECT (demux, "Adding pad '%s' with caps %" GST_PTR_FORMAT,
1836       padname, caps);
1837
1838   context->pending_tags = list;
1839
1840   gst_pad_set_element_private (context->pad, context);
1841
1842   gst_pad_use_fixed_caps (context->pad);
1843   gst_pad_set_caps (context->pad, context->caps);
1844   gst_pad_set_active (context->pad, TRUE);
1845   gst_element_add_pad (GST_ELEMENT (demux), context->pad);
1846
1847   g_free (padname);
1848
1849   /* tadaah! */
1850   return ret;
1851 }
1852
1853 static const GstQueryType *
1854 gst_matroska_demux_get_src_query_types (GstPad * pad)
1855 {
1856   static const GstQueryType query_types[] = {
1857     GST_QUERY_POSITION,
1858     GST_QUERY_DURATION,
1859     GST_QUERY_SEEKING,
1860     0
1861   };
1862
1863   return query_types;
1864 }
1865
1866 static gboolean
1867 gst_matroska_demux_query (GstMatroskaDemux * demux, GstPad * pad,
1868     GstQuery * query)
1869 {
1870   gboolean res = FALSE;
1871   GstMatroskaTrackContext *context = NULL;
1872
1873   if (pad) {
1874     context = gst_pad_get_element_private (pad);
1875   }
1876
1877   switch (GST_QUERY_TYPE (query)) {
1878     case GST_QUERY_POSITION:
1879     {
1880       GstFormat format;
1881
1882       gst_query_parse_position (query, &format, NULL);
1883
1884       if (format == GST_FORMAT_TIME) {
1885         GST_OBJECT_LOCK (demux);
1886         if (context)
1887           gst_query_set_position (query, GST_FORMAT_TIME, context->pos);
1888         else
1889           gst_query_set_position (query, GST_FORMAT_TIME,
1890               demux->segment.last_stop);
1891         GST_OBJECT_UNLOCK (demux);
1892       } else if (format == GST_FORMAT_DEFAULT && context
1893           && context->default_duration) {
1894         GST_OBJECT_LOCK (demux);
1895         gst_query_set_position (query, GST_FORMAT_DEFAULT,
1896             context->pos / context->default_duration);
1897         GST_OBJECT_UNLOCK (demux);
1898       } else {
1899         GST_DEBUG_OBJECT (demux,
1900             "only position query in TIME and DEFAULT format is supported");
1901       }
1902
1903       res = TRUE;
1904       break;
1905     }
1906     case GST_QUERY_DURATION:
1907     {
1908       GstFormat format;
1909
1910       gst_query_parse_duration (query, &format, NULL);
1911
1912       if (format == GST_FORMAT_TIME) {
1913         GST_OBJECT_LOCK (demux);
1914         gst_query_set_duration (query, GST_FORMAT_TIME, demux->duration);
1915         GST_OBJECT_UNLOCK (demux);
1916       } else if (format == GST_FORMAT_DEFAULT && context
1917           && context->default_duration) {
1918         GST_OBJECT_LOCK (demux);
1919         gst_query_set_duration (query, GST_FORMAT_DEFAULT,
1920             demux->duration / context->default_duration);
1921         GST_OBJECT_UNLOCK (demux);
1922       } else {
1923         GST_DEBUG_OBJECT (demux,
1924             "only duration query in TIME and DEFAULT format is supported");
1925       }
1926
1927       res = TRUE;
1928       break;
1929     }
1930
1931     case GST_QUERY_SEEKING:{
1932       GstFormat fmt;
1933
1934       res = TRUE;
1935       gst_query_parse_seeking (query, &fmt, NULL, NULL, NULL);
1936
1937       if (fmt != GST_FORMAT_TIME || !demux->index) {
1938         gst_query_set_seeking (query, fmt, FALSE, -1, -1);
1939       } else {
1940         gst_query_set_seeking (query, GST_FORMAT_TIME, TRUE, 0,
1941             demux->duration);
1942       }
1943
1944       break;
1945     }
1946     default:
1947       res = gst_pad_query_default (pad, query);
1948       break;
1949   }
1950
1951   return res;
1952 }
1953
1954 static gboolean
1955 gst_matroska_demux_element_query (GstElement * element, GstQuery * query)
1956 {
1957   return gst_matroska_demux_query (GST_MATROSKA_DEMUX (element), NULL, query);
1958 }
1959
1960 static gboolean
1961 gst_matroska_demux_handle_src_query (GstPad * pad, GstQuery * query)
1962 {
1963   gboolean ret;
1964   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (gst_pad_get_parent (pad));
1965
1966   ret = gst_matroska_demux_query (demux, pad, query);
1967
1968   gst_object_unref (demux);
1969
1970   return ret;
1971 }
1972
1973 static gint
1974 gst_matroska_index_seek_find (GstMatroskaIndex * i1, GstClockTime * time,
1975     gpointer user_data)
1976 {
1977   if (i1->time < *time)
1978     return -1;
1979   else if (i1->time > *time)
1980     return 1;
1981   else
1982     return 0;
1983 }
1984
1985 static GstMatroskaIndex *
1986 gst_matroskademux_do_index_seek (GstMatroskaDemux * demux,
1987     GstMatroskaTrackContext * track, gint64 seek_pos, gint64 segment_stop,
1988     gboolean keyunit)
1989 {
1990   GstMatroskaIndex *entry = NULL;
1991   GArray *index;
1992
1993   if (!demux->index || !demux->index->len)
1994     return NULL;
1995
1996   /* find entry just before or at the requested position */
1997   if (track && track->index_table)
1998     index = track->index_table;
1999   else
2000     index = demux->index;
2001
2002   entry =
2003       gst_util_array_binary_search (index->data, index->len,
2004       sizeof (GstMatroskaIndex),
2005       (GCompareDataFunc) gst_matroska_index_seek_find, GST_SEARCH_MODE_BEFORE,
2006       &seek_pos, NULL);
2007
2008   if (entry == NULL)
2009     entry = &g_array_index (index, GstMatroskaIndex, 0);
2010
2011   return entry;
2012 }
2013
2014 /* takes ownership of the passed event! */
2015 static gboolean
2016 gst_matroska_demux_send_event (GstMatroskaDemux * demux, GstEvent * event)
2017 {
2018   gboolean ret = TRUE;
2019   gint i;
2020
2021   g_return_val_if_fail (event != NULL, FALSE);
2022
2023   GST_DEBUG_OBJECT (demux, "Sending event of type %s to all source pads",
2024       GST_EVENT_TYPE_NAME (event));
2025
2026   g_assert (demux->src->len == demux->num_streams);
2027   for (i = 0; i < demux->src->len; i++) {
2028     GstMatroskaTrackContext *stream;
2029
2030     stream = g_ptr_array_index (demux->src, i);
2031     gst_event_ref (event);
2032     gst_pad_push_event (stream->pad, event);
2033
2034     if (stream->pending_tags) {
2035       GST_DEBUG_OBJECT (demux, "Sending pending_tags %p for pad %s:%s",
2036           stream->pending_tags, GST_DEBUG_PAD_NAME (stream->pad));
2037       gst_element_found_tags_for_pad (GST_ELEMENT (demux), stream->pad,
2038           stream->pending_tags);
2039       stream->pending_tags = NULL;
2040     }
2041   }
2042   gst_event_unref (event);
2043   return ret;
2044 }
2045
2046 static gboolean
2047 gst_matroska_demux_element_send_event (GstElement * element, GstEvent * event)
2048 {
2049   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
2050   gboolean res;
2051
2052   g_return_val_if_fail (event != NULL, FALSE);
2053
2054   if (GST_EVENT_TYPE (event) == GST_EVENT_SEEK) {
2055     res = gst_matroska_demux_handle_seek_event (demux, NULL, event);
2056   } else {
2057     GST_WARNING_OBJECT (demux, "Unhandled event of type %s",
2058         GST_EVENT_TYPE_NAME (event));
2059     res = FALSE;
2060   }
2061   gst_event_unref (event);
2062   return res;
2063 }
2064
2065 static gboolean
2066 gst_matroska_demux_handle_seek_event (GstMatroskaDemux * demux,
2067     GstPad * pad, GstEvent * event)
2068 {
2069   GstMatroskaIndex *entry = NULL;
2070   GstSeekFlags flags;
2071   GstSeekType cur_type, stop_type;
2072   GstFormat format;
2073   gboolean flush, keyunit;
2074   gdouble rate;
2075   gint64 cur, stop;
2076   gint64 segment_start, segment_stop;
2077   gint i;
2078   GstMatroskaTrackContext *track = NULL;
2079
2080   if (pad)
2081     track = gst_pad_get_element_private (pad);
2082
2083   gst_event_parse_seek (event, &rate, &format, &flags, &cur_type, &cur,
2084       &stop_type, &stop);
2085
2086   /* we can only seek on time */
2087   if (format != GST_FORMAT_TIME) {
2088     GST_DEBUG_OBJECT (demux, "Can only seek on TIME");
2089     return FALSE;
2090   }
2091
2092   /* cannot yet do backwards playback */
2093   if (rate <= 0.0) {
2094     GST_DEBUG_OBJECT (demux, "Can only seek with positive rate");
2095     return FALSE;
2096   }
2097
2098   /* check sanity before we start flushing and all that */
2099   if (cur_type == GST_SEEK_TYPE_SET) {
2100     GST_OBJECT_LOCK (demux);
2101     if ((entry =
2102             gst_matroskademux_do_index_seek (demux, track, cur, -1,
2103                 FALSE)) == NULL) {
2104       GST_DEBUG_OBJECT (demux, "No matching seek entry in index");
2105       GST_OBJECT_UNLOCK (demux);
2106       return FALSE;
2107     }
2108     GST_DEBUG_OBJECT (demux, "Seek position looks sane");
2109     GST_OBJECT_UNLOCK (demux);
2110   }
2111
2112   flush = !!(flags & GST_SEEK_FLAG_FLUSH);
2113   keyunit = !!(flags & GST_SEEK_FLAG_KEY_UNIT);
2114
2115   if (flush) {
2116     GST_DEBUG_OBJECT (demux, "Starting flush");
2117     gst_pad_push_event (demux->sinkpad, gst_event_new_flush_start ());
2118     gst_matroska_demux_send_event (demux, gst_event_new_flush_start ());
2119   } else {
2120     gst_pad_pause_task (demux->sinkpad);
2121   }
2122
2123   /* now grab the stream lock so that streaming cannot continue, for
2124    * non flushing seeks when the element is in PAUSED this could block
2125    * forever. */
2126   GST_PAD_STREAM_LOCK (demux->sinkpad);
2127
2128   GST_OBJECT_LOCK (demux);
2129
2130   /* if nothing configured, play complete file */
2131   if (!GST_CLOCK_TIME_IS_VALID (cur))
2132     cur = 0;
2133   /* prevent some calculations and comparisons involving INVALID */
2134   segment_start = demux->segment.start;
2135   segment_stop = demux->segment.stop;
2136   if (!GST_CLOCK_TIME_IS_VALID (segment_start))
2137     segment_start = 0;
2138
2139   if (cur_type == GST_SEEK_TYPE_SET)
2140     segment_start = cur;
2141   else if (cur_type == GST_SEEK_TYPE_CUR)
2142     segment_start += cur;
2143
2144   if (stop_type == GST_SEEK_TYPE_SET) {
2145     segment_stop = stop;
2146   } else if (stop_type == GST_SEEK_TYPE_CUR) {
2147     if (GST_CLOCK_TIME_IS_VALID (segment_stop)
2148         && GST_CLOCK_TIME_IS_VALID (stop))
2149       segment_stop += stop;
2150     else
2151       segment_stop = -1;
2152   }
2153
2154   GST_DEBUG_OBJECT (demux,
2155       "New segment positions: %" GST_TIME_FORMAT "-%" GST_TIME_FORMAT,
2156       GST_TIME_ARGS (segment_start), GST_TIME_ARGS (segment_stop));
2157
2158   if (entry == NULL)
2159     entry = gst_matroskademux_do_index_seek (demux, track, segment_start,
2160         segment_stop, keyunit);
2161
2162   if (!entry) {
2163     GST_DEBUG_OBJECT (demux, "No matching seek entry in index");
2164     goto seek_error;
2165   }
2166
2167   /* seek (relative to matroska segment) */
2168   if (gst_ebml_read_seek (GST_EBML_READ (demux),
2169           entry->pos + demux->ebml_segment_start) != GST_FLOW_OK) {
2170     GST_DEBUG_OBJECT (demux, "Failed to seek to offset %" G_GUINT64_FORMAT,
2171         entry->pos + demux->ebml_segment_start);
2172     goto seek_error;
2173   }
2174
2175   GST_DEBUG_OBJECT (demux, "Seeked to offset %" G_GUINT64_FORMAT, entry->pos +
2176       demux->ebml_segment_start);
2177
2178   if (keyunit) {
2179     GST_DEBUG_OBJECT (demux, "seek to key unit, adjusting segment start to %"
2180         GST_TIME_FORMAT, GST_TIME_ARGS (entry->time));
2181     segment_start = entry->time;
2182   }
2183
2184   GST_OBJECT_UNLOCK (demux);
2185
2186   if (flush) {
2187     GST_DEBUG_OBJECT (demux, "Stopping flush");
2188     gst_pad_push_event (demux->sinkpad, gst_event_new_flush_stop ());
2189     gst_matroska_demux_send_event (demux, gst_event_new_flush_stop ());
2190   } else if (demux->segment_running) {
2191     GST_DEBUG_OBJECT (demux, "Closing currently running segment");
2192
2193     GST_OBJECT_LOCK (demux);
2194     if (demux->close_segment)
2195       gst_event_unref (demux->close_segment);
2196
2197     demux->close_segment = gst_event_new_new_segment (TRUE,
2198         demux->segment.rate, GST_FORMAT_TIME, demux->segment.start,
2199         demux->segment.last_stop, demux->segment.last_stop);
2200     GST_OBJECT_UNLOCK (demux);
2201   }
2202
2203   GST_OBJECT_LOCK (demux);
2204   GST_DEBUG_OBJECT (demux, "Committing new seek segment");
2205
2206   demux->segment.rate = rate;
2207   demux->segment.flags = flags;
2208
2209   demux->segment.start = segment_start;
2210   demux->segment.stop = segment_stop;
2211
2212   GST_OBJECT_UNLOCK (demux);
2213
2214   /* notify start of new segment */
2215   if (demux->segment.flags & GST_SEEK_FLAG_SEGMENT) {
2216     GstMessage *msg;
2217
2218     msg = gst_message_new_segment_start (GST_OBJECT (demux),
2219         GST_FORMAT_TIME, demux->segment.start);
2220     gst_element_post_message (GST_ELEMENT (demux), msg);
2221   }
2222
2223   GST_OBJECT_LOCK (demux);
2224   if (demux->new_segment)
2225     gst_event_unref (demux->new_segment);
2226   demux->new_segment = gst_event_new_new_segment (FALSE, rate,
2227       GST_FORMAT_TIME, segment_start, segment_stop, segment_start);
2228   GST_OBJECT_UNLOCK (demux);
2229
2230   /* update the time */
2231   g_assert (demux->src->len == demux->num_streams);
2232   for (i = 0; i < demux->src->len; i++) {
2233     GstMatroskaTrackContext *context = g_ptr_array_index (demux->src, i);
2234     context->pos = entry->time;
2235     context->set_discont = TRUE;
2236     context->last_flow = GST_FLOW_OK;
2237   }
2238   demux->segment.last_stop = entry->time;
2239
2240   /* restart our task since it might have been stopped when we did the
2241    * flush. */
2242   demux->segment_running = TRUE;
2243   gst_pad_start_task (demux->sinkpad, (GstTaskFunction) gst_matroska_demux_loop,
2244       demux->sinkpad);
2245
2246   /* streaming can continue now */
2247   GST_PAD_STREAM_UNLOCK (demux->sinkpad);
2248
2249   return TRUE;
2250
2251 seek_error:
2252   {
2253     /* FIXME: shouldn't we either make it a real error or start the task
2254      * function again so that things can continue from where they left off? */
2255     GST_DEBUG_OBJECT (demux, "Got a seek error");
2256     GST_OBJECT_UNLOCK (demux);
2257     GST_PAD_STREAM_UNLOCK (demux->sinkpad);
2258     return FALSE;
2259   }
2260 }
2261
2262 static gboolean
2263 gst_matroska_demux_handle_src_event (GstPad * pad, GstEvent * event)
2264 {
2265   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (gst_pad_get_parent (pad));
2266   gboolean res = TRUE;
2267
2268   switch (GST_EVENT_TYPE (event)) {
2269     case GST_EVENT_SEEK:
2270       res = gst_matroska_demux_handle_seek_event (demux, pad, event);
2271       gst_event_unref (event);
2272       break;
2273
2274       /* events we don't need to handle */
2275     case GST_EVENT_NAVIGATION:
2276     case GST_EVENT_QOS:
2277       gst_event_unref (event);
2278       res = FALSE;
2279       break;
2280
2281     case GST_EVENT_LATENCY:
2282     default:
2283       res = gst_pad_push_event (demux->sinkpad, event);
2284       break;
2285   }
2286
2287   gst_object_unref (demux);
2288
2289   return res;
2290 }
2291
2292 static GstFlowReturn
2293 gst_matroska_demux_init_stream (GstMatroskaDemux * demux)
2294 {
2295   GstEbmlRead *ebml = GST_EBML_READ (demux);
2296   guint32 id;
2297   gchar *doctype;
2298   guint version;
2299   GstFlowReturn ret;
2300
2301   GST_DEBUG_OBJECT (demux, "Init stream");
2302
2303   if ((ret = gst_ebml_read_header (ebml, &doctype, &version)) != GST_FLOW_OK)
2304     return ret;
2305
2306   if (!doctype || strcmp (doctype, "matroska") != 0) {
2307     GST_ELEMENT_ERROR (demux, STREAM, WRONG_TYPE, (NULL),
2308         ("Input is not a matroska stream (doctype=%s)",
2309             doctype ? doctype : "none"));
2310     g_free (doctype);
2311     return GST_FLOW_ERROR;
2312   }
2313   g_free (doctype);
2314   if (version > 2) {
2315     GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL),
2316         ("Demuxer version (2) is too old to read stream version %d", version));
2317     return GST_FLOW_ERROR;
2318   }
2319
2320   /* find segment, must be the next element but search as long as
2321    * we find it anyway */
2322   while (TRUE) {
2323     guint last_level;
2324
2325     if ((ret = gst_ebml_peek_id (ebml, &last_level, &id)) != GST_FLOW_OK) {
2326       GST_DEBUG_OBJECT (demux, "gst_ebml_peek_id() failed!");
2327       return ret;
2328     }
2329
2330     if (id == GST_MATROSKA_ID_SEGMENT)
2331       break;
2332
2333     /* oi! */
2334     GST_WARNING_OBJECT (demux,
2335         "Expected a Segment ID (0x%x), but received 0x%x!",
2336         GST_MATROSKA_ID_SEGMENT, id);
2337
2338     if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
2339       return ret;
2340   }
2341
2342   /* we now have a EBML segment */
2343   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2344     GST_DEBUG_OBJECT (demux, "gst_ebml_read_master() failed!");
2345     return ret;
2346   }
2347
2348   GST_DEBUG_OBJECT (demux, "Found Segment start at offset %" G_GUINT64_FORMAT,
2349       ebml->offset);
2350   /* seeks are from the beginning of the segment,
2351    * after the segment ID/length */
2352   demux->ebml_segment_start = ebml->offset;
2353
2354   return ret;
2355 }
2356
2357 static GstFlowReturn
2358 gst_matroska_demux_parse_tracks (GstMatroskaDemux * demux)
2359 {
2360   GstEbmlRead *ebml = GST_EBML_READ (demux);
2361   GstFlowReturn ret = GST_FLOW_OK;
2362   guint32 id;
2363
2364   DEBUG_ELEMENT_START (demux, ebml, "Tracks");
2365
2366   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2367     DEBUG_ELEMENT_STOP (demux, ebml, "Tracks", ret);
2368     return ret;
2369   }
2370
2371   while (ret == GST_FLOW_OK) {
2372     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2373       break;
2374
2375     if (demux->level_up) {
2376       demux->level_up--;
2377       break;
2378     }
2379
2380     switch (id) {
2381         /* one track within the "all-tracks" header */
2382       case GST_MATROSKA_ID_TRACKENTRY:
2383         ret = gst_matroska_demux_add_stream (demux);
2384         break;
2385
2386       default:
2387         GST_WARNING ("Unknown Track subelement 0x%x - ignoring", id);
2388         ret = gst_ebml_read_skip (ebml);
2389         break;
2390     }
2391
2392     if (demux->level_up) {
2393       demux->level_up--;
2394       break;
2395     }
2396   }
2397   DEBUG_ELEMENT_STOP (demux, ebml, "Tracks", ret);
2398
2399   demux->tracks_parsed = TRUE;
2400
2401   return ret;
2402 }
2403
2404 static GstFlowReturn
2405 gst_matroska_demux_parse_index_cuetrack (GstMatroskaDemux * demux,
2406     guint * nentries)
2407 {
2408   GstEbmlRead *ebml = GST_EBML_READ (demux);
2409   guint32 id;
2410   GstFlowReturn ret;
2411   GstMatroskaIndex idx;
2412
2413   idx.pos = (guint64) - 1;
2414   idx.track = 0;
2415   idx.time = GST_CLOCK_TIME_NONE;
2416   idx.block = 1;
2417
2418   DEBUG_ELEMENT_START (demux, ebml, "CueTrackPositions");
2419
2420   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2421     DEBUG_ELEMENT_STOP (demux, ebml, "CueTrackPositions", ret);
2422     return ret;
2423   }
2424
2425   while (ret == GST_FLOW_OK) {
2426     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2427       break;
2428
2429     if (demux->level_up) {
2430       demux->level_up--;
2431       break;
2432     }
2433
2434     switch (id) {
2435         /* track number */
2436       case GST_MATROSKA_ID_CUETRACK:
2437       {
2438         guint64 num;
2439
2440         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
2441           break;
2442
2443         if (num == 0) {
2444           idx.track = 0;
2445           GST_WARNING_OBJECT (demux, "Invalid CueTrack 0");
2446           break;
2447         }
2448
2449         GST_DEBUG_OBJECT (demux, "CueTrack: %" G_GUINT64_FORMAT, num);
2450         idx.track = num;
2451         break;
2452       }
2453
2454         /* position in file */
2455       case GST_MATROSKA_ID_CUECLUSTERPOSITION:
2456       {
2457         guint64 num;
2458
2459         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
2460           break;
2461
2462         if (num > G_MAXINT64) {
2463           GST_WARNING_OBJECT (demux, "CueClusterPosition %" G_GUINT64_FORMAT
2464               " too large", num);
2465           break;
2466         }
2467
2468         idx.pos = num;
2469         break;
2470       }
2471
2472         /* number of block in the cluster */
2473       case GST_MATROSKA_ID_CUEBLOCKNUMBER:
2474       {
2475         guint64 num;
2476
2477         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
2478           break;
2479
2480         if (num == 0) {
2481           GST_WARNING_OBJECT (demux, "Invalid CueBlockNumber 0");
2482           break;
2483         }
2484
2485         GST_DEBUG_OBJECT (demux, "CueBlockNumber: %" G_GUINT64_FORMAT, num);
2486         idx.block = num;
2487         break;
2488       }
2489
2490       default:
2491         GST_WARNING ("Unknown CueTrackPositions subelement 0x%x - ignoring",
2492             id);
2493         /* fall-through */
2494
2495       case GST_MATROSKA_ID_CUECODECSTATE:
2496       case GST_MATROSKA_ID_CUEREFERENCE:
2497         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
2498           break;
2499         break;
2500     }
2501
2502     if (demux->level_up) {
2503       demux->level_up--;
2504       break;
2505     }
2506   }
2507
2508   DEBUG_ELEMENT_STOP (demux, ebml, "CueTrackPositions", ret);
2509
2510   if ((ret == GST_FLOW_OK || ret == GST_FLOW_UNEXPECTED)
2511       && idx.pos != (guint64) - 1 && idx.track > 0) {
2512     g_array_append_val (demux->index, idx);
2513     (*nentries)++;
2514   } else if (ret == GST_FLOW_OK || ret == GST_FLOW_UNEXPECTED) {
2515     GST_DEBUG_OBJECT (demux, "CueTrackPositions without valid content");
2516   }
2517
2518   return ret;
2519 }
2520
2521 static GstFlowReturn
2522 gst_matroska_demux_parse_index_pointentry (GstMatroskaDemux * demux)
2523 {
2524   GstEbmlRead *ebml = GST_EBML_READ (demux);
2525   guint32 id;
2526   GstFlowReturn ret;
2527   GstClockTime time = GST_CLOCK_TIME_NONE;
2528   guint nentries = 0;
2529
2530   DEBUG_ELEMENT_START (demux, ebml, "CuePoint");
2531
2532   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2533     DEBUG_ELEMENT_STOP (demux, ebml, "CuePoint", ret);
2534     return ret;
2535   }
2536
2537   while (ret == GST_FLOW_OK) {
2538     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2539       break;
2540
2541     if (demux->level_up) {
2542       demux->level_up--;
2543       break;
2544     }
2545
2546     switch (id) {
2547         /* one single index entry ('point') */
2548       case GST_MATROSKA_ID_CUETIME:
2549       {
2550         if ((ret = gst_ebml_read_uint (ebml, &id, &time)) != GST_FLOW_OK)
2551           break;
2552
2553         GST_DEBUG_OBJECT (demux, "CueTime: %" G_GUINT64_FORMAT, time);
2554         time = time * demux->time_scale;
2555         break;
2556       }
2557
2558         /* position in the file + track to which it belongs */
2559       case GST_MATROSKA_ID_CUETRACKPOSITIONS:
2560       {
2561         if ((ret =
2562                 gst_matroska_demux_parse_index_cuetrack (demux,
2563                     &nentries)) != GST_FLOW_OK)
2564           break;
2565         break;
2566       }
2567
2568       default:
2569         GST_WARNING_OBJECT (demux,
2570             "Unknown CuePoint subelement 0x%x - ignoring", id);
2571         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
2572           break;
2573         break;
2574     }
2575
2576     if (demux->level_up) {
2577       demux->level_up--;
2578       break;
2579     }
2580   }
2581
2582   DEBUG_ELEMENT_STOP (demux, ebml, "CuePoint", ret);
2583
2584   if (nentries > 0) {
2585     if (time == GST_CLOCK_TIME_NONE) {
2586       GST_WARNING_OBJECT (demux, "CuePoint without valid time");
2587       g_array_remove_range (demux->index, demux->index->len - nentries,
2588           nentries);
2589     } else {
2590       gint i;
2591
2592       for (i = demux->index->len - nentries; i < demux->index->len; i++) {
2593         GstMatroskaIndex *idx =
2594             &g_array_index (demux->index, GstMatroskaIndex, i);
2595
2596         idx->time = time;
2597         GST_DEBUG_OBJECT (demux, "Index entry: pos=%" G_GUINT64_FORMAT
2598             ", time=%" GST_TIME_FORMAT ", track=%u, block=%u", idx->pos,
2599             GST_TIME_ARGS (idx->time), (guint) idx->track, (guint) idx->block);
2600       }
2601     }
2602   } else {
2603     GST_DEBUG_OBJECT (demux, "Empty CuePoint");
2604   }
2605
2606   return ret;
2607 }
2608
2609 static gint
2610 gst_matroska_index_compare (GstMatroskaIndex * i1, GstMatroskaIndex * i2)
2611 {
2612   if (i1->time < i2->time)
2613     return -1;
2614   else if (i1->time > i2->time)
2615     return 1;
2616   else if (i1->block < i2->block)
2617     return -1;
2618   else if (i1->block > i2->block)
2619     return 1;
2620   else
2621     return 0;
2622 }
2623
2624 static GstFlowReturn
2625 gst_matroska_demux_parse_index (GstMatroskaDemux * demux)
2626 {
2627   GstEbmlRead *ebml = GST_EBML_READ (demux);
2628   guint32 id;
2629   GstFlowReturn ret = GST_FLOW_OK;
2630   guint i;
2631
2632   if (demux->index)
2633     g_array_free (demux->index, TRUE);
2634   demux->index =
2635       g_array_sized_new (FALSE, FALSE, sizeof (GstMatroskaIndex), 128);
2636
2637   DEBUG_ELEMENT_START (demux, ebml, "Cues");
2638
2639   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2640     DEBUG_ELEMENT_STOP (demux, ebml, "Cues", ret);
2641     return ret;
2642   }
2643
2644   while (ret == GST_FLOW_OK) {
2645     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2646       break;
2647
2648     if (demux->level_up) {
2649       demux->level_up--;
2650       break;
2651     }
2652
2653     switch (id) {
2654         /* one single index entry ('point') */
2655       case GST_MATROSKA_ID_POINTENTRY:
2656         ret = gst_matroska_demux_parse_index_pointentry (demux);
2657         break;
2658
2659       default:
2660         GST_WARNING ("Unknown Cues subelement 0x%x - ignoring", id);
2661         ret = gst_ebml_read_skip (ebml);
2662         break;
2663     }
2664
2665     if (demux->level_up) {
2666       demux->level_up--;
2667       break;
2668     }
2669   }
2670   DEBUG_ELEMENT_STOP (demux, ebml, "Cues", ret);
2671
2672   /* Sort index by time, smallest time first, for easier searching */
2673   g_array_sort (demux->index, (GCompareFunc) gst_matroska_index_compare);
2674
2675   /* Now sort the track specific index entries into their own arrays */
2676   for (i = 0; i < demux->index->len; i++) {
2677     GstMatroskaIndex *idx = &g_array_index (demux->index, GstMatroskaIndex, i);
2678     gint track_num;
2679     GstMatroskaTrackContext *ctx;
2680
2681     if (demux->element_index) {
2682       gint writer_id;
2683
2684       if (idx->track != 0 &&
2685           (track_num =
2686               gst_matroska_demux_stream_from_num (demux, idx->track)) != -1) {
2687         ctx = g_ptr_array_index (demux->src, track_num);
2688
2689         if (ctx->index_writer_id == -1)
2690           gst_index_get_writer_id (demux->element_index, GST_OBJECT (ctx->pad),
2691               &ctx->index_writer_id);
2692         writer_id = ctx->index_writer_id;
2693       } else {
2694         if (demux->element_index_writer_id == -1)
2695           gst_index_get_writer_id (demux->element_index, GST_OBJECT (demux),
2696               &demux->element_index_writer_id);
2697         writer_id = demux->element_index_writer_id;
2698       }
2699
2700       GST_LOG_OBJECT (demux, "adding association %" GST_TIME_FORMAT "-> %"
2701           G_GUINT64_FORMAT " for writer id %d", GST_TIME_ARGS (idx->time),
2702           idx->pos, writer_id);
2703       gst_index_add_association (demux->element_index, writer_id,
2704           GST_ASSOCIATION_FLAG_KEY_UNIT, GST_FORMAT_TIME, idx->time,
2705           GST_FORMAT_BYTES, idx->pos + demux->ebml_segment_start, NULL);
2706     }
2707
2708     if (idx->track == 0)
2709       continue;
2710
2711     track_num = gst_matroska_demux_stream_from_num (demux, idx->track);
2712     if (track_num == -1)
2713       continue;
2714
2715     ctx = g_ptr_array_index (demux->src, track_num);
2716
2717     if (ctx->index_table == NULL)
2718       ctx->index_table =
2719           g_array_sized_new (FALSE, FALSE, sizeof (GstMatroskaIndex), 128);
2720
2721     g_array_append_vals (ctx->index_table, idx, 1);
2722   }
2723
2724   demux->index_parsed = TRUE;
2725
2726   return ret;
2727 }
2728
2729 static GstFlowReturn
2730 gst_matroska_demux_parse_info (GstMatroskaDemux * demux)
2731 {
2732   GstEbmlRead *ebml = GST_EBML_READ (demux);
2733   GstFlowReturn ret = GST_FLOW_OK;
2734   guint32 id;
2735
2736   DEBUG_ELEMENT_START (demux, ebml, "SegmentInfo");
2737
2738   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2739     DEBUG_ELEMENT_STOP (demux, ebml, "SegmentInfo", ret);
2740     return ret;
2741   }
2742
2743   while (ret == GST_FLOW_OK) {
2744     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2745       break;
2746
2747     if (demux->level_up) {
2748       demux->level_up--;
2749       break;
2750     }
2751
2752     switch (id) {
2753         /* cluster timecode */
2754       case GST_MATROSKA_ID_TIMECODESCALE:{
2755         guint64 num;
2756
2757         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
2758           break;
2759
2760
2761         GST_DEBUG_OBJECT (demux, "TimeCodeScale: %" G_GUINT64_FORMAT, num);
2762         demux->time_scale = num;
2763         break;
2764       }
2765
2766       case GST_MATROSKA_ID_DURATION:{
2767         gdouble num;
2768         GstClockTime dur;
2769
2770         if ((ret = gst_ebml_read_float (ebml, &id, &num)) != GST_FLOW_OK)
2771           break;
2772
2773         if (num <= 0.0) {
2774           GST_WARNING_OBJECT (demux, "Invalid duration %lf", num);
2775           break;
2776         }
2777
2778         GST_DEBUG_OBJECT (demux, "Duration: %lf", num);
2779
2780         dur = gst_gdouble_to_guint64 (num *
2781             gst_guint64_to_gdouble (demux->time_scale));
2782         if (GST_CLOCK_TIME_IS_VALID (dur) && dur <= G_MAXINT64)
2783           demux->duration = dur;
2784         break;
2785       }
2786
2787       case GST_MATROSKA_ID_WRITINGAPP:{
2788         gchar *text;
2789
2790         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
2791           break;
2792
2793         GST_DEBUG_OBJECT (demux, "WritingApp: %s", GST_STR_NULL (text));
2794         demux->writing_app = text;
2795         break;
2796       }
2797
2798       case GST_MATROSKA_ID_MUXINGAPP:{
2799         gchar *text;
2800
2801         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
2802           break;
2803
2804         GST_DEBUG_OBJECT (demux, "MuxingApp: %s", GST_STR_NULL (text));
2805         demux->muxing_app = text;
2806         break;
2807       }
2808
2809       case GST_MATROSKA_ID_DATEUTC:{
2810         gint64 time;
2811
2812         if ((ret = gst_ebml_read_date (ebml, &id, &time)) != GST_FLOW_OK)
2813           break;
2814
2815         GST_DEBUG_OBJECT (demux, "DateUTC: %" G_GINT64_FORMAT, time);
2816         demux->created = time;
2817         break;
2818       }
2819
2820       case GST_MATROSKA_ID_TITLE:{
2821         gchar *text;
2822         GstTagList *taglist;
2823
2824         if ((ret = gst_ebml_read_utf8 (ebml, &id, &text)) != GST_FLOW_OK)
2825           break;
2826
2827         GST_DEBUG_OBJECT (demux, "Title: %s", GST_STR_NULL (text));
2828         taglist = gst_tag_list_new ();
2829         gst_tag_list_add (taglist, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, text,
2830             NULL);
2831         gst_element_found_tags (GST_ELEMENT (ebml), taglist);
2832         g_free (text);
2833         break;
2834       }
2835
2836       default:
2837         GST_WARNING_OBJECT (demux,
2838             "Unknown SegmentInfo subelement 0x%x - ignoring", id);
2839
2840         /* fall through */
2841       case GST_MATROSKA_ID_SEGMENTUID:
2842       case GST_MATROSKA_ID_SEGMENTFILENAME:
2843       case GST_MATROSKA_ID_PREVUID:
2844       case GST_MATROSKA_ID_PREVFILENAME:
2845       case GST_MATROSKA_ID_NEXTUID:
2846       case GST_MATROSKA_ID_NEXTFILENAME:
2847       case GST_MATROSKA_ID_SEGMENTFAMILY:
2848       case GST_MATROSKA_ID_CHAPTERTRANSLATE:
2849         ret = gst_ebml_read_skip (ebml);
2850         break;
2851     }
2852
2853     if (demux->level_up) {
2854       demux->level_up--;
2855       break;
2856     }
2857   }
2858
2859   DEBUG_ELEMENT_STOP (demux, ebml, "SegmentInfo", ret);
2860
2861   demux->segmentinfo_parsed = TRUE;
2862
2863   return ret;
2864 }
2865
2866 static GstFlowReturn
2867 gst_matroska_demux_parse_metadata_id_simple_tag (GstMatroskaDemux * demux,
2868     GstTagList ** p_taglist)
2869 {
2870   /* FIXME: check if there are more useful mappings */
2871   struct
2872   {
2873     gchar *matroska_tagname;
2874     gchar *gstreamer_tagname;
2875   }
2876   tag_conv[] = {
2877     {
2878     GST_MATROSKA_TAG_ID_TITLE, GST_TAG_TITLE}, {
2879     GST_MATROSKA_TAG_ID_AUTHOR, GST_TAG_ARTIST}, {
2880     GST_MATROSKA_TAG_ID_ALBUM, GST_TAG_ALBUM}, {
2881     GST_MATROSKA_TAG_ID_COMMENTS, GST_TAG_COMMENT}, {
2882     GST_MATROSKA_TAG_ID_BITSPS, GST_TAG_BITRATE}, {
2883     GST_MATROSKA_TAG_ID_BPS, GST_TAG_BITRATE}, {
2884     GST_MATROSKA_TAG_ID_ENCODER, GST_TAG_ENCODER}, {
2885     GST_MATROSKA_TAG_ID_DATE, GST_TAG_DATE}, {
2886     GST_MATROSKA_TAG_ID_ISRC, GST_TAG_ISRC}, {
2887     GST_MATROSKA_TAG_ID_COPYRIGHT, GST_TAG_COPYRIGHT}, {
2888     GST_MATROSKA_TAG_ID_BPM, GST_TAG_BEATS_PER_MINUTE}, {
2889     GST_MATROSKA_TAG_ID_TERMS_OF_USE, GST_TAG_LICENSE}, {
2890     GST_MATROSKA_TAG_ID_COMPOSER, GST_TAG_COMPOSER}, {
2891     GST_MATROSKA_TAG_ID_LEAD_PERFORMER, GST_TAG_PERFORMER}, {
2892     GST_MATROSKA_TAG_ID_GENRE, GST_TAG_GENRE}
2893   };
2894   GstEbmlRead *ebml = GST_EBML_READ (demux);
2895   GstFlowReturn ret;
2896   guint32 id;
2897   gchar *value = NULL;
2898   gchar *tag = NULL;
2899
2900   DEBUG_ELEMENT_START (demux, ebml, "SimpleTag");
2901
2902   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2903     DEBUG_ELEMENT_STOP (demux, ebml, "SimpleTag", ret);
2904     return ret;
2905   }
2906
2907   while (ret == GST_FLOW_OK) {
2908     /* read all sub-entries */
2909
2910     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
2911       break;
2912
2913     if (demux->level_up) {
2914       demux->level_up--;
2915       break;
2916     }
2917
2918     switch (id) {
2919       case GST_MATROSKA_ID_TAGNAME:
2920         g_free (tag);
2921         tag = NULL;
2922         ret = gst_ebml_read_ascii (ebml, &id, &tag);
2923         GST_DEBUG_OBJECT (demux, "TagName: %s", GST_STR_NULL (tag));
2924         break;
2925
2926       case GST_MATROSKA_ID_TAGSTRING:
2927         g_free (value);
2928         value = NULL;
2929         ret = gst_ebml_read_utf8 (ebml, &id, &value);
2930         GST_DEBUG_OBJECT (demux, "TagString: %s", GST_STR_NULL (value));
2931         break;
2932
2933       default:
2934         GST_WARNING_OBJECT (demux,
2935             "Unknown SimpleTag subelement 0x%x - ignoring", id);
2936         /* fall-through */
2937
2938       case GST_MATROSKA_ID_TAGLANGUAGE:
2939       case GST_MATROSKA_ID_TAGDEFAULT:
2940       case GST_MATROSKA_ID_TAGBINARY:
2941         ret = gst_ebml_read_skip (ebml);
2942         break;
2943     }
2944
2945     if (demux->level_up) {
2946       demux->level_up--;
2947       break;
2948     }
2949   }
2950
2951   DEBUG_ELEMENT_STOP (demux, ebml, "SimpleTag", ret);
2952
2953   if (tag && value) {
2954     guint i;
2955
2956     for (i = 0; i < G_N_ELEMENTS (tag_conv); i++) {
2957       const gchar *tagname_gst = tag_conv[i].gstreamer_tagname;
2958
2959       const gchar *tagname_mkv = tag_conv[i].matroska_tagname;
2960
2961       if (strcmp (tagname_mkv, tag) == 0) {
2962         GValue dest = { 0, };
2963         GType dest_type = gst_tag_get_type (tagname_gst);
2964
2965         g_value_init (&dest, dest_type);
2966         if (gst_value_deserialize (&dest, value)) {
2967           gst_tag_list_add_values (*p_taglist, GST_TAG_MERGE_APPEND,
2968               tagname_gst, &dest, NULL);
2969         } else {
2970           GST_WARNING_OBJECT (demux, "Can't transform tag '%s' with "
2971               "value '%s' to target type '%s'", tag, value,
2972               g_type_name (dest_type));
2973         }
2974         g_value_unset (&dest);
2975         break;
2976       }
2977     }
2978   }
2979
2980   g_free (tag);
2981   g_free (value);
2982
2983   return ret;
2984 }
2985
2986 static GstFlowReturn
2987 gst_matroska_demux_parse_metadata_id_tag (GstMatroskaDemux * demux,
2988     GstTagList ** p_taglist)
2989 {
2990   GstEbmlRead *ebml = GST_EBML_READ (demux);
2991   guint32 id;
2992   GstFlowReturn ret;
2993
2994   DEBUG_ELEMENT_START (demux, ebml, "Tag");
2995
2996   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
2997     DEBUG_ELEMENT_STOP (demux, ebml, "Tag", ret);
2998     return ret;
2999   }
3000
3001   while (ret == GST_FLOW_OK) {
3002     /* read all sub-entries */
3003
3004     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
3005       break;
3006
3007     if (demux->level_up) {
3008       demux->level_up--;
3009       break;
3010     }
3011
3012     switch (id) {
3013       case GST_MATROSKA_ID_SIMPLETAG:
3014         ret =
3015             gst_matroska_demux_parse_metadata_id_simple_tag (demux, p_taglist);
3016         break;
3017
3018       default:
3019         GST_WARNING_OBJECT (demux, "Unknown Tag subelement 0x%x - ignoring",
3020             id);
3021         ret = gst_ebml_read_skip (ebml);
3022         break;
3023     }
3024
3025     if (demux->level_up) {
3026       demux->level_up--;
3027       break;
3028     }
3029   }
3030
3031   DEBUG_ELEMENT_STOP (demux, ebml, "Tag", ret);
3032
3033   return ret;
3034 }
3035
3036 static GstFlowReturn
3037 gst_matroska_demux_parse_metadata (GstMatroskaDemux * demux)
3038 {
3039   GstEbmlRead *ebml = GST_EBML_READ (demux);
3040   GstTagList *taglist;
3041   GstFlowReturn ret = GST_FLOW_OK;
3042   guint32 id;
3043   GList *l;
3044   GstEbmlLevel *curlevel;
3045
3046   /* Can't be NULL at this point */
3047   g_assert (ebml->level != NULL);
3048   curlevel = ebml->level->data;
3049
3050   /* Make sure we don't parse a tags element twice and
3051    * post it's tags twice */
3052   for (l = demux->tags_parsed; l; l = l->next) {
3053     GstEbmlLevel *level = l->data;
3054
3055     if (ebml->level)
3056       curlevel = ebml->level->data;
3057     else
3058       break;
3059
3060     if (level->start == curlevel->start && level->length == curlevel->length) {
3061       GST_DEBUG_OBJECT (demux, "Skipping already parsed Tags at offset %"
3062           G_GUINT64_FORMAT, ebml->offset);
3063       ret = gst_ebml_read_skip (ebml);
3064       return ret;
3065     }
3066   }
3067
3068   DEBUG_ELEMENT_START (demux, ebml, "Tags");
3069
3070   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
3071     DEBUG_ELEMENT_STOP (demux, ebml, "Tags", ret);
3072     return ret;
3073   }
3074
3075   taglist = gst_tag_list_new ();
3076
3077   /* TODO: g_slice_dup() if we depend on GLib 2.14 */
3078   curlevel = g_slice_new (GstEbmlLevel);
3079   memcpy (curlevel, ebml->level->data, sizeof (GstEbmlLevel));
3080   demux->tags_parsed = g_list_prepend (demux->tags_parsed, curlevel);
3081
3082   while (ret == GST_FLOW_OK) {
3083     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
3084       break;
3085
3086     if (demux->level_up) {
3087       demux->level_up--;
3088       break;
3089     }
3090
3091     switch (id) {
3092       case GST_MATROSKA_ID_TAG:
3093         ret = gst_matroska_demux_parse_metadata_id_tag (demux, &taglist);
3094         break;
3095
3096       default:
3097         GST_WARNING_OBJECT (demux, "Unknown Tags subelement 0x%x - ignoring",
3098             id);
3099         /* FIXME: Use to limit the tags to specific pads */
3100       case GST_MATROSKA_ID_TARGETS:
3101         ret = gst_ebml_read_skip (ebml);
3102         break;
3103     }
3104
3105     if (demux->level_up) {
3106       demux->level_up--;
3107       break;
3108     }
3109   }
3110
3111   DEBUG_ELEMENT_STOP (demux, ebml, "Tags", ret);
3112
3113   /* FIXME: tags must be pushed *after* the initial newsegment event */
3114   gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE, GST_TAG_CONTAINER_FORMAT,
3115       "Matroska", NULL);
3116   gst_element_found_tags (GST_ELEMENT (ebml), taglist);
3117
3118   return ret;
3119 }
3120
3121 static GstFlowReturn
3122 gst_matroska_demux_parse_attached_file (GstMatroskaDemux * demux,
3123     GstTagList * taglist)
3124 {
3125   GstEbmlRead *ebml = GST_EBML_READ (demux);
3126   guint32 id;
3127   GstFlowReturn ret;
3128   gchar *description = NULL;
3129   gchar *filename = NULL;
3130   gchar *mimetype = NULL;
3131   guint8 *data = NULL;
3132   guint64 datalen = 0;
3133
3134   DEBUG_ELEMENT_START (demux, ebml, "AttachedFile");
3135
3136   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
3137     DEBUG_ELEMENT_STOP (demux, ebml, "AttachedFile", ret);
3138     return ret;
3139   }
3140
3141   while (ret == GST_FLOW_OK) {
3142     /* read all sub-entries */
3143
3144     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
3145       break;
3146
3147     if (demux->level_up) {
3148       demux->level_up--;
3149       break;
3150     }
3151
3152     switch (id) {
3153       case GST_MATROSKA_ID_FILEDESCRIPTION:
3154         if (description) {
3155           GST_WARNING_OBJECT (demux, "FileDescription can only appear once");
3156           break;
3157         }
3158
3159         ret = gst_ebml_read_utf8 (ebml, &id, &description);
3160         GST_DEBUG_OBJECT (demux, "FileDescription: %s",
3161             GST_STR_NULL (description));
3162         break;
3163       case GST_MATROSKA_ID_FILENAME:
3164         if (filename) {
3165           GST_WARNING_OBJECT (demux, "FileName can only appear once");
3166           break;
3167         }
3168
3169         ret = gst_ebml_read_utf8 (ebml, &id, &filename);
3170
3171         GST_DEBUG_OBJECT (demux, "FileName: %s", GST_STR_NULL (filename));
3172         break;
3173       case GST_MATROSKA_ID_FILEMIMETYPE:
3174         if (mimetype) {
3175           GST_WARNING_OBJECT (demux, "FileMimeType can only appear once");
3176           break;
3177         }
3178
3179         ret = gst_ebml_read_ascii (ebml, &id, &mimetype);
3180         GST_DEBUG_OBJECT (demux, "FileMimeType: %s", GST_STR_NULL (mimetype));
3181         break;
3182       case GST_MATROSKA_ID_FILEDATA:
3183         if (data) {
3184           GST_WARNING_OBJECT (demux, "FileData can only appear once");
3185           break;
3186         }
3187
3188         ret = gst_ebml_read_binary (ebml, &id, &data, &datalen);
3189         GST_DEBUG_OBJECT (demux, "FileData of size %" G_GUINT64_FORMAT,
3190             datalen);
3191         break;
3192
3193       default:
3194         GST_WARNING_OBJECT (demux,
3195             "Unknown AttachedFile subelement 0x%x - ignoring", id);
3196         /* fall through */
3197       case GST_MATROSKA_ID_FILEUID:
3198         ret = gst_ebml_read_skip (ebml);
3199         break;
3200     }
3201
3202     if (demux->level_up) {
3203       demux->level_up--;
3204       break;
3205     }
3206   }
3207
3208   DEBUG_ELEMENT_STOP (demux, ebml, "AttachedFile", ret);
3209
3210   if (filename && mimetype && data && datalen > 0) {
3211     GstTagImageType image_type = GST_TAG_IMAGE_TYPE_NONE;
3212     GstBuffer *tagbuffer = NULL;
3213     GstCaps *caps;
3214     gchar *filename_lc = g_utf8_strdown (filename, -1);
3215
3216     GST_DEBUG_OBJECT (demux, "Creating tag for attachment with filename '%s', "
3217         "mimetype '%s', description '%s', size %" G_GUINT64_FORMAT, filename,
3218         mimetype, GST_STR_NULL (description), datalen);
3219
3220     /* TODO: better heuristics for different image types */
3221     if (strstr (filename_lc, "cover")) {
3222       if (strstr (filename_lc, "back"))
3223         image_type = GST_TAG_IMAGE_TYPE_BACK_COVER;
3224       else
3225         image_type = GST_TAG_IMAGE_TYPE_FRONT_COVER;
3226     } else if (g_str_has_prefix (mimetype, "image/") ||
3227         g_str_has_suffix (filename_lc, "png") ||
3228         g_str_has_suffix (filename_lc, "jpg") ||
3229         g_str_has_suffix (filename_lc, "jpeg") ||
3230         g_str_has_suffix (filename_lc, "gif") ||
3231         g_str_has_suffix (filename_lc, "bmp")) {
3232       image_type = GST_TAG_IMAGE_TYPE_UNDEFINED;
3233     }
3234     g_free (filename_lc);
3235
3236     /* First try to create an image tag buffer from this */
3237     if (image_type != GST_TAG_IMAGE_TYPE_NONE) {
3238       tagbuffer =
3239           gst_tag_image_data_to_image_buffer (data, datalen, image_type);
3240
3241       if (!tagbuffer)
3242         image_type = GST_TAG_IMAGE_TYPE_NONE;
3243     }
3244
3245     /* if this failed create an attachment buffer */
3246     if (!tagbuffer) {
3247       tagbuffer = gst_buffer_new_and_alloc (datalen);
3248
3249       memcpy (GST_BUFFER_DATA (tagbuffer), data, datalen);
3250       GST_BUFFER_SIZE (tagbuffer) = datalen;
3251
3252       caps = gst_type_find_helper_for_buffer (NULL, tagbuffer, NULL);
3253       if (caps == NULL)
3254         caps = gst_caps_new_simple (mimetype, NULL);
3255       gst_buffer_set_caps (tagbuffer, caps);
3256       gst_caps_unref (caps);
3257     }
3258
3259     /* Set filename and description on the caps */
3260     caps = GST_BUFFER_CAPS (tagbuffer);
3261     gst_caps_set_simple (caps, "filename", G_TYPE_STRING, filename, NULL);
3262     if (description)
3263       gst_caps_set_simple (caps, "description", G_TYPE_STRING, description,
3264           NULL);
3265
3266     GST_DEBUG_OBJECT (demux,
3267         "Created attachment buffer with caps: %" GST_PTR_FORMAT, caps);
3268
3269     /* and append to the tag list */
3270     if (image_type != GST_TAG_IMAGE_TYPE_NONE)
3271       gst_tag_list_add (taglist, GST_TAG_MERGE_APPEND, GST_TAG_IMAGE, tagbuffer,
3272           NULL);
3273     else
3274       gst_tag_list_add (taglist, GST_TAG_MERGE_APPEND, GST_TAG_ATTACHMENT,
3275           tagbuffer, NULL);
3276   }
3277
3278   g_free (filename);
3279   g_free (mimetype);
3280   g_free (data);
3281   g_free (description);
3282
3283   return ret;
3284 }
3285
3286 static GstFlowReturn
3287 gst_matroska_demux_parse_attachments (GstMatroskaDemux * demux)
3288 {
3289   GstEbmlRead *ebml = GST_EBML_READ (demux);
3290   guint32 id;
3291   GstFlowReturn ret = GST_FLOW_OK;
3292   GstTagList *taglist;
3293
3294   DEBUG_ELEMENT_START (demux, ebml, "Attachments");
3295
3296   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
3297     DEBUG_ELEMENT_STOP (demux, ebml, "Attachments", ret);
3298     return ret;
3299   }
3300
3301   taglist = gst_tag_list_new ();
3302
3303   while (ret == GST_FLOW_OK) {
3304     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
3305       break;
3306
3307     if (demux->level_up) {
3308       demux->level_up--;
3309       break;
3310     }
3311
3312     switch (id) {
3313       case GST_MATROSKA_ID_ATTACHEDFILE:
3314         ret = gst_matroska_demux_parse_attached_file (demux, taglist);
3315         break;
3316
3317       default:
3318         GST_WARNING ("Unknown Attachments subelement 0x%x - ignoring", id);
3319         ret = gst_ebml_read_skip (ebml);
3320         break;
3321     }
3322
3323     if (demux->level_up) {
3324       demux->level_up--;
3325       break;
3326     }
3327   }
3328   DEBUG_ELEMENT_STOP (demux, ebml, "Attachments", ret);
3329
3330   if (gst_structure_n_fields (GST_STRUCTURE (taglist)) > 0) {
3331     GST_DEBUG_OBJECT (demux, "Posting attachment tags");
3332     gst_element_found_tags (GST_ELEMENT (ebml), taglist);
3333   } else {
3334     GST_DEBUG_OBJECT (demux, "No valid attachments found");
3335     gst_tag_list_free (taglist);
3336   }
3337
3338   demux->attachments_parsed = TRUE;
3339
3340   return ret;
3341 }
3342
3343 static GstFlowReturn
3344 gst_matroska_demux_parse_chapters (GstMatroskaDemux * demux)
3345 {
3346   GstEbmlRead *ebml = GST_EBML_READ (demux);
3347   guint32 id;
3348   GstFlowReturn ret = GST_FLOW_OK;
3349
3350   GST_WARNING_OBJECT (demux, "Parsing of chapters not implemented yet");
3351
3352   /* TODO: implement parsing of chapters */
3353
3354   DEBUG_ELEMENT_START (demux, ebml, "Chapters");
3355
3356   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
3357     DEBUG_ELEMENT_STOP (demux, ebml, "Chapters", ret);
3358     return ret;
3359   }
3360
3361   while (ret == GST_FLOW_OK) {
3362     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
3363       break;
3364
3365     if (demux->level_up) {
3366       demux->level_up--;
3367       break;
3368     }
3369
3370     switch (id) {
3371       default:
3372         ret = gst_ebml_read_skip (ebml);
3373         break;
3374     }
3375
3376     if (demux->level_up) {
3377       demux->level_up--;
3378       break;
3379     }
3380   }
3381
3382   DEBUG_ELEMENT_STOP (demux, ebml, "Chapters", ret);
3383   return ret;
3384 }
3385
3386 /*
3387  * Read signed/unsigned "EBML" numbers.
3388  * Return: number of bytes processed.
3389  */
3390
3391 static gint
3392 gst_matroska_ebmlnum_uint (guint8 * data, guint size, guint64 * num)
3393 {
3394   gint len_mask = 0x80, read = 1, n = 1, num_ffs = 0;
3395   guint64 total;
3396
3397   if (size <= 0) {
3398     return -1;
3399   }
3400
3401   total = data[0];
3402   while (read <= 8 && !(total & len_mask)) {
3403     read++;
3404     len_mask >>= 1;
3405   }
3406   if (read > 8)
3407     return -1;
3408
3409   if ((total &= (len_mask - 1)) == len_mask - 1)
3410     num_ffs++;
3411   if (size < read)
3412     return -1;
3413   while (n < read) {
3414     if (data[n] == 0xff)
3415       num_ffs++;
3416     total = (total << 8) | data[n];
3417     n++;
3418   }
3419
3420   if (read == num_ffs && total != 0)
3421     *num = G_MAXUINT64;
3422   else
3423     *num = total;
3424
3425   return read;
3426 }
3427
3428 static gint
3429 gst_matroska_ebmlnum_sint (guint8 * data, guint size, gint64 * num)
3430 {
3431   guint64 unum;
3432   gint res;
3433
3434   /* read as unsigned number first */
3435   if ((res = gst_matroska_ebmlnum_uint (data, size, &unum)) < 0)
3436     return -1;
3437
3438   /* make signed */
3439   if (unum == G_MAXUINT64)
3440     *num = G_MAXINT64;
3441   else
3442     *num = unum - ((1 << ((7 * res) - 1)) - 1);
3443
3444   return res;
3445 }
3446
3447 /*
3448  * Mostly used for subtitles. We add void filler data for each
3449  * lagging stream to make sure we don't deadlock.
3450  */
3451
3452 static void
3453 gst_matroska_demux_sync_streams (GstMatroskaDemux * demux)
3454 {
3455   gint stream_nr;
3456
3457   GST_LOG_OBJECT (demux, "Sync to %" GST_TIME_FORMAT,
3458       GST_TIME_ARGS (demux->segment.last_stop));
3459
3460   g_assert (demux->num_streams == demux->src->len);
3461   for (stream_nr = 0; stream_nr < demux->src->len; stream_nr++) {
3462     GstMatroskaTrackContext *context;
3463
3464     context = g_ptr_array_index (demux->src, stream_nr);
3465
3466     GST_LOG_OBJECT (demux,
3467         "Checking for resync on stream %d (%" GST_TIME_FORMAT ")", stream_nr,
3468         GST_TIME_ARGS (context->pos));
3469
3470     /* does it lag? 0.5 seconds is a random treshold... */
3471     if (context->pos + (GST_SECOND / 2) < demux->segment.last_stop) {
3472       GST_DEBUG_OBJECT (demux,
3473           "Synchronizing stream %d with others by advancing time " "from %"
3474           GST_TIME_FORMAT " to %" GST_TIME_FORMAT, stream_nr,
3475           GST_TIME_ARGS (context->pos),
3476           GST_TIME_ARGS (demux->segment.last_stop));
3477
3478       context->pos = demux->segment.last_stop;
3479
3480       /* advance stream time */
3481       gst_pad_push_event (context->pad,
3482           gst_event_new_new_segment (TRUE, demux->segment.rate,
3483               GST_FORMAT_TIME, demux->segment.last_stop, -1,
3484               demux->segment.last_stop));
3485     }
3486   }
3487 }
3488
3489 static GstFlowReturn
3490 gst_matroska_demux_push_hdr_buf (GstMatroskaDemux * demux,
3491     GstMatroskaTrackContext * stream, guint8 * data, guint len)
3492 {
3493   GstFlowReturn ret, cret;
3494   GstBuffer *header_buf = NULL;
3495
3496   ret = gst_pad_alloc_buffer_and_set_caps (stream->pad,
3497       GST_BUFFER_OFFSET_NONE, len, stream->caps, &header_buf);
3498
3499   /* we combine but don't use the combined value to check if we have a buffer
3500    * or not. The combined value is what we return. */
3501   cret = gst_matroska_demux_combine_flows (demux, stream, ret);
3502   if (ret != GST_FLOW_OK)
3503     goto no_buffer;
3504
3505   memcpy (GST_BUFFER_DATA (header_buf), data, len);
3506
3507   if (stream->set_discont) {
3508     GST_BUFFER_FLAG_SET (header_buf, GST_BUFFER_FLAG_DISCONT);
3509     stream->set_discont = FALSE;
3510   }
3511
3512   ret = gst_pad_push (stream->pad, header_buf);
3513
3514   /* combine flows */
3515   cret = gst_matroska_demux_combine_flows (demux, stream, ret);
3516
3517   return cret;
3518
3519   /* ERRORS */
3520 no_buffer:
3521   {
3522     GST_DEBUG_OBJECT (demux, "could not alloc buffer: %s, combined %s",
3523         gst_flow_get_name (ret), gst_flow_get_name (cret));
3524     return cret;
3525   }
3526 }
3527
3528 static GstFlowReturn
3529 gst_matroska_demux_push_flac_codec_priv_data (GstMatroskaDemux * demux,
3530     GstMatroskaTrackContext * stream)
3531 {
3532   GstFlowReturn ret;
3533   guint8 *pdata;
3534   guint off, len;
3535
3536   GST_LOG_OBJECT (demux, "priv data size = %u", stream->codec_priv_size);
3537
3538   pdata = (guint8 *) stream->codec_priv;
3539
3540   /* need at least 'fLaC' marker + STREAMINFO metadata block */
3541   if (stream->codec_priv_size < ((4) + (4 + 34))) {
3542     GST_WARNING_OBJECT (demux, "not enough codec priv data for flac headers");
3543     return GST_FLOW_ERROR;
3544   }
3545
3546   if (memcmp (pdata, "fLaC", 4) != 0) {
3547     GST_WARNING_OBJECT (demux, "no flac marker at start of stream headers");
3548     return GST_FLOW_ERROR;
3549   }
3550
3551   ret = gst_matroska_demux_push_hdr_buf (demux, stream, pdata, 4);
3552   if (ret != GST_FLOW_OK)
3553     return ret;
3554
3555   off = 4;                      /* skip fLaC marker */
3556   while (off < stream->codec_priv_size) {
3557     len = GST_READ_UINT8 (pdata + off + 1) << 16;
3558     len |= GST_READ_UINT8 (pdata + off + 2) << 8;
3559     len |= GST_READ_UINT8 (pdata + off + 3);
3560
3561     GST_DEBUG_OBJECT (demux, "header packet: len=%u bytes, flags=0x%02x",
3562         len, (guint) pdata[off]);
3563
3564     ret = gst_matroska_demux_push_hdr_buf (demux, stream, pdata + off, len);
3565     if (ret != GST_FLOW_OK)
3566       return ret;
3567
3568     off += 4 + len;
3569   }
3570   return GST_FLOW_OK;
3571 }
3572
3573 static GstFlowReturn
3574 gst_matroska_demux_push_speex_codec_priv_data (GstMatroskaDemux * demux,
3575     GstMatroskaTrackContext * stream)
3576 {
3577   GstFlowReturn ret;
3578   guint8 *pdata;
3579
3580   GST_LOG_OBJECT (demux, "priv data size = %u", stream->codec_priv_size);
3581
3582   pdata = (guint8 *) stream->codec_priv;
3583
3584   /* need at least 'fLaC' marker + STREAMINFO metadata block */
3585   if (stream->codec_priv_size < 80) {
3586     GST_WARNING_OBJECT (demux, "not enough codec priv data for speex headers");
3587     return GST_FLOW_ERROR;
3588   }
3589
3590   if (memcmp (pdata, "Speex   ", 8) != 0) {
3591     GST_WARNING_OBJECT (demux, "no Speex marker at start of stream headers");
3592     return GST_FLOW_ERROR;
3593   }
3594
3595   ret = gst_matroska_demux_push_hdr_buf (demux, stream, pdata, 80);
3596   if (ret != GST_FLOW_OK)
3597     return ret;
3598
3599   if (stream->codec_priv_size == 80)
3600     return ret;
3601   else
3602     return gst_matroska_demux_push_hdr_buf (demux, stream, pdata + 80,
3603         stream->codec_priv_size - 80);
3604 }
3605
3606 static GstFlowReturn
3607 gst_matroska_demux_push_xiph_codec_priv_data (GstMatroskaDemux * demux,
3608     GstMatroskaTrackContext * stream)
3609 {
3610   GstFlowReturn ret;
3611   guint8 *p = (guint8 *) stream->codec_priv;
3612   gint i, offset, num_packets;
3613   guint *length, last;
3614
3615   /* start of the stream and vorbis audio or theora video, need to
3616    * send the codec_priv data as first three packets */
3617   num_packets = p[0] + 1;
3618   GST_DEBUG_OBJECT (demux, "%u stream headers, total length=%u bytes",
3619       (guint) num_packets, stream->codec_priv_size);
3620
3621   length = g_alloca (num_packets * sizeof (guint));
3622   last = 0;
3623   offset = 1;
3624
3625   /* first packets, read length values */
3626   for (i = 0; i < num_packets - 1; i++) {
3627     length[i] = 0;
3628     while (offset < stream->codec_priv_size) {
3629       length[i] += p[offset];
3630       if (p[offset++] != 0xff)
3631         break;
3632     }
3633     last += length[i];
3634   }
3635   if (offset + last > stream->codec_priv_size)
3636     return GST_FLOW_ERROR;
3637
3638   /* last packet is the remaining size */
3639   length[i] = stream->codec_priv_size - offset - last;
3640
3641   for (i = 0; i < num_packets; i++) {
3642     GST_DEBUG_OBJECT (demux, "buffer %d: length=%u bytes", i,
3643         (guint) length[i]);
3644     if (offset + length[i] > stream->codec_priv_size)
3645       return GST_FLOW_ERROR;
3646
3647     ret =
3648         gst_matroska_demux_push_hdr_buf (demux, stream, p + offset, length[i]);
3649     if (ret != GST_FLOW_OK)
3650       return ret;
3651
3652     offset += length[i];
3653   }
3654   return GST_FLOW_OK;
3655 }
3656
3657 static void
3658 gst_matroska_demux_push_dvd_clut_change_event (GstMatroskaDemux * demux,
3659     GstMatroskaTrackContext * stream)
3660 {
3661   gchar *buf, *start;
3662
3663   g_assert (!strcmp (stream->codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_VOBSUB));
3664
3665   if (!stream->codec_priv)
3666     return;
3667
3668   /* ideally, VobSub private data should be parsed and stored more convenient
3669    * elsewhere, but for now, only interested in a small part */
3670
3671   /* make sure we have terminating 0 */
3672   buf = g_strndup ((gchar *) stream->codec_priv, stream->codec_priv_size);
3673
3674   /* just locate and parse palette part */
3675   start = strstr ((gchar *) stream->codec_priv, "palette:");
3676   if (start) {
3677     gint i;
3678     guint32 clut[16];
3679     guint32 col;
3680     guint8 r, g, b, y, u, v;
3681
3682     start += 8;
3683     while (g_ascii_isspace (*start))
3684       start++;
3685     for (i = 0; i < 16; i++) {
3686       if (sscanf (start, "%06x", &col) != 1)
3687         break;
3688       start += 6;
3689       while ((*start == ',') || g_ascii_isspace (*start))
3690         start++;
3691       /* sigh, need to convert this from vobsub pseudo-RGB to YUV */
3692       r = (col >> 16) & 0xff;
3693       g = (col >> 8) & 0xff;
3694       b = col & 0xff;
3695       y = CLAMP ((0.1494 * r + 0.6061 * g + 0.2445 * b) * 219 / 255 + 16, 0,
3696           255);
3697       u = CLAMP (0.6066 * r - 0.4322 * g - 0.1744 * b + 128, 0, 255);
3698       v = CLAMP (-0.08435 * r - 0.3422 * g + 0.4266 * b + 128, 0, 255);
3699       clut[i] = (y << 16) | (u << 8) | v;
3700     }
3701
3702     /* got them all without problems; build and send event */
3703     if (i == 16) {
3704       GstStructure *s;
3705
3706       s = gst_structure_new ("application/x-gst-dvd", "event", G_TYPE_STRING,
3707           "dvd-spu-clut-change", "clut00", G_TYPE_INT, clut[0], "clut01",
3708           G_TYPE_INT, clut[1], "clut02", G_TYPE_INT, clut[2], "clut03",
3709           G_TYPE_INT, clut[3], "clut04", G_TYPE_INT, clut[4], "clut05",
3710           G_TYPE_INT, clut[5], "clut06", G_TYPE_INT, clut[6], "clut07",
3711           G_TYPE_INT, clut[7], "clut08", G_TYPE_INT, clut[8], "clut09",
3712           G_TYPE_INT, clut[9], "clut10", G_TYPE_INT, clut[10], "clut11",
3713           G_TYPE_INT, clut[11], "clut12", G_TYPE_INT, clut[12], "clut13",
3714           G_TYPE_INT, clut[13], "clut14", G_TYPE_INT, clut[14], "clut15",
3715           G_TYPE_INT, clut[15], NULL);
3716
3717       gst_pad_push_event (stream->pad,
3718           gst_event_new_custom (GST_EVENT_CUSTOM_DOWNSTREAM, s));
3719     }
3720   }
3721   g_free (buf);
3722 }
3723
3724 static GstFlowReturn
3725 gst_matroska_demux_add_mpeg_seq_header (GstElement * element,
3726     GstMatroskaTrackContext * stream, GstBuffer ** buf)
3727 {
3728   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
3729   guint8 *seq_header;
3730   guint seq_header_len;
3731   guint32 header;
3732
3733   if (stream->codec_state) {
3734     seq_header = stream->codec_state;
3735     seq_header_len = stream->codec_state_size;
3736   } else if (stream->codec_priv) {
3737     seq_header = stream->codec_priv;
3738     seq_header_len = stream->codec_priv_size;
3739   } else {
3740     return GST_FLOW_OK;
3741   }
3742
3743   /* Sequence header only needed for keyframes */
3744   if (GST_BUFFER_FLAG_IS_SET (*buf, GST_BUFFER_FLAG_DELTA_UNIT))
3745     return GST_FLOW_OK;
3746
3747   if (GST_BUFFER_SIZE (*buf) < 4)
3748     return GST_FLOW_OK;
3749
3750   header = GST_READ_UINT32_BE (GST_BUFFER_DATA (*buf));
3751   /* Sequence start code, if not found prepend */
3752   if (header != 0x000001b3) {
3753     GstBuffer *newbuf;
3754     GstFlowReturn ret, cret;
3755
3756     ret = gst_pad_alloc_buffer_and_set_caps (stream->pad,
3757         GST_BUFFER_OFFSET_NONE, GST_BUFFER_SIZE (*buf) + seq_header_len,
3758         stream->caps, &newbuf);
3759     cret = gst_matroska_demux_combine_flows (demux, stream, ret);
3760     if (ret != GST_FLOW_OK) {
3761       GST_WARNING_OBJECT (demux, "Reallocating buffer for sequence header "
3762           "failed: %s, combined flow return: %s", gst_flow_get_name (ret),
3763           gst_flow_get_name (cret));
3764       return cret;
3765     }
3766
3767     GST_DEBUG_OBJECT (demux, "Prepending MPEG sequence header");
3768     gst_buffer_copy_metadata (newbuf, *buf, GST_BUFFER_COPY_TIMESTAMPS |
3769         GST_BUFFER_COPY_FLAGS);
3770     g_memmove (GST_BUFFER_DATA (newbuf), seq_header, seq_header_len);
3771     g_memmove (GST_BUFFER_DATA (newbuf) + seq_header_len,
3772         GST_BUFFER_DATA (*buf), GST_BUFFER_SIZE (*buf));
3773     gst_buffer_unref (*buf);
3774     *buf = newbuf;
3775   }
3776
3777   return GST_FLOW_OK;
3778 }
3779
3780 static GstFlowReturn
3781 gst_matroska_demux_add_wvpk_header (GstElement * element,
3782     GstMatroskaTrackContext * stream, GstBuffer ** buf)
3783 {
3784   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
3785   GstMatroskaTrackAudioContext *audiocontext =
3786       (GstMatroskaTrackAudioContext *) stream;
3787   GstBuffer *newbuf = NULL;
3788   guint8 *data;
3789   guint newlen;
3790   GstFlowReturn ret, cret = GST_FLOW_OK;
3791   Wavpack4Header wvh;
3792
3793   wvh.ck_id[0] = 'w';
3794   wvh.ck_id[1] = 'v';
3795   wvh.ck_id[2] = 'p';
3796   wvh.ck_id[3] = 'k';
3797
3798   wvh.version = GST_READ_UINT16_LE (stream->codec_priv);
3799   wvh.track_no = 0;
3800   wvh.index_no = 0;
3801   wvh.total_samples = -1;
3802   wvh.block_index = audiocontext->wvpk_block_index;
3803
3804   if (audiocontext->channels <= 2) {
3805     guint32 block_samples;
3806
3807     block_samples = GST_READ_UINT32_LE (GST_BUFFER_DATA (*buf));
3808     /* we need to reconstruct the header of the wavpack block */
3809
3810     /* -20 because ck_size is the size of the wavpack block -8
3811      * and lace_size is the size of the wavpack block + 12
3812      * (the three guint32 of the header that already are in the buffer) */
3813     wvh.ck_size = GST_BUFFER_SIZE (*buf) + sizeof (Wavpack4Header) - 20;
3814
3815     /* block_samples, flags and crc are already in the buffer */
3816     newlen = GST_BUFFER_SIZE (*buf) + sizeof (Wavpack4Header) - 12;
3817     ret =
3818         gst_pad_alloc_buffer_and_set_caps (stream->pad, GST_BUFFER_OFFSET_NONE,
3819         newlen, stream->caps, &newbuf);
3820     cret = gst_matroska_demux_combine_flows (demux, stream, ret);
3821     if (ret != GST_FLOW_OK) {
3822       GST_DEBUG_OBJECT (demux, "pad_alloc failed %s, combined %s",
3823           gst_flow_get_name (ret), gst_flow_get_name (cret));
3824       return cret;
3825     }
3826
3827     data = GST_BUFFER_DATA (newbuf);
3828     data[0] = 'w';
3829     data[1] = 'v';
3830     data[2] = 'p';
3831     data[3] = 'k';
3832     GST_WRITE_UINT32_LE (data + 4, wvh.ck_size);
3833     GST_WRITE_UINT16_LE (data + 8, wvh.version);
3834     GST_WRITE_UINT8 (data + 10, wvh.track_no);
3835     GST_WRITE_UINT8 (data + 11, wvh.index_no);
3836     GST_WRITE_UINT32_LE (data + 12, wvh.total_samples);
3837     GST_WRITE_UINT32_LE (data + 16, wvh.block_index);
3838     g_memmove (data + 20, GST_BUFFER_DATA (*buf), GST_BUFFER_SIZE (*buf));
3839     gst_buffer_copy_metadata (newbuf, *buf,
3840         GST_BUFFER_COPY_TIMESTAMPS | GST_BUFFER_COPY_FLAGS);
3841     gst_buffer_unref (*buf);
3842     *buf = newbuf;
3843     audiocontext->wvpk_block_index += block_samples;
3844   } else {
3845     guint8 *outdata;
3846     guint outpos = 0;
3847     guint size;
3848     guint32 block_samples, flags, crc, blocksize;
3849
3850     data = GST_BUFFER_DATA (*buf);
3851     size = GST_BUFFER_SIZE (*buf);
3852
3853     if (size < 4) {
3854       GST_ERROR_OBJECT (demux, "Too small wavpack buffer");
3855       return GST_FLOW_ERROR;
3856     }
3857
3858     block_samples = GST_READ_UINT32_LE (data);
3859     data += 4;
3860     size -= 4;
3861
3862     while (size > 12) {
3863       flags = GST_READ_UINT32_LE (data);
3864       data += 4;
3865       size -= 4;
3866       crc = GST_READ_UINT32_LE (data);
3867       data += 4;
3868       size -= 4;
3869       blocksize = GST_READ_UINT32_LE (data);
3870       data += 4;
3871       size -= 4;
3872
3873       if (blocksize == 0 || size < blocksize)
3874         break;
3875
3876       if (newbuf == NULL) {
3877         newbuf = gst_buffer_new_and_alloc (sizeof (Wavpack4Header) + blocksize);
3878         gst_buffer_set_caps (newbuf, stream->caps);
3879
3880         gst_buffer_copy_metadata (newbuf, *buf,
3881             GST_BUFFER_COPY_TIMESTAMPS | GST_BUFFER_COPY_FLAGS);
3882
3883         outpos = 0;
3884         outdata = GST_BUFFER_DATA (newbuf);
3885       } else {
3886         GST_BUFFER_SIZE (newbuf) += sizeof (Wavpack4Header) + blocksize;
3887         GST_BUFFER_DATA (newbuf) =
3888             g_realloc (GST_BUFFER_DATA (newbuf), GST_BUFFER_SIZE (newbuf));
3889         GST_BUFFER_MALLOCDATA (newbuf) = GST_BUFFER_DATA (newbuf);
3890         outdata = GST_BUFFER_DATA (newbuf);
3891       }
3892
3893       outdata[outpos] = 'w';
3894       outdata[outpos + 1] = 'v';
3895       outdata[outpos + 2] = 'p';
3896       outdata[outpos + 3] = 'k';
3897       outpos += 4;
3898
3899       GST_WRITE_UINT32_LE (outdata + outpos,
3900           blocksize + sizeof (Wavpack4Header) - 8);
3901       GST_WRITE_UINT16_LE (outdata + outpos + 4, wvh.version);
3902       GST_WRITE_UINT8 (outdata + outpos + 6, wvh.track_no);
3903       GST_WRITE_UINT8 (outdata + outpos + 7, wvh.index_no);
3904       GST_WRITE_UINT32_LE (outdata + outpos + 8, wvh.total_samples);
3905       GST_WRITE_UINT32_LE (outdata + outpos + 12, wvh.block_index);
3906       GST_WRITE_UINT32_LE (outdata + outpos + 16, block_samples);
3907       GST_WRITE_UINT32_LE (outdata + outpos + 20, flags);
3908       GST_WRITE_UINT32_LE (outdata + outpos + 24, crc);
3909       outpos += 28;
3910
3911       g_memmove (outdata + outpos, data, blocksize);
3912       outpos += blocksize;
3913       data += blocksize;
3914       size -= blocksize;
3915     }
3916     gst_buffer_unref (*buf);
3917     *buf = newbuf;
3918     audiocontext->wvpk_block_index += block_samples;
3919   }
3920
3921   return cret;
3922 }
3923
3924 static GstFlowReturn
3925 gst_matroska_demux_check_subtitle_buffer (GstElement * element,
3926     GstMatroskaTrackContext * stream, GstBuffer ** buf)
3927 {
3928   GstMatroskaTrackSubtitleContext *sub_stream;
3929   const gchar *encoding, *data;
3930   GError *err = NULL;
3931   GstBuffer *newbuf;
3932   gchar *utf8;
3933   guint size;
3934
3935   sub_stream = (GstMatroskaTrackSubtitleContext *) stream;
3936
3937   data = (const gchar *) GST_BUFFER_DATA (*buf);
3938   size = GST_BUFFER_SIZE (*buf);
3939
3940   if (!sub_stream->invalid_utf8) {
3941     if (g_utf8_validate (data, size, NULL)) {
3942       return GST_FLOW_OK;
3943     }
3944     GST_WARNING_OBJECT (element, "subtitle stream %d is not valid UTF-8, this "
3945         "is broken according to the matroska specification", stream->num);
3946     sub_stream->invalid_utf8 = TRUE;
3947   }
3948
3949   /* file with broken non-UTF8 subtitle, do the best we can do to fix it */
3950   encoding = g_getenv ("GST_SUBTITLE_ENCODING");
3951   if (encoding == NULL || *encoding == '\0') {
3952     /* if local encoding is UTF-8 and no encoding specified
3953      * via the environment variable, assume ISO-8859-15 */
3954     if (g_get_charset (&encoding)) {
3955       encoding = "ISO-8859-15";
3956     }
3957   }
3958
3959   utf8 = g_convert_with_fallback (data, size, "UTF-8", encoding, "*",
3960       NULL, NULL, &err);
3961
3962   if (err) {
3963     GST_LOG_OBJECT (element, "could not convert string from '%s' to UTF-8: %s",
3964         encoding, err->message);
3965     g_error_free (err);
3966     g_free (utf8);
3967
3968     /* invalid input encoding, fall back to ISO-8859-15 (always succeeds) */
3969     encoding = "ISO-8859-15";
3970     utf8 = g_convert_with_fallback (data, size, "UTF-8", encoding, "*",
3971         NULL, NULL, NULL);
3972   }
3973
3974   GST_LOG_OBJECT (element, "converted subtitle text from %s to UTF-8 %s",
3975       encoding, (err) ? "(using ISO-8859-15 as fallback)" : "");
3976
3977   if (utf8 == NULL)
3978     utf8 = g_strdup ("invalid subtitle");
3979
3980   newbuf = gst_buffer_new ();
3981   GST_BUFFER_MALLOCDATA (newbuf) = (guint8 *) utf8;
3982   GST_BUFFER_DATA (newbuf) = (guint8 *) utf8;
3983   GST_BUFFER_SIZE (newbuf) = strlen (utf8);
3984   gst_buffer_copy_metadata (newbuf, *buf,
3985       GST_BUFFER_COPY_TIMESTAMPS | GST_BUFFER_COPY_FLAGS);
3986   gst_buffer_unref (*buf);
3987
3988   *buf = newbuf;
3989   return GST_FLOW_OK;
3990 }
3991
3992 static GstFlowReturn
3993 gst_matroska_demux_parse_blockgroup_or_simpleblock (GstMatroskaDemux * demux,
3994     guint64 cluster_time, guint64 cluster_offset, gboolean is_simpleblock)
3995 {
3996   GstMatroskaTrackContext *stream = NULL;
3997   GstEbmlRead *ebml = GST_EBML_READ (demux);
3998   GstFlowReturn ret = GST_FLOW_OK;
3999   gboolean readblock = FALSE;
4000   guint32 id;
4001   guint64 block_duration = 0;
4002   GstBuffer *buf = NULL;
4003   gint stream_num = -1, n, laces = 0;
4004   guint size = 0;
4005   gint *lace_size = NULL;
4006   gint64 time = 0;
4007   gint flags = 0;
4008   gint64 referenceblock = 0;
4009
4010   while (ret == GST_FLOW_OK) {
4011     if (!is_simpleblock) {
4012       if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4013         break;
4014
4015       if (demux->level_up) {
4016         demux->level_up--;
4017         break;
4018       }
4019     } else {
4020       id = GST_MATROSKA_ID_SIMPLEBLOCK;
4021     }
4022
4023     switch (id) {
4024         /* one block inside the group. Note, block parsing is one
4025          * of the harder things, so this code is a bit complicated.
4026          * See http://www.matroska.org/ for documentation. */
4027       case GST_MATROSKA_ID_SIMPLEBLOCK:
4028       case GST_MATROSKA_ID_BLOCK:
4029       {
4030         guint64 num;
4031         guint8 *data;
4032
4033         if (buf) {
4034           gst_buffer_unref (buf);
4035           buf = NULL;
4036         }
4037         if ((ret = gst_ebml_read_buffer (ebml, &id, &buf)) != GST_FLOW_OK)
4038           break;
4039
4040         data = GST_BUFFER_DATA (buf);
4041         size = GST_BUFFER_SIZE (buf);
4042
4043         /* first byte(s): blocknum */
4044         if ((n = gst_matroska_ebmlnum_uint (data, size, &num)) < 0) {
4045           GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL), ("Data error"));
4046           gst_buffer_unref (buf);
4047           buf = NULL;
4048           ret = GST_FLOW_ERROR;
4049           break;
4050         }
4051         data += n;
4052         size -= n;
4053
4054         /* fetch stream from num */
4055         stream_num = gst_matroska_demux_stream_from_num (demux, num);
4056         if (size < 3 || stream_num < 0 || stream_num >= demux->num_streams) {
4057           gst_buffer_unref (buf);
4058           buf = NULL;
4059           GST_WARNING_OBJECT (demux, "Invalid stream %d or size %u", stream_num,
4060               size);
4061           ret = GST_FLOW_ERROR;
4062           break;
4063         }
4064
4065         stream = g_ptr_array_index (demux->src, stream_num);
4066
4067         /* time (relative to cluster time) */
4068         time = ((gint16) GST_READ_UINT16_BE (data));
4069         data += 2;
4070         size -= 2;
4071         flags = GST_READ_UINT8 (data);
4072         data += 1;
4073         size -= 1;
4074
4075         GST_LOG_OBJECT (demux, "time %" G_GUINT64_FORMAT ", flags %d", time,
4076             flags);
4077
4078         switch ((flags & 0x06) >> 1) {
4079           case 0x0:            /* no lacing */
4080             laces = 1;
4081             lace_size = g_new (gint, 1);
4082             lace_size[0] = size;
4083             break;
4084
4085           case 0x1:            /* xiph lacing */
4086           case 0x2:            /* fixed-size lacing */
4087           case 0x3:            /* EBML lacing */
4088             if (size == 0) {
4089               GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL),
4090                   ("Invalid lacing size"));
4091               ret = GST_FLOW_ERROR;
4092               break;
4093             }
4094             laces = GST_READ_UINT8 (data) + 1;
4095             data += 1;
4096             size -= 1;
4097             lace_size = g_new0 (gint, laces);
4098
4099             switch ((flags & 0x06) >> 1) {
4100               case 0x1:        /* xiph lacing */  {
4101                 guint temp, total = 0;
4102
4103                 for (n = 0; ret == GST_FLOW_OK && n < laces - 1; n++) {
4104                   while (1) {
4105                     if (size == 0) {
4106                       GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL),
4107                           ("Invalid lacing size"));
4108                       ret = GST_FLOW_ERROR;
4109                       break;
4110                     }
4111                     temp = GST_READ_UINT8 (data);
4112                     lace_size[n] += temp;
4113                     data += 1;
4114                     size -= 1;
4115                     if (temp != 0xff)
4116                       break;
4117                   }
4118                   total += lace_size[n];
4119                 }
4120                 lace_size[n] = size - total;
4121                 break;
4122               }
4123
4124               case 0x2:        /* fixed-size lacing */
4125                 for (n = 0; n < laces; n++)
4126                   lace_size[n] = size / laces;
4127                 break;
4128
4129               case 0x3:        /* EBML lacing */  {
4130                 guint total;
4131
4132                 if ((n = gst_matroska_ebmlnum_uint (data, size, &num)) < 0) {
4133                   GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL),
4134                       ("Data error"));
4135                   ret = GST_FLOW_ERROR;
4136                   break;
4137                 }
4138                 data += n;
4139                 size -= n;
4140                 total = lace_size[0] = num;
4141                 for (n = 1; ret == GST_FLOW_OK && n < laces - 1; n++) {
4142                   gint64 snum;
4143                   gint r;
4144
4145                   if ((r = gst_matroska_ebmlnum_sint (data, size, &snum)) < 0) {
4146                     GST_ELEMENT_ERROR (demux, STREAM, DEMUX, (NULL),
4147                         ("Data error"));
4148                     ret = GST_FLOW_ERROR;
4149                     break;
4150                   }
4151                   data += r;
4152                   size -= r;
4153                   lace_size[n] = lace_size[n - 1] + snum;
4154                   total += lace_size[n];
4155                 }
4156                 if (n < laces)
4157                   lace_size[n] = size - total;
4158                 break;
4159               }
4160             }
4161             break;
4162         }
4163
4164         if (stream->send_xiph_headers) {
4165           ret = gst_matroska_demux_push_xiph_codec_priv_data (demux, stream);
4166           stream->send_xiph_headers = FALSE;
4167         }
4168
4169         if (stream->send_flac_headers) {
4170           ret = gst_matroska_demux_push_flac_codec_priv_data (demux, stream);
4171           stream->send_flac_headers = FALSE;
4172         }
4173
4174         if (stream->send_speex_headers) {
4175           ret = gst_matroska_demux_push_speex_codec_priv_data (demux, stream);
4176           stream->send_speex_headers = FALSE;
4177         }
4178
4179         if (stream->send_dvd_event) {
4180           gst_matroska_demux_push_dvd_clut_change_event (demux, stream);
4181           /* FIXME: should we send this event again after (flushing) seek ? */
4182           stream->send_dvd_event = FALSE;
4183         }
4184
4185         if (ret != GST_FLOW_OK)
4186           break;
4187
4188         readblock = TRUE;
4189         break;
4190       }
4191
4192       case GST_MATROSKA_ID_BLOCKDURATION:{
4193         ret = gst_ebml_read_uint (ebml, &id, &block_duration);
4194         GST_DEBUG_OBJECT (demux, "BlockDuration: %" G_GUINT64_FORMAT,
4195             block_duration);
4196         break;
4197       }
4198
4199       case GST_MATROSKA_ID_REFERENCEBLOCK:{
4200         ret = gst_ebml_read_sint (ebml, &id, &referenceblock);
4201         GST_DEBUG_OBJECT (demux, "ReferenceBlock: %" G_GINT64_FORMAT,
4202             referenceblock);
4203         break;
4204       }
4205
4206       case GST_MATROSKA_ID_CODECSTATE:{
4207         guint8 *data;
4208         guint64 data_len = 0;
4209
4210         if ((ret =
4211                 gst_ebml_read_binary (ebml, &id, &data,
4212                     &data_len)) != GST_FLOW_OK)
4213           break;
4214
4215         g_free (stream->codec_state);
4216         stream->codec_state = data;
4217         stream->codec_state_size = data_len;
4218
4219         /* Decode if necessary */
4220         if (stream->encodings && stream->encodings->len > 0
4221             && stream->codec_state && stream->codec_state_size > 0) {
4222           if (!gst_matroska_decode_data (stream->encodings,
4223                   &stream->codec_state, &stream->codec_state_size,
4224                   GST_MATROSKA_TRACK_ENCODING_SCOPE_CODEC_DATA, TRUE)) {
4225             GST_WARNING_OBJECT (demux, "Decoding codec state failed");
4226           }
4227         }
4228
4229         GST_DEBUG_OBJECT (demux, "CodecState of %u bytes",
4230             stream->codec_state_size);
4231         break;
4232       }
4233
4234       default:
4235         GST_WARNING_OBJECT (demux,
4236             "Unknown BlockGroup subelement 0x%x - ignoring", id);
4237         /* fall-through */
4238
4239       case GST_MATROSKA_ID_BLOCKVIRTUAL:
4240       case GST_MATROSKA_ID_BLOCKADDITIONS:
4241       case GST_MATROSKA_ID_REFERENCEPRIORITY:
4242       case GST_MATROSKA_ID_REFERENCEVIRTUAL:
4243       case GST_MATROSKA_ID_SLICES:
4244         GST_DEBUG_OBJECT (demux,
4245             "Skipping BlockGroup subelement 0x%x - ignoring", id);
4246         ret = gst_ebml_read_skip (ebml);
4247         break;
4248     }
4249
4250     if (is_simpleblock)
4251       break;
4252
4253     if (demux->level_up) {
4254       demux->level_up--;
4255       break;
4256     }
4257   }
4258
4259   if (ret == GST_FLOW_OK && readblock) {
4260     guint64 duration = 0;
4261     gint64 lace_time = 0;
4262
4263     stream = g_ptr_array_index (demux->src, stream_num);
4264
4265     if (cluster_time != GST_CLOCK_TIME_NONE) {
4266       /* FIXME: What to do with negative timestamps? Give timestamp 0 or -1?
4267        * Drop unless the lace contains timestamp 0? */
4268       if (time < 0 && (-time) > cluster_time) {
4269         lace_time = 0;
4270       } else {
4271         if (stream->timecodescale == 1.0)
4272           lace_time = (cluster_time + time) * demux->time_scale;
4273         else
4274           lace_time =
4275               gst_util_guint64_to_gdouble ((cluster_time + time) *
4276               demux->time_scale) * stream->timecodescale;
4277       }
4278     } else {
4279       lace_time = GST_CLOCK_TIME_NONE;
4280     }
4281
4282     if (block_duration) {
4283       if (stream->timecodescale == 1.0)
4284         duration = block_duration * demux->time_scale;
4285       else
4286         duration =
4287             gst_util_gdouble_to_guint64 (gst_util_guint64_to_gdouble
4288             (block_duration * demux->time_scale) * stream->timecodescale);
4289     } else if (stream->default_duration) {
4290       duration = stream->default_duration * laces;
4291     }
4292     /* else duration is diff between timecode of this and next block */
4293     for (n = 0; n < laces; n++) {
4294       GstBuffer *sub;
4295       GstClockTimeDiff diff;
4296
4297       sub = gst_buffer_create_sub (buf,
4298           GST_BUFFER_SIZE (buf) - size, lace_size[n]);
4299       GST_WARNING_OBJECT (demux, "created subbuffer %p", sub);
4300
4301       if (stream->encodings != NULL && stream->encodings->len > 0)
4302         sub = gst_matroska_decode_buffer (stream, sub);
4303
4304       if (sub == NULL) {
4305         GST_WARNING_OBJECT (demux, "Decoding buffer failed");
4306         goto next_lace;
4307       }
4308
4309       GST_BUFFER_TIMESTAMP (sub) = lace_time;
4310
4311       if (lace_time != GST_CLOCK_TIME_NONE) {
4312         demux->segment.last_stop = lace_time;
4313
4314         diff = GST_CLOCK_DIFF (stream->pos, lace_time);
4315         if (diff < -GST_SECOND / 2 || diff > GST_SECOND / 2) {
4316           GST_DEBUG_OBJECT (demux, "Gap of %" G_GINT64_FORMAT " ns detected in"
4317               "stream %d. Sending updated NEWSEGMENT event", diff,
4318               stream->index);
4319           gst_pad_push_event (stream->pad, gst_event_new_new_segment (TRUE,
4320                   demux->segment.rate, GST_FORMAT_TIME, lace_time, -1,
4321                   lace_time));
4322         }
4323       }
4324
4325       stream->pos = demux->segment.last_stop;
4326
4327       gst_matroska_demux_sync_streams (demux);
4328
4329       if (duration) {
4330         GST_BUFFER_DURATION (sub) = duration / laces;
4331         stream->pos += GST_BUFFER_DURATION (sub);
4332         demux->segment.last_stop += GST_BUFFER_DURATION (sub);
4333       }
4334
4335       if (is_simpleblock) {
4336         if (flags & 0x80)
4337           GST_BUFFER_FLAG_UNSET (sub, GST_BUFFER_FLAG_DELTA_UNIT);
4338         else
4339           GST_BUFFER_FLAG_SET (sub, GST_BUFFER_FLAG_DELTA_UNIT);
4340       } else {
4341         if (referenceblock) {
4342           GST_BUFFER_FLAG_SET (sub, GST_BUFFER_FLAG_DELTA_UNIT);
4343         } else {
4344           GST_BUFFER_FLAG_UNSET (sub, GST_BUFFER_FLAG_DELTA_UNIT);
4345         }
4346       }
4347
4348       if (GST_BUFFER_FLAG_IS_SET (sub, GST_BUFFER_FLAG_DELTA_UNIT)
4349           && stream->set_discont) {
4350         /* When doing seeks or such, we need to restart on key frames or
4351          * decoders might choke. */
4352         GST_DEBUG_OBJECT (demux, "skipping delta unit");
4353         gst_buffer_unref (sub);
4354         goto done;
4355       }
4356
4357       if (stream->set_discont) {
4358         GST_BUFFER_FLAG_SET (sub, GST_BUFFER_FLAG_DISCONT);
4359         stream->set_discont = FALSE;
4360       }
4361
4362       GST_DEBUG_OBJECT (demux,
4363           "Pushing lace %d, data of size %d for stream %d, time=%"
4364           GST_TIME_FORMAT " and duration=%" GST_TIME_FORMAT, n,
4365           GST_BUFFER_SIZE (sub), stream_num,
4366           GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (sub)),
4367           GST_TIME_ARGS (GST_BUFFER_DURATION (sub)));
4368
4369       if (demux->element_index) {
4370         if (stream->index_writer_id == -1)
4371           gst_index_get_writer_id (demux->element_index,
4372               GST_OBJECT (stream->pad), &stream->index_writer_id);
4373
4374         GST_LOG_OBJECT (demux, "adding association %" GST_TIME_FORMAT "-> %"
4375             G_GUINT64_FORMAT " for writer id %d",
4376             GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (sub)), cluster_offset,
4377             stream->index_writer_id);
4378         gst_index_add_association (demux->element_index,
4379             stream->index_writer_id, GST_BUFFER_FLAG_IS_SET (sub,
4380                 GST_BUFFER_FLAG_DELTA_UNIT) ? 0 : GST_ASSOCIATION_FLAG_KEY_UNIT,
4381             GST_FORMAT_TIME, GST_BUFFER_TIMESTAMP (sub), GST_FORMAT_BYTES,
4382             cluster_offset, NULL);
4383       }
4384
4385       gst_buffer_set_caps (sub, GST_PAD_CAPS (stream->pad));
4386
4387       /* Postprocess the buffers depending on the codec used */
4388       if (stream->postprocess_frame) {
4389         GST_LOG_OBJECT (demux, "running post process");
4390         ret = stream->postprocess_frame (GST_ELEMENT (demux), stream, &sub);
4391       }
4392
4393       ret = gst_pad_push (stream->pad, sub);
4394       /* combine flows */
4395       ret = gst_matroska_demux_combine_flows (demux, stream, ret);
4396
4397     next_lace:
4398       size -= lace_size[n];
4399       if (lace_time != GST_CLOCK_TIME_NONE && duration)
4400         lace_time += duration / laces;
4401       else
4402         lace_time = GST_CLOCK_TIME_NONE;
4403     }
4404   }
4405
4406 done:
4407   if (buf)
4408     gst_buffer_unref (buf);
4409   g_free (lace_size);
4410
4411   return ret;
4412 }
4413
4414 static GstFlowReturn
4415 gst_matroska_demux_parse_cluster (GstMatroskaDemux * demux)
4416 {
4417   GstEbmlRead *ebml = GST_EBML_READ (demux);
4418   GstFlowReturn ret = GST_FLOW_OK;
4419   guint64 cluster_time = GST_CLOCK_TIME_NONE;
4420   guint32 id;
4421   guint64 cluster_offset = demux->parent.offset;
4422
4423   DEBUG_ELEMENT_START (demux, ebml, "Cluster");
4424
4425   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
4426     DEBUG_ELEMENT_STOP (demux, ebml, "Cluster", ret);
4427     return ret;
4428   }
4429
4430   while (ret == GST_FLOW_OK) {
4431     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4432       break;
4433
4434     if (demux->level_up) {
4435       demux->level_up--;
4436       break;
4437     }
4438
4439     switch (id) {
4440         /* cluster timecode */
4441       case GST_MATROSKA_ID_CLUSTERTIMECODE:
4442       {
4443         guint64 num;
4444
4445         if ((ret = gst_ebml_read_uint (ebml, &id, &num)) != GST_FLOW_OK)
4446           break;
4447
4448         GST_DEBUG_OBJECT (demux, "ClusterTimeCode: %" G_GUINT64_FORMAT, num);
4449         cluster_time = num;
4450         break;
4451       }
4452
4453         /* a group of blocks inside a cluster */
4454       case GST_MATROSKA_ID_BLOCKGROUP:
4455         DEBUG_ELEMENT_START (demux, ebml, "BlockGroup");
4456         if ((ret = gst_ebml_read_master (ebml, &id)) == GST_FLOW_OK) {
4457           ret = gst_matroska_demux_parse_blockgroup_or_simpleblock (demux,
4458               cluster_time, cluster_offset, FALSE);
4459         }
4460         DEBUG_ELEMENT_STOP (demux, ebml, "BlockGroup", ret);
4461         break;
4462
4463       case GST_MATROSKA_ID_SIMPLEBLOCK:
4464       {
4465         DEBUG_ELEMENT_START (demux, ebml, "SimpleBlock");
4466         ret = gst_matroska_demux_parse_blockgroup_or_simpleblock (demux,
4467             cluster_time, cluster_offset, TRUE);
4468         DEBUG_ELEMENT_STOP (demux, ebml, "SimpleBlock", ret);
4469         break;
4470       }
4471
4472       default:
4473         GST_WARNING ("Unknown Cluster subelement 0x%x - ignoring", id);
4474         /* fall-through */
4475       case GST_MATROSKA_ID_POSITION:
4476       case GST_MATROSKA_ID_PREVSIZE:
4477       case GST_MATROSKA_ID_ENCRYPTEDBLOCK:
4478       case GST_MATROSKA_ID_SILENTTRACKS:
4479         GST_DEBUG ("Skipping Cluster subelement 0x%x - ignoring", id);
4480         ret = gst_ebml_read_skip (ebml);
4481         break;
4482     }
4483
4484     if (demux->level_up) {
4485       demux->level_up--;
4486       break;
4487     }
4488   }
4489
4490   if (demux->element_index) {
4491     if (demux->element_index_writer_id == -1)
4492       gst_index_get_writer_id (demux->element_index,
4493           GST_OBJECT (demux), &demux->element_index_writer_id);
4494
4495     GST_LOG_OBJECT (demux, "adding association %" GST_TIME_FORMAT "-> %"
4496         G_GUINT64_FORMAT " for writer id %d",
4497         GST_TIME_ARGS (cluster_time), cluster_offset,
4498         demux->element_index_writer_id);
4499     gst_index_add_association (demux->element_index,
4500         demux->element_index_writer_id, GST_ASSOCIATION_FLAG_KEY_UNIT,
4501         GST_FORMAT_TIME, cluster_time, GST_FORMAT_BYTES, cluster_offset, NULL);
4502   }
4503
4504   DEBUG_ELEMENT_STOP (demux, ebml, "Cluster", ret);
4505
4506   return ret;
4507 }
4508
4509 static GstFlowReturn
4510 gst_matroska_demux_parse_contents_seekentry (GstMatroskaDemux * demux)
4511 {
4512   GstEbmlRead *ebml = GST_EBML_READ (demux);
4513   GstFlowReturn ret;
4514   guint64 seek_pos = (guint64) - 1;
4515   guint32 seek_id = 0;
4516   guint32 id;
4517
4518   DEBUG_ELEMENT_START (demux, ebml, "Seek");
4519
4520   if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK) {
4521     DEBUG_ELEMENT_STOP (demux, ebml, "Seek", ret);
4522     return ret;
4523   }
4524
4525   while (ret == GST_FLOW_OK) {
4526     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4527       break;
4528
4529     if (demux->level_up) {
4530       demux->level_up--;
4531       break;
4532     }
4533
4534     switch (id) {
4535       case GST_MATROSKA_ID_SEEKID:
4536       {
4537         guint64 t;
4538
4539         if ((ret = gst_ebml_read_uint (ebml, &id, &t)) != GST_FLOW_OK)
4540           break;
4541
4542         GST_DEBUG_OBJECT (demux, "SeekID: %" G_GUINT64_FORMAT, t);
4543         seek_id = t;
4544         break;
4545       }
4546
4547       case GST_MATROSKA_ID_SEEKPOSITION:
4548       {
4549         guint64 t;
4550
4551         if ((ret = gst_ebml_read_uint (ebml, &id, &t)) != GST_FLOW_OK)
4552           break;
4553
4554         if (t > G_MAXINT64) {
4555           GST_WARNING_OBJECT (demux,
4556               "Too large SeekPosition %" G_GUINT64_FORMAT, t);
4557           break;
4558         }
4559
4560         GST_DEBUG_OBJECT (demux, "SeekPosition: %" G_GUINT64_FORMAT, t);
4561         seek_pos = t;
4562         break;
4563       }
4564
4565       default:
4566         GST_WARNING_OBJECT (demux,
4567             "Unknown SeekHead subelement 0x%x - ignoring", id);
4568         ret = gst_ebml_read_skip (ebml);
4569         break;
4570     }
4571
4572     if (demux->level_up) {
4573       demux->level_up--;
4574       break;
4575     }
4576   }
4577
4578   if (ret != GST_FLOW_OK && ret != GST_FLOW_UNEXPECTED)
4579     return ret;
4580
4581   if (!seek_id || seek_pos == (guint64) - 1) {
4582     GST_WARNING_OBJECT (demux, "Incomplete seekhead entry (0x%x/%"
4583         G_GUINT64_FORMAT ")", seek_id, seek_pos);
4584     return GST_FLOW_OK;
4585   }
4586
4587   switch (seek_id) {
4588     case GST_MATROSKA_ID_CUES:
4589     case GST_MATROSKA_ID_TAGS:
4590     case GST_MATROSKA_ID_TRACKS:
4591     case GST_MATROSKA_ID_SEEKHEAD:
4592     case GST_MATROSKA_ID_SEGMENTINFO:
4593     case GST_MATROSKA_ID_ATTACHMENTS:
4594     case GST_MATROSKA_ID_CHAPTERS:
4595     {
4596       guint level_up = demux->level_up;
4597       guint64 before_pos, length;
4598       GstEbmlLevel *level;
4599
4600       /* remember */
4601       length = gst_ebml_read_get_length (ebml);
4602       before_pos = ebml->offset;
4603
4604       /* check for validity */
4605       if (seek_pos + demux->ebml_segment_start + 12 >= length) {
4606         GST_WARNING_OBJECT (demux,
4607             "SeekHead reference lies outside file!" " (%"
4608             G_GUINT64_FORMAT "+%" G_GUINT64_FORMAT "+12 >= %"
4609             G_GUINT64_FORMAT ")", seek_pos, demux->ebml_segment_start, length);
4610         break;
4611       }
4612
4613       /* seek */
4614       if (gst_ebml_read_seek (ebml, seek_pos + demux->ebml_segment_start) !=
4615           GST_FLOW_OK)
4616         break;
4617
4618       /* we don't want to lose our seekhead level, so we add
4619        * a dummy. This is a crude hack. */
4620       level = g_slice_new (GstEbmlLevel);
4621       level->start = 0;
4622       level->length = G_MAXUINT64;
4623       ebml->level = g_list_prepend (ebml->level, level);
4624
4625       /* check ID */
4626       if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4627         goto finish;
4628
4629       if (id != seek_id) {
4630         GST_WARNING_OBJECT (demux,
4631             "We looked for ID=0x%x but got ID=0x%x (pos=%" G_GUINT64_FORMAT ")",
4632             seek_id, id, seek_pos + demux->ebml_segment_start);
4633         goto finish;
4634       }
4635
4636       /* read master + parse */
4637       switch (id) {
4638         case GST_MATROSKA_ID_CUES:
4639           if (!demux->index_parsed) {
4640             ret = gst_matroska_demux_parse_index (demux);
4641           }
4642           break;
4643         case GST_MATROSKA_ID_TAGS:
4644           ret = gst_matroska_demux_parse_metadata (demux);
4645           break;
4646         case GST_MATROSKA_ID_TRACKS:
4647           if (!demux->tracks_parsed) {
4648             ret = gst_matroska_demux_parse_tracks (demux);
4649           }
4650           break;
4651
4652         case GST_MATROSKA_ID_SEGMENTINFO:
4653           if (!demux->segmentinfo_parsed) {
4654             ret = gst_matroska_demux_parse_info (demux);
4655           }
4656           break;
4657         case GST_MATROSKA_ID_SEEKHEAD:
4658         {
4659           GList *l;
4660
4661           DEBUG_ELEMENT_START (demux, ebml, "SeekHead");
4662           if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK)
4663             goto finish;
4664
4665           /* Prevent infinite recursion if there's a cycle from
4666            * one seekhead to the same again. Simply break if
4667            * we already had this seekhead, finish will clean up
4668            * everything. */
4669           for (l = ebml->level; l; l = l->next) {
4670             GstEbmlLevel *level = (GstEbmlLevel *) l->data;
4671
4672             if (level->start == ebml->offset && l->prev)
4673               goto finish;
4674           }
4675
4676           ret = gst_matroska_demux_parse_contents (demux);
4677           break;
4678         }
4679         case GST_MATROSKA_ID_ATTACHMENTS:
4680           if (!demux->attachments_parsed) {
4681             ret = gst_matroska_demux_parse_attachments (demux);
4682           }
4683           break;
4684         case GST_MATROSKA_ID_CHAPTERS:
4685           ret = gst_matroska_demux_parse_chapters (demux);
4686           break;
4687       }
4688
4689     finish:
4690       /* remove dummy level */
4691       while (ebml->level) {
4692         guint64 length;
4693
4694         level = ebml->level->data;
4695         ebml->level = g_list_delete_link (ebml->level, ebml->level);
4696         length = level->length;
4697         g_slice_free (GstEbmlLevel, level);
4698         if (length == G_MAXUINT64)
4699           break;
4700       }
4701
4702       /* seek back */
4703       (void) gst_ebml_read_seek (ebml, before_pos);
4704       demux->level_up = level_up;
4705       break;
4706     }
4707
4708     default:
4709       GST_DEBUG_OBJECT (demux, "Ignoring Seek entry for ID=0x%x", seek_id);
4710       break;
4711   }
4712   DEBUG_ELEMENT_STOP (demux, ebml, "Seek", ret);
4713
4714   return ret;
4715 }
4716
4717 static GstFlowReturn
4718 gst_matroska_demux_parse_contents (GstMatroskaDemux * demux)
4719 {
4720   GstEbmlRead *ebml = GST_EBML_READ (demux);
4721   GstFlowReturn ret = GST_FLOW_OK;
4722   guint32 id;
4723
4724   while (ret == GST_FLOW_OK) {
4725     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4726       break;
4727
4728     if (demux->level_up) {
4729       demux->level_up--;
4730       break;
4731     }
4732
4733     switch (id) {
4734       case GST_MATROSKA_ID_SEEKENTRY:
4735       {
4736         ret = gst_matroska_demux_parse_contents_seekentry (demux);
4737         /* Ignore EOS and errors here */
4738         if (ret != GST_FLOW_OK) {
4739           GST_DEBUG_OBJECT (demux, "Ignoring %s", gst_flow_get_name (ret));
4740           ret = GST_FLOW_OK;
4741         }
4742         break;
4743       }
4744
4745       default:
4746         GST_WARNING ("Unknown SeekHead subelement 0x%x - ignoring", id);
4747         ret = gst_ebml_read_skip (ebml);
4748         break;
4749     }
4750
4751     if (demux->level_up) {
4752       demux->level_up--;
4753       break;
4754     }
4755   }
4756
4757   DEBUG_ELEMENT_STOP (demux, ebml, "SeekHead", ret);
4758
4759   return ret;
4760 }
4761
4762 /* returns FALSE on error, otherwise TRUE */
4763 static GstFlowReturn
4764 gst_matroska_demux_loop_stream_parse_id (GstMatroskaDemux * demux,
4765     guint32 id, gboolean * p_run_loop)
4766 {
4767   GstEbmlRead *ebml = GST_EBML_READ (demux);
4768   GstFlowReturn ret = GST_FLOW_OK;
4769
4770   switch (id) {
4771       /* stream info 
4772        * Can exist more than once but following occurences
4773        * must have the same content so ignore them */
4774     case GST_MATROSKA_ID_SEGMENTINFO:
4775       if (!demux->segmentinfo_parsed) {
4776         if ((ret = gst_matroska_demux_parse_info (demux)) != GST_FLOW_OK)
4777           return ret;
4778       } else {
4779         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
4780           return ret;
4781       }
4782       break;
4783
4784       /* track info headers
4785        * Can exist more than once but following occurences
4786        * must have the same content so ignore them */
4787     case GST_MATROSKA_ID_TRACKS:
4788     {
4789       if (!demux->tracks_parsed) {
4790         if ((ret = gst_matroska_demux_parse_tracks (demux)) != GST_FLOW_OK)
4791           return ret;
4792       } else {
4793         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
4794           return ret;
4795       }
4796       break;
4797     }
4798
4799       /* cues - seek table
4800        * Either exists exactly one time or never but ignore
4801        * following occurences for the sake of sanity */
4802     case GST_MATROSKA_ID_CUES:
4803     {
4804       if (!demux->index_parsed) {
4805         if ((ret = gst_matroska_demux_parse_index (demux)) != GST_FLOW_OK)
4806           return ret;
4807       } else {
4808         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
4809           return ret;
4810       }
4811       break;
4812     }
4813
4814       /* metadata
4815        * can exist more than one time with different content */
4816     case GST_MATROSKA_ID_TAGS:
4817     {
4818       if ((ret = gst_matroska_demux_parse_metadata (demux)) != GST_FLOW_OK)
4819         return ret;
4820       break;
4821     }
4822
4823       /* file index (if seekable, seek to Cues/Tags/etc to parse it) */
4824     case GST_MATROSKA_ID_SEEKHEAD:
4825     {
4826       DEBUG_ELEMENT_START (demux, ebml, "SeekHead");
4827       if ((ret = gst_ebml_read_master (ebml, &id)) != GST_FLOW_OK)
4828         return ret;
4829       if ((ret = gst_matroska_demux_parse_contents (demux)) != GST_FLOW_OK)
4830         return ret;
4831       break;
4832     }
4833
4834       /* cluster - contains the payload */
4835     case GST_MATROSKA_ID_CLUSTER:
4836     {
4837       if (demux->state != GST_MATROSKA_DEMUX_STATE_DATA) {
4838         /* We need a Tracks element first before we can output anything.
4839          * Search it!
4840          */
4841         if (!demux->tracks_parsed) {
4842           GstEbmlLevel *level;
4843           guint32 iid;
4844           guint level_up;
4845           guint64 before_pos;
4846
4847           GST_WARNING_OBJECT (demux,
4848               "Found Cluster element before Tracks, searching Tracks");
4849
4850           /* remember */
4851           level_up = demux->level_up;
4852           before_pos = ebml->offset;
4853
4854           /* we don't want to lose our seekhead level, so we add
4855            * a dummy. This is a crude hack. */
4856
4857           level = g_slice_new (GstEbmlLevel);
4858           level->start = 0;
4859           level->length = G_MAXUINT64;
4860           ebml->level = g_list_prepend (ebml->level, level);
4861
4862           /* Search Tracks element */
4863           while (TRUE) {
4864             if (gst_ebml_read_skip (ebml) != GST_FLOW_OK)
4865               break;
4866
4867             if (gst_ebml_peek_id (ebml, &demux->level_up, &iid) != GST_FLOW_OK)
4868               break;
4869
4870             if (iid != GST_MATROSKA_ID_TRACKS)
4871               continue;
4872
4873             gst_matroska_demux_parse_tracks (demux);
4874             break;
4875           }
4876
4877           if (!demux->tracks_parsed) {
4878             GST_ERROR_OBJECT (demux, "No Tracks element found");
4879             ret = GST_FLOW_ERROR;
4880           }
4881
4882           /* remove dummy level */
4883           while (ebml->level) {
4884             guint64 length;
4885
4886             level = ebml->level->data;
4887             ebml->level = g_list_delete_link (ebml->level, ebml->level);
4888             length = level->length;
4889             g_slice_free (GstEbmlLevel, level);
4890             if (length == G_MAXUINT64)
4891               break;
4892           }
4893
4894           /* seek back */
4895           gst_ebml_read_seek (ebml, before_pos);
4896           demux->level_up = level_up;
4897         }
4898
4899         if (ret != GST_FLOW_OK)
4900           return ret;
4901
4902         demux->state = GST_MATROSKA_DEMUX_STATE_DATA;
4903         /* send initial discont */
4904         gst_matroska_demux_send_event (demux,
4905             gst_event_new_new_segment (FALSE, 1.0,
4906                 GST_FORMAT_TIME, 0,
4907                 (demux->segment.duration > 0) ? demux->segment.duration : -1,
4908                 0));
4909         GST_DEBUG_OBJECT (demux, "signaling no more pads");
4910         gst_element_no_more_pads (GST_ELEMENT (demux));
4911       } else {
4912         /* The idea is that we parse one cluster per loop and
4913          * then break out of the loop here. In the next call
4914          * of the loopfunc, we will get back here with the
4915          * next cluster. If an error occurs, we didn't
4916          * actually push a buffer, but we still want to break
4917          * out of the loop to handle a possible error. We'll
4918          * get back here if it's recoverable. */
4919         if ((ret = gst_matroska_demux_parse_cluster (demux)) != GST_FLOW_OK)
4920           return ret;
4921         *p_run_loop = FALSE;
4922       }
4923       break;
4924     }
4925
4926       /* attachments - contains files attached to the mkv container
4927        * like album art, etc */
4928     case GST_MATROSKA_ID_ATTACHMENTS:{
4929       if (!demux->attachments_parsed) {
4930         if ((ret = gst_matroska_demux_parse_attachments (demux)) != GST_FLOW_OK)
4931           return ret;
4932       } else {
4933         if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
4934           return ret;
4935       }
4936       break;
4937     }
4938
4939       /* chapters - contains meta information about how to group
4940        * the file into chapters, similar to DVD */
4941     case GST_MATROSKA_ID_CHAPTERS:{
4942       if ((ret = gst_matroska_demux_parse_chapters (demux)) != GST_FLOW_OK)
4943         return ret;
4944       break;
4945     }
4946
4947     default:
4948       GST_WARNING_OBJECT (demux, "Unknown Segment subelement 0x%x at %"
4949           G_GUINT64_FORMAT " - ignoring", id, GST_EBML_READ (demux)->offset);
4950       if ((ret = gst_ebml_read_skip (ebml)) != GST_FLOW_OK)
4951         return ret;
4952       break;
4953   }
4954   return ret;
4955 }
4956
4957 static GstFlowReturn
4958 gst_matroska_demux_loop_stream (GstMatroskaDemux * demux)
4959 {
4960   GstEbmlRead *ebml = GST_EBML_READ (demux);
4961   GstFlowReturn ret = GST_FLOW_OK;
4962   gboolean run_loop = TRUE;
4963   guint32 id;
4964
4965   /* we've found our segment, start reading the different contents in here */
4966   while (run_loop && ret == GST_FLOW_OK) {
4967     if ((ret = gst_ebml_peek_id (ebml, &demux->level_up, &id)) != GST_FLOW_OK)
4968       return ret;
4969
4970     if (demux->level_up) {
4971       demux->level_up--;
4972       break;
4973     }
4974
4975     ret = gst_matroska_demux_loop_stream_parse_id (demux, id, &run_loop);
4976
4977     if (demux->level_up) {
4978       demux->level_up--;
4979       break;
4980     }
4981   }
4982   return ret;
4983 }
4984
4985 static void
4986 gst_matroska_demux_loop (GstPad * pad)
4987 {
4988   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (GST_PAD_PARENT (pad));
4989   GstEbmlRead *ebml = GST_EBML_READ (demux);
4990   GstFlowReturn ret;
4991
4992   /* first, if we're to start, let's actually get starting */
4993   if (demux->state == GST_MATROSKA_DEMUX_STATE_START) {
4994     ret = gst_matroska_demux_init_stream (demux);
4995     if (ret != GST_FLOW_OK) {
4996       GST_WARNING_OBJECT (demux, "init stream failed!");
4997       goto pause;
4998     }
4999     demux->state = GST_MATROSKA_DEMUX_STATE_HEADER;
5000   }
5001
5002   /* If we have to close a segment are send a new segment do
5003    * this now */
5004
5005   if (demux->state == GST_MATROSKA_DEMUX_STATE_DATA) {
5006     if (demux->close_segment) {
5007       gst_matroska_demux_send_event (demux, demux->close_segment);
5008       demux->close_segment = NULL;
5009     }
5010     if (demux->new_segment) {
5011       gst_matroska_demux_send_event (demux, demux->new_segment);
5012       demux->new_segment = NULL;
5013     }
5014   }
5015
5016   ret = gst_matroska_demux_loop_stream (demux);
5017   if (ret != GST_FLOW_OK)
5018     goto pause;
5019
5020   /* check if we're at the end of a configured segment */
5021   if (GST_CLOCK_TIME_IS_VALID (demux->segment.stop)) {
5022     guint i;
5023
5024     g_assert (demux->num_streams == demux->src->len);
5025     for (i = 0; i < demux->src->len; i++) {
5026       GstMatroskaTrackContext *context = g_ptr_array_index (demux->src, i);
5027       if (context->pos >= demux->segment.stop) {
5028         GST_INFO_OBJECT (demux, "Reached end of segment (%" G_GUINT64_FORMAT
5029             "-%" G_GUINT64_FORMAT ") on pad %s:%s", demux->segment.start,
5030             demux->segment.stop, GST_DEBUG_PAD_NAME (context->pad));
5031         ret = GST_FLOW_UNEXPECTED;
5032         goto pause;
5033       }
5034     }
5035   }
5036
5037   if (ebml->offset == gst_ebml_read_get_length (ebml)) {
5038     GST_LOG_OBJECT (demux, "Reached end of stream, sending EOS");
5039     ret = GST_FLOW_UNEXPECTED;
5040     goto pause;
5041   }
5042
5043   return;
5044
5045   /* ERRORS */
5046 pause:
5047   {
5048     const gchar *reason = gst_flow_get_name (ret);
5049
5050     GST_LOG_OBJECT (demux, "pausing task, reason %s", reason);
5051     demux->segment_running = FALSE;
5052     gst_pad_pause_task (demux->sinkpad);
5053
5054     if (GST_FLOW_IS_FATAL (ret) || ret == GST_FLOW_NOT_LINKED) {
5055       if (ret == GST_FLOW_UNEXPECTED) {
5056         /* perform EOS logic */
5057         if (demux->segment.flags & GST_SEEK_FLAG_SEGMENT) {
5058           gint64 stop;
5059
5060           /* for segment playback we need to post when (in stream time)
5061            * we stopped, this is either stop (when set) or the duration. */
5062           if ((stop = demux->segment.stop) == -1)
5063             stop = demux->segment.duration;
5064
5065           GST_LOG_OBJECT (demux, "Sending segment done, at end of segment");
5066           gst_element_post_message (GST_ELEMENT (demux),
5067               gst_message_new_segment_done (GST_OBJECT (demux), GST_FORMAT_TIME,
5068                   stop));
5069         } else {
5070           /* normal playback, send EOS to all linked pads */
5071           GST_LOG_OBJECT (demux, "Sending EOS, at end of stream");
5072           gst_matroska_demux_send_event (demux, gst_event_new_eos ());
5073         }
5074       } else {
5075         GST_ELEMENT_ERROR (demux, STREAM, FAILED, (NULL),
5076             ("stream stopped, reason %s", reason));
5077         gst_matroska_demux_send_event (demux, gst_event_new_eos ());
5078       }
5079     }
5080     return;
5081   }
5082 }
5083
5084 static gboolean
5085 gst_matroska_demux_sink_activate (GstPad * sinkpad)
5086 {
5087   if (gst_pad_check_pull_range (sinkpad))
5088     return gst_pad_activate_pull (sinkpad, TRUE);
5089
5090   return FALSE;
5091 }
5092
5093 static gboolean
5094 gst_matroska_demux_sink_activate_pull (GstPad * sinkpad, gboolean active)
5095 {
5096   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (GST_PAD_PARENT (sinkpad));
5097
5098   if (active) {
5099     /* if we have a scheduler we can start the task */
5100     demux->segment_running = TRUE;
5101     gst_pad_start_task (sinkpad, (GstTaskFunction) gst_matroska_demux_loop,
5102         sinkpad);
5103   } else {
5104     demux->segment_running = FALSE;
5105     gst_pad_stop_task (sinkpad);
5106   }
5107
5108   return TRUE;
5109 }
5110
5111 static GstCaps *
5112 gst_matroska_demux_video_caps (GstMatroskaTrackVideoContext *
5113     videocontext, const gchar * codec_id, guint8 * data, guint size,
5114     gchar ** codec_name)
5115 {
5116   GstMatroskaTrackContext *context = (GstMatroskaTrackContext *) videocontext;
5117   GstCaps *caps = NULL;
5118
5119   g_assert (videocontext != NULL);
5120   g_assert (codec_name != NULL);
5121
5122   context->send_xiph_headers = FALSE;
5123   context->send_flac_headers = FALSE;
5124   context->send_speex_headers = FALSE;
5125
5126   /* TODO: check if we have all codec types from matroska-ids.h
5127    *       check if we have to do more special things with codec_private
5128    *
5129    * Add support for
5130    *  GST_MATROSKA_CODEC_ID_VIDEO_QUICKTIME
5131    *  GST_MATROSKA_CODEC_ID_VIDEO_SNOW
5132    */
5133
5134   if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_VFW_FOURCC)) {
5135     gst_riff_strf_vids *vids = NULL;
5136
5137     if (data) {
5138       GstBuffer *buf = NULL;
5139
5140       vids = (gst_riff_strf_vids *) data;
5141
5142       /* assure size is big enough */
5143       if (size < 24) {
5144         GST_WARNING ("Too small BITMAPINFOHEADER (%d bytes)", size);
5145         return NULL;
5146       }
5147       if (size < sizeof (gst_riff_strf_vids)) {
5148         vids = g_new (gst_riff_strf_vids, 1);
5149         memcpy (vids, data, size);
5150       }
5151
5152       /* little-endian -> byte-order */
5153       vids->size = GUINT32_FROM_LE (vids->size);
5154       vids->width = GUINT32_FROM_LE (vids->width);
5155       vids->height = GUINT32_FROM_LE (vids->height);
5156       vids->planes = GUINT16_FROM_LE (vids->planes);
5157       vids->bit_cnt = GUINT16_FROM_LE (vids->bit_cnt);
5158       vids->compression = GUINT32_FROM_LE (vids->compression);
5159       vids->image_size = GUINT32_FROM_LE (vids->image_size);
5160       vids->xpels_meter = GUINT32_FROM_LE (vids->xpels_meter);
5161       vids->ypels_meter = GUINT32_FROM_LE (vids->ypels_meter);
5162       vids->num_colors = GUINT32_FROM_LE (vids->num_colors);
5163       vids->imp_colors = GUINT32_FROM_LE (vids->imp_colors);
5164
5165       if (size > sizeof (gst_riff_strf_vids)) { /* some extra_data */
5166         buf = gst_buffer_new_and_alloc (size - sizeof (gst_riff_strf_vids));
5167         memcpy (GST_BUFFER_DATA (buf),
5168             (guint8 *) vids + sizeof (gst_riff_strf_vids),
5169             GST_BUFFER_SIZE (buf));
5170       }
5171
5172       caps = gst_riff_create_video_caps (vids->compression, NULL, vids,
5173           buf, NULL, codec_name);
5174
5175       if (buf)
5176         gst_buffer_unref (buf);
5177
5178       if (vids != (gst_riff_strf_vids *) data)
5179         g_free (vids);
5180     }
5181   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_UNCOMPRESSED)) {
5182     guint32 fourcc = 0;
5183
5184     switch (videocontext->fourcc) {
5185       case GST_MAKE_FOURCC ('I', '4', '2', '0'):
5186         *codec_name = g_strdup ("Raw planar YUV 4:2:0");
5187         fourcc = videocontext->fourcc;
5188         break;
5189       case GST_MAKE_FOURCC ('Y', 'U', 'Y', '2'):
5190         *codec_name = g_strdup ("Raw packed YUV 4:2:2");
5191         fourcc = videocontext->fourcc;
5192         break;
5193       case GST_MAKE_FOURCC ('Y', 'V', '1', '2'):
5194         *codec_name = g_strdup ("Raw packed YUV 4:2:0");
5195         fourcc = videocontext->fourcc;
5196         break;
5197       case GST_MAKE_FOURCC ('U', 'Y', 'V', 'Y'):
5198         *codec_name = g_strdup ("Raw packed YUV 4:2:2");
5199         fourcc = videocontext->fourcc;
5200         break;
5201       case GST_MAKE_FOURCC ('A', 'Y', 'U', 'V'):
5202         *codec_name = g_strdup ("Raw packed YUV 4:4:4 with alpha channel");
5203         fourcc = videocontext->fourcc;
5204         break;
5205
5206       default:
5207         GST_DEBUG ("Unknown fourcc %" GST_FOURCC_FORMAT,
5208             GST_FOURCC_ARGS (videocontext->fourcc));
5209         return NULL;
5210     }
5211
5212     caps = gst_caps_new_simple ("video/x-raw-yuv",
5213         "format", GST_TYPE_FOURCC, fourcc, NULL);
5214   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG4_SP)) {
5215     caps = gst_caps_new_simple ("video/x-divx",
5216         "divxversion", G_TYPE_INT, 4, NULL);
5217     *codec_name = g_strdup ("MPEG-4 simple profile");
5218   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG4_ASP) ||
5219       !strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG4_AP)) {
5220 #if 0
5221     caps = gst_caps_new_full (gst_structure_new ("video/x-divx",
5222             "divxversion", G_TYPE_INT, 5, NULL),
5223         gst_structure_new ("video/x-xvid", NULL),
5224         gst_structure_new ("video/mpeg",
5225             "mpegversion", G_TYPE_INT, 4,
5226             "systemstream", G_TYPE_BOOLEAN, FALSE, NULL), NULL);
5227 #endif
5228     caps = gst_caps_new_simple ("video/mpeg",
5229         "mpegversion", G_TYPE_INT, 4,
5230         "systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
5231     if (data) {
5232       GstBuffer *priv = gst_buffer_new_and_alloc (size);
5233
5234       memcpy (GST_BUFFER_DATA (priv), data, size);
5235       gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, priv, NULL);
5236       gst_buffer_unref (priv);
5237     }
5238     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG4_ASP))
5239       *codec_name = g_strdup ("MPEG-4 advanced simple profile");
5240     else
5241       *codec_name = g_strdup ("MPEG-4 advanced profile");
5242   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MSMPEG4V3)) {
5243 #if 0
5244     caps = gst_caps_new_full (gst_structure_new ("video/x-divx",
5245             "divxversion", G_TYPE_INT, 3, NULL),
5246         gst_structure_new ("video/x-msmpeg",
5247             "msmpegversion", G_TYPE_INT, 43, NULL), NULL);
5248 #endif
5249     caps = gst_caps_new_simple ("video/x-msmpeg",
5250         "msmpegversion", G_TYPE_INT, 43, NULL);
5251     *codec_name = g_strdup ("Microsoft MPEG-4 v.3");
5252   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG1) ||
5253       !strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG2)) {
5254     gint mpegversion = -1;
5255
5256     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG1))
5257       mpegversion = 1;
5258     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG2))
5259       mpegversion = 2;
5260     else
5261       g_assert_not_reached ();
5262
5263     caps = gst_caps_new_simple ("video/mpeg",
5264         "systemstream", G_TYPE_BOOLEAN, FALSE,
5265         "mpegversion", G_TYPE_INT, mpegversion, NULL);
5266     *codec_name = g_strdup_printf ("MPEG-%d video", mpegversion);
5267     context->postprocess_frame = gst_matroska_demux_add_mpeg_seq_header;
5268   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MJPEG)) {
5269     caps = gst_caps_new_simple ("image/jpeg", NULL);
5270     *codec_name = g_strdup ("Motion-JPEG");
5271   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_MPEG4_AVC)) {
5272     caps = gst_caps_new_simple ("video/x-h264", NULL);
5273     if (data) {
5274       GstBuffer *priv = gst_buffer_new_and_alloc (size);
5275
5276       memcpy (GST_BUFFER_DATA (priv), data, size);
5277       gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, priv, NULL);
5278       gst_buffer_unref (priv);
5279
5280     }
5281     *codec_name = g_strdup ("H264");
5282   } else if ((!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO1)) ||
5283       (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO2)) ||
5284       (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO3)) ||
5285       (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO4))) {
5286     gint rmversion = -1;
5287
5288     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO1))
5289       rmversion = 1;
5290     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO2))
5291       rmversion = 2;
5292     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO3))
5293       rmversion = 3;
5294     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_REALVIDEO4))
5295       rmversion = 4;
5296
5297     caps = gst_caps_new_simple ("video/x-pn-realvideo",
5298         "rmversion", G_TYPE_INT, rmversion, NULL);
5299     GST_DEBUG ("data:%p, size:0x%x", data, size);
5300     /* We need to extract the extradata ! */
5301     if (data && (size >= 0x22)) {
5302       GstBuffer *priv;
5303       guint rformat;
5304       guint subformat;
5305
5306       subformat = GST_READ_UINT32_BE (data + 0x1a);
5307       rformat = GST_READ_UINT32_BE (data + 0x1e);
5308
5309       priv = gst_buffer_new_and_alloc (size - 0x1a);
5310
5311       memcpy (GST_BUFFER_DATA (priv), data + 0x1a, size - 0x1a);
5312       gst_caps_set_simple (caps,
5313           "codec_data", GST_TYPE_BUFFER, priv,
5314           "format", G_TYPE_INT, rformat,
5315           "subformat", G_TYPE_INT, subformat, NULL);
5316       gst_buffer_unref (priv);
5317
5318     }
5319     *codec_name = g_strdup_printf ("RealVideo %d.0", rmversion);
5320   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_THEORA)) {
5321     caps = gst_caps_new_simple ("video/x-theora", NULL);
5322     context->send_xiph_headers = TRUE;
5323   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_VIDEO_DIRAC)) {
5324     caps = gst_caps_new_simple ("video/x-dirac", NULL);
5325     context->send_xiph_headers = FALSE;
5326   } else {
5327     GST_WARNING ("Unknown codec '%s', cannot build Caps", codec_id);
5328     return NULL;
5329   }
5330
5331   if (caps != NULL) {
5332     int i;
5333     GstStructure *structure;
5334
5335     for (i = 0; i < gst_caps_get_size (caps); i++) {
5336       structure = gst_caps_get_structure (caps, i);
5337
5338       /* FIXME: use the real unit here! */
5339       GST_DEBUG ("video size %dx%d, target display size %dx%d (any unit)",
5340           videocontext->pixel_width,
5341           videocontext->pixel_height,
5342           videocontext->display_width, videocontext->display_height);
5343
5344       /* pixel width and height are the w and h of the video in pixels */
5345       if (videocontext->pixel_width > 0 && videocontext->pixel_height > 0) {
5346         gint w = videocontext->pixel_width;
5347
5348         gint h = videocontext->pixel_height;
5349
5350         gst_structure_set (structure,
5351             "width", G_TYPE_INT, w, "height", G_TYPE_INT, h, NULL);
5352       }
5353
5354       if (videocontext->display_width > 0 && videocontext->display_height > 0) {
5355         int n, d;
5356
5357         /* calculate the pixel aspect ratio using the display and pixel w/h */
5358         n = videocontext->display_width * videocontext->pixel_height;
5359         d = videocontext->display_height * videocontext->pixel_width;
5360         GST_DEBUG ("setting PAR to %d/%d", n, d);
5361         gst_structure_set (structure, "pixel-aspect-ratio",
5362             GST_TYPE_FRACTION,
5363             videocontext->display_width * videocontext->pixel_height,
5364             videocontext->display_height * videocontext->pixel_width, NULL);
5365       }
5366
5367       if (videocontext->default_fps > 0.0) {
5368         GValue fps_double = { 0, };
5369         GValue fps_fraction = { 0, };
5370
5371         g_value_init (&fps_double, G_TYPE_DOUBLE);
5372         g_value_init (&fps_fraction, GST_TYPE_FRACTION);
5373         g_value_set_double (&fps_double, videocontext->default_fps);
5374         g_value_transform (&fps_double, &fps_fraction);
5375
5376         GST_DEBUG ("using default fps %f", videocontext->default_fps);
5377
5378         gst_structure_set_value (structure, "framerate", &fps_fraction);
5379         g_value_unset (&fps_double);
5380         g_value_unset (&fps_fraction);
5381       } else if (context->default_duration > 0) {
5382         GValue fps_double = { 0, };
5383         GValue fps_fraction = { 0, };
5384
5385         g_value_init (&fps_double, G_TYPE_DOUBLE);
5386         g_value_init (&fps_fraction, GST_TYPE_FRACTION);
5387         g_value_set_double (&fps_double, (gdouble) GST_SECOND /
5388             gst_guint64_to_gdouble (context->default_duration));
5389         g_value_transform (&fps_double, &fps_fraction);
5390
5391         GST_DEBUG ("using default duration %" G_GUINT64_FORMAT,
5392             context->default_duration);
5393
5394         gst_structure_set_value (structure, "framerate", &fps_fraction);
5395         g_value_unset (&fps_double);
5396         g_value_unset (&fps_fraction);
5397       } else {
5398         /* sort of a hack to get most codecs to support,
5399          * even if the default_duration is missing */
5400         gst_structure_set (structure, "framerate", GST_TYPE_FRACTION,
5401             25, 1, NULL);
5402       }
5403     }
5404
5405     gst_caps_do_simplify (caps);
5406   }
5407
5408   return caps;
5409 }
5410
5411 /*
5412  * Some AAC specific code... *sigh*
5413  * FIXME: maybe we should use '15' and code the sample rate explicitly
5414  * if the sample rate doesn't match the predefined rates exactly? (tpm)
5415  */
5416
5417 static gint
5418 aac_rate_idx (gint rate)
5419 {
5420   if (92017 <= rate)
5421     return 0;
5422   else if (75132 <= rate)
5423     return 1;
5424   else if (55426 <= rate)
5425     return 2;
5426   else if (46009 <= rate)
5427     return 3;
5428   else if (37566 <= rate)
5429     return 4;
5430   else if (27713 <= rate)
5431     return 5;
5432   else if (23004 <= rate)
5433     return 6;
5434   else if (18783 <= rate)
5435     return 7;
5436   else if (13856 <= rate)
5437     return 8;
5438   else if (11502 <= rate)
5439     return 9;
5440   else if (9391 <= rate)
5441     return 10;
5442   else
5443     return 11;
5444 }
5445
5446 static gint
5447 aac_profile_idx (const gchar * codec_id)
5448 {
5449   gint profile;
5450
5451   if (strlen (codec_id) <= 12)
5452     profile = 3;
5453   else if (!strncmp (&codec_id[12], "MAIN", 4))
5454     profile = 0;
5455   else if (!strncmp (&codec_id[12], "LC", 2))
5456     profile = 1;
5457   else if (!strncmp (&codec_id[12], "SSR", 3))
5458     profile = 2;
5459   else
5460     profile = 3;
5461
5462   return profile;
5463 }
5464
5465 #define AAC_SYNC_EXTENSION_TYPE 0x02b7
5466
5467 static GstCaps *
5468 gst_matroska_demux_audio_caps (GstMatroskaTrackAudioContext *
5469     audiocontext, const gchar * codec_id, guint8 * data, guint size,
5470     gchar ** codec_name)
5471 {
5472   GstMatroskaTrackContext *context = (GstMatroskaTrackContext *) audiocontext;
5473   GstCaps *caps = NULL;
5474
5475   g_assert (audiocontext != NULL);
5476   g_assert (codec_name != NULL);
5477
5478   context->send_xiph_headers = FALSE;
5479   context->send_flac_headers = FALSE;
5480   context->send_speex_headers = FALSE;
5481
5482   /* TODO: check if we have all codec types from matroska-ids.h
5483    *       check if we have to do more special things with codec_private
5484    *       check if we need bitdepth in different places too
5485    *       implement channel position magic
5486    * Add support for:
5487    *  GST_MATROSKA_CODEC_ID_AUDIO_AC3_BSID9
5488    *  GST_MATROSKA_CODEC_ID_AUDIO_AC3_BSID10
5489    *  GST_MATROSKA_CODEC_ID_AUDIO_QUICKTIME_QDMC
5490    *  GST_MATROSKA_CODEC_ID_AUDIO_QUICKTIME_QDM2
5491    */
5492
5493   if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L1) ||
5494       !strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L2) ||
5495       !strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L3)) {
5496     gint layer = -1;
5497
5498     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L1))
5499       layer = 1;
5500     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L2))
5501       layer = 2;
5502     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_MPEG1_L3))
5503       layer = 3;
5504     else
5505       g_assert_not_reached ();
5506
5507     caps = gst_caps_new_simple ("audio/mpeg",
5508         "mpegversion", G_TYPE_INT, 1, "layer", G_TYPE_INT, layer, NULL);
5509     *codec_name = g_strdup_printf ("MPEG-1 layer %d", layer);
5510   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_PCM_INT_BE) ||
5511       !strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_PCM_INT_LE)) {
5512     gint endianness = -1;
5513
5514     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_PCM_INT_BE))
5515       endianness = G_BIG_ENDIAN;
5516     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_PCM_INT_LE))
5517       endianness = G_LITTLE_ENDIAN;
5518     else
5519       g_assert_not_reached ();
5520
5521     caps = gst_caps_new_simple ("audio/x-raw-int",
5522         "width", G_TYPE_INT, audiocontext->bitdepth,
5523         "depth", G_TYPE_INT, audiocontext->bitdepth,
5524         "signed", G_TYPE_BOOLEAN, audiocontext->bitdepth != 8,
5525         "endianness", G_TYPE_INT, endianness, NULL);
5526
5527     *codec_name = g_strdup_printf ("Raw %d-bit PCM audio",
5528         audiocontext->bitdepth);
5529   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_PCM_FLOAT)) {
5530     caps = gst_caps_new_simple ("audio/x-raw-float",
5531         "endianness", G_TYPE_INT, G_LITTLE_ENDIAN,
5532         "width", G_TYPE_INT, audiocontext->bitdepth, NULL);
5533     *codec_name = g_strdup_printf ("Raw %d-bit floating-point audio",
5534         audiocontext->bitdepth);
5535   } else if (!strncmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_AC3,
5536           strlen (GST_MATROSKA_CODEC_ID_AUDIO_AC3))) {
5537     caps = gst_caps_new_simple ("audio/x-ac3", NULL);
5538     *codec_name = g_strdup ("AC-3 audio");
5539   } else if (!strncmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_EAC3,
5540           strlen (GST_MATROSKA_CODEC_ID_AUDIO_EAC3))) {
5541     caps = gst_caps_new_simple ("audio/x-eac3", NULL);
5542     *codec_name = g_strdup ("E-AC-3 audio");
5543   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_DTS)) {
5544     caps = gst_caps_new_simple ("audio/x-dts", NULL);
5545     *codec_name = g_strdup ("DTS audio");
5546   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_VORBIS)) {
5547     caps = gst_caps_new_simple ("audio/x-vorbis", NULL);
5548     context->send_xiph_headers = TRUE;
5549     /* vorbis decoder does tags */
5550   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_FLAC)) {
5551     caps = gst_caps_new_simple ("audio/x-flac", NULL);
5552     context->send_flac_headers = TRUE;
5553   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_SPEEX)) {
5554     caps = gst_caps_new_simple ("audio/x-speex", NULL);
5555     context->send_speex_headers = TRUE;
5556   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_ACM)) {
5557     gst_riff_strf_auds auds;
5558
5559     if (data) {
5560       GstBuffer *codec_data = gst_buffer_new ();
5561
5562       /* little-endian -> byte-order */
5563       auds.format = GST_READ_UINT16_LE (data);
5564       auds.channels = GST_READ_UINT16_LE (data + 2);
5565       auds.rate = GST_READ_UINT32_LE (data + 4);
5566       auds.av_bps = GST_READ_UINT32_LE (data + 8);
5567       auds.blockalign = GST_READ_UINT16_LE (data + 12);
5568       auds.size = GST_READ_UINT16_LE (data + 16);
5569
5570       /* 18 is the waveformatex size */
5571       gst_buffer_set_data (codec_data, data + 18, auds.size);
5572
5573       caps = gst_riff_create_audio_caps (auds.format, NULL, &auds, NULL,
5574           codec_data, codec_name);
5575       gst_buffer_unref (codec_data);
5576     }
5577   } else if (g_str_has_prefix (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_AAC)) {
5578     GstBuffer *priv = NULL;
5579     gint mpegversion = -1;
5580     gint rate_idx, profile;
5581     guint8 *data = NULL;
5582
5583     /* unspecified AAC profile with opaque private codec data */
5584     if (strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_AAC) == 0) {
5585       if (context->codec_priv_size >= 2) {
5586         guint obj_type, freq_index, explicit_freq_bytes = 0;
5587
5588         codec_id = GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG4;
5589         freq_index = (GST_READ_UINT16_BE (context->codec_priv) & 0x780) >> 7;
5590         obj_type = (GST_READ_UINT16_BE (context->codec_priv) & 0xF800) >> 11;
5591         if (freq_index == 15)
5592           explicit_freq_bytes = 3;
5593         GST_DEBUG ("obj_type = %u, freq_index = %u", obj_type, freq_index);
5594         priv = gst_buffer_new_and_alloc (context->codec_priv_size);
5595         memcpy (GST_BUFFER_DATA (priv), context->codec_priv,
5596             context->codec_priv_size);
5597         /* assume SBR if samplerate <= 24kHz */
5598         if (obj_type == 5 || (freq_index >= 6 && freq_index != 15) ||
5599             (context->codec_priv_size == (5 + explicit_freq_bytes))) {
5600           audiocontext->samplerate *= 2;
5601         }
5602       } else {
5603         GST_WARNING ("Opaque A_AAC codec ID, but no codec private data");
5604         /* just try this and see what happens ... */
5605         codec_id = GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG4;
5606       }
5607     }
5608
5609     /* make up decoder-specific data if it is not supplied */
5610     if (priv == NULL) {
5611       priv = gst_buffer_new_and_alloc (5);
5612       data = GST_BUFFER_DATA (priv);
5613       rate_idx = aac_rate_idx (audiocontext->samplerate);
5614       profile = aac_profile_idx (codec_id);
5615
5616       data[0] = ((profile + 1) << 3) | ((rate_idx & 0xE) >> 1);
5617       data[1] = ((rate_idx & 0x1) << 7) | (audiocontext->channels << 3);
5618       GST_BUFFER_SIZE (priv) = 2;
5619     }
5620
5621     if (!strncmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG2,
5622             strlen (GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG2))) {
5623       mpegversion = 2;
5624     } else if (!strncmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG4,
5625             strlen (GST_MATROSKA_CODEC_ID_AUDIO_AAC_MPEG4))) {
5626       mpegversion = 4;
5627
5628       if (g_strrstr (codec_id, "SBR")) {
5629         /* HE-AAC (aka SBR AAC) */
5630         audiocontext->samplerate *= 2;
5631         rate_idx = aac_rate_idx (audiocontext->samplerate);
5632         data[2] = AAC_SYNC_EXTENSION_TYPE >> 3;
5633         data[3] = ((AAC_SYNC_EXTENSION_TYPE & 0x07) << 5) | 5;
5634         data[4] = (1 << 7) | (rate_idx << 3);
5635         GST_BUFFER_SIZE (priv) = 5;
5636       }
5637     } else {
5638       g_assert_not_reached ();
5639     }
5640
5641     caps = gst_caps_new_simple ("audio/mpeg",
5642         "mpegversion", G_TYPE_INT, mpegversion,
5643         "framed", G_TYPE_BOOLEAN, TRUE, NULL);
5644     if (priv) {
5645       gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, priv, NULL);
5646     }
5647     *codec_name = g_strdup_printf ("MPEG-%d AAC audio", mpegversion);
5648   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_TTA)) {
5649     caps = gst_caps_new_simple ("audio/x-tta",
5650         "width", G_TYPE_INT, audiocontext->bitdepth, NULL);
5651     *codec_name = g_strdup ("TTA audio");
5652   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_WAVPACK4)) {
5653     caps = gst_caps_new_simple ("audio/x-wavpack",
5654         "width", G_TYPE_INT, audiocontext->bitdepth,
5655         "framed", G_TYPE_BOOLEAN, TRUE, NULL);
5656     *codec_name = g_strdup ("Wavpack audio");
5657     context->postprocess_frame = gst_matroska_demux_add_wvpk_header;
5658     audiocontext->wvpk_block_index = 0;
5659   } else if ((!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_14_4)) ||
5660       (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_14_4)) ||
5661       (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_COOK))) {
5662     gint raversion = -1;
5663
5664     if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_14_4))
5665       raversion = 1;
5666     else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_COOK))
5667       raversion = 8;
5668     else
5669       raversion = 2;
5670
5671     caps = gst_caps_new_simple ("audio/x-pn-realaudio",
5672         "raversion", G_TYPE_INT, raversion, NULL);
5673     /* Extract extra information from caps, mapping varies based on codec */
5674     if (data && (size >= 0x50)) {
5675       GstBuffer *priv;
5676       guint flavor;
5677       guint packet_size;
5678       guint height;
5679       guint leaf_size;
5680       guint sample_width;
5681       guint extra_data_size;
5682
5683       GST_ERROR ("real audio raversion:%d", raversion);
5684       if (raversion == 8) {
5685         /* COOK */
5686         flavor = GST_READ_UINT16_BE (data + 22);
5687         packet_size = GST_READ_UINT32_BE (data + 24);
5688         height = GST_READ_UINT16_BE (data + 40);
5689         leaf_size = GST_READ_UINT16_BE (data + 44);
5690         sample_width = GST_READ_UINT16_BE (data + 58);
5691         extra_data_size = GST_READ_UINT32_BE (data + 74);
5692
5693         GST_ERROR
5694             ("flavor:%d, packet_size:%d, height:%d, leaf_size:%d, sample_width:%d, extra_data_size:%d",
5695             flavor, packet_size, height, leaf_size, sample_width,
5696             extra_data_size);
5697         gst_caps_set_simple (caps, "flavor", G_TYPE_INT, flavor, "packet_size",
5698             G_TYPE_INT, packet_size, "height", G_TYPE_INT, height, "leaf_size",
5699             G_TYPE_INT, leaf_size, "width", G_TYPE_INT, sample_width, NULL);
5700
5701         if ((size - 78) >= extra_data_size) {
5702           priv = gst_buffer_new_and_alloc (extra_data_size);
5703           memcpy (GST_BUFFER_DATA (priv), data + 78, extra_data_size);
5704           gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, priv, NULL);
5705           gst_buffer_unref (priv);
5706         }
5707       }
5708     }
5709
5710     *codec_name = g_strdup_printf ("RealAudio %d.0", raversion);
5711   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_SIPR)) {
5712     caps = gst_caps_new_simple ("audio/x-sipro", NULL);
5713     *codec_name = g_strdup ("Sipro/ACELP.NET Voice Codec");
5714   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_RALF)) {
5715     caps = gst_caps_new_simple ("audio/x-ralf-mpeg4-generic", NULL);
5716     *codec_name = g_strdup ("Real Audio Lossless");
5717   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_AUDIO_REAL_ATRC)) {
5718     caps = gst_caps_new_simple ("audio/x-vnd.sony.atrac3", NULL);
5719     *codec_name = g_strdup ("Sony ATRAC3");
5720   } else {
5721     GST_WARNING ("Unknown codec '%s', cannot build Caps", codec_id);
5722     return NULL;
5723   }
5724
5725   if (caps != NULL) {
5726     if (audiocontext->samplerate > 0 && audiocontext->channels > 0) {
5727       gint i;
5728
5729       for (i = 0; i < gst_caps_get_size (caps); i++) {
5730         gst_structure_set (gst_caps_get_structure (caps, i),
5731             "channels", G_TYPE_INT, audiocontext->channels,
5732             "rate", G_TYPE_INT, audiocontext->samplerate, NULL);
5733       }
5734     }
5735
5736     gst_caps_do_simplify (caps);
5737   }
5738
5739   return caps;
5740 }
5741
5742 static GstCaps *
5743 gst_matroska_demux_subtitle_caps (GstMatroskaTrackSubtitleContext *
5744     subtitlecontext, const gchar * codec_id, gpointer data, guint size)
5745 {
5746   GstCaps *caps = NULL;
5747   GstMatroskaTrackContext *context =
5748       (GstMatroskaTrackContext *) subtitlecontext;
5749
5750   /* for backwards compatibility */
5751   if (!g_ascii_strcasecmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_ASCII))
5752     codec_id = GST_MATROSKA_CODEC_ID_SUBTITLE_UTF8;
5753   else if (!g_ascii_strcasecmp (codec_id, "S_SSA"))
5754     codec_id = GST_MATROSKA_CODEC_ID_SUBTITLE_SSA;
5755   else if (!g_ascii_strcasecmp (codec_id, "S_ASS"))
5756     codec_id = GST_MATROSKA_CODEC_ID_SUBTITLE_ASS;
5757   else if (!g_ascii_strcasecmp (codec_id, "S_USF"))
5758     codec_id = GST_MATROSKA_CODEC_ID_SUBTITLE_USF;
5759
5760   /* TODO: Add GST_MATROSKA_CODEC_ID_SUBTITLE_BMP support
5761    * Check if we have to do something with codec_private */
5762   if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_UTF8)) {
5763     caps = gst_caps_new_simple ("text/plain", NULL);
5764     context->postprocess_frame = gst_matroska_demux_check_subtitle_buffer;
5765   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_SSA)) {
5766     caps = gst_caps_new_simple ("application/x-ssa", NULL);
5767     context->postprocess_frame = gst_matroska_demux_check_subtitle_buffer;
5768   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_ASS)) {
5769     caps = gst_caps_new_simple ("application/x-ass", NULL);
5770     context->postprocess_frame = gst_matroska_demux_check_subtitle_buffer;
5771   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_USF)) {
5772     caps = gst_caps_new_simple ("application/x-usf", NULL);
5773     context->postprocess_frame = gst_matroska_demux_check_subtitle_buffer;
5774   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_VOBSUB)) {
5775     caps = gst_caps_new_simple ("video/x-dvd-subpicture", NULL);
5776     ((GstMatroskaTrackContext *) subtitlecontext)->send_dvd_event = TRUE;
5777   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_HDMVPGS)) {
5778     caps = gst_caps_new_simple ("subpicture/x-pgs", NULL);
5779   } else if (!strcmp (codec_id, GST_MATROSKA_CODEC_ID_SUBTITLE_KATE)) {
5780     caps = gst_caps_new_simple ("subtitle/x-kate", NULL);
5781     context->send_xiph_headers = TRUE;
5782   } else {
5783     GST_DEBUG ("Unknown subtitle stream: codec_id='%s'", codec_id);
5784     caps = gst_caps_new_simple ("application/x-subtitle-unknown", NULL);
5785   }
5786
5787   if (data != NULL && size > 0) {
5788     GstBuffer *buf;
5789
5790     buf = gst_buffer_new_and_alloc (size);
5791     memcpy (GST_BUFFER_DATA (buf), data, size);
5792     gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, buf, NULL);
5793     gst_buffer_unref (buf);
5794   }
5795
5796   return caps;
5797 }
5798
5799 static void
5800 gst_matroska_demux_set_index (GstElement * element, GstIndex * index)
5801 {
5802   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
5803
5804   GST_OBJECT_LOCK (demux);
5805   if (demux->element_index)
5806     gst_object_unref (demux->element_index);
5807   demux->element_index = gst_object_ref (index);
5808   GST_OBJECT_UNLOCK (demux);
5809   GST_DEBUG_OBJECT (demux, "Set index %" GST_PTR_FORMAT, demux->element_index);
5810 }
5811
5812 static GstIndex *
5813 gst_matroska_demux_get_index (GstElement * element)
5814 {
5815   GstIndex *result = NULL;
5816   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
5817
5818   GST_OBJECT_LOCK (demux);
5819   if (demux->element_index)
5820     result = gst_object_ref (demux->element_index);
5821   GST_OBJECT_UNLOCK (demux);
5822
5823   GST_DEBUG_OBJECT (demux, "Returning index %" GST_PTR_FORMAT, result);
5824
5825   return result;
5826 }
5827
5828 static GstStateChangeReturn
5829 gst_matroska_demux_change_state (GstElement * element,
5830     GstStateChange transition)
5831 {
5832   GstMatroskaDemux *demux = GST_MATROSKA_DEMUX (element);
5833   GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS;
5834
5835   /* handle upwards state changes here */
5836   switch (transition) {
5837     default:
5838       break;
5839   }
5840
5841   ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition);
5842
5843   /* handle downwards state changes */
5844   switch (transition) {
5845     case GST_STATE_CHANGE_PAUSED_TO_READY:
5846       gst_matroska_demux_reset (GST_ELEMENT (demux));
5847       break;
5848     default:
5849       break;
5850   }
5851
5852   return ret;
5853 }
5854
5855 gboolean
5856 gst_matroska_demux_plugin_init (GstPlugin * plugin)
5857 {
5858   gst_riff_init ();
5859
5860   /* create an elementfactory for the matroska_demux element */
5861   if (!gst_element_register (plugin, "matroskademux",
5862           GST_RANK_PRIMARY, GST_TYPE_MATROSKA_DEMUX))
5863     return FALSE;
5864
5865   return TRUE;
5866 }