handle src buffer underflow corner cases
[sdl_omap.git] / src / audio / SDL_wave.c
CommitLineData
e14743d1 1/*
2 SDL - Simple DirectMedia Layer
3 Copyright (C) 1997-2009 Sam Lantinga
4
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
9
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public
16 License along with this library; if not, write to the Free Software
17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
18
19 Sam Lantinga
20 slouken@libsdl.org
21*/
22#include "SDL_config.h"
23
24/* Microsoft WAVE file loading routines */
25
26#include "SDL_audio.h"
27#include "SDL_wave.h"
28
29
30static int ReadChunk(SDL_RWops *src, Chunk *chunk);
31
32struct MS_ADPCM_decodestate {
33 Uint8 hPredictor;
34 Uint16 iDelta;
35 Sint16 iSamp1;
36 Sint16 iSamp2;
37};
38static struct MS_ADPCM_decoder {
39 WaveFMT wavefmt;
40 Uint16 wSamplesPerBlock;
41 Uint16 wNumCoef;
42 Sint16 aCoeff[7][2];
43 /* * * */
44 struct MS_ADPCM_decodestate state[2];
45} MS_ADPCM_state;
46
47static int InitMS_ADPCM(WaveFMT *format)
48{
49 Uint8 *rogue_feel;
50 Uint16 extra_info;
51 int i;
52
53 /* Set the rogue pointer to the MS_ADPCM specific data */
54 MS_ADPCM_state.wavefmt.encoding = SDL_SwapLE16(format->encoding);
55 MS_ADPCM_state.wavefmt.channels = SDL_SwapLE16(format->channels);
56 MS_ADPCM_state.wavefmt.frequency = SDL_SwapLE32(format->frequency);
57 MS_ADPCM_state.wavefmt.byterate = SDL_SwapLE32(format->byterate);
58 MS_ADPCM_state.wavefmt.blockalign = SDL_SwapLE16(format->blockalign);
59 MS_ADPCM_state.wavefmt.bitspersample =
60 SDL_SwapLE16(format->bitspersample);
61 rogue_feel = (Uint8 *)format+sizeof(*format);
62 if ( sizeof(*format) == 16 ) {
63 extra_info = ((rogue_feel[1]<<8)|rogue_feel[0]);
64 rogue_feel += sizeof(Uint16);
65 }
66 MS_ADPCM_state.wSamplesPerBlock = ((rogue_feel[1]<<8)|rogue_feel[0]);
67 rogue_feel += sizeof(Uint16);
68 MS_ADPCM_state.wNumCoef = ((rogue_feel[1]<<8)|rogue_feel[0]);
69 rogue_feel += sizeof(Uint16);
70 if ( MS_ADPCM_state.wNumCoef != 7 ) {
71 SDL_SetError("Unknown set of MS_ADPCM coefficients");
72 return(-1);
73 }
74 for ( i=0; i<MS_ADPCM_state.wNumCoef; ++i ) {
75 MS_ADPCM_state.aCoeff[i][0] = ((rogue_feel[1]<<8)|rogue_feel[0]);
76 rogue_feel += sizeof(Uint16);
77 MS_ADPCM_state.aCoeff[i][1] = ((rogue_feel[1]<<8)|rogue_feel[0]);
78 rogue_feel += sizeof(Uint16);
79 }
80 return(0);
81}
82
83static Sint32 MS_ADPCM_nibble(struct MS_ADPCM_decodestate *state,
84 Uint8 nybble, Sint16 *coeff)
85{
86 const Sint32 max_audioval = ((1<<(16-1))-1);
87 const Sint32 min_audioval = -(1<<(16-1));
88 const Sint32 adaptive[] = {
89 230, 230, 230, 230, 307, 409, 512, 614,
90 768, 614, 512, 409, 307, 230, 230, 230
91 };
92 Sint32 new_sample, delta;
93
94 new_sample = ((state->iSamp1 * coeff[0]) +
95 (state->iSamp2 * coeff[1]))/256;
96 if ( nybble & 0x08 ) {
97 new_sample += state->iDelta * (nybble-0x10);
98 } else {
99 new_sample += state->iDelta * nybble;
100 }
101 if ( new_sample < min_audioval ) {
102 new_sample = min_audioval;
103 } else
104 if ( new_sample > max_audioval ) {
105 new_sample = max_audioval;
106 }
107 delta = ((Sint32)state->iDelta * adaptive[nybble])/256;
108 if ( delta < 16 ) {
109 delta = 16;
110 }
111 state->iDelta = (Uint16)delta;
112 state->iSamp2 = state->iSamp1;
113 state->iSamp1 = (Sint16)new_sample;
114 return(new_sample);
115}
116
117static int MS_ADPCM_decode(Uint8 **audio_buf, Uint32 *audio_len)
118{
119 struct MS_ADPCM_decodestate *state[2];
120 Uint8 *freeable, *encoded, *decoded;
121 Sint32 encoded_len, samplesleft;
122 Sint8 nybble, stereo;
123 Sint16 *coeff[2];
124 Sint32 new_sample;
125
126 /* Allocate the proper sized output buffer */
127 encoded_len = *audio_len;
128 encoded = *audio_buf;
129 freeable = *audio_buf;
130 *audio_len = (encoded_len/MS_ADPCM_state.wavefmt.blockalign) *
131 MS_ADPCM_state.wSamplesPerBlock*
132 MS_ADPCM_state.wavefmt.channels*sizeof(Sint16);
133 *audio_buf = (Uint8 *)SDL_malloc(*audio_len);
134 if ( *audio_buf == NULL ) {
135 SDL_Error(SDL_ENOMEM);
136 return(-1);
137 }
138 decoded = *audio_buf;
139
140 /* Get ready... Go! */
141 stereo = (MS_ADPCM_state.wavefmt.channels == 2);
142 state[0] = &MS_ADPCM_state.state[0];
143 state[1] = &MS_ADPCM_state.state[stereo];
144 while ( encoded_len >= MS_ADPCM_state.wavefmt.blockalign ) {
145 /* Grab the initial information for this block */
146 state[0]->hPredictor = *encoded++;
147 if ( stereo ) {
148 state[1]->hPredictor = *encoded++;
149 }
150 state[0]->iDelta = ((encoded[1]<<8)|encoded[0]);
151 encoded += sizeof(Sint16);
152 if ( stereo ) {
153 state[1]->iDelta = ((encoded[1]<<8)|encoded[0]);
154 encoded += sizeof(Sint16);
155 }
156 state[0]->iSamp1 = ((encoded[1]<<8)|encoded[0]);
157 encoded += sizeof(Sint16);
158 if ( stereo ) {
159 state[1]->iSamp1 = ((encoded[1]<<8)|encoded[0]);
160 encoded += sizeof(Sint16);
161 }
162 state[0]->iSamp2 = ((encoded[1]<<8)|encoded[0]);
163 encoded += sizeof(Sint16);
164 if ( stereo ) {
165 state[1]->iSamp2 = ((encoded[1]<<8)|encoded[0]);
166 encoded += sizeof(Sint16);
167 }
168 coeff[0] = MS_ADPCM_state.aCoeff[state[0]->hPredictor];
169 coeff[1] = MS_ADPCM_state.aCoeff[state[1]->hPredictor];
170
171 /* Store the two initial samples we start with */
172 decoded[0] = state[0]->iSamp2&0xFF;
173 decoded[1] = state[0]->iSamp2>>8;
174 decoded += 2;
175 if ( stereo ) {
176 decoded[0] = state[1]->iSamp2&0xFF;
177 decoded[1] = state[1]->iSamp2>>8;
178 decoded += 2;
179 }
180 decoded[0] = state[0]->iSamp1&0xFF;
181 decoded[1] = state[0]->iSamp1>>8;
182 decoded += 2;
183 if ( stereo ) {
184 decoded[0] = state[1]->iSamp1&0xFF;
185 decoded[1] = state[1]->iSamp1>>8;
186 decoded += 2;
187 }
188
189 /* Decode and store the other samples in this block */
190 samplesleft = (MS_ADPCM_state.wSamplesPerBlock-2)*
191 MS_ADPCM_state.wavefmt.channels;
192 while ( samplesleft > 0 ) {
193 nybble = (*encoded)>>4;
194 new_sample = MS_ADPCM_nibble(state[0],nybble,coeff[0]);
195 decoded[0] = new_sample&0xFF;
196 new_sample >>= 8;
197 decoded[1] = new_sample&0xFF;
198 decoded += 2;
199
200 nybble = (*encoded)&0x0F;
201 new_sample = MS_ADPCM_nibble(state[1],nybble,coeff[1]);
202 decoded[0] = new_sample&0xFF;
203 new_sample >>= 8;
204 decoded[1] = new_sample&0xFF;
205 decoded += 2;
206
207 ++encoded;
208 samplesleft -= 2;
209 }
210 encoded_len -= MS_ADPCM_state.wavefmt.blockalign;
211 }
212 SDL_free(freeable);
213 return(0);
214}
215
216struct IMA_ADPCM_decodestate {
217 Sint32 sample;
218 Sint8 index;
219};
220static struct IMA_ADPCM_decoder {
221 WaveFMT wavefmt;
222 Uint16 wSamplesPerBlock;
223 /* * * */
224 struct IMA_ADPCM_decodestate state[2];
225} IMA_ADPCM_state;
226
227static int InitIMA_ADPCM(WaveFMT *format)
228{
229 Uint8 *rogue_feel;
230 Uint16 extra_info;
231
232 /* Set the rogue pointer to the IMA_ADPCM specific data */
233 IMA_ADPCM_state.wavefmt.encoding = SDL_SwapLE16(format->encoding);
234 IMA_ADPCM_state.wavefmt.channels = SDL_SwapLE16(format->channels);
235 IMA_ADPCM_state.wavefmt.frequency = SDL_SwapLE32(format->frequency);
236 IMA_ADPCM_state.wavefmt.byterate = SDL_SwapLE32(format->byterate);
237 IMA_ADPCM_state.wavefmt.blockalign = SDL_SwapLE16(format->blockalign);
238 IMA_ADPCM_state.wavefmt.bitspersample =
239 SDL_SwapLE16(format->bitspersample);
240 rogue_feel = (Uint8 *)format+sizeof(*format);
241 if ( sizeof(*format) == 16 ) {
242 extra_info = ((rogue_feel[1]<<8)|rogue_feel[0]);
243 rogue_feel += sizeof(Uint16);
244 }
245 IMA_ADPCM_state.wSamplesPerBlock = ((rogue_feel[1]<<8)|rogue_feel[0]);
246 return(0);
247}
248
249static Sint32 IMA_ADPCM_nibble(struct IMA_ADPCM_decodestate *state,Uint8 nybble)
250{
251 const Sint32 max_audioval = ((1<<(16-1))-1);
252 const Sint32 min_audioval = -(1<<(16-1));
253 const int index_table[16] = {
254 -1, -1, -1, -1,
255 2, 4, 6, 8,
256 -1, -1, -1, -1,
257 2, 4, 6, 8
258 };
259 const Sint32 step_table[89] = {
260 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, 19, 21, 23, 25, 28, 31,
261 34, 37, 41, 45, 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130,
262 143, 157, 173, 190, 209, 230, 253, 279, 307, 337, 371, 408,
263 449, 494, 544, 598, 658, 724, 796, 876, 963, 1060, 1166, 1282,
264 1411, 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024, 3327,
265 3660, 4026, 4428, 4871, 5358, 5894, 6484, 7132, 7845, 8630,
266 9493, 10442, 11487, 12635, 13899, 15289, 16818, 18500, 20350,
267 22385, 24623, 27086, 29794, 32767
268 };
269 Sint32 delta, step;
270
271 /* Compute difference and new sample value */
272 step = step_table[state->index];
273 delta = step >> 3;
274 if ( nybble & 0x04 ) delta += step;
275 if ( nybble & 0x02 ) delta += (step >> 1);
276 if ( nybble & 0x01 ) delta += (step >> 2);
277 if ( nybble & 0x08 ) delta = -delta;
278 state->sample += delta;
279
280 /* Update index value */
281 state->index += index_table[nybble];
282 if ( state->index > 88 ) {
283 state->index = 88;
284 } else
285 if ( state->index < 0 ) {
286 state->index = 0;
287 }
288
289 /* Clamp output sample */
290 if ( state->sample > max_audioval ) {
291 state->sample = max_audioval;
292 } else
293 if ( state->sample < min_audioval ) {
294 state->sample = min_audioval;
295 }
296 return(state->sample);
297}
298
299/* Fill the decode buffer with a channel block of data (8 samples) */
300static void Fill_IMA_ADPCM_block(Uint8 *decoded, Uint8 *encoded,
301 int channel, int numchannels, struct IMA_ADPCM_decodestate *state)
302{
303 int i;
304 Sint8 nybble;
305 Sint32 new_sample;
306
307 decoded += (channel * 2);
308 for ( i=0; i<4; ++i ) {
309 nybble = (*encoded)&0x0F;
310 new_sample = IMA_ADPCM_nibble(state, nybble);
311 decoded[0] = new_sample&0xFF;
312 new_sample >>= 8;
313 decoded[1] = new_sample&0xFF;
314 decoded += 2 * numchannels;
315
316 nybble = (*encoded)>>4;
317 new_sample = IMA_ADPCM_nibble(state, nybble);
318 decoded[0] = new_sample&0xFF;
319 new_sample >>= 8;
320 decoded[1] = new_sample&0xFF;
321 decoded += 2 * numchannels;
322
323 ++encoded;
324 }
325}
326
327static int IMA_ADPCM_decode(Uint8 **audio_buf, Uint32 *audio_len)
328{
329 struct IMA_ADPCM_decodestate *state;
330 Uint8 *freeable, *encoded, *decoded;
331 Sint32 encoded_len, samplesleft;
332 unsigned int c, channels;
333
334 /* Check to make sure we have enough variables in the state array */
335 channels = IMA_ADPCM_state.wavefmt.channels;
336 if ( channels > SDL_arraysize(IMA_ADPCM_state.state) ) {
337 SDL_SetError("IMA ADPCM decoder can only handle %d channels",
338 SDL_arraysize(IMA_ADPCM_state.state));
339 return(-1);
340 }
341 state = IMA_ADPCM_state.state;
342
343 /* Allocate the proper sized output buffer */
344 encoded_len = *audio_len;
345 encoded = *audio_buf;
346 freeable = *audio_buf;
347 *audio_len = (encoded_len/IMA_ADPCM_state.wavefmt.blockalign) *
348 IMA_ADPCM_state.wSamplesPerBlock*
349 IMA_ADPCM_state.wavefmt.channels*sizeof(Sint16);
350 *audio_buf = (Uint8 *)SDL_malloc(*audio_len);
351 if ( *audio_buf == NULL ) {
352 SDL_Error(SDL_ENOMEM);
353 return(-1);
354 }
355 decoded = *audio_buf;
356
357 /* Get ready... Go! */
358 while ( encoded_len >= IMA_ADPCM_state.wavefmt.blockalign ) {
359 /* Grab the initial information for this block */
360 for ( c=0; c<channels; ++c ) {
361 /* Fill the state information for this block */
362 state[c].sample = ((encoded[1]<<8)|encoded[0]);
363 encoded += 2;
364 if ( state[c].sample & 0x8000 ) {
365 state[c].sample -= 0x10000;
366 }
367 state[c].index = *encoded++;
368 /* Reserved byte in buffer header, should be 0 */
369 if ( *encoded++ != 0 ) {
370 /* Uh oh, corrupt data? Buggy code? */;
371 }
372
373 /* Store the initial sample we start with */
374 decoded[0] = (Uint8)(state[c].sample&0xFF);
375 decoded[1] = (Uint8)(state[c].sample>>8);
376 decoded += 2;
377 }
378
379 /* Decode and store the other samples in this block */
380 samplesleft = (IMA_ADPCM_state.wSamplesPerBlock-1)*channels;
381 while ( samplesleft > 0 ) {
382 for ( c=0; c<channels; ++c ) {
383 Fill_IMA_ADPCM_block(decoded, encoded,
384 c, channels, &state[c]);
385 encoded += 4;
386 samplesleft -= 8;
387 }
388 decoded += (channels * 8 * 2);
389 }
390 encoded_len -= IMA_ADPCM_state.wavefmt.blockalign;
391 }
392 SDL_free(freeable);
393 return(0);
394}
395
396SDL_AudioSpec * SDL_LoadWAV_RW (SDL_RWops *src, int freesrc,
397 SDL_AudioSpec *spec, Uint8 **audio_buf, Uint32 *audio_len)
398{
399 int was_error;
400 Chunk chunk;
401 int lenread;
402 int MS_ADPCM_encoded, IMA_ADPCM_encoded;
403 int samplesize;
404
405 /* WAV magic header */
406 Uint32 RIFFchunk;
407 Uint32 wavelen = 0;
408 Uint32 WAVEmagic;
409 Uint32 headerDiff = 0;
410
411 /* FMT chunk */
412 WaveFMT *format = NULL;
413
414 /* Make sure we are passed a valid data source */
415 was_error = 0;
416 if ( src == NULL ) {
417 was_error = 1;
418 goto done;
419 }
420
421 /* Check the magic header */
422 RIFFchunk = SDL_ReadLE32(src);
423 wavelen = SDL_ReadLE32(src);
424 if ( wavelen == WAVE ) { /* The RIFFchunk has already been read */
425 WAVEmagic = wavelen;
426 wavelen = RIFFchunk;
427 RIFFchunk = RIFF;
428 } else {
429 WAVEmagic = SDL_ReadLE32(src);
430 }
431 if ( (RIFFchunk != RIFF) || (WAVEmagic != WAVE) ) {
432 SDL_SetError("Unrecognized file type (not WAVE)");
433 was_error = 1;
434 goto done;
435 }
436 headerDiff += sizeof(Uint32); /* for WAVE */
437
438 /* Read the audio data format chunk */
439 chunk.data = NULL;
440 do {
441 if ( chunk.data != NULL ) {
442 SDL_free(chunk.data);
443 chunk.data = NULL;
444 }
445 lenread = ReadChunk(src, &chunk);
446 if ( lenread < 0 ) {
447 was_error = 1;
448 goto done;
449 }
450 /* 2 Uint32's for chunk header+len, plus the lenread */
451 headerDiff += lenread + 2 * sizeof(Uint32);
452 } while ( (chunk.magic == FACT) || (chunk.magic == LIST) );
453
454 /* Decode the audio data format */
455 format = (WaveFMT *)chunk.data;
456 if ( chunk.magic != FMT ) {
457 SDL_SetError("Complex WAVE files not supported");
458 was_error = 1;
459 goto done;
460 }
461 MS_ADPCM_encoded = IMA_ADPCM_encoded = 0;
462 switch (SDL_SwapLE16(format->encoding)) {
463 case PCM_CODE:
464 /* We can understand this */
465 break;
466 case MS_ADPCM_CODE:
467 /* Try to understand this */
468 if ( InitMS_ADPCM(format) < 0 ) {
469 was_error = 1;
470 goto done;
471 }
472 MS_ADPCM_encoded = 1;
473 break;
474 case IMA_ADPCM_CODE:
475 /* Try to understand this */
476 if ( InitIMA_ADPCM(format) < 0 ) {
477 was_error = 1;
478 goto done;
479 }
480 IMA_ADPCM_encoded = 1;
481 break;
482 case MP3_CODE:
483 SDL_SetError("MPEG Layer 3 data not supported",
484 SDL_SwapLE16(format->encoding));
485 was_error = 1;
486 goto done;
487 default:
488 SDL_SetError("Unknown WAVE data format: 0x%.4x",
489 SDL_SwapLE16(format->encoding));
490 was_error = 1;
491 goto done;
492 }
493 SDL_memset(spec, 0, (sizeof *spec));
494 spec->freq = SDL_SwapLE32(format->frequency);
495 switch (SDL_SwapLE16(format->bitspersample)) {
496 case 4:
497 if ( MS_ADPCM_encoded || IMA_ADPCM_encoded ) {
498 spec->format = AUDIO_S16;
499 } else {
500 was_error = 1;
501 }
502 break;
503 case 8:
504 spec->format = AUDIO_U8;
505 break;
506 case 16:
507 spec->format = AUDIO_S16;
508 break;
509 default:
510 was_error = 1;
511 break;
512 }
513 if ( was_error ) {
514 SDL_SetError("Unknown %d-bit PCM data format",
515 SDL_SwapLE16(format->bitspersample));
516 goto done;
517 }
518 spec->channels = (Uint8)SDL_SwapLE16(format->channels);
519 spec->samples = 4096; /* Good default buffer size */
520
521 /* Read the audio data chunk */
522 *audio_buf = NULL;
523 do {
524 if ( *audio_buf != NULL ) {
525 SDL_free(*audio_buf);
526 *audio_buf = NULL;
527 }
528 lenread = ReadChunk(src, &chunk);
529 if ( lenread < 0 ) {
530 was_error = 1;
531 goto done;
532 }
533 *audio_len = lenread;
534 *audio_buf = chunk.data;
535 if(chunk.magic != DATA) headerDiff += lenread + 2 * sizeof(Uint32);
536 } while ( chunk.magic != DATA );
537 headerDiff += 2 * sizeof(Uint32); /* for the data chunk and len */
538
539 if ( MS_ADPCM_encoded ) {
540 if ( MS_ADPCM_decode(audio_buf, audio_len) < 0 ) {
541 was_error = 1;
542 goto done;
543 }
544 }
545 if ( IMA_ADPCM_encoded ) {
546 if ( IMA_ADPCM_decode(audio_buf, audio_len) < 0 ) {
547 was_error = 1;
548 goto done;
549 }
550 }
551
552 /* Don't return a buffer that isn't a multiple of samplesize */
553 samplesize = ((spec->format & 0xFF)/8)*spec->channels;
554 *audio_len &= ~(samplesize-1);
555
556done:
557 if ( format != NULL ) {
558 SDL_free(format);
559 }
560 if ( src ) {
561 if ( freesrc ) {
562 SDL_RWclose(src);
563 } else {
564 /* seek to the end of the file (given by the RIFF chunk) */
565 SDL_RWseek(src, wavelen - chunk.length - headerDiff, RW_SEEK_CUR);
566 }
567 }
568 if ( was_error ) {
569 spec = NULL;
570 }
571 return(spec);
572}
573
574/* Since the WAV memory is allocated in the shared library, it must also
575 be freed here. (Necessary under Win32, VC++)
576 */
577void SDL_FreeWAV(Uint8 *audio_buf)
578{
579 if ( audio_buf != NULL ) {
580 SDL_free(audio_buf);
581 }
582}
583
584static int ReadChunk(SDL_RWops *src, Chunk *chunk)
585{
586 chunk->magic = SDL_ReadLE32(src);
587 chunk->length = SDL_ReadLE32(src);
588 chunk->data = (Uint8 *)SDL_malloc(chunk->length);
589 if ( chunk->data == NULL ) {
590 SDL_Error(SDL_ENOMEM);
591 return(-1);
592 }
593 if ( SDL_RWread(src, chunk->data, chunk->length, 1) != 1 ) {
594 SDL_Error(SDL_EFREAD);
595 SDL_free(chunk->data);
596 chunk->data = NULL;
597 return(-1);
598 }
599 return(chunk->length);
600}