make the g_print a debug message
[swfdec.git] / libswfdec / swfdec_codec_adpcm.c
blob1fc17ee66911f6f929c413bb1ab36bc83709ce25
1 /* Swfdec
2 * Copyright (C) 2006 Benjamin Otte <otte@gnome.org>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 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 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301 USA
20 #ifdef HAVE_CONFIG_H
21 #include "config.h"
22 #endif
24 #include "swfdec_codec_audio.h"
25 #include "swfdec_bits.h"
26 #include "swfdec_debug.h"
27 #include "swfdec_internal.h"
29 typedef struct {
30 SwfdecAudioDecoder decoder;
31 SwfdecBufferQueue * queue;
32 } SwfdecAudioDecoderAdpcm;
34 static const int indexTable[4][16] = {
35 { -1, 2 },
36 { -1, -1, 2, 4 },
37 { -1, -1, -1, -1, 2, 4, 6, 8 },
38 { -1, -1, -1, -1, -1, -1, -1, -1, 1, 2, 4, 6, 8, 10, 13, 16 }
41 static const int stepSizeTable[89] = {
42 7, 8, 9, 10, 11, 12, 13, 14, 16, 17,
43 19, 21, 23, 25, 28, 31, 34, 37, 41, 45,
44 50, 55, 60, 66, 73, 80, 88, 97, 107, 118,
45 130, 143, 157, 173, 190, 209, 230, 253, 279, 307,
46 337, 371, 408, 449, 494, 544, 598, 658, 724, 796,
47 876, 963, 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066,
48 2272, 2499, 2749, 3024, 3327, 3660, 4026, 4428, 4871, 5358,
49 5894, 6484, 7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899,
50 15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794, 32767
53 static SwfdecBuffer *
54 swfdec_audio_decoder_adpcm_decode_chunk (SwfdecBits *bits, guint n_bits, guint channels)
56 SwfdecBuffer *ret;
57 guint len;
58 guint i, j, ch;
59 guint index[2];
60 int pred[2];
61 gint16 *out;
62 guint delta, sign, sign_mask;
63 int diff;
64 const int *realIndexTable;
65 guint step[2];
67 realIndexTable = indexTable[n_bits - 2];
68 for (ch = 0; ch < channels; ch++) {
69 /* can't use get_s16 here since that would be aligned */
70 pred[ch] = swfdec_bits_getsbits (bits, 16);
71 index[ch] = swfdec_bits_getbits (bits, 6);
72 if (index[ch] >= G_N_ELEMENTS (stepSizeTable)) {
73 SWFDEC_ERROR ("initial index too big: %u, max allowed is %td",
74 index[ch], G_N_ELEMENTS (stepSizeTable) - 1);
75 index[ch] = G_N_ELEMENTS (stepSizeTable) - 1;
77 step[ch] = stepSizeTable[index[ch]];
79 len = swfdec_bits_left (bits) / channels / n_bits;
80 len = MIN (len, 4095);
81 ret = swfdec_buffer_new_and_alloc ((len + 1) * sizeof (gint16) * channels);
82 out = (gint16 *) ret->data;
83 /* output initial value */
84 SWFDEC_LOG ("decoding %u samples", len + 1);
85 for (ch = 0; ch < channels; ch++)
86 *out++ = pred[ch];
87 sign_mask = 1 << (n_bits - 1);
88 for (i = 0; i < len; i++) {
89 for (ch = 0; ch < channels; ch++) {
90 /* Step 1 - get the delta value */
91 delta = swfdec_bits_getbits (bits, n_bits);
93 /* Step 2 - Separate sign and magnitude */
94 sign = delta & sign_mask;
95 delta -= sign;
97 /* Step 3 - Find new index value (for later) */
98 index[ch] += realIndexTable[delta];
99 if ( index[ch] >= G_MAXINT ) index[ch] = 0; /* underflow */
100 if ( index[ch] >= G_N_ELEMENTS (stepSizeTable) ) index[ch] = G_N_ELEMENTS (stepSizeTable) - 1;
102 /* Step 4 - Compute difference and new predicted value */
103 j = n_bits - 1;
104 diff = step[ch] >> j;
105 do {
106 j--;
107 if (delta & 1)
108 diff += step[ch] >> j;
109 delta >>= 1;
110 } while (j > 0 && delta);
112 if ( sign )
113 pred[ch] -= diff;
114 else
115 pred[ch] += diff;
117 /* Step 5 - clamp output value */
118 pred[ch] = CLAMP (pred[ch], -32768, 32767);
120 /* Step 6 - Update step value */
121 step[ch] = stepSizeTable[index[ch]];
123 /* Step 7 - Output value */
124 *out++ = pred[ch];
127 return ret;
130 static void
131 swfdec_audio_decoder_adpcm_push (SwfdecAudioDecoder *dec, SwfdecBuffer *buffer)
133 SwfdecAudioDecoderAdpcm *adpcm = (SwfdecAudioDecoderAdpcm *) dec;
134 guint channels, n_bits;
135 SwfdecBits bits;
137 if (buffer == NULL)
138 return;
140 channels = swfdec_audio_format_get_channels (dec->format);
141 swfdec_bits_init (&bits, buffer);
142 n_bits = swfdec_bits_getbits (&bits, 2) + 2;
143 SWFDEC_DEBUG ("starting decoding: %u channels, %u bits", channels, n_bits);
144 /* 22 is minimum required header size */
145 while (swfdec_bits_left (&bits) >= 22) {
146 buffer = swfdec_audio_decoder_adpcm_decode_chunk (&bits, n_bits, channels);
147 if (buffer)
148 swfdec_buffer_queue_push (adpcm->queue, buffer);
152 static SwfdecBuffer *
153 swfdec_audio_decoder_adpcm_pull (SwfdecAudioDecoder *dec)
155 SwfdecAudioDecoderAdpcm *adpcm = (SwfdecAudioDecoderAdpcm *) dec;
157 return swfdec_buffer_queue_pull_buffer (adpcm->queue);
160 static void
161 swfdec_audio_decoder_adpcm_free (SwfdecAudioDecoder *dec)
163 SwfdecAudioDecoderAdpcm *adpcm = (SwfdecAudioDecoderAdpcm *) dec;
165 swfdec_buffer_queue_unref (adpcm->queue);
166 g_slice_free (SwfdecAudioDecoderAdpcm, adpcm);
169 SwfdecAudioDecoder *
170 swfdec_audio_decoder_adpcm_new (guint type, SwfdecAudioFormat format)
172 SwfdecAudioDecoderAdpcm *adpcm;
174 if (type != SWFDEC_AUDIO_CODEC_ADPCM)
175 return NULL;
176 adpcm = g_slice_new (SwfdecAudioDecoderAdpcm);
177 adpcm->decoder.format = swfdec_audio_format_new (swfdec_audio_format_get_rate (format),
178 swfdec_audio_format_get_channels (format), TRUE);
179 adpcm->decoder.push = swfdec_audio_decoder_adpcm_push;
180 adpcm->decoder.pull = swfdec_audio_decoder_adpcm_pull;
181 adpcm->decoder.free = swfdec_audio_decoder_adpcm_free;
182 adpcm->queue = swfdec_buffer_queue_new ();
184 return &adpcm->decoder;