5a9ab7d2a8df2e2071fcfe2918ab2ec85cbf4136
1 /* GStreamer
2 * Copyright (C) <1999> Erik Walthinsen <omega@cse.ogi.edu>
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
13 *
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
18 */
20 #ifdef HAVE_CONFIG_H
21 #include "config.h"
22 #endif
24 #include <string.h>
25 #include "gstmad.h"
27 #define GST_TYPE_MAD \
28 (gst_mad_get_type())
29 #define GST_MAD(obj) \
30 (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_MAD,GstMad))
31 #define GST_MAD_CLASS(klass) \
32 (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_MAD,GstMad))
33 #define GST_IS_MAD(obj) \
34 (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_MAD))
35 #define GST_IS_MAD_CLASS(obj) \
36 (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_MAD))
39 typedef struct _GstMad GstMad;
40 typedef struct _GstMadClass GstMadClass;
42 struct _GstMad
43 {
44 GstElement element;
46 /* pads */
47 GstPad *sinkpad, *srcpad;
49 /* state */
50 struct mad_stream stream;
51 struct mad_frame frame;
52 struct mad_synth synth;
53 guchar *tempbuffer; /* temporary buffer to serve to mad */
54 glong tempsize; /* running count of temp buffer size */
55 GstClockTime last_ts;
56 guint64 base_byte_offset;
57 guint64 bytes_consumed; /* since the base_byte_offset */
58 guint64 total_samples; /* the number of samples since the sync point */
60 gboolean in_error; /* set when mad's in an error state */
61 gboolean restart;
62 guint64 segment_start;
64 /* info */
65 struct mad_header header;
66 gboolean new_header;
67 guint framecount;
68 gint vbr_average; /* average bitrate */
69 guint64 vbr_rate; /* average * framecount */
71 gboolean half;
72 gboolean ignore_crc;
74 GstTagList *tags;
76 /* negotiated format */
77 gint rate, pending_rate;
78 gint channels, pending_channels;
79 gint times_pending;
81 gboolean caps_set; /* used to keep track of whether to change/update caps */
82 GstIndex *index;
83 gint index_id;
85 gboolean check_for_xing;
86 };
88 struct _GstMadClass
89 {
90 GstElementClass parent_class;
91 };
93 /* elementfactory information */
94 static GstElementDetails gst_mad_details =
95 GST_ELEMENT_DETAILS ("mad mp3 decoder",
96 "Codec/Decoder/Audio",
97 "Uses mad code to decode mp3 streams",
98 "Wim Taymans <wim.taymans@chello.be>");
101 /* Mad signals and args */
102 enum
103 {
104 /* FILL ME */
105 LAST_SIGNAL
106 };
108 enum
109 {
110 ARG_0,
111 ARG_HALF,
112 ARG_IGNORE_CRC,
113 ARG_METADATA,
114 ARG_STREAMINFO
115 /* FILL ME */
116 };
118 GST_DEBUG_CATEGORY_STATIC (mad_debug);
119 #define GST_CAT_DEFAULT mad_debug
121 static GstStaticPadTemplate mad_src_template_factory =
122 GST_STATIC_PAD_TEMPLATE ("src",
123 GST_PAD_SRC,
124 GST_PAD_ALWAYS,
125 GST_STATIC_CAPS ("audio/x-raw-int, "
126 "endianness = (int) " G_STRINGIFY (G_BYTE_ORDER) ", "
127 "signed = (boolean) true, "
128 "width = (int) 16, "
129 "depth = (int) 16, "
130 "rate = (int) { 8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000 }, "
131 "channels = (int) [ 1, 2 ]")
132 );
134 /* FIXME: make three caps, for mpegversion 1, 2 and 2.5 */
135 static GstStaticPadTemplate mad_sink_template_factory =
136 GST_STATIC_PAD_TEMPLATE ("sink",
137 GST_PAD_SINK,
138 GST_PAD_ALWAYS,
139 GST_STATIC_CAPS ("audio/mpeg, "
140 "mpegversion = (int) 1, "
141 "layer = (int) [ 1, 3 ], "
142 "rate = (int) { 8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000 }, "
143 "channels = (int) [ 1, 2 ]")
144 );
146 static void gst_mad_base_init (gpointer g_class);
147 static void gst_mad_class_init (GstMadClass * klass);
148 static void gst_mad_init (GstMad * mad);
149 static void gst_mad_dispose (GObject * object);
151 static void gst_mad_set_property (GObject * object, guint prop_id,
152 const GValue * value, GParamSpec * pspec);
153 static void gst_mad_get_property (GObject * object, guint prop_id,
154 GValue * value, GParamSpec * pspec);
156 static gboolean gst_mad_src_event (GstPad * pad, GstEvent * event);
158 #if 0
159 static const GstFormat *gst_mad_get_formats (GstPad * pad);
160 #endif
162 static const GstQueryType *gst_mad_get_query_types (GstPad * pad);
164 static gboolean gst_mad_src_query (GstPad * pad, GstQuery * query);
165 static gboolean gst_mad_convert_sink (GstPad * pad, GstFormat src_format,
166 gint64 src_value, GstFormat * dest_format, gint64 * dest_value);
167 static gboolean gst_mad_convert_src (GstPad * pad, GstFormat src_format,
168 gint64 src_value, GstFormat * dest_format, gint64 * dest_value);
170 static gboolean gst_mad_sink_event (GstPad * pad, GstEvent * event);
171 static GstFlowReturn gst_mad_chain (GstPad * pad, GstBuffer * buffer);
173 static GstStateChangeReturn gst_mad_change_state (GstElement * element,
174 GstStateChange transition);
176 static void gst_mad_set_index (GstElement * element, GstIndex * index);
177 static GstIndex *gst_mad_get_index (GstElement * element);
180 static GstElementClass *parent_class = NULL;
182 /* static guint gst_mad_signals[LAST_SIGNAL] = { 0 }; */
184 GType
185 gst_mad_get_type (void)
186 {
187 static GType mad_type = 0;
189 if (!mad_type) {
190 static const GTypeInfo mad_info = {
191 sizeof (GstMadClass),
192 gst_mad_base_init,
193 NULL,
194 (GClassInitFunc) gst_mad_class_init,
195 NULL,
196 NULL,
197 sizeof (GstMad),
198 0,
199 (GInstanceInitFunc) gst_mad_init,
200 };
202 mad_type =
203 g_type_register_static (GST_TYPE_ELEMENT, "GstMad", &mad_info, 0);
204 }
205 GST_DEBUG_CATEGORY_INIT (mad_debug, "mad", 0, "mad mp3 decoding");
206 return mad_type;
207 }
209 #define GST_TYPE_MAD_LAYER (gst_mad_layer_get_type())
210 G_GNUC_UNUSED static GType
211 gst_mad_layer_get_type (void)
212 {
213 static GType mad_layer_type = 0;
214 static GEnumValue mad_layer[] = {
215 {0, "0", "Unknown"},
216 {MAD_LAYER_I, "1", "I"},
217 {MAD_LAYER_II, "2", "II"},
218 {MAD_LAYER_III, "3", "III"},
219 {0, NULL, NULL},
220 };
222 if (!mad_layer_type) {
223 mad_layer_type = g_enum_register_static ("GstMadLayer", mad_layer);
224 }
225 return mad_layer_type;
226 }
228 #define GST_TYPE_MAD_MODE (gst_mad_mode_get_type())
229 G_GNUC_UNUSED static GType
230 gst_mad_mode_get_type (void)
231 {
232 static GType mad_mode_type = 0;
233 static GEnumValue mad_mode[] = {
234 {-1, "-1", "Unknown"},
235 {MAD_MODE_SINGLE_CHANNEL, "0", "Single Channel"},
236 {MAD_MODE_DUAL_CHANNEL, "1", "Dual Channel"},
237 {MAD_MODE_JOINT_STEREO, "2", "Joint Stereo"},
238 {MAD_MODE_STEREO, "3", "Stereo"},
239 {0, NULL, NULL},
240 };
242 if (!mad_mode_type) {
243 mad_mode_type = g_enum_register_static ("GstMadMode", mad_mode);
244 }
245 return mad_mode_type;
246 }
248 #define GST_TYPE_MAD_EMPHASIS (gst_mad_emphasis_get_type())
249 G_GNUC_UNUSED static GType
250 gst_mad_emphasis_get_type (void)
251 {
252 static GType mad_emphasis_type = 0;
253 static GEnumValue mad_emphasis[] = {
254 {-1, "-1", "Unknown"},
255 {MAD_EMPHASIS_NONE, "0", "None"},
256 {MAD_EMPHASIS_50_15_US, "1", "50/15 Microseconds"},
257 {MAD_EMPHASIS_CCITT_J_17, "2", "CCITT J.17"},
258 {MAD_EMPHASIS_RESERVED, "3", "Reserved"},
259 {0, NULL, NULL},
260 };
262 if (!mad_emphasis_type) {
263 mad_emphasis_type = g_enum_register_static ("GstMadEmphasis", mad_emphasis);
264 }
265 return mad_emphasis_type;
266 }
268 static void
269 gst_mad_base_init (gpointer g_class)
270 {
271 GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
273 gst_element_class_add_pad_template (element_class,
274 gst_static_pad_template_get (&mad_sink_template_factory));
275 gst_element_class_add_pad_template (element_class,
276 gst_static_pad_template_get (&mad_src_template_factory));
277 gst_element_class_set_details (element_class, &gst_mad_details);
278 }
279 static void
280 gst_mad_class_init (GstMadClass * klass)
281 {
282 GObjectClass *gobject_class;
283 GstElementClass *gstelement_class;
285 gobject_class = (GObjectClass *) klass;
286 gstelement_class = (GstElementClass *) klass;
288 parent_class = g_type_class_ref (GST_TYPE_ELEMENT);
290 gobject_class->set_property = gst_mad_set_property;
291 gobject_class->get_property = gst_mad_get_property;
292 gobject_class->dispose = gst_mad_dispose;
294 gstelement_class->change_state = gst_mad_change_state;
295 gstelement_class->set_index = gst_mad_set_index;
296 gstelement_class->get_index = gst_mad_get_index;
298 /* init properties */
299 /* currently, string representations are used, we might want to change that */
300 /* FIXME: descriptions need to be more technical,
301 * default values and ranges need to be selected right */
302 g_object_class_install_property (gobject_class, ARG_HALF,
303 g_param_spec_boolean ("half", "Half", "Generate PCM at 1/2 sample rate",
304 FALSE, G_PARAM_READWRITE));
305 g_object_class_install_property (gobject_class, ARG_IGNORE_CRC,
306 g_param_spec_boolean ("ignore_crc", "Ignore CRC", "Ignore CRC errors",
307 TRUE, G_PARAM_READWRITE));
309 /* register tags */
310 #define GST_TAG_LAYER "layer"
311 #define GST_TAG_MODE "mode"
312 #define GST_TAG_EMPHASIS "emphasis"
314 gst_tag_register (GST_TAG_LAYER, GST_TAG_FLAG_ENCODED, G_TYPE_UINT,
315 "layer", "MPEG audio layer", NULL);
316 gst_tag_register (GST_TAG_MODE, GST_TAG_FLAG_ENCODED, G_TYPE_STRING,
317 "mode", "MPEG audio channel mode", NULL);
318 gst_tag_register (GST_TAG_EMPHASIS, GST_TAG_FLAG_ENCODED, G_TYPE_STRING,
319 "emphasis", "MPEG audio emphasis", NULL);
320 }
322 static void
323 gst_mad_init (GstMad * mad)
324 {
325 GstPadTemplate *template;
327 /* create the sink and src pads */
328 template = gst_static_pad_template_get (&mad_sink_template_factory);
329 mad->sinkpad = gst_pad_new_from_template (template, "sink");
330 gst_object_unref (template);
331 gst_element_add_pad (GST_ELEMENT (mad), mad->sinkpad);
332 gst_pad_set_chain_function (mad->sinkpad, GST_DEBUG_FUNCPTR (gst_mad_chain));
333 gst_pad_set_event_function (mad->sinkpad,
334 GST_DEBUG_FUNCPTR (gst_mad_sink_event));
335 #if 0
336 gst_pad_set_convert_function (mad->sinkpad,
337 GST_DEBUG_FUNCPTR (gst_mad_convert_sink));
338 gst_pad_set_formats_function (mad->sinkpad,
339 GST_DEBUG_FUNCPTR (gst_mad_get_formats));
340 #endif
341 template = gst_static_pad_template_get (&mad_src_template_factory);
342 mad->srcpad = gst_pad_new_from_template (template, "src");
343 gst_object_unref (template);
344 gst_element_add_pad (GST_ELEMENT (mad), mad->srcpad);
345 gst_pad_set_event_function (mad->srcpad,
346 GST_DEBUG_FUNCPTR (gst_mad_src_event));
347 gst_pad_set_query_function (mad->srcpad,
348 GST_DEBUG_FUNCPTR (gst_mad_src_query));
349 gst_pad_set_query_type_function (mad->srcpad,
350 GST_DEBUG_FUNCPTR (gst_mad_get_query_types));
351 gst_pad_use_fixed_caps (mad->srcpad);
352 #if 0
353 gst_pad_set_convert_function (mad->srcpad,
354 GST_DEBUG_FUNCPTR (gst_mad_convert_src));
355 gst_pad_set_formats_function (mad->srcpad,
356 GST_DEBUG_FUNCPTR (gst_mad_get_formats));
357 #endif
358 mad->tempbuffer = g_malloc (MAD_BUFFER_MDLEN * 3);
359 mad->tempsize = 0;
360 mad->base_byte_offset = 0;
361 mad->bytes_consumed = 0;
362 mad->total_samples = 0;
363 mad->new_header = TRUE;
364 mad->framecount = 0;
365 mad->vbr_average = 0;
366 mad->vbr_rate = 0;
367 mad->restart = TRUE;
368 mad->segment_start = 0;
369 mad->header.mode = -1;
370 mad->header.emphasis = -1;
371 mad->tags = NULL;
373 mad->half = FALSE;
374 mad->ignore_crc = TRUE;
375 mad->check_for_xing = TRUE;
376 }
378 static void
379 gst_mad_dispose (GObject * object)
380 {
381 GstMad *mad = GST_MAD (object);
383 gst_mad_set_index (GST_ELEMENT (object), NULL);
385 G_OBJECT_CLASS (parent_class)->dispose (object);
387 g_free (mad->tempbuffer);
388 }
390 static void
391 gst_mad_set_index (GstElement * element, GstIndex * index)
392 {
393 GstMad *mad = GST_MAD (element);
395 mad->index = index;
397 if (index)
398 gst_index_get_writer_id (index, GST_OBJECT (element), &mad->index_id);
399 }
401 static GstIndex *
402 gst_mad_get_index (GstElement * element)
403 {
404 GstMad *mad = GST_MAD (element);
406 return mad->index;
407 }
409 #if 0
410 static const GstFormat *
411 gst_mad_get_formats (GstPad * pad)
412 {
413 static const GstFormat src_formats[] = {
414 GST_FORMAT_BYTES,
415 GST_FORMAT_DEFAULT,
416 GST_FORMAT_TIME,
417 0
418 };
419 static const GstFormat sink_formats[] = {
420 GST_FORMAT_BYTES,
421 GST_FORMAT_TIME,
422 0
423 };
425 return (GST_PAD_IS_SRC (pad) ? src_formats : sink_formats);
426 }
427 #endif
429 static gboolean
430 gst_mad_convert_sink (GstPad * pad, GstFormat src_format, gint64 src_value,
431 GstFormat * dest_format, gint64 * dest_value)
432 {
433 gboolean res = TRUE;
434 GstMad *mad;
436 mad = GST_MAD (GST_PAD_PARENT (pad));
438 if (mad->vbr_average == 0)
439 return FALSE;
441 switch (src_format) {
442 case GST_FORMAT_BYTES:
443 switch (*dest_format) {
444 case GST_FORMAT_TIME:
445 /* multiply by 8 because vbr is in bits/second */
446 *dest_value = src_value * 8 * GST_SECOND / mad->vbr_average;
447 break;
448 default:
449 res = FALSE;
450 }
451 break;
452 case GST_FORMAT_TIME:
453 switch (*dest_format) {
454 case GST_FORMAT_BYTES:
455 /* multiply by 8 because vbr is in bits/second */
456 *dest_value = src_value * mad->vbr_average / (8 * GST_SECOND);
457 break;
458 default:
459 res = FALSE;
460 }
461 break;
462 default:
463 res = FALSE;
464 }
465 return res;
466 }
468 static gboolean
469 gst_mad_convert_src (GstPad * pad, GstFormat src_format, gint64 src_value,
470 GstFormat * dest_format, gint64 * dest_value)
471 {
472 gboolean res = TRUE;
473 guint scale = 1;
474 gint bytes_per_sample;
475 GstMad *mad;
477 mad = GST_MAD (GST_PAD_PARENT (pad));
479 bytes_per_sample = MAD_NCHANNELS (&mad->frame.header) << 1;
481 switch (src_format) {
482 case GST_FORMAT_BYTES:
483 switch (*dest_format) {
484 case GST_FORMAT_DEFAULT:
485 if (bytes_per_sample == 0)
486 return FALSE;
487 *dest_value = src_value / bytes_per_sample;
488 break;
489 case GST_FORMAT_TIME:
490 {
491 gint byterate = bytes_per_sample * mad->frame.header.samplerate;
493 if (byterate == 0)
494 return FALSE;
495 *dest_value = src_value * GST_SECOND / byterate;
496 break;
497 }
498 default:
499 res = FALSE;
500 }
501 break;
502 case GST_FORMAT_DEFAULT:
503 switch (*dest_format) {
504 case GST_FORMAT_BYTES:
505 *dest_value = src_value * bytes_per_sample;
506 break;
507 case GST_FORMAT_TIME:
508 if (mad->frame.header.samplerate == 0)
509 return FALSE;
510 *dest_value = src_value * GST_SECOND / mad->frame.header.samplerate;
511 break;
512 default:
513 res = FALSE;
514 }
515 break;
516 case GST_FORMAT_TIME:
517 switch (*dest_format) {
518 case GST_FORMAT_BYTES:
519 scale = bytes_per_sample;
520 /* fallthrough */
521 case GST_FORMAT_DEFAULT:
522 *dest_value =
523 src_value * scale * mad->frame.header.samplerate / GST_SECOND;
524 break;
525 default:
526 res = FALSE;
527 }
528 break;
529 default:
530 res = FALSE;
531 }
532 return res;
533 }
535 static const GstQueryType *
536 gst_mad_get_query_types (GstPad * pad)
537 {
538 static const GstQueryType gst_mad_src_query_types[] = {
539 GST_QUERY_POSITION,
540 GST_QUERY_DURATION,
541 GST_QUERY_CONVERT,
542 0
543 };
545 return gst_mad_src_query_types;
546 }
548 static gboolean
549 gst_mad_src_query (GstPad * pad, GstQuery * query)
550 {
551 gboolean res = TRUE;
552 GstMad *mad;
554 mad = GST_MAD (GST_PAD_PARENT (pad));
556 switch (GST_QUERY_TYPE (query)) {
557 case GST_QUERY_POSITION:
558 {
559 GstFormat format;
560 gint64 cur;
562 /* save requested format */
563 gst_query_parse_position (query, &format, NULL);
565 /* and convert to the requested format */
566 if (format != GST_FORMAT_DEFAULT) {
567 if (!gst_mad_convert_src (pad, GST_FORMAT_DEFAULT, mad->total_samples,
568 &format, &cur))
569 goto error;
570 } else {
571 cur = mad->total_samples;
572 }
574 gst_query_set_position (query, format, cur);
576 GST_LOG_OBJECT (mad,
577 "position query: we return %llu (format %u)", cur, format);
578 break;
579 }
580 case GST_QUERY_DURATION:
581 {
582 GstFormat format;
583 GstFormat rformat;
584 gint64 total, total_bytes;
585 GstPad *peer;
587 /* save requested format */
588 gst_query_parse_duration (query, &format, NULL);
590 /* query peer for total length in bytes */
591 gst_query_set_duration (query, GST_FORMAT_BYTES, -1);
593 if ((peer = gst_pad_get_peer (mad->sinkpad)) == NULL)
594 goto error;
596 if (!gst_pad_query (peer, query)) {
597 GST_LOG_OBJECT (mad, "query on peer pad failed");
598 goto error;
599 }
600 gst_object_unref (peer);
602 /* get the returned format */
603 gst_query_parse_duration (query, &rformat, &total_bytes);
604 if (rformat == GST_FORMAT_BYTES)
605 GST_LOG_OBJECT (mad, "peer pad returned total=%lld bytes", total_bytes);
606 else if (rformat == GST_FORMAT_TIME)
607 GST_LOG_OBJECT (mad, "peer pad returned time=%lld", total_bytes);
609 /* Check if requested format is returned format */
610 if (format == rformat)
611 return TRUE;
613 if (total_bytes != -1) {
614 if (format != GST_FORMAT_BYTES) {
615 if (!gst_mad_convert_sink (pad, GST_FORMAT_BYTES, total_bytes,
616 &format, &total))
617 goto error;
618 } else {
619 total = total_bytes;
620 }
621 } else {
622 total = -1;
623 }
625 gst_query_set_duration (query, format, total);
627 GST_LOG_OBJECT (mad,
628 "position query: we return %llu (format %u)", total, format);
629 break;
630 }
631 case GST_QUERY_CONVERT:
632 {
633 GstFormat src_fmt, dest_fmt;
634 gint64 src_val, dest_val;
636 gst_query_parse_convert (query, &src_fmt, &src_val, &dest_fmt, &dest_val);
637 if (!(res =
638 gst_mad_convert_src (pad, src_fmt, src_val, &dest_fmt,
639 &dest_val)))
640 goto error;
641 gst_query_set_convert (query, src_fmt, src_val, dest_fmt, dest_val);
642 break;
643 }
644 default:
645 res = FALSE;
646 break;
647 }
648 return res;
650 error:
652 GST_DEBUG ("error handling query");
653 return FALSE;
654 }
656 static gboolean
657 index_seek (GstMad * mad, GstPad * pad, GstEvent * event)
658 {
659 gdouble rate;
660 GstFormat format;
661 GstSeekFlags flags;
662 GstSeekType cur_type, stop_type;
663 gint64 cur, stop;
665 /* since we know the exact byteoffset of the frame,
666 make sure to try bytes first */
668 const GstFormat try_all_formats[] = {
669 GST_FORMAT_BYTES,
670 GST_FORMAT_TIME,
671 0
672 };
673 const GstFormat *try_formats = try_all_formats;
674 const GstFormat *peer_formats;
676 gst_event_parse_seek (event, &rate, &format, &flags,
677 &cur_type, &cur, &stop_type, &stop);
679 GstIndexEntry *entry = gst_index_get_assoc_entry (mad->index, mad->index_id,
680 GST_INDEX_LOOKUP_BEFORE, 0,
681 format, cur);
683 GST_DEBUG ("index seek");
685 if (!entry)
686 return FALSE;
688 #if 0
689 peer_formats = gst_pad_get_formats (GST_PAD_PEER (mad->sinkpad));
690 #else
691 peer_formats = try_all_formats; /* FIXME */
692 #endif
694 while (gst_formats_contains (peer_formats, *try_formats)) {
695 gint64 value;
696 GstEvent *seek_event;
698 if (gst_index_entry_assoc_map (entry, *try_formats, &value)) {
699 /* lookup succeeded, create the seek */
701 GST_DEBUG ("index %s %" G_GINT64_FORMAT
702 " -> %s %" G_GINT64_FORMAT,
703 gst_format_get_details (format)->nick,
704 cur, gst_format_get_details (*try_formats)->nick, value);
706 seek_event = gst_event_new_seek (rate, *try_formats, flags,
707 cur_type, value, stop_type, stop);
709 if (gst_pad_send_event (GST_PAD_PEER (mad->sinkpad), seek_event)) {
710 /* seek worked, we're done, loop will exit */
711 mad->restart = TRUE;
712 g_assert (format == GST_FORMAT_TIME);
713 mad->segment_start = cur;
714 return TRUE;
715 }
716 }
717 try_formats++;
718 }
720 return FALSE;
721 }
723 static gboolean
724 normal_seek (GstMad * mad, GstPad * pad, GstEvent * event)
725 {
726 gdouble rate;
727 GstFormat format, conv;
728 GstSeekFlags flags;
729 GstSeekType cur_type, stop_type;
730 gint64 cur, stop;
731 gint64 time_cur, time_stop;
732 gint64 bytes_cur, bytes_stop;
733 guint flush;
735 /* const GstFormat *peer_formats; */
736 gboolean res;
738 GST_DEBUG ("normal seek");
740 gst_event_parse_seek (event, &rate, &format, &flags,
741 &cur_type, &cur, &stop_type, &stop);
743 if (format != GST_FORMAT_TIME) {
744 conv = GST_FORMAT_TIME;
745 if (!gst_mad_convert_src (pad, format, cur, &conv, &time_cur))
746 goto convert_error;
747 if (!gst_mad_convert_src (pad, format, stop, &conv, &time_stop))
748 goto convert_error;
749 } else {
750 time_cur = cur;
751 time_stop = stop;
752 }
754 GST_DEBUG ("seek to time %" GST_TIME_FORMAT "-%" GST_TIME_FORMAT,
755 GST_TIME_ARGS (time_cur), GST_TIME_ARGS (time_stop));
757 /* shave off the flush flag, we'll need it later */
758 flush = flags & GST_SEEK_FLAG_FLUSH;
760 /* assume the worst */
761 res = FALSE;
763 conv = GST_FORMAT_BYTES;
764 if (!gst_mad_convert_sink (pad, GST_FORMAT_TIME, time_cur, &conv, &bytes_cur))
765 goto convert_error;
766 if (!gst_mad_convert_sink (pad, GST_FORMAT_TIME, time_stop, &conv,
767 &bytes_stop))
768 goto convert_error;
770 {
771 GstEvent *seek_event;
773 /* conversion succeeded, create the seek */
774 seek_event =
775 gst_event_new_seek (rate, GST_FORMAT_BYTES, flags, cur_type,
776 bytes_cur, stop_type, bytes_stop);
778 /* do the seek */
779 res = gst_pad_push_event (mad->sinkpad, seek_event);
780 }
781 #if 0
782 peer_formats = gst_pad_get_formats (GST_PAD_PEER (mad->sinkpad));
783 /* while we did not exhaust our seek formats without result */
784 while (peer_formats && *peer_formats && !res) {
785 gint64 desired_offset;
787 format = *peer_formats;
789 /* try to convert requested format to one we can seek with on the sinkpad */
790 if (gst_pad_convert (mad->sinkpad, GST_FORMAT_TIME, src_offset,
791 &format, &desired_offset)) {
792 GstEvent *seek_event;
794 /* conversion succeeded, create the seek */
795 seek_event =
796 gst_event_new_seek (format | GST_EVENT_SEEK_METHOD (event) | flush,
797 desired_offset);
798 /* do the seek */
799 if (gst_pad_send_event (GST_PAD_PEER (mad->sinkpad), seek_event)) {
800 /* seek worked, we're done, loop will exit */
801 res = TRUE;
802 }
803 }
804 /* at this point, either the seek worked or res == FALSE */
805 if (res)
806 /* we need to break out of the processing loop on flush */
807 mad->restart = flush;
809 peer_formats++;
810 }
811 #endif
813 return res;
815 /* ERRORS */
816 convert_error:
817 {
818 /* probably unsupported seek format */
819 GST_DEBUG ("failed to convert format %u into GST_FORMAT_TIME", format);
820 return FALSE;
821 }
822 }
824 static gboolean
825 gst_mad_src_event (GstPad * pad, GstEvent * event)
826 {
827 gboolean res = TRUE;
828 GstMad *mad;
830 mad = GST_MAD (GST_PAD_PARENT (pad));
832 switch (GST_EVENT_TYPE (event)) {
833 /* the all-formats seek logic */
834 case GST_EVENT_SEEK:
835 gst_event_ref (event);
836 if (!(res = gst_pad_event_default (pad, event))) {
837 if (mad->index)
838 res = index_seek (mad, pad, event);
839 else
840 res = normal_seek (mad, pad, event);
841 }
842 break;
844 default:
845 res = FALSE;
846 break;
847 }
849 gst_event_unref (event);
850 return res;
851 }
853 static inline signed int
854 scale (mad_fixed_t sample)
855 {
856 /* round */
857 sample += (1L << (MAD_F_FRACBITS - 16));
859 /* clip */
860 if (sample >= MAD_F_ONE)
861 sample = MAD_F_ONE - 1;
862 else if (sample < -MAD_F_ONE)
863 sample = -MAD_F_ONE;
865 /* quantize */
866 return sample >> (MAD_F_FRACBITS + 1 - 16);
867 }
869 /* do we need this function? */
870 static void
871 gst_mad_set_property (GObject * object, guint prop_id,
872 const GValue * value, GParamSpec * pspec)
873 {
874 GstMad *mad;
876 g_return_if_fail (GST_IS_MAD (object));
878 mad = GST_MAD (object);
880 switch (prop_id) {
881 case ARG_HALF:
882 mad->half = g_value_get_boolean (value);
883 break;
884 case ARG_IGNORE_CRC:
885 mad->ignore_crc = g_value_get_boolean (value);
886 break;
887 default:
888 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
889 break;
890 }
891 }
892 static void
893 gst_mad_get_property (GObject * object, guint prop_id,
894 GValue * value, GParamSpec * pspec)
895 {
896 GstMad *mad;
898 g_return_if_fail (GST_IS_MAD (object));
900 mad = GST_MAD (object);
902 switch (prop_id) {
903 case ARG_HALF:
904 g_value_set_boolean (value, mad->half);
905 break;
906 case ARG_IGNORE_CRC:
907 g_value_set_boolean (value, mad->ignore_crc);
908 break;
909 default:
910 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
911 break;
912 }
913 }
915 static void
916 gst_mad_update_info (GstMad * mad)
917 {
918 gint abr = mad->vbr_average;
919 struct mad_header *header = &mad->frame.header;
920 gboolean changed = FALSE;
922 #define CHECK_HEADER(h1,str) \
923 G_STMT_START{ \
924 if (mad->header.h1 != header->h1 || mad->new_header) { \
925 mad->header.h1 = header->h1; \
926 changed = TRUE; \
927 }; \
928 } G_STMT_END
930 /* update average bitrate */
931 if (mad->new_header) {
932 mad->framecount = 1;
933 mad->vbr_rate = header->bitrate;
934 abr = 0;
935 } else {
936 mad->framecount++;
937 mad->vbr_rate += header->bitrate;
938 }
939 mad->vbr_average = (gint) (mad->vbr_rate / mad->framecount);
941 CHECK_HEADER (layer, "layer");
942 CHECK_HEADER (mode, "mode");
943 CHECK_HEADER (emphasis, "emphasis");
945 if (header->bitrate != mad->header.bitrate || mad->new_header) {
946 mad->header.bitrate = header->bitrate;
947 }
948 mad->new_header = FALSE;
950 if (changed) {
951 GstTagList *list;
952 GEnumValue *mode;
953 GEnumValue *emphasis;
955 mode =
956 g_enum_get_value (g_type_class_ref (GST_TYPE_MAD_MODE),
957 mad->header.mode);
958 emphasis =
959 g_enum_get_value (g_type_class_ref (GST_TYPE_MAD_EMPHASIS),
960 mad->header.emphasis);
961 list = gst_tag_list_new ();
962 gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
963 GST_TAG_LAYER, mad->header.layer,
964 GST_TAG_MODE, mode->value_nick,
965 GST_TAG_EMPHASIS, emphasis->value_nick, NULL);
966 gst_element_post_message (GST_ELEMENT (mad),
967 gst_message_new_tag (GST_OBJECT (mad), list));
968 }
969 #undef CHECK_HEADER
971 }
973 static gboolean
974 gst_mad_sink_event (GstPad * pad, GstEvent * event)
975 {
976 GstMad *mad = GST_MAD (GST_PAD_PARENT (pad));
977 gboolean result;
979 GST_DEBUG ("handling event %d", GST_EVENT_TYPE (event));
981 switch (GST_EVENT_TYPE (event)) {
982 case GST_EVENT_NEWSEGMENT:
983 /* this isn't really correct? */
984 result = gst_pad_push_event (mad->srcpad, event);
985 mad->tempsize = 0;
986 /* we don't need to restart when we get here */
987 mad->restart = FALSE;
988 break;
989 case GST_EVENT_EOS:
990 mad->caps_set = FALSE; /* could be a new stream */
991 result = gst_pad_push_event (mad->srcpad, event);
992 break;
993 default:
994 result = gst_pad_push_event (mad->srcpad, event);
995 break;
996 }
997 return TRUE;
998 }
1000 static gboolean
1001 gst_mad_check_restart (GstMad * mad)
1002 {
1003 gboolean yes = mad->restart;
1005 if (mad->restart) {
1006 mad->restart = FALSE;
1007 mad->tempsize = 0;
1008 }
1009 return yes;
1010 }
1013 /* The following code has been taken from
1014 * rhythmbox/metadata/monkey-media/stream-info-impl/id3-vfs/mp3bitrate.c
1015 * which took it from xine-lib/src/demuxers/demux_mpgaudio.c
1016 * This code has been kindly relicensed to LGPL by Thibaut Mattern and
1017 * Bastien Nocera
1018 */
1019 #define BE_32(x) GST_READ_UINT32_BE(x)
1021 #define FOURCC_TAG( ch0, ch1, ch2, ch3 ) \
1022 ( (long)(unsigned char)(ch3) | \
1023 ( (long)(unsigned char)(ch2) << 8 ) | \
1024 ( (long)(unsigned char)(ch1) << 16 ) | \
1025 ( (long)(unsigned char)(ch0) << 24 ) )
1027 /* Xing header stuff */
1028 #define XING_TAG FOURCC_TAG('X', 'i', 'n', 'g')
1029 #define XING_FRAMES_FLAG 0x0001
1030 #define XING_BYTES_FLAG 0x0002
1031 #define XING_TOC_FLAG 0x0004
1032 #define XING_VBR_SCALE_FLAG 0x0008
1033 #define XING_TOC_LENGTH 100
1035 /* check for valid "Xing" VBR header */
1036 static int
1037 is_xhead (unsigned char *buf)
1038 {
1039 return (BE_32 (buf) == XING_TAG);
1040 }
1043 #undef LOG
1044 /*#define LOG*/
1045 #ifdef LOG
1046 #define lprintf(x...) g_print(x)
1047 #else
1048 #define lprintf(x...)
1049 #endif
1051 static int
1052 mpg123_parse_xing_header (struct mad_header *header,
1053 const guint8 * buf, int bufsize, int *bitrate, int *time)
1054 {
1055 int i;
1056 guint8 *ptr = (guint8 *) buf;
1057 double frame_duration;
1058 int xflags, xframes, xbytes, xvbr_scale;
1059 int abr;
1060 guint8 xtoc[XING_TOC_LENGTH];
1061 int lsf_bit = !(header->flags & MAD_FLAG_LSF_EXT);
1063 xframes = xbytes = 0;
1065 /* offset of the Xing header */
1066 if (lsf_bit) {
1067 if (header->mode != MAD_MODE_SINGLE_CHANNEL)
1068 ptr += (32 + 4);
1069 else
1070 ptr += (17 + 4);
1071 } else {
1072 if (header->mode != MAD_MODE_SINGLE_CHANNEL)
1073 ptr += (17 + 4);
1074 else
1075 ptr += (9 + 4);
1076 }
1078 if (ptr >= (buf + bufsize - 4))
1079 return 0;
1081 if (is_xhead (ptr)) {
1082 lprintf ("Xing header found\n");
1084 ptr += 4;
1085 if (ptr >= (buf + bufsize - 4))
1086 return 0;
1088 xflags = BE_32 (ptr);
1089 ptr += 4;
1091 if (xflags & XING_FRAMES_FLAG) {
1092 if (ptr >= (buf + bufsize - 4))
1093 return 0;
1094 xframes = BE_32 (ptr);
1095 lprintf ("xframes: %d\n", xframes);
1096 ptr += 4;
1097 }
1098 if (xflags & XING_BYTES_FLAG) {
1099 if (ptr >= (buf + bufsize - 4))
1100 return 0;
1101 xbytes = BE_32 (ptr);
1102 lprintf ("xbytes: %d\n", xbytes);
1103 ptr += 4;
1104 }
1105 if (xflags & XING_TOC_FLAG) {
1106 lprintf ("toc found\n");
1107 if (ptr >= (buf + bufsize - XING_TOC_LENGTH))
1108 return 0;
1109 for (i = 0; i < XING_TOC_LENGTH; i++) {
1110 xtoc[i] = *(ptr + i);
1111 lprintf ("%d ", xtoc[i]);
1112 }
1113 lprintf ("\n");
1114 ptr += XING_TOC_LENGTH;
1115 }
1117 xvbr_scale = -1;
1118 if (xflags & XING_VBR_SCALE_FLAG) {
1119 if (ptr >= (buf + bufsize - 4))
1120 return 0;
1121 xvbr_scale = BE_32 (ptr);
1122 lprintf ("xvbr_scale: %d\n", xvbr_scale);
1123 }
1125 /* 1 kbit = 1000 bits ! (and not 1024 bits) */
1126 if (xflags & (XING_FRAMES_FLAG | XING_BYTES_FLAG)) {
1127 if (header->layer == MAD_LAYER_I) {
1128 frame_duration = 384.0 / (double) header->samplerate;
1129 } else {
1130 int slots_per_frame;
1132 slots_per_frame = ((header->layer == MAD_LAYER_III)
1133 && !lsf_bit) ? 72 : 144;
1134 frame_duration = slots_per_frame * 8.0 / (double) header->samplerate;
1135 }
1136 abr = ((double) xbytes * 8.0) / ((double) xframes * frame_duration);
1137 lprintf ("abr: %d bps\n", abr);
1138 if (bitrate != NULL) {
1139 *bitrate = abr;
1140 }
1141 if (time != NULL) {
1142 *time = (double) xframes *frame_duration;
1144 lprintf ("stream_length: %d s, %d min %d s\n", *time,
1145 *time / 60, *time % 60);
1146 }
1147 } else {
1148 /* it's a stupid Xing header */
1149 lprintf ("not a Xing VBR file\n");
1150 }
1151 return 1;
1152 } else {
1153 lprintf ("Xing header not found\n");
1154 return 0;
1155 }
1156 }
1158 /* End of Xine code */
1160 /* internal function to check if the header has changed and thus the
1161 * caps need to be reset. Only call during normal mode, not resyncing */
1162 static void
1163 gst_mad_check_caps_reset (GstMad * mad)
1164 {
1165 guint nchannels;
1166 guint rate;
1168 nchannels = MAD_NCHANNELS (&mad->frame.header);
1170 #if MAD_VERSION_MINOR <= 12
1171 rate = mad->header.sfreq;
1172 #else
1173 rate = mad->frame.header.samplerate;
1174 #endif
1176 /* rate and channels are not supposed to change in a continuous stream,
1177 * so check this first before doing anything */
1179 /* only set caps if they weren't already set for this continuous stream */
1180 if (mad->channels != nchannels || mad->rate != rate) {
1181 if (mad->caps_set) {
1182 GST_DEBUG
1183 ("Header changed from %d Hz/%d ch to %d Hz/%d ch, failed sync after seek ?",
1184 mad->rate, mad->channels, rate, nchannels);
1185 /* we're conservative on stream changes. However, our *initial* caps
1186 * might have been wrong as well - mad ain't perfect in syncing. So,
1187 * we count caps changes and change if we pass a limit treshold (3). */
1188 if (nchannels != mad->pending_channels || rate != mad->pending_rate) {
1189 mad->times_pending = 0;
1190 mad->pending_channels = nchannels;
1191 mad->pending_rate = rate;
1192 }
1193 if (++mad->times_pending < 3)
1194 return;
1195 }
1196 }
1197 gst_mad_update_info (mad);
1199 if (mad->channels != nchannels || mad->rate != rate) {
1200 GstCaps *caps;
1202 if (mad->stream.options & MAD_OPTION_HALFSAMPLERATE)
1203 rate >>= 1;
1205 /* FIXME see if peer can accept the caps */
1207 /* we set the caps even when the pad is not connected so they
1208 * can be gotten for streaminfo */
1209 caps = gst_caps_new_simple ("audio/x-raw-int",
1210 "endianness", G_TYPE_INT, G_BYTE_ORDER,
1211 "signed", G_TYPE_BOOLEAN, TRUE,
1212 "width", G_TYPE_INT, 16,
1213 "depth", G_TYPE_INT, 16,
1214 "rate", G_TYPE_INT, rate, "channels", G_TYPE_INT, nchannels, NULL);
1216 gst_pad_set_caps (mad->srcpad, caps);
1217 gst_caps_unref (caps);
1219 mad->caps_set = TRUE; /* set back to FALSE on discont */
1220 mad->channels = nchannels;
1221 mad->rate = rate;
1222 }
1223 }
1225 static GstFlowReturn
1226 gst_mad_chain (GstPad * pad, GstBuffer * buffer)
1227 {
1228 GstMad *mad;
1229 guint8 *data;
1230 glong size;
1231 gboolean new_pts = FALSE;
1232 GstClockTime timestamp;
1233 GstFlowReturn result = GST_FLOW_OK;
1234 gboolean do_send_discont = FALSE;
1236 mad = GST_MAD (GST_PAD_PARENT (pad));
1238 /* restarts happen on discontinuities, ie. seek, flush, PAUSED to PLAYING */
1239 if (gst_mad_check_restart (mad)) {
1240 do_send_discont = TRUE;
1241 GST_DEBUG ("mad restarted");
1242 }
1244 timestamp = GST_BUFFER_TIMESTAMP (buffer);
1245 GST_DEBUG ("mad in timestamp %" GST_TIME_FORMAT, GST_TIME_ARGS (timestamp));
1247 /* handle timestamps */
1248 if (GST_CLOCK_TIME_IS_VALID (timestamp)) {
1249 /* if there is nothing left to process in our temporary buffer,
1250 * we can set this timestamp on the next outgoing buffer */
1251 if (mad->tempsize == 0) {
1252 /* we have to save the result here because we can't yet convert
1253 * the timestamp to a sample offset yet,
1254 * the samplerate might not be known yet */
1255 mad->last_ts = timestamp;
1256 mad->base_byte_offset = GST_BUFFER_OFFSET (buffer);
1257 mad->bytes_consumed = 0;
1258 }
1259 /* else we need to finish the current partial frame with the old timestamp
1260 * and queue this timestamp for the next frame */
1261 else {
1262 new_pts = TRUE;
1263 }
1264 }
1265 GST_DEBUG ("last_ts %" GST_TIME_FORMAT, GST_TIME_ARGS (mad->last_ts));
1267 /* handle data */
1268 data = GST_BUFFER_DATA (buffer);
1269 size = GST_BUFFER_SIZE (buffer);
1271 /* process the incoming buffer in chunks of maximum MAD_BUFFER_MDLEN bytes;
1272 * this is the upper limit on processable chunk sizes set by mad */
1273 while (size > 0) {
1274 gint tocopy;
1275 guchar *mad_input_buffer; /* convenience pointer to tempbuffer */
1277 tocopy =
1278 MIN (MAD_BUFFER_MDLEN, MIN (size,
1279 MAD_BUFFER_MDLEN * 3 - mad->tempsize));
1280 if (tocopy == 0) {
1281 GST_ELEMENT_ERROR (mad, STREAM, DECODE, (NULL),
1282 ("mad claims to need more data than %u bytes, we don't have that much",
1283 MAD_BUFFER_MDLEN * 3));
1284 result = GST_FLOW_ERROR;
1285 goto end;
1286 }
1288 /* append the chunk to process to our internal temporary buffer */
1289 GST_LOG ("tempbuffer size %d, copying %d bytes from incoming buffer",
1290 mad->tempsize, tocopy);
1291 memcpy (mad->tempbuffer + mad->tempsize, data, tocopy);
1292 mad->tempsize += tocopy;
1294 /* update our incoming buffer's parameters to reflect this */
1295 size -= tocopy;
1296 data += tocopy;
1298 mad_input_buffer = mad->tempbuffer;
1300 /* while we have data we can consume it */
1301 while (mad->tempsize >= 0) {
1302 gint consumed = 0;
1303 guint nsamples;
1304 guint64 time_offset;
1305 guint64 time_duration;
1306 unsigned char const *before_sync, *after_sync;
1308 mad->in_error = FALSE;
1310 mad_stream_buffer (&mad->stream, mad_input_buffer, mad->tempsize);
1312 /* added separate header decoding to catch errors earlier, also fixes
1313 * some weird decoding errors... */
1314 GST_LOG ("decoding the header now");
1315 if (mad_header_decode (&mad->frame.header, &mad->stream) == -1) {
1316 GST_DEBUG ("mad_frame_decode had an error: %s",
1317 mad_stream_errorstr (&mad->stream));
1318 }
1320 GST_LOG ("decoding one frame now");
1322 if (mad_frame_decode (&mad->frame, &mad->stream) == -1) {
1323 GST_LOG ("got error %d", mad->stream.error);
1325 /* not enough data, need to wait for next buffer? */
1326 if (mad->stream.error == MAD_ERROR_BUFLEN) {
1327 if (mad->stream.next_frame == mad_input_buffer) {
1328 GST_LOG ("not enough data in tempbuffer (%d), breaking to get more",
1329 mad->tempsize);
1330 break;
1331 } else {
1332 GST_LOG ("sync error, flushing unneeded data");
1333 goto next;
1334 }
1335 }
1336 /* we are in an error state */
1337 mad->in_error = TRUE;
1338 GST_DEBUG ("mad_frame_decode had an error: %s",
1339 mad_stream_errorstr (&mad->stream));
1340 if (!MAD_RECOVERABLE (mad->stream.error)) {
1341 GST_ELEMENT_ERROR (mad, STREAM, DECODE, (NULL), (NULL));
1342 result = GST_FLOW_ERROR;
1343 goto end;
1344 } else if (mad->stream.error == MAD_ERROR_LOSTSYNC) {
1345 /* lost sync, force a resync */
1346 signed long tagsize;
1348 GST_INFO ("recoverable lost sync error");
1350 tagsize = id3_tag_query (mad->stream.this_frame,
1351 mad->stream.bufend - mad->stream.this_frame);
1353 if (tagsize > mad->tempsize) {
1354 GST_INFO ("mad: got partial id3 tag in buffer, skipping");
1355 } else if (tagsize > 0) {
1356 struct id3_tag *tag;
1357 id3_byte_t const *data;
1359 GST_INFO ("mad: got ID3 tag size %ld", tagsize);
1361 data = mad->stream.this_frame;
1363 /* mad has moved the pointer to the next frame over the start of the
1364 * id3 tags, so we need to flush one byte less than the tagsize */
1365 mad_stream_skip (&mad->stream, tagsize - 1);
1367 tag = id3_tag_parse (data, tagsize);
1368 if (tag) {
1369 GstTagList *list;
1371 list = gst_mad_id3_to_tag_list (tag);
1372 id3_tag_delete (tag);
1373 GST_DEBUG ("found tag");
1374 gst_element_post_message (GST_ELEMENT (mad),
1375 gst_message_new_tag (GST_OBJECT (mad),
1376 gst_tag_list_copy (list)));
1377 if (mad->tags) {
1378 gst_tag_list_insert (mad->tags, list, GST_TAG_MERGE_PREPEND);
1379 } else {
1380 mad->tags = gst_tag_list_copy (list);
1381 }
1382 gst_pad_push_event (mad->srcpad, gst_event_new_tag (list));
1383 }
1384 }
1385 }
1387 mad_frame_mute (&mad->frame);
1388 mad_synth_mute (&mad->synth);
1389 before_sync = mad->stream.ptr.byte;
1390 if (mad_stream_sync (&mad->stream) != 0)
1391 GST_WARNING ("mad_stream_sync failed");
1392 after_sync = mad->stream.ptr.byte;
1393 /* a succesful resync should make us drop bytes as consumed, so
1394 calculate from the byte pointers before and after resync */
1395 consumed = after_sync - before_sync;
1396 GST_DEBUG ("resynchronization consumes %d bytes", consumed);
1397 GST_DEBUG ("synced to data: 0x%0x 0x%0x", *mad->stream.ptr.byte,
1398 *(mad->stream.ptr.byte + 1));
1401 mad_stream_sync (&mad->stream);
1402 /* recoverable errors pass */
1403 goto next;
1404 }
1406 if (mad->check_for_xing) {
1407 int bitrate = 0, time = 0;
1408 GstTagList *list;
1409 int frame_len = mad->stream.next_frame - mad->stream.this_frame;
1411 /* Assume Xing headers can only be the first frame in a mp3 file */
1412 if (mpg123_parse_xing_header (&mad->frame.header,
1413 mad->stream.this_frame, frame_len, &bitrate, &time)) {
1414 list = gst_tag_list_new ();
1415 gst_tag_list_add (list, GST_TAG_MERGE_REPLACE,
1416 GST_TAG_DURATION, (gint64) time * 1000 * 1000 * 1000,
1417 GST_TAG_BITRATE, bitrate, NULL);
1418 gst_element_post_message (GST_ELEMENT (mad),
1419 gst_message_new_tag (GST_OBJECT (mad), gst_tag_list_copy (list)));
1420 gst_pad_push_event (mad->srcpad, gst_event_new_tag (list));
1421 }
1423 mad->check_for_xing = FALSE;
1424 goto next;
1425 }
1427 /* if we're not resyncing/in error, check if caps need to be set again */
1428 if (!mad->in_error)
1429 gst_mad_check_caps_reset (mad);
1430 nsamples = MAD_NSBSAMPLES (&mad->frame.header) *
1431 (mad->stream.options & MAD_OPTION_HALFSAMPLERATE ? 16 : 32);
1433 if (mad->frame.header.samplerate == 0) {
1434 g_warning
1435 ("mad->frame.header.samplerate is 0; timestamps cannot be calculated");
1436 time_offset = GST_CLOCK_TIME_NONE;
1437 time_duration = GST_CLOCK_TIME_NONE;
1438 } else {
1439 /* if we have a pending timestamp, we can use it now to calculate the sample offset */
1440 if (GST_CLOCK_TIME_IS_VALID (mad->last_ts)) {
1441 GstFormat format = GST_FORMAT_DEFAULT;
1442 gint64 total;
1444 gst_pad_query_convert (mad->srcpad, GST_FORMAT_TIME, mad->last_ts,
1445 &format, &total);
1446 mad->total_samples = total;
1447 mad->last_ts = GST_CLOCK_TIME_NONE;
1448 }
1449 time_offset = mad->total_samples * GST_SECOND / mad->rate;
1450 time_duration = (nsamples * GST_SECOND / mad->rate);
1451 }
1453 if (mad->index) {
1454 guint64 x_bytes = mad->base_byte_offset + mad->bytes_consumed;
1456 gst_index_add_association (mad->index, mad->index_id, 0,
1457 GST_FORMAT_BYTES, x_bytes, GST_FORMAT_TIME, time_offset, NULL);
1458 }
1460 if (mad->segment_start <= (time_offset ==
1461 GST_CLOCK_TIME_NONE ? 0 : time_offset)) {
1463 /* for sample accurate seeking, calculate how many samples
1464 to skip and send the remaining pcm samples */
1466 GstBuffer *outbuffer;
1467 gint16 *outdata;
1468 mad_fixed_t const *left_ch, *right_ch;
1470 mad_synth_frame (&mad->synth, &mad->frame);
1471 left_ch = mad->synth.pcm.samples[0];
1472 right_ch = mad->synth.pcm.samples[1];
1474 /* will attach the caps to the buffer */
1475 result =
1476 gst_pad_alloc_buffer (mad->srcpad, 0, nsamples * mad->channels * 2,
1477 GST_PAD_CAPS (mad->srcpad), &outbuffer);
1478 if (result != GST_FLOW_OK)
1479 goto end;
1481 outdata = (gint16 *) GST_BUFFER_DATA (outbuffer);
1483 GST_DEBUG ("mad out timestamp %" GST_TIME_FORMAT,
1484 GST_TIME_ARGS (time_offset));
1486 GST_BUFFER_TIMESTAMP (outbuffer) = time_offset;
1487 GST_BUFFER_DURATION (outbuffer) = time_duration;
1488 GST_BUFFER_OFFSET (outbuffer) = mad->total_samples;
1490 /* output sample(s) in 16-bit signed native-endian PCM */
1491 if (mad->channels == 1) {
1492 gint count = nsamples;
1494 while (count--) {
1495 *outdata++ = scale (*left_ch++) & 0xffff;
1496 }
1497 } else {
1498 gint count = nsamples;
1500 while (count--) {
1501 *outdata++ = scale (*left_ch++) & 0xffff;
1502 *outdata++ = scale (*right_ch++) & 0xffff;
1503 }
1504 }
1506 if (do_send_discont) {
1507 gst_pad_push_event (mad->srcpad,
1508 gst_event_new_new_segment (FALSE, 1.0, GST_FORMAT_TIME,
1509 GST_BUFFER_TIMESTAMP (outbuffer), GST_CLOCK_TIME_NONE, 0));
1510 do_send_discont = FALSE;
1511 }
1513 result = gst_pad_push (mad->srcpad, outbuffer);
1514 if (result != GST_FLOW_OK) {
1515 goto end;
1516 }
1517 }
1519 mad->total_samples += nsamples;
1521 /* we have a queued timestamp on the incoming buffer that we should
1522 * use for the next frame */
1523 if (new_pts) {
1524 mad->last_ts = timestamp;
1525 new_pts = FALSE;
1526 mad->base_byte_offset = GST_BUFFER_OFFSET (buffer);
1527 mad->bytes_consumed = 0;
1528 }
1530 if (gst_mad_check_restart (mad)) {
1531 goto end;
1532 }
1534 next:
1535 /* figure out how many bytes mad consumed */
1536 /* if consumed is already set, it's from the resync higher up, so
1537 we need to use that value instead. Otherwise, recalculate from
1538 mad's consumption */
1539 if (consumed == 0)
1540 consumed = mad->stream.next_frame - mad_input_buffer;
1542 GST_LOG ("mad consumed %d bytes", consumed);
1543 /* move out pointer to where mad want the next data */
1544 mad_input_buffer += consumed;
1545 mad->tempsize -= consumed;
1546 mad->bytes_consumed += consumed;
1547 }
1548 /* we only get here from breaks, tempsize never actually drops below 0 */
1549 memmove (mad->tempbuffer, mad_input_buffer, mad->tempsize);
1550 }
1551 result = GST_FLOW_OK;
1553 end:
1554 gst_buffer_unref (buffer);
1556 return result;
1557 }
1559 static GstStateChangeReturn
1560 gst_mad_change_state (GstElement * element, GstStateChange transition)
1561 {
1562 GstMad *mad;
1563 GstStateChangeReturn ret;
1565 mad = GST_MAD (element);
1567 switch (transition) {
1568 case GST_STATE_CHANGE_NULL_TO_READY:
1569 break;
1570 case GST_STATE_CHANGE_READY_TO_PAUSED:
1571 {
1572 guint options = 0;
1574 mad_stream_init (&mad->stream);
1575 mad_frame_init (&mad->frame);
1576 mad_synth_init (&mad->synth);
1577 mad->tempsize = 0;
1578 mad->total_samples = 0;
1579 mad->rate = 0;
1580 mad->channels = 0;
1581 mad->caps_set = FALSE;
1582 mad->times_pending = mad->pending_rate = mad->pending_channels = 0;
1583 mad->vbr_average = 0;
1584 mad->segment_start = 0;
1585 mad->new_header = TRUE;
1586 mad->framecount = 0;
1587 mad->vbr_rate = 0;
1588 mad->frame.header.samplerate = 0;
1589 mad->last_ts = GST_CLOCK_TIME_NONE;
1590 if (mad->ignore_crc)
1591 options |= MAD_OPTION_IGNORECRC;
1592 if (mad->half)
1593 options |= MAD_OPTION_HALFSAMPLERATE;
1594 mad_stream_options (&mad->stream, options);
1595 break;
1596 }
1597 case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
1598 break;
1599 default:
1600 break;
1601 }
1603 ret = parent_class->change_state (element, transition);
1605 switch (transition) {
1606 case GST_STATE_CHANGE_PLAYING_TO_PAUSED:
1607 break;
1608 case GST_STATE_CHANGE_PAUSED_TO_READY:
1609 mad_synth_finish (&mad->synth);
1610 mad_frame_finish (&mad->frame);
1611 mad_stream_finish (&mad->stream);
1612 mad->restart = TRUE;
1613 if (mad->tags) {
1614 gst_tag_list_free (mad->tags);
1615 mad->tags = NULL;
1616 }
1617 break;
1618 case GST_STATE_CHANGE_READY_TO_NULL:
1619 break;
1620 default:
1621 break;
1622 }
1623 return ret;
1624 }