Mercurial > SDL_sound_CoreAudio
annotate decoders/wav.c @ 591:8faf61a640f0 tip
Resynced fixes for unit conversion bugs in the Ogg Tremor decoder from SoundDecoder/ALmixer.
Ogg Vorbis uses seconds and we multiply by 1000 to convert to milliseconds. But Ogg Tremor already uses milliseconds but I was still multiplying by 1000.
author | Eric Wing <ewing . public |-at-| gmail . com> |
---|---|
date | Thu, 25 Oct 2012 16:34:18 -0700 |
parents | 2e8907ff98e9 |
children |
rev | line source |
---|---|
17 | 1 /* |
2 * SDL_sound -- An abstract sound format decoding API. | |
3 * Copyright (C) 2001 Ryan C. Gordon. | |
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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | |
18 */ | |
19 | |
20 /* | |
21 * WAV decoder for SDL_sound. | |
22 * | |
23 * This driver handles Microsoft .WAVs, in as many of the thousands of | |
24 * variations as we can. | |
25 * | |
552
2e8907ff98e9
Replaced references to COPYING with references to LICENSE.txt ...
Ryan C. Gordon <icculus@icculus.org>
parents:
526
diff
changeset
|
26 * Please see the file LICENSE.txt in the source's root directory. |
17 | 27 * |
526
2df1f5c62d38
Updated my email address.
Ryan C. Gordon <icculus@icculus.org>
parents:
477
diff
changeset
|
28 * This file written by Ryan C. Gordon. (icculus@icculus.org) |
17 | 29 */ |
30 | |
106
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
31 #if HAVE_CONFIG_H |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
32 # include <config.h> |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
33 #endif |
100
6d9fdec2f708
added config.h, added --enable-debug flag, various other changes to the build system
fingolfin
parents:
64
diff
changeset
|
34 |
104
103cfcb3c014
Updated to fix build system problem.
Ryan C. Gordon <icculus@icculus.org>
parents:
100
diff
changeset
|
35 #ifdef SOUND_SUPPORTS_WAV |
103cfcb3c014
Updated to fix build system problem.
Ryan C. Gordon <icculus@icculus.org>
parents:
100
diff
changeset
|
36 |
17 | 37 #include <stdio.h> |
38 #include <stdlib.h> | |
39 #include <string.h> | |
40 | |
106
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
41 #include "SDL_sound.h" |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
42 |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
43 #define __SDL_SOUND_INTERNAL__ |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
44 #include "SDL_sound_internal.h" |
40de367eb59e
Changing my include structure to do this right.
Ryan C. Gordon <icculus@icculus.org>
parents:
104
diff
changeset
|
45 |
47
ea58bc3b15d7
Added init() and quit() methods.
Ryan C. Gordon <icculus@icculus.org>
parents:
40
diff
changeset
|
46 static int WAV_init(void); |
ea58bc3b15d7
Added init() and quit() methods.
Ryan C. Gordon <icculus@icculus.org>
parents:
40
diff
changeset
|
47 static void WAV_quit(void); |
17 | 48 static int WAV_open(Sound_Sample *sample, const char *ext); |
49 static void WAV_close(Sound_Sample *sample); | |
50 static Uint32 WAV_read(Sound_Sample *sample); | |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
51 static int WAV_rewind(Sound_Sample *sample); |
306
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
52 static int WAV_seek(Sound_Sample *sample, Uint32 ms); |
17 | 53 |
149
1df5c106504e
Decoders can now list multiple file extensions.
Ryan C. Gordon <icculus@icculus.org>
parents:
124
diff
changeset
|
54 static const char *extensions_wav[] = { "WAV", NULL }; |
17 | 55 const Sound_DecoderFunctions __Sound_DecoderFunctions_WAV = |
56 { | |
57 { | |
149
1df5c106504e
Decoders can now list multiple file extensions.
Ryan C. Gordon <icculus@icculus.org>
parents:
124
diff
changeset
|
58 extensions_wav, |
17 | 59 "Microsoft WAVE audio format", |
526
2df1f5c62d38
Updated my email address.
Ryan C. Gordon <icculus@icculus.org>
parents:
477
diff
changeset
|
60 "Ryan C. Gordon <icculus@icculus.org>", |
17 | 61 "http://www.icculus.org/SDL_sound/" |
62 }, | |
63 | |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
64 WAV_init, /* init() method */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
65 WAV_quit, /* quit() method */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
66 WAV_open, /* open() method */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
67 WAV_close, /* close() method */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
68 WAV_read, /* read() method */ |
306
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
69 WAV_rewind, /* rewind() method */ |
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
70 WAV_seek /* seek() method */ |
17 | 71 }; |
72 | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
73 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
74 /* Better than SDL_ReadLE16, since you can detect i/o errors... */ |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
75 static __inline__ int read_le16(SDL_RWops *rw, Uint16 *ui16) |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
76 { |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
77 int rc = SDL_RWread(rw, ui16, sizeof (Uint16), 1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
78 BAIL_IF_MACRO(rc != 1, ERR_IO_ERROR, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
79 *ui16 = SDL_SwapLE16(*ui16); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
80 return(1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
81 } /* read_le16 */ |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
82 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
83 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
84 /* Better than SDL_ReadLE32, since you can detect i/o errors... */ |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
85 static __inline__ int read_le32(SDL_RWops *rw, Uint32 *ui32) |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
86 { |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
87 int rc = SDL_RWread(rw, ui32, sizeof (Uint32), 1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
88 BAIL_IF_MACRO(rc != 1, ERR_IO_ERROR, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
89 *ui32 = SDL_SwapLE32(*ui32); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
90 return(1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
91 } /* read_le32 */ |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
92 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
93 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
94 /* This is just cleaner on the caller's end... */ |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
95 static __inline__ int read_uint8(SDL_RWops *rw, Uint8 *ui8) |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
96 { |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
97 int rc = SDL_RWread(rw, ui8, sizeof (Uint8), 1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
98 BAIL_IF_MACRO(rc != 1, ERR_IO_ERROR, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
99 return(1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
100 } /* read_uint8 */ |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
101 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
102 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
103 /* Chunk management code... */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
104 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
105 #define riffID 0x46464952 /* "RIFF", in ascii. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
106 #define waveID 0x45564157 /* "WAVE", in ascii. */ |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
107 #define factID 0x74636166 /* "fact", in ascii. */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
108 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
109 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
110 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
111 * The FORMAT chunk... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
112 *****************************************************************************/ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
113 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
114 #define fmtID 0x20746D66 /* "fmt ", in ascii. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
115 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
116 #define FMT_NORMAL 0x0001 /* Uncompressed waveform data. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
117 #define FMT_ADPCM 0x0002 /* ADPCM compressed waveform data. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
118 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
119 typedef struct |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
120 { |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
121 Sint16 iCoef1; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
122 Sint16 iCoef2; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
123 } ADPCMCOEFSET; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
124 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
125 typedef struct |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
126 { |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
127 Uint8 bPredictor; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
128 Uint16 iDelta; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
129 Sint16 iSamp1; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
130 Sint16 iSamp2; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
131 } ADPCMBLOCKHEADER; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
132 |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
133 typedef struct S_WAV_FMT_T |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
134 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
135 Uint32 chunkID; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
136 Sint32 chunkSize; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
137 Sint16 wFormatTag; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
138 Uint16 wChannels; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
139 Uint32 dwSamplesPerSec; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
140 Uint32 dwAvgBytesPerSec; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
141 Uint16 wBlockAlign; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
142 Uint16 wBitsPerSample; |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
143 |
364
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
144 Uint32 next_chunk_offset; |
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
145 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
146 Uint32 sample_frame_size; |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
147 Uint32 data_starting_offset; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
148 Uint32 total_bytes; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
149 |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
150 void (*free)(struct S_WAV_FMT_T *fmt); |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
151 Uint32 (*read_sample)(Sound_Sample *sample); |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
152 int (*rewind_sample)(Sound_Sample *sample); |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
153 int (*seek_sample)(Sound_Sample *sample, Uint32 ms); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
154 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
155 union |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
156 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
157 struct |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
158 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
159 Uint16 cbSize; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
160 Uint16 wSamplesPerBlock; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
161 Uint16 wNumCoef; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
162 ADPCMCOEFSET *aCoef; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
163 ADPCMBLOCKHEADER *blockheaders; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
164 Uint32 samples_left_in_block; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
165 int nibble_state; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
166 Sint8 nibble; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
167 } adpcm; |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
168 |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
169 /* put other format-specific data here... */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
170 } fmt; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
171 } fmt_t; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
172 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
173 |
17 | 174 /* |
175 * Read in a fmt_t from disk. This makes this process safe regardless of | |
176 * the processor's byte order or how the fmt_t structure is packed. | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
177 * Note that the union "fmt" is not read in here; that is handled as |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
178 * needed in the read_fmt_* functions. |
17 | 179 */ |
180 static int read_fmt_chunk(SDL_RWops *rw, fmt_t *fmt) | |
181 { | |
182 /* skip reading the chunk ID, since it was already read at this point... */ | |
183 fmt->chunkID = fmtID; | |
184 | |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
185 BAIL_IF_MACRO(!read_le32(rw, &fmt->chunkSize), NULL, 0); |
364
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
186 BAIL_IF_MACRO(fmt->chunkSize < 16, "WAV: Invalid chunk size", 0); |
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
187 fmt->next_chunk_offset = SDL_RWtell(rw) + fmt->chunkSize; |
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
188 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
189 BAIL_IF_MACRO(!read_le16(rw, &fmt->wFormatTag), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
190 BAIL_IF_MACRO(!read_le16(rw, &fmt->wChannels), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
191 BAIL_IF_MACRO(!read_le32(rw, &fmt->dwSamplesPerSec), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
192 BAIL_IF_MACRO(!read_le32(rw, &fmt->dwAvgBytesPerSec), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
193 BAIL_IF_MACRO(!read_le16(rw, &fmt->wBlockAlign), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
194 BAIL_IF_MACRO(!read_le16(rw, &fmt->wBitsPerSample), NULL, 0); |
17 | 195 |
196 return(1); | |
197 } /* read_fmt_chunk */ | |
198 | |
199 | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
200 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
201 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
202 * The DATA chunk... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
203 *****************************************************************************/ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
204 |
17 | 205 #define dataID 0x61746164 /* "data", in ascii. */ |
206 | |
207 typedef struct | |
208 { | |
209 Uint32 chunkID; | |
210 Sint32 chunkSize; | |
211 /* Then, (chunkSize) bytes of waveform data... */ | |
212 } data_t; | |
213 | |
214 | |
215 /* | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
216 * Read in a data_t from disk. This makes this process safe regardless of |
17 | 217 * the processor's byte order or how the fmt_t structure is packed. |
218 */ | |
219 static int read_data_chunk(SDL_RWops *rw, data_t *data) | |
220 { | |
221 /* skip reading the chunk ID, since it was already read at this point... */ | |
222 data->chunkID = dataID; | |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
223 BAIL_IF_MACRO(!read_le32(rw, &data->chunkSize), NULL, 0); |
17 | 224 return(1); |
40
c15396fc0e55
Fixed incorrect comment, by Torbj�rn Andersson. :)
Ryan C. Gordon <icculus@icculus.org>
parents:
17
diff
changeset
|
225 } /* read_data_chunk */ |
17 | 226 |
227 | |
228 | |
229 | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
230 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
231 * this is what we store in our internal->decoder_private field... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
232 *****************************************************************************/ |
17 | 233 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
234 typedef struct |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
235 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
236 fmt_t *fmt; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
237 Sint32 bytesLeft; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
238 } wav_t; |
17 | 239 |
240 | |
241 | |
242 | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
243 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
244 * Normal, uncompressed waveform handler... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
245 *****************************************************************************/ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
246 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
247 /* |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
248 * Sound_Decode() lands here for uncompressed WAVs... |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
249 */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
250 static Uint32 read_sample_fmt_normal(Sound_Sample *sample) |
17 | 251 { |
252 Uint32 retval; | |
253 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; | |
254 wav_t *w = (wav_t *) internal->decoder_private; | |
255 Uint32 max = (internal->buffer_size < (Uint32) w->bytesLeft) ? | |
256 internal->buffer_size : (Uint32) w->bytesLeft; | |
257 | |
258 assert(max > 0); | |
259 | |
260 /* | |
261 * We don't actually do any decoding, so we read the wav data | |
262 * directly into the internal buffer... | |
263 */ | |
264 retval = SDL_RWread(internal->rw, internal->buffer, 1, max); | |
265 | |
266 w->bytesLeft -= retval; | |
267 | |
268 /* Make sure the read went smoothly... */ | |
269 if ((retval == 0) || (w->bytesLeft == 0)) | |
270 sample->flags |= SOUND_SAMPLEFLAG_EOF; | |
271 | |
272 else if (retval == -1) | |
273 sample->flags |= SOUND_SAMPLEFLAG_ERROR; | |
274 | |
275 /* (next call this EAGAIN may turn into an EOF or error.) */ | |
276 else if (retval < internal->buffer_size) | |
277 sample->flags |= SOUND_SAMPLEFLAG_EAGAIN; | |
278 | |
279 return(retval); | |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
280 } /* read_sample_fmt_normal */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
281 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
282 |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
283 static int seek_sample_fmt_normal(Sound_Sample *sample, Uint32 ms) |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
284 { |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
285 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
286 wav_t *w = (wav_t *) internal->decoder_private; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
287 fmt_t *fmt = w->fmt; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
288 int offset = __Sound_convertMsToBytePos(&sample->actual, ms); |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
289 int pos = (int) (fmt->data_starting_offset + offset); |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
290 int rc = SDL_RWseek(internal->rw, pos, SEEK_SET); |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
291 BAIL_IF_MACRO(rc != pos, ERR_IO_ERROR, 0); |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
292 w->bytesLeft = fmt->total_bytes - offset; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
293 return(1); /* success. */ |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
294 } /* seek_sample_fmt_normal */ |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
295 |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
296 |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
297 static int rewind_sample_fmt_normal(Sound_Sample *sample) |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
298 { |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
299 /* no-op. */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
300 return(1); |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
301 } /* rewind_sample_fmt_normal */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
302 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
303 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
304 static int read_fmt_normal(SDL_RWops *rw, fmt_t *fmt) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
305 { |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
306 /* (don't need to read more from the RWops...) */ |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
307 fmt->free = NULL; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
308 fmt->read_sample = read_sample_fmt_normal; |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
309 fmt->rewind_sample = rewind_sample_fmt_normal; |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
310 fmt->seek_sample = seek_sample_fmt_normal; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
311 return(1); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
312 } /* read_fmt_normal */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
313 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
314 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
315 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
316 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
317 * ADPCM compression handler... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
318 *****************************************************************************/ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
319 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
320 #define FIXED_POINT_COEF_BASE 256 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
321 #define FIXED_POINT_ADAPTION_BASE 256 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
322 #define SMALLEST_ADPCM_DELTA 16 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
323 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
324 |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
325 static __inline__ int read_adpcm_block_headers(Sound_Sample *sample) |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
326 { |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
327 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
328 SDL_RWops *rw = internal->rw; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
329 wav_t *w = (wav_t *) internal->decoder_private; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
330 fmt_t *fmt = w->fmt; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
331 ADPCMBLOCKHEADER *headers = fmt->fmt.adpcm.blockheaders; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
332 int i; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
333 int max = fmt->wChannels; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
334 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
335 if (w->bytesLeft < fmt->wBlockAlign) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
336 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
337 sample->flags |= SOUND_SAMPLEFLAG_EOF; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
338 return(0); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
339 } /* if */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
340 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
341 w->bytesLeft -= fmt->wBlockAlign; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
342 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
343 for (i = 0; i < max; i++) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
344 BAIL_IF_MACRO(!read_uint8(rw, &headers[i].bPredictor), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
345 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
346 for (i = 0; i < max; i++) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
347 BAIL_IF_MACRO(!read_le16(rw, &headers[i].iDelta), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
348 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
349 for (i = 0; i < max; i++) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
350 BAIL_IF_MACRO(!read_le16(rw, &headers[i].iSamp1), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
351 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
352 for (i = 0; i < max; i++) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
353 BAIL_IF_MACRO(!read_le16(rw, &headers[i].iSamp2), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
354 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
355 fmt->fmt.adpcm.samples_left_in_block = fmt->fmt.adpcm.wSamplesPerBlock; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
356 fmt->fmt.adpcm.nibble_state = 0; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
357 return(1); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
358 } /* read_adpcm_block_headers */ |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
359 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
360 |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
361 static __inline__ void do_adpcm_nibble(Uint8 nib, |
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
362 ADPCMBLOCKHEADER *header, |
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
363 Sint32 lPredSamp) |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
364 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
365 static const Sint32 max_audioval = ((1<<(16-1))-1); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
366 static const Sint32 min_audioval = -(1<<(16-1)); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
367 static const Sint32 AdaptionTable[] = |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
368 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
369 230, 230, 230, 230, 307, 409, 512, 614, |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
370 768, 614, 512, 409, 307, 230, 230, 230 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
371 }; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
372 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
373 Sint32 lNewSamp; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
374 Sint32 delta; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
375 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
376 if (nib & 0x08) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
377 lNewSamp = lPredSamp + (header->iDelta * (nib - 0x10)); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
378 else |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
379 lNewSamp = lPredSamp + (header->iDelta * nib); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
380 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
381 /* clamp value... */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
382 if (lNewSamp < min_audioval) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
383 lNewSamp = min_audioval; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
384 else if (lNewSamp > max_audioval) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
385 lNewSamp = max_audioval; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
386 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
387 delta = ((Sint32) header->iDelta * AdaptionTable[nib]) / |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
388 FIXED_POINT_ADAPTION_BASE; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
389 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
390 if (delta < SMALLEST_ADPCM_DELTA) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
391 delta = SMALLEST_ADPCM_DELTA; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
392 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
393 header->iDelta = delta; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
394 header->iSamp2 = header->iSamp1; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
395 header->iSamp1 = lNewSamp; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
396 } /* do_adpcm_nibble */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
397 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
398 |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
399 static __inline__ int decode_adpcm_sample_frame(Sound_Sample *sample) |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
400 { |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
401 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
402 wav_t *w = (wav_t *) internal->decoder_private; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
403 fmt_t *fmt = w->fmt; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
404 ADPCMBLOCKHEADER *headers = fmt->fmt.adpcm.blockheaders; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
405 SDL_RWops *rw = internal->rw; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
406 int i; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
407 int max = fmt->wChannels; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
408 Sint32 delta; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
409 Uint8 nib = fmt->fmt.adpcm.nibble; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
410 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
411 for (i = 0; i < max; i++) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
412 { |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
413 Uint8 byte; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
414 Sint16 iCoef1 = fmt->fmt.adpcm.aCoef[headers[i].bPredictor].iCoef1; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
415 Sint16 iCoef2 = fmt->fmt.adpcm.aCoef[headers[i].bPredictor].iCoef2; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
416 Sint32 lPredSamp = ((headers[i].iSamp1 * iCoef1) + |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
417 (headers[i].iSamp2 * iCoef2)) / |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
418 FIXED_POINT_COEF_BASE; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
419 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
420 if (fmt->fmt.adpcm.nibble_state == 0) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
421 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
422 BAIL_IF_MACRO(!read_uint8(rw, &nib), NULL, 0); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
423 fmt->fmt.adpcm.nibble_state = 1; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
424 do_adpcm_nibble(nib >> 4, &headers[i], lPredSamp); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
425 } /* if */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
426 else |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
427 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
428 fmt->fmt.adpcm.nibble_state = 0; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
429 do_adpcm_nibble(nib & 0x0F, &headers[i], lPredSamp); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
430 } /* else */ |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
431 } /* for */ |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
432 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
433 fmt->fmt.adpcm.nibble = nib; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
434 return(1); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
435 } /* decode_adpcm_sample_frame */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
436 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
437 |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
438 static __inline__ void put_adpcm_sample_frame1(void *_buf, fmt_t *fmt) |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
439 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
440 Uint16 *buf = (Uint16 *) _buf; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
441 ADPCMBLOCKHEADER *headers = fmt->fmt.adpcm.blockheaders; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
442 int i; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
443 for (i = 0; i < fmt->wChannels; i++) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
444 *(buf++) = headers[i].iSamp1; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
445 } /* put_adpcm_sample_frame1 */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
446 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
447 |
401
c42ac9ee2ce4
Fixed "inline" keyword to compile.
Ryan C. Gordon <icculus@icculus.org>
parents:
387
diff
changeset
|
448 static __inline__ void put_adpcm_sample_frame2(void *_buf, fmt_t *fmt) |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
449 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
450 Uint16 *buf = (Uint16 *) _buf; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
451 ADPCMBLOCKHEADER *headers = fmt->fmt.adpcm.blockheaders; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
452 int i; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
453 for (i = 0; i < fmt->wChannels; i++) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
454 *(buf++) = headers[i].iSamp2; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
455 } /* put_adpcm_sample_frame2 */ |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
456 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
457 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
458 /* |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
459 * Sound_Decode() lands here for ADPCM-encoded WAVs... |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
460 */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
461 static Uint32 read_sample_fmt_adpcm(Sound_Sample *sample) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
462 { |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
463 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
464 wav_t *w = (wav_t *) internal->decoder_private; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
465 fmt_t *fmt = w->fmt; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
466 Uint32 bw = 0; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
467 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
468 while (bw < internal->buffer_size) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
469 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
470 /* write ongoing sample frame before reading more data... */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
471 switch (fmt->fmt.adpcm.samples_left_in_block) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
472 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
473 case 0: /* need to read a new block... */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
474 if (!read_adpcm_block_headers(sample)) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
475 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
476 if ((sample->flags & SOUND_SAMPLEFLAG_EOF) == 0) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
477 sample->flags |= SOUND_SAMPLEFLAG_ERROR; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
478 return(bw); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
479 } /* if */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
480 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
481 /* only write first sample frame for now. */ |
246
170b1400e060
Cast to prevent pointer arithmatic on a (void *).
Ryan C. Gordon <icculus@icculus.org>
parents:
242
diff
changeset
|
482 put_adpcm_sample_frame2((Uint8 *) internal->buffer + bw, fmt); |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
483 fmt->fmt.adpcm.samples_left_in_block--; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
484 bw += fmt->sample_frame_size; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
485 break; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
486 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
487 case 1: /* output last sample frame of block... */ |
246
170b1400e060
Cast to prevent pointer arithmatic on a (void *).
Ryan C. Gordon <icculus@icculus.org>
parents:
242
diff
changeset
|
488 put_adpcm_sample_frame1((Uint8 *) internal->buffer + bw, fmt); |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
489 fmt->fmt.adpcm.samples_left_in_block--; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
490 bw += fmt->sample_frame_size; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
491 break; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
492 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
493 default: /* output latest sample frame and read a new one... */ |
246
170b1400e060
Cast to prevent pointer arithmatic on a (void *).
Ryan C. Gordon <icculus@icculus.org>
parents:
242
diff
changeset
|
494 put_adpcm_sample_frame1((Uint8 *) internal->buffer + bw, fmt); |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
495 fmt->fmt.adpcm.samples_left_in_block--; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
496 bw += fmt->sample_frame_size; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
497 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
498 if (!decode_adpcm_sample_frame(sample)) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
499 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
500 sample->flags |= SOUND_SAMPLEFLAG_ERROR; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
501 return(bw); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
502 } /* if */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
503 } /* switch */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
504 } /* while */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
505 |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
506 return(bw); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
507 } /* read_sample_fmt_adpcm */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
508 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
509 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
510 /* |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
511 * Sound_FreeSample() lands here for ADPCM-encoded WAVs... |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
512 */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
513 static void free_fmt_adpcm(fmt_t *fmt) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
514 { |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
515 if (fmt->fmt.adpcm.aCoef != NULL) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
516 free(fmt->fmt.adpcm.aCoef); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
517 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
518 if (fmt->fmt.adpcm.blockheaders != NULL) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
519 free(fmt->fmt.adpcm.blockheaders); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
520 } /* free_fmt_adpcm */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
521 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
522 |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
523 static int rewind_sample_fmt_adpcm(Sound_Sample *sample) |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
524 { |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
525 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
526 wav_t *w = (wav_t *) internal->decoder_private; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
527 w->fmt->fmt.adpcm.samples_left_in_block = 0; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
528 return(1); |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
529 } /* rewind_sample_fmt_adpcm */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
530 |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
531 |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
532 static int seek_sample_fmt_adpcm(Sound_Sample *sample, Uint32 ms) |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
533 { |
333
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
534 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
535 wav_t *w = (wav_t *) internal->decoder_private; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
536 fmt_t *fmt = w->fmt; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
537 Uint32 origsampsleft = fmt->fmt.adpcm.samples_left_in_block; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
538 int origpos = SDL_RWtell(internal->rw); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
539 int offset = __Sound_convertMsToBytePos(&sample->actual, ms); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
540 int bpb = (fmt->fmt.adpcm.wSamplesPerBlock * fmt->sample_frame_size); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
541 int skipsize = (offset / bpb) * fmt->wBlockAlign; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
542 int pos = skipsize + fmt->data_starting_offset; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
543 int rc = SDL_RWseek(internal->rw, pos, SEEK_SET); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
544 BAIL_IF_MACRO(rc != pos, ERR_IO_ERROR, 0); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
545 |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
546 /* The offset we need is in this block, so we need to decode to there. */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
547 skipsize += (offset % bpb); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
548 rc = (offset % bpb); /* bytes into this block we need to decode */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
549 if (!read_adpcm_block_headers(sample)) |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
550 { |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
551 SDL_RWseek(internal->rw, origpos, SEEK_SET); /* try to make sane. */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
552 return(0); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
553 } /* if */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
554 |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
555 /* first sample frame of block is a freebie. :) */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
556 fmt->fmt.adpcm.samples_left_in_block--; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
557 rc -= fmt->sample_frame_size; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
558 while (rc > 0) |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
559 { |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
560 if (!decode_adpcm_sample_frame(sample)) |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
561 { |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
562 SDL_RWseek(internal->rw, origpos, SEEK_SET); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
563 fmt->fmt.adpcm.samples_left_in_block = origsampsleft; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
564 return(0); |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
565 } /* if */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
566 |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
567 fmt->fmt.adpcm.samples_left_in_block--; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
568 rc -= fmt->sample_frame_size; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
569 } /* while */ |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
570 |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
571 w->bytesLeft = fmt->total_bytes - skipsize; |
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
572 return(1); /* success. */ |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
573 } /* seek_sample_fmt_adpcm */ |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
574 |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
575 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
576 /* |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
577 * Read in the adpcm-specific info from disk. This makes this process |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
578 * safe regardless of the processor's byte order or how the fmt_t |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
579 * structure is packed. |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
580 */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
581 static int read_fmt_adpcm(SDL_RWops *rw, fmt_t *fmt) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
582 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
583 size_t i; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
584 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
585 memset(&fmt->fmt.adpcm, '\0', sizeof (fmt->fmt.adpcm)); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
586 fmt->free = free_fmt_adpcm; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
587 fmt->read_sample = read_sample_fmt_adpcm; |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
588 fmt->rewind_sample = rewind_sample_fmt_adpcm; |
333
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
589 fmt->seek_sample = seek_sample_fmt_adpcm; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
590 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
591 BAIL_IF_MACRO(!read_le16(rw, &fmt->fmt.adpcm.cbSize), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
592 BAIL_IF_MACRO(!read_le16(rw, &fmt->fmt.adpcm.wSamplesPerBlock), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
593 BAIL_IF_MACRO(!read_le16(rw, &fmt->fmt.adpcm.wNumCoef), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
594 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
595 /* fmt->free() is always called, so these malloc()s will be cleaned up. */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
596 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
597 i = sizeof (ADPCMCOEFSET) * fmt->fmt.adpcm.wNumCoef; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
598 fmt->fmt.adpcm.aCoef = (ADPCMCOEFSET *) malloc(i); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
599 BAIL_IF_MACRO(fmt->fmt.adpcm.aCoef == NULL, ERR_OUT_OF_MEMORY, 0); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
600 |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
601 for (i = 0; i < fmt->fmt.adpcm.wNumCoef; i++) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
602 { |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
603 BAIL_IF_MACRO(!read_le16(rw, &fmt->fmt.adpcm.aCoef[i].iCoef1), NULL, 0); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
604 BAIL_IF_MACRO(!read_le16(rw, &fmt->fmt.adpcm.aCoef[i].iCoef2), NULL, 0); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
605 } /* for */ |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
606 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
607 i = sizeof (ADPCMBLOCKHEADER) * fmt->wChannels; |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
608 fmt->fmt.adpcm.blockheaders = (ADPCMBLOCKHEADER *) malloc(i); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
609 BAIL_IF_MACRO(fmt->fmt.adpcm.blockheaders == NULL, ERR_OUT_OF_MEMORY, 0); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
610 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
611 return(1); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
612 } /* read_fmt_adpcm */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
613 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
614 |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
615 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
616 /***************************************************************************** |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
617 * Everything else... * |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
618 *****************************************************************************/ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
619 |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
620 static int WAV_init(void) |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
621 { |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
622 return(1); /* always succeeds. */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
623 } /* WAV_init */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
624 |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
625 |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
626 static void WAV_quit(void) |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
627 { |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
628 /* it's a no-op. */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
629 } /* WAV_quit */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
630 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
631 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
632 static int read_fmt(SDL_RWops *rw, fmt_t *fmt) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
633 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
634 /* if it's in this switch statement, we support the format. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
635 switch (fmt->wFormatTag) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
636 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
637 case FMT_NORMAL: |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
638 SNDDBG(("WAV: Appears to be uncompressed audio.\n")); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
639 return(read_fmt_normal(rw, fmt)); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
640 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
641 case FMT_ADPCM: |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
642 SNDDBG(("WAV: Appears to be ADPCM compressed audio.\n")); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
643 return(read_fmt_adpcm(rw, fmt)); |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
644 |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
645 /* add other types here. */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
646 |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
647 default: |
193
6cd07211a235
Added some debugging output in preparation for future codecs (gsm, maybe?)
Ryan C. Gordon <icculus@icculus.org>
parents:
185
diff
changeset
|
648 SNDDBG(("WAV: Format 0x%X is unknown.\n", |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
649 (unsigned int) fmt->wFormatTag)); |
387
fb519e6028e3
Changed all the Sound_SetError() calls to __Sound_SetError (or BAIL*_MACRO)
Ryan C. Gordon <icculus@icculus.org>
parents:
377
diff
changeset
|
650 BAIL_MACRO("WAV: Unsupported format", 0); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
651 } /* switch */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
652 |
178
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
653 assert(0); /* shouldn't hit this point. */ |
bdbe09014724
Minor tweaks and such.
Ryan C. Gordon <icculus@icculus.org>
parents:
149
diff
changeset
|
654 return(0); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
655 } /* read_fmt */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
656 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
657 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
658 /* |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
659 * Locate a specific chunk in the WAVE file by ID... |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
660 */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
661 static int find_chunk(SDL_RWops *rw, Uint32 id) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
662 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
663 Sint32 siz = 0; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
664 Uint32 _id = 0; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
665 Uint32 pos = SDL_RWtell(rw); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
666 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
667 while (1) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
668 { |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
669 BAIL_IF_MACRO(!read_le32(rw, &_id), NULL, 0); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
670 if (_id == id) |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
671 return(1); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
672 |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
673 /* skip ahead and see what next chunk is... */ |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
674 BAIL_IF_MACRO(!read_le32(rw, &siz), NULL, 0); |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
675 assert(siz >= 0); |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
676 pos += (sizeof (Uint32) * 2) + siz; |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
677 if (siz > 0) |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
678 BAIL_IF_MACRO(SDL_RWseek(rw, pos, SEEK_SET) != pos, NULL, 0); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
679 } /* while */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
680 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
681 return(0); /* shouldn't hit this, but just in case... */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
682 } /* find_chunk */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
683 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
684 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
685 static int WAV_open_internal(Sound_Sample *sample, const char *ext, fmt_t *fmt) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
686 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
687 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
688 SDL_RWops *rw = internal->rw; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
689 data_t d; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
690 wav_t *w; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
691 Uint32 pos; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
692 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
693 BAIL_IF_MACRO(SDL_ReadLE32(rw) != riffID, "WAV: Not a RIFF file.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
694 SDL_ReadLE32(rw); /* throw the length away; we get this info later. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
695 BAIL_IF_MACRO(SDL_ReadLE32(rw) != waveID, "WAV: Not a WAVE file.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
696 BAIL_IF_MACRO(!find_chunk(rw, fmtID), "WAV: No format chunk.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
697 BAIL_IF_MACRO(!read_fmt_chunk(rw, fmt), "WAV: Can't read format chunk.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
698 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
699 sample->actual.channels = (Uint8) fmt->wChannels; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
700 sample->actual.rate = fmt->dwSamplesPerSec; |
193
6cd07211a235
Added some debugging output in preparation for future codecs (gsm, maybe?)
Ryan C. Gordon <icculus@icculus.org>
parents:
185
diff
changeset
|
701 if ((fmt->wBitsPerSample == 4) /*|| (fmt->wBitsPerSample == 0) */ ) |
351 | 702 sample->actual.format = AUDIO_S16SYS; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
703 else if (fmt->wBitsPerSample == 8) |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
704 sample->actual.format = AUDIO_U8; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
705 else if (fmt->wBitsPerSample == 16) |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
706 sample->actual.format = AUDIO_S16LSB; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
707 else |
193
6cd07211a235
Added some debugging output in preparation for future codecs (gsm, maybe?)
Ryan C. Gordon <icculus@icculus.org>
parents:
185
diff
changeset
|
708 { |
6cd07211a235
Added some debugging output in preparation for future codecs (gsm, maybe?)
Ryan C. Gordon <icculus@icculus.org>
parents:
185
diff
changeset
|
709 SNDDBG(("WAV: %d bits per sample!?\n", (int) fmt->wBitsPerSample)); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
710 BAIL_MACRO("WAV: Unsupported sample size.", 0); |
193
6cd07211a235
Added some debugging output in preparation for future codecs (gsm, maybe?)
Ryan C. Gordon <icculus@icculus.org>
parents:
185
diff
changeset
|
711 } /* else */ |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
712 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
713 BAIL_IF_MACRO(!read_fmt(rw, fmt), NULL, 0); |
364
4bcbc442d145
Fix to handle strange WAV fmt chunks.
Ryan C. Gordon <icculus@icculus.org>
parents:
351
diff
changeset
|
714 SDL_RWseek(rw, fmt->next_chunk_offset, SEEK_SET); |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
715 BAIL_IF_MACRO(!find_chunk(rw, dataID), "WAV: No data chunk.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
716 BAIL_IF_MACRO(!read_data_chunk(rw, &d), "WAV: Can't read data chunk.", 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
717 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
718 w = (wav_t *) malloc(sizeof(wav_t)); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
719 BAIL_IF_MACRO(w == NULL, ERR_OUT_OF_MEMORY, 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
720 w->fmt = fmt; |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
721 fmt->total_bytes = w->bytesLeft = d.chunkSize; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
722 fmt->data_starting_offset = SDL_RWtell(rw); |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
723 fmt->sample_frame_size = ( ((sample->actual.format & 0xFF) / 8) * |
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
724 sample->actual.channels ); |
474
c66080364dff
Most decoders now report total sample play time, now. Technically, this
Ryan C. Gordon <icculus@icculus.org>
parents:
401
diff
changeset
|
725 internal->decoder_private = (void *) w; |
185
6bb68b3bdcf1
ADPCM decoder seems to be complete, other fixes too...
Ryan C. Gordon <icculus@icculus.org>
parents:
183
diff
changeset
|
726 |
477
3e705c9180e5
Fixed binary compatibility, added Sound_GetDuration().
Ryan C. Gordon <icculus@icculus.org>
parents:
474
diff
changeset
|
727 internal->total_time = (fmt->total_bytes / fmt->dwAvgBytesPerSec) * 1000; |
3e705c9180e5
Fixed binary compatibility, added Sound_GetDuration().
Ryan C. Gordon <icculus@icculus.org>
parents:
474
diff
changeset
|
728 internal->total_time += (fmt->total_bytes % fmt->dwAvgBytesPerSec) |
3e705c9180e5
Fixed binary compatibility, added Sound_GetDuration().
Ryan C. Gordon <icculus@icculus.org>
parents:
474
diff
changeset
|
729 * 1000 / fmt->dwAvgBytesPerSec; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
730 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
731 sample->flags = SOUND_SAMPLEFLAG_NONE; |
333
565ae12fa74e
Implemented seek support for ADPCM-compressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
307
diff
changeset
|
732 if (fmt->seek_sample != NULL) |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
733 sample->flags |= SOUND_SAMPLEFLAG_CANSEEK; |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
734 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
735 SNDDBG(("WAV: Accepting data stream.\n")); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
736 return(1); /* we'll handle this data. */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
737 } /* WAV_open_internal */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
738 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
739 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
740 static int WAV_open(Sound_Sample *sample, const char *ext) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
741 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
742 int rc; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
743 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
744 fmt_t *fmt = (fmt_t *) malloc(sizeof (fmt_t)); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
745 BAIL_IF_MACRO(fmt == NULL, ERR_OUT_OF_MEMORY, 0); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
746 memset(fmt, '\0', sizeof (fmt_t)); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
747 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
748 rc = WAV_open_internal(sample, ext, fmt); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
749 if (!rc) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
750 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
751 if (fmt->free != NULL) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
752 fmt->free(fmt); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
753 free(fmt); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
754 } /* if */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
755 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
756 return(rc); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
757 } /* WAV_open */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
758 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
759 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
760 static void WAV_close(Sound_Sample *sample) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
761 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
762 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
763 wav_t *w = (wav_t *) internal->decoder_private; |
183
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
764 |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
765 if (w->fmt->free != NULL) |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
766 w->fmt->free(w->fmt); |
26996236d790
Updated comments to reflect change from LICENSE to COPYING file, and put a
Ryan C. Gordon <icculus@icculus.org>
parents:
178
diff
changeset
|
767 |
124
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
768 free(w->fmt); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
769 free(w); |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
770 } /* WAV_close */ |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
771 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
772 |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
773 static Uint32 WAV_read(Sound_Sample *sample) |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
774 { |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
775 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
776 wav_t *w = (wav_t *) internal->decoder_private; |
e46e31fdecfd
Restructured to handle multiple formats.
Ryan C. Gordon <icculus@icculus.org>
parents:
106
diff
changeset
|
777 return(w->fmt->read_sample(sample)); |
17 | 778 } /* WAV_read */ |
779 | |
221
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
780 |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
781 static int WAV_rewind(Sound_Sample *sample) |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
782 { |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
783 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
784 wav_t *w = (wav_t *) internal->decoder_private; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
785 fmt_t *fmt = w->fmt; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
786 int rc = SDL_RWseek(internal->rw, fmt->data_starting_offset, SEEK_SET); |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
787 BAIL_IF_MACRO(rc != fmt->data_starting_offset, ERR_IO_ERROR, 0); |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
788 w->bytesLeft = fmt->total_bytes; |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
789 return(fmt->rewind_sample(sample)); |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
790 } /* WAV_rewind */ |
c9772a9f5271
Initial implementation or stubs for rewind method. Other cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
193
diff
changeset
|
791 |
306
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
792 |
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
793 static int WAV_seek(Sound_Sample *sample, Uint32 ms) |
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
794 { |
307
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
795 Sound_SampleInternal *internal = (Sound_SampleInternal *) sample->opaque; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
796 wav_t *w = (wav_t *) internal->decoder_private; |
eb7c929193dd
Added seek support for uncompressed WAVs.
Ryan C. Gordon <icculus@icculus.org>
parents:
306
diff
changeset
|
797 return(w->fmt->seek_sample(sample, ms)); |
306
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
798 } /* WAV_seek */ |
c97be6e1bd27
Added framework for Sound_Seek() support.
Ryan C. Gordon <icculus@icculus.org>
parents:
246
diff
changeset
|
799 |
64
40006625142a
Changes in preparation of autoconf support.
Ryan C. Gordon <icculus@icculus.org>
parents:
62
diff
changeset
|
800 #endif /* SOUND_SUPPORTS_WAV */ |
17 | 801 |
802 /* end of wav.c ... */ | |
803 |