21 #include "../SDL_internal.h"
28 #define INT_MAX SDL_MAX_SINT32
31 #define SIZE_MAX ((size_t)-1)
49 if (*f1 > 0 &&
SIZE_MAX / *f1 <= f2) {
104 #ifdef SDL_WAVE_DEBUG_LOG_FORMAT
109 const char *fmtstr =
"WAVE file: %s, %u Hz, %s, %u bits, %u %s/s";
110 const char *waveformat, *wavechannel, *wavebpsunit =
"B";
116 switch (
format->encoding) {
121 waveformat =
"IEEE Float";
124 waveformat =
"A-law";
127 waveformat =
"\xc2\xb5-law";
130 waveformat =
"MS ADPCM";
133 waveformat =
"IMA ADPCM";
136 waveformat =
"Unknown";
140 #define SDL_WAVE_DEBUG_CHANNELCFG(STR, CODE) case CODE: wavechannel = STR; break;
141 #define SDL_WAVE_DEBUG_CHANNELSTR(STR, CODE) if (format->channelmask & CODE) { \
142 SDL_strlcat(channelstr, channelstr[0] ? "-" STR : STR, sizeof(channelstr));}
145 switch (
format->channelmask) {
146 SDL_WAVE_DEBUG_CHANNELCFG(
"1.0 Mono", 0x4)
147 SDL_WAVE_DEBUG_CHANNELCFG("1.1 Mono", 0xc)
148 SDL_WAVE_DEBUG_CHANNELCFG("2.0 Stereo", 0x3)
149 SDL_WAVE_DEBUG_CHANNELCFG("2.1 Stereo", 0xb)
150 SDL_WAVE_DEBUG_CHANNELCFG("3.0 Stereo", 0x7)
151 SDL_WAVE_DEBUG_CHANNELCFG("3.1 Stereo", 0xf)
152 SDL_WAVE_DEBUG_CHANNELCFG("3.0 Surround", 0x103)
153 SDL_WAVE_DEBUG_CHANNELCFG("3.1 Surround", 0x10b)
154 SDL_WAVE_DEBUG_CHANNELCFG("4.0 Quad", 0x33)
155 SDL_WAVE_DEBUG_CHANNELCFG("4.1 Quad", 0x3b)
156 SDL_WAVE_DEBUG_CHANNELCFG("4.0 Surround", 0x107)
157 SDL_WAVE_DEBUG_CHANNELCFG("4.1 Surround", 0x10f)
158 SDL_WAVE_DEBUG_CHANNELCFG("5.0", 0x37)
159 SDL_WAVE_DEBUG_CHANNELCFG("5.1", 0x3f)
160 SDL_WAVE_DEBUG_CHANNELCFG("5.0 Side", 0x607)
161 SDL_WAVE_DEBUG_CHANNELCFG("5.1 Side", 0x60f)
162 SDL_WAVE_DEBUG_CHANNELCFG("6.0", 0x137)
163 SDL_WAVE_DEBUG_CHANNELCFG("6.1", 0x13f)
164 SDL_WAVE_DEBUG_CHANNELCFG("6.0 Side", 0x707)
165 SDL_WAVE_DEBUG_CHANNELCFG("6.1 Side", 0x70f)
166 SDL_WAVE_DEBUG_CHANNELCFG("7.0", 0xf7)
167 SDL_WAVE_DEBUG_CHANNELCFG("7.1", 0xff)
168 SDL_WAVE_DEBUG_CHANNELCFG("7.0 Side", 0x6c7)
169 SDL_WAVE_DEBUG_CHANNELCFG("7.1 Side", 0x6cf)
170 SDL_WAVE_DEBUG_CHANNELCFG("7.0 Surround", 0x637)
171 SDL_WAVE_DEBUG_CHANNELCFG("7.1 Surround", 0x63f)
172 SDL_WAVE_DEBUG_CHANNELCFG("9.0 Surround", 0x5637)
173 SDL_WAVE_DEBUG_CHANNELCFG("9.1 Surround", 0x563f)
174 SDL_WAVE_DEBUG_CHANNELCFG("11.0 Surround", 0x56f7)
175 SDL_WAVE_DEBUG_CHANNELCFG("11.1 Surround", 0x56ff)
177 SDL_WAVE_DEBUG_CHANNELSTR("FL", 0
x1)
178 SDL_WAVE_DEBUG_CHANNELSTR("FR", 0
x2)
179 SDL_WAVE_DEBUG_CHANNELSTR("FC", 0x4)
180 SDL_WAVE_DEBUG_CHANNELSTR("LF", 0x8)
181 SDL_WAVE_DEBUG_CHANNELSTR("BL", 0x10)
182 SDL_WAVE_DEBUG_CHANNELSTR("BR", 0x20)
183 SDL_WAVE_DEBUG_CHANNELSTR("FLC", 0x40)
184 SDL_WAVE_DEBUG_CHANNELSTR("FRC", 0x80)
185 SDL_WAVE_DEBUG_CHANNELSTR("BC", 0x100)
186 SDL_WAVE_DEBUG_CHANNELSTR("SL", 0x200)
187 SDL_WAVE_DEBUG_CHANNELSTR("SR", 0x400)
188 SDL_WAVE_DEBUG_CHANNELSTR("TC", 0x800)
189 SDL_WAVE_DEBUG_CHANNELSTR("TFL", 0x1000)
190 SDL_WAVE_DEBUG_CHANNELSTR("TFC", 0x2000)
191 SDL_WAVE_DEBUG_CHANNELSTR("TFR", 0x4000)
192 SDL_WAVE_DEBUG_CHANNELSTR("TBL", 0x8000)
193 SDL_WAVE_DEBUG_CHANNELSTR("TBC", 0x10000)
194 SDL_WAVE_DEBUG_CHANNELSTR("TBR", 0x20000)
198 switch (
format->channels) {
200 if (
SDL_snprintf(channelstr,
sizeof(channelstr),
"%u channels",
format->channels) >= 0) {
201 wavechannel = channelstr;
205 wavechannel =
"Unknown";
208 wavechannel =
"Mono";
211 wavechannel =
"Setero";
216 #undef SDL_WAVE_DEBUG_CHANNELCFG
217 #undef SDL_WAVE_DEBUG_CHANNELSTR
219 if (wavebps >= 1024) {
221 wavebps = wavebps / 1024 + (wavebps & 0x3ff ? 1 : 0);
228 #ifdef SDL_WAVE_DEBUG_DUMP_FORMAT
233 const char *fmtstr1 =
"WAVE chunk dump:\n"
234 "-------------------------------------------\n"
236 "-------------------------------------------\n"
238 " wFormatTag 0x%04x\n"
240 " nSamplesPerSec %11u\n"
241 " nAvgBytesPerSec %11u\n"
242 " nBlockAlign %11u\n";
243 const char *fmtstr2 =
" wBitsPerSample %11u\n";
244 const char *fmtstr3 =
" cbSize %11u\n";
245 const char *fmtstr4a =
" wValidBitsPerSample %11u\n";
246 const char *fmtstr4b =
" wSamplesPerBlock %11u\n";
247 const char *fmtstr5 =
" dwChannelMask 0x%08x\n"
249 " %08x-%04x-%04x-%02x%02x%02x%02x%02x%02x%02x%02x\n";
250 const char *fmtstr6 =
"-------------------------------------------\n"
252 " dwSampleLength %11u\n";
253 const char *fmtstr7 =
"-------------------------------------------\n"
255 "-------------------------------------------\n";
262 if (dumpstr ==
NULL) {
268 dumppos +=
res > 0 ?
res : 0;
271 dumppos +=
res > 0 ?
res : 0;
275 dumppos +=
res > 0 ?
res : 0;
283 switch (
format->encoding) {
286 dumppos +=
res > 0 ?
res : 0;
291 dumppos +=
res > 0 ?
res : 0;
294 res =
SDL_snprintf(dumpstr + dumppos,
bufsize - dumppos, fmtstr5,
format->channelmask, g1, g2, g3,
g[8],
g[9],
g[10],
g[11],
g[12],
g[13],
g[14],
g[15]);
295 dumppos +=
res > 0 ?
res : 0;
297 switch (
format->encoding) {
300 if (fmtlen >= 20 &&
format->extsize >= 2) {
302 dumppos +=
res > 0 ?
res : 0;
309 dumppos +=
res > 0 ?
res : 0;
312 dumppos +=
res > 0 ?
res : 0;
325 return SDL_SetError(
"Invalid number of sample frames in WAVE fact chunk (too many)");
345 if (datalength < blockheadersize || trailingdata > 0) {
352 if (trailingdata > 0) {
356 if (trailingdata >= blockheadersize) {
357 size_t trailingsamples = 2 + (trailingdata - blockheadersize) * 8 / blockframebitsize;
358 if (trailingsamples >
format->samplesperblock) {
359 trailingsamples =
format->samplesperblock;
379 const size_t blockheadersize = (
size_t)
format->channels * 7;
380 const size_t blockdatasize = (
size_t)
format->blockalign - blockheadersize;
382 const size_t blockdatasamples = (blockdatasize * 8) / blockframebitsize;
383 const Sint16 presetcoeffs[14] = {256, 0, 512, -256, 0, 0, 192, 64, 240, 0, 460, -208, 392, -232};
384 size_t i, coeffcount;
393 if (
format->channels > 2) {
397 if (
format->bitspersample != 4) {
398 return SDL_SetError(
"Invalid MS ADPCM bits per sample of %u", (
unsigned int)
format->bitspersample);
402 if (
format->blockalign < blockheadersize) {
403 return SDL_SetError(
"Invalid MS ADPCM block size (nBlockAlign)");
411 return SDL_SetError(
"MS ADPCM with the extensible header is not supported");
417 if (chunk->
size < 22) {
418 return SDL_SetError(
"Could not read MS ADPCM format header");
428 if (coeffcount > 256) {
432 if (chunk->
size < 22 + coeffcount * 4) {
433 return SDL_SetError(
"Could not read custom coefficients in MS ADPCM format header");
434 }
else if (
format->extsize < 4 + coeffcount * 4) {
435 return SDL_SetError(
"Invalid MS ADPCM format header (too small)");
436 }
else if (coeffcount < 7) {
437 return SDL_SetError(
"Missing required coefficients in MS ADPCM format header");
442 if (coeffdata ==
NULL) {
449 for (
i = 0;
i < coeffcount * 2;
i++) {
454 if (
i < 14 &&
c != presetcoeffs[
i]) {
455 return SDL_SetError(
"Wrong preset coefficients in MS ADPCM format header");
463 if (
format->samplesperblock == 0) {
482 if (
format->samplesperblock == 1 || blockdatasamples < format->samplesperblock - 2) {
483 return SDL_SetError(
"Invalid number of samples per MS ADPCM block (wSamplesPerBlock)");
496 const Sint32 max_audioval = 32767;
497 const Sint32 min_audioval = -32768;
498 const Uint16 max_deltaval = 65535;
499 const Uint16 adaptive[] = {
500 230, 230, 230, 230, 307, 409, 512, 614,
501 768, 614, 512, 409, 307, 230, 230, 230
507 new_sample = (sample1 * cstate->
coeff1 + sample2 * cstate->
coeff2) / 256;
509 errordelta = (
Sint32)nybble - (nybble >= 0x08 ? 0x10 : 0);
510 new_sample += (
Sint32)delta * errordelta;
511 if (new_sample < min_audioval) {
512 new_sample = min_audioval;
513 }
else if (new_sample > max_audioval) {
514 new_sample = max_audioval;
516 delta = (delta * adaptive[nybble]) / 256;
519 }
else if (delta > max_deltaval) {
523 delta = max_deltaval;
527 return (
Sint16)new_sample;
540 for (
c = 0;
c < channels;
c++) {
544 coeffindex =
state->block.data[o];
545 if (coeffindex > ddata->coeffcount) {
546 return SDL_SetError(
"Invalid MS ADPCM coefficient index in block header");
548 cstate[
c].
coeff1 = ddata->coeff[coeffindex * 2];
549 cstate[
c].
coeff2 = ddata->coeff[coeffindex * 2 + 1];
552 o = channels +
c * 2;
558 o = channels * 3 +
c * 2;
560 if (sample >= 0x8000) {
565 o = channels * 5 +
c * 2;
567 if (sample >= 0x8000) {
581 state->framesleft -= 2;
600 size_t blockpos =
state->block.pos;
601 size_t blocksize =
state->block.size;
603 size_t outpos =
state->output.pos;
605 Sint64 blockframesleft =
state->samplesperblock - 2;
606 if (blockframesleft >
state->framesleft) {
607 blockframesleft =
state->framesleft;
610 while (blockframesleft > 0) {
611 for (
c = 0;
c < channels;
c++) {
612 if (nybble & 0x4000) {
614 }
else if (blockpos < blocksize) {
615 nybble =
state->block.data[blockpos++] | 0x4000;
618 state->output.pos = outpos -
c;
623 sample1 =
state->output.data[outpos - channels];
624 sample2 =
state->output.data[outpos - channels * 2];
627 state->output.data[outpos++] = sample1;
634 state->output.pos = outpos;
643 size_t bytesleft, outputsize;
686 state.output.pos = 0;
693 state.cstate = cstate;
696 bytesleft =
state.input.size -
state.input.pos;
697 while (
state.framesleft > 0 && bytesleft >=
state.blockheadersize) {
699 state.block.size = bytesleft <
state.blocksize ? bytesleft :
state.blocksize;
705 return SDL_SetError(
"Unexpected overflow in MS ADPCM decoder");
730 bytesleft =
state.input.size -
state.input.pos;
734 *audio_len = (
Uint32)outputsize;
744 const size_t subblockframesize = (
size_t)
format->channels * 4;
745 const size_t availableblocks = datalength /
format->blockalign;
746 const size_t trailingdata = datalength %
format->blockalign;
750 if (datalength < blockheadersize || trailingdata > 0) {
757 if (trailingdata > 0) {
763 size_t trailingsamples = 1;
765 if (trailingdata > blockheadersize) {
767 const size_t trailingblockdata = trailingdata - blockheadersize;
768 const size_t trailingsubblockdata = trailingblockdata % subblockframesize;
769 trailingsamples += (trailingblockdata / subblockframesize) * 8;
773 if (trailingsubblockdata > subblockframesize - 4) {
774 trailingsamples += (trailingsubblockdata % 4) * 2;
778 if (trailingsamples >
format->samplesperblock) {
779 trailingsamples =
format->samplesperblock;
798 const size_t blockheadersize = (
size_t)
format->channels * 4;
799 const size_t blockdatasize = (
size_t)
format->blockalign - blockheadersize;
801 const size_t blockdatasamples = (blockdatasize * 8) / blockframebitsize;
806 if (
format->bitspersample == 3) {
807 return SDL_SetError(
"3-bit IMA ADPCM currently not supported");
808 }
else if (
format->bitspersample != 4) {
809 return SDL_SetError(
"Invalid IMA ADPCM bits per sample of %u", (
unsigned int)
format->bitspersample);
815 if (
format->blockalign < blockheadersize ||
format->blockalign % 4) {
816 return SDL_SetError(
"Invalid IMA ADPCM block size (nBlockAlign)");
825 if (chunk->
size >= 20 &&
format->extsize >= 2) {
830 if (
format->samplesperblock == 0) {
848 if (blockdatasamples < format->samplesperblock - 1) {
849 return SDL_SetError(
"Invalid number of samples per IMA ADPCM block (wSamplesPerBlock)");
862 const Sint32 max_audioval = 32767;
863 const Sint32 min_audioval = -32768;
864 const Sint8 index_table_4b[16] = {
870 const Uint16 step_table[89] = {
871 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, 19, 21, 23, 25, 28, 31,
872 34, 37, 41, 45, 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130,
873 143, 157, 173, 190, 209, 230, 253, 279, 307, 337, 371, 408,
874 449, 494, 544, 598, 658, 724, 796, 876, 963, 1060, 1166, 1282,
875 1411, 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024, 3327,
876 3660, 4026, 4428, 4871, 5358, 5894, 6484, 7132, 7845, 8630,
877 9493, 10442, 11487, 12635, 13899, 15289, 16818, 18500, 20350,
878 22385, 24623, 27086, 29794, 32767
887 }
else if (
index < 0) {
895 *cindex =
index + index_table_4b[nybble];
913 sample = lastsample + delta;
916 if (sample > max_audioval) {
917 sample = max_audioval;
918 }
else if (sample < min_audioval) {
919 sample = min_audioval;
932 for (
c = 0;
c <
state->channels;
c++) {
933 size_t o =
state->block.pos +
c * 4;
937 if (sample >= 0x8000) {
944 cstate[
c] = (
Sint8)(step > 0x80 ? step - 0x100 : step);
947 if (
state->block.data[o + 3] != 0) {
971 const size_t subblockframesize = channels * 4;
975 size_t blockpos =
state->block.pos;
976 size_t blocksize =
state->block.size;
977 size_t blockleft = blocksize - blockpos;
979 size_t outpos =
state->output.pos;
981 Sint64 blockframesleft =
state->samplesperblock - 1;
982 if (blockframesleft >
state->framesleft) {
983 blockframesleft =
state->framesleft;
986 bytesrequired = (blockframesleft + 7) / 8 * subblockframesize;
987 if (blockleft < bytesrequired) {
989 const size_t guaranteedframes = blockleft / subblockframesize;
990 const size_t remainingbytes = blockleft % subblockframesize;
991 blockframesleft = guaranteedframes;
992 if (remainingbytes > subblockframesize - 4) {
993 blockframesleft += (remainingbytes % 4) * 2;
1004 while (blockframesleft > 0) {
1005 const size_t subblocksamples = blockframesleft < 8 ? (
size_t)blockframesleft : 8;
1007 for (
c = 0;
c < channels;
c++) {
1010 Sint16 sample =
state->output.data[outpos +
c - channels];
1012 for (
i = 0;
i < subblocksamples;
i++) {
1016 nybble =
state->block.data[blockpos++];
1020 state->output.data[outpos +
c +
i * channels] = sample;
1024 outpos += channels * subblocksamples;
1025 state->framesleft -= subblocksamples;
1026 blockframesleft -= subblocksamples;
1029 state->block.pos = blockpos;
1030 state->output.pos = outpos;
1039 size_t bytesleft, outputsize;
1069 state.input.pos = 0;
1079 state.output.pos = 0;
1087 if (cstate ==
NULL) {
1091 state.cstate = cstate;
1094 bytesleft =
state.input.size -
state.input.pos;
1095 while (
state.framesleft > 0 && bytesleft >=
state.blockheadersize) {
1097 state.block.size = bytesleft <
state.blocksize ? bytesleft :
state.blocksize;
1098 state.block.pos = 0;
1104 return SDL_SetError(
"Unexpected overflow in IMA ADPCM decoder");
1128 bytesleft =
state.input.size -
state.input.pos;
1132 *audio_len = (
Uint32)outputsize;
1145 if (
format->bitspersample != 8) {
1146 return SDL_SetError(
"Invalid companded bits per sample of %u", (
unsigned int)
format->bitspersample);
1155 if (
format->blockalign > 1 && datalength %
format->blockalign) {
1156 return SDL_SetError(
"Truncated data chunk in WAVE file");
1171 #ifdef SDL_WAVE_LAW_LUT
1172 const Sint16 alaw_lut[256] = {
1173 -5504, -5248, -6016, -5760, -4480, -4224, -4992, -4736, -7552, -7296, -8064, -7808, -6528, -6272, -7040, -6784, -2752,
1174 -2624, -3008, -2880, -2240, -2112, -2496, -2368, -3776, -3648, -4032, -3904, -3264, -3136, -3520, -3392, -22016,
1175 -20992, -24064, -23040, -17920, -16896, -19968, -18944, -30208, -29184, -32256, -31232, -26112, -25088, -28160, -27136, -11008,
1176 -10496, -12032, -11520, -8960, -8448, -9984, -9472, -15104, -14592, -16128, -15616, -13056, -12544, -14080, -13568, -344,
1177 -328, -376, -360, -280, -264, -312, -296, -472, -456, -504, -488, -408, -392, -440, -424, -88,
1178 -72, -120, -104, -24, -8, -56, -40, -216, -200, -248, -232, -152, -136, -184, -168, -1376,
1179 -1312, -1504, -1440, -1120, -1056, -1248, -1184, -1888, -1824, -2016, -1952, -1632, -1568, -1760, -1696, -688,
1180 -656, -752, -720, -560, -528, -624, -592, -944, -912, -1008, -976, -816, -784, -880, -848, 5504,
1181 5248, 6016, 5760, 4480, 4224, 4992, 4736, 7552, 7296, 8064, 7808, 6528, 6272, 7040, 6784, 2752,
1182 2624, 3008, 2880, 2240, 2112, 2496, 2368, 3776, 3648, 4032, 3904, 3264, 3136, 3520, 3392, 22016,
1183 20992, 24064, 23040, 17920, 16896, 19968, 18944, 30208, 29184, 32256, 31232, 26112, 25088, 28160, 27136, 11008,
1184 10496, 12032, 11520, 8960, 8448, 9984, 9472, 15104, 14592, 16128, 15616, 13056, 12544, 14080, 13568, 344,
1185 328, 376, 360, 280, 264, 312, 296, 472, 456, 504, 488, 408, 392, 440, 424, 88,
1186 72, 120, 104, 24, 8, 56, 40, 216, 200, 248, 232, 152, 136, 184, 168, 1376,
1187 1312, 1504, 1440, 1120, 1056, 1248, 1184, 1888, 1824, 2016, 1952, 1632, 1568, 1760, 1696, 688,
1188 656, 752, 720, 560, 528, 624, 592, 944, 912, 1008, 976, 816, 784, 880, 848
1190 const Sint16 mulaw_lut[256] = {
1191 -32124, -31100, -30076, -29052, -28028, -27004, -25980, -24956, -23932, -22908, -21884, -20860, -19836, -18812, -17788, -16764, -15996,
1192 -15484, -14972, -14460, -13948, -13436, -12924, -12412, -11900, -11388, -10876, -10364, -9852, -9340, -8828, -8316, -7932,
1193 -7676, -7420, -7164, -6908, -6652, -6396, -6140, -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092, -3900,
1194 -3772, -3644, -3516, -3388, -3260, -3132, -3004, -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980, -1884,
1195 -1820, -1756, -1692, -1628, -1564, -1500, -1436, -1372, -1308, -1244, -1180, -1116, -1052, -988, -924, -876,
1196 -844, -812, -780, -748, -716, -684, -652, -620, -588, -556, -524, -492, -460, -428, -396, -372,
1197 -356, -340, -324, -308, -292, -276, -260, -244, -228, -212, -196, -180, -164, -148, -132, -120,
1198 -112, -104, -96, -88, -80, -72, -64, -56, -48, -40, -32, -24, -16, -8, 0, 32124,
1199 31100, 30076, 29052, 28028, 27004, 25980, 24956, 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764, 15996,
1200 15484, 14972, 14460, 13948, 13436, 12924, 12412, 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316, 7932,
1201 7676, 7420, 7164, 6908, 6652, 6396, 6140, 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092, 3900,
1202 3772, 3644, 3516, 3388, 3260, 3132, 3004, 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980, 1884,
1203 1820, 1756, 1692, 1628, 1564, 1500, 1436, 1372, 1308, 1244, 1180, 1116, 1052, 988, 924, 876,
1204 844, 812, 780, 748, 716, 684, 652, 620, 588, 556, 524, 492, 460, 428, 396, 372,
1205 356, 340, 324, 308, 292, 276, 260, 244, 228, 212, 196, 180, 164, 148, 132, 120,
1206 112, 104, 96, 88, 80, 72, 64, 56, 48, 40, 32, 24, 16, 8, 0
1212 size_t i, sample_count, expanded_len;
1235 expanded_len = sample_count;
1257 #ifdef SDL_WAVE_LAW_LUT
1279 mantissa = (mantissa << 4) | 0x8;
1284 dst[
i] =
nibble & 0x80 ? mantissa : -mantissa;
1294 mantissa = (0x80 <<
exponent) + step * mantissa + step / 2 - 132;
1296 dst[
i] =
nibble & 0x80 ? -mantissa : mantissa;
1306 *audio_len = (
Uint32)expanded_len;
1317 switch (
format->bitspersample) {
1325 return SDL_SetError(
"%u-bit PCM format not supported", (
unsigned int)
format->bitspersample);
1328 if (
format->bitspersample != 32) {
1329 return SDL_SetError(
"%u-bit IEEE floating-point format not supported", (
unsigned int)
format->bitspersample);
1342 if (
format->blockalign > 1 && datalength %
format->blockalign) {
1343 return SDL_SetError(
"Truncated data chunk in WAVE file");
1360 size_t i, expanded_len, sample_count;
1368 expanded_len = sample_count;
1386 *audio_len = (
Uint32)expanded_len;
1389 for (
i = sample_count;
i > 0;
i--) {
1390 const size_t o =
i - 1;
1395 b[2] =
ptr[o * 3 + 1];
1396 b[3] =
ptr[o * 3 + 2];
1398 ptr[o * 4 + 0] =
b[0];
1399 ptr[o * 4 + 1] =
b[1];
1400 ptr[o * 4 + 2] =
b[2];
1401 ptr[o * 4 + 3] =
b[3];
1440 *audio_buf = chunk->
data;
1441 *audio_len = (
Uint32)outputsize;
1458 }
else if (
SDL_strcmp(hint,
"ignore") == 0) {
1460 }
else if (
SDL_strcmp(hint,
"ignorezero") == 0) {
1462 }
else if (
SDL_strcmp(hint,
"maximum") == 0) {
1478 }
else if (
SDL_strcmp(hint,
"strict") == 0) {
1480 }
else if (
SDL_strcmp(hint,
"dropframe") == 0) {
1482 }
else if (
SDL_strcmp(hint,
"dropblock") == 0) {
1498 }
else if (
SDL_strcmp(hint,
"strict") == 0) {
1500 }
else if (
SDL_strcmp(hint,
"ignorezero") == 0) {
1502 }
else if (
SDL_strcmp(hint,
"ignore") == 0) {
1548 chunk->
position = nextposition + 8;
1594 #define WAVE_FORMATTAG_GUID(tag) {(tag) & 0xff, (tag) >> 8, 0, 0, 0, 0, 16, 0, 128, 0, 0, 170, 0, 56, 155, 113}
1622 size_t fmtlen = chunk->
size;
1629 if (fmtsrc ==
NULL) {
1645 return SDL_SetError(
"Missing wBitsPerSample field in WAVE fmt chunk");
1661 if (fmtlen < 40 || format->extsize < 22) {
1663 return SDL_SetError(
"Extensible WAVE header too small");
1685 if (
format->channels == 0) {
1687 }
else if (
format->channels > 255) {
1689 return SDL_SetError(
"Number of channels exceeds limit of 255");
1692 if (
format->frequency == 0) {
1701 return SDL_SetError(
"Invalid fact chunk in WAVE file");
1708 switch (
format->encoding) {
1716 return SDL_SetError(
"Missing fact chunk in WAVE file");
1722 return SDL_SetError(
"Missing wBitsPerSample field in WAVE fmt chunk");
1723 }
else if (
format->bitspersample == 0) {
1728 if (
format->blockalign == 0) {
1745 switch (
format->encoding) {
1748 if (
PCM_Init(file, datalength) < 0) {
1754 if (
LAW_Init(file, datalength) < 0) {
1773 const char *errstr =
"Unknown WAVE format GUID: %08x-%04x-%04x-%02x%02x%02x%02x%02x%02x%02x%02x";
1778 return SDL_SetError(errstr, g1, g2, g3,
g[8],
g[9],
g[10],
g[11],
g[12],
g[13],
g[14],
g[15]);
1780 return SDL_SetError(
"Unknown WAVE format tag: 0x%04x", (
unsigned int)
format->encoding);
1791 Uint32 chunkcountlimit = 10000;
1792 char *envchunkcountlimit;
1793 Sint64 RIFFstart, RIFFend, lastchunkpos;
1805 envchunkcountlimit =
SDL_getenv(
"SDL_WAVE_CHUNK_LIMIT");
1806 if (envchunkcountlimit !=
NULL) {
1814 if (RIFFstart < 0) {
1830 return SDL_SetError(
"RIFF form type is not WAVE (not a Waveform file)");
1837 return SDL_SetError(
"Could not find RIFF or WAVE identifiers (not a Waveform file)");
1853 if (RIFFchunk.
length == 0) {
1873 if (chunkcount++ >= chunkcountlimit) {
1874 return SDL_SetError(
"Chunk count in WAVE file exceeds limit of %u", chunkcountlimit);
1885 }
else if (
result == -2) {
1886 return SDL_SetError(
"Could not seek to WAVE chunk header");
1895 return SDL_SetError(
"fmt chunk after data chunk in WAVE file");
1952 return SDL_SetError(
"Missing data chunk in WAVE file");
1961 return SDL_SetError(
"Could not seek to WAVE chunk data");
1975 return SDL_SetError(
"Could not read data of WAVE fmt chunk");
1981 if (chunk->
length < 14) {
1982 return SDL_SetError(
"Invalid WAVE fmt chunk length (too small)");
1983 }
else if (chunk->
size < 14) {
1984 return SDL_SetError(
"Could not read data of WAVE fmt chunk");
1991 #ifdef SDL_WAVE_DEBUG_LOG_FORMAT
1992 WaveDebugLogFormat(file);
1994 #ifdef SDL_WAVE_DEBUG_DUMP_FORMAT
2007 }
else if (
result == -2) {
2008 return SDL_SetError(
"Could not seek data of WAVE data chunk");
2015 return SDL_SetError(
"Could not read data of WAVE data chunk");
2021 switch (
format->encoding) {
2024 if (
PCM_Decode(file, audio_buf, audio_len) < 0) {
2030 if (
LAW_Decode(file, audio_buf, audio_len) < 0) {
2054 switch (
format->encoding) {
2066 switch (
format->bitspersample) {
2079 return SDL_SetError(
"Unexpected %u-bit PCM data format", (
unsigned int)
format->bitspersample);
2087 if (RIFFlengthknown) {
2111 }
else if (audio_buf ==
NULL) {
2114 }
else if (audio_len ==
NULL) {
Uint8 SDL_SilenceValueForFormat(const SDL_AudioFormat format)
#define SDL_RWFromConstMem
#define SDL_OutOfMemory()
#define SDL_InvalidParamError(param)
#define SDL_HINT_WAVE_TRUNCATION
Controls how a truncated WAVE file is handled.
#define SDL_HINT_WAVE_FACT_CHUNK
Controls how the fact chunk affects the loading of a WAVE file.
#define SDL_HINT_WAVE_RIFF_CHUNK_SIZE
Controls how the size of the RIFF chunk affects the loading of a WAVE file.
static unsigned char nibble(char c)
GLuint GLuint GLsizei count
GLint GLint GLsizei GLsizei GLsizei GLint GLenum format
GLboolean GLboolean GLboolean b
GLuint GLfloat GLfloat GLfloat x1
GLenum GLuint GLsizei bufsize
GLuint GLsizei GLsizei * length
#define SDL_MAX_UINT32
An unsigned 32-bit integer type.
#define SDL_MAX_SINT64
A signed 64-bit integer type.
#define SDL_arraysize(array)
#define SDL_MAX_SINT32
A signed 32-bit integer type.
static int IMA_ADPCM_Init(WaveFile *file, size_t datalength)
static int IMA_ADPCM_DecodeBlockHeader(ADPCM_DecoderState *state)
static Sint64 WaveAdjustToFactValue(WaveFile *file, Sint64 sampleframes)
static int WaveLoad(SDL_RWops *src, WaveFile *file, SDL_AudioSpec *spec, Uint8 **audio_buf, Uint32 *audio_len)
static int MS_ADPCM_DecodeBlockHeader(ADPCM_DecoderState *state)
static WaveTruncationHint WaveGetTruncationHint()
#define WAVE_FORMATTAG_GUID(tag)
static int MS_ADPCM_Decode(WaveFile *file, Uint8 **audio_buf, Uint32 *audio_len)
static int LAW_Decode(WaveFile *file, Uint8 **audio_buf, Uint32 *audio_len)
static WaveExtensibleGUID extensible_guids[]
static int IMA_ADPCM_DecodeBlockData(ADPCM_DecoderState *state)
static int WaveReadChunkData(SDL_RWops *src, WaveChunk *chunk)
static Sint16 IMA_ADPCM_ProcessNibble(Sint8 *cindex, Sint16 lastsample, Uint8 nybble)
static WaveRiffSizeHint WaveGetRiffSizeHint()
static int WaveReadFormat(WaveFile *file)
static int WaveCheckFormat(WaveFile *file, size_t datalength)
static int MS_ADPCM_DecodeBlockData(ADPCM_DecoderState *state)
SDL_AudioSpec * SDL_LoadWAV_RW(SDL_RWops *src, int freesrc, SDL_AudioSpec *spec, Uint8 **audio_buf, Uint32 *audio_len)
Load the audio data of a WAVE file into memory.
static int PCM_Init(WaveFile *file, size_t datalength)
static int SafeMult(size_t *f1, size_t f2)
static void WaveFreeChunkData(WaveChunk *chunk)
static int IMA_ADPCM_CalculateSampleFrames(WaveFile *file, size_t datalength)
static WaveFactChunkHint WaveGetFactChunkHint()
static Sint16 MS_ADPCM_ProcessNibble(MS_ADPCM_ChannelState *cstate, Sint32 sample1, Sint32 sample2, Uint8 nybble)
static int WaveReadPartialChunkData(SDL_RWops *src, WaveChunk *chunk, size_t length)
static int PCM_ConvertSint24ToSint32(WaveFile *file, Uint8 **audio_buf, Uint32 *audio_len)
static int PCM_Decode(WaveFile *file, Uint8 **audio_buf, Uint32 *audio_len)
static int MS_ADPCM_CalculateSampleFrames(WaveFile *file, size_t datalength)
static Uint16 WaveGetFormatGUIDEncoding(WaveFormat *format)
static int WaveNextChunk(SDL_RWops *src, WaveChunk *chunk)
static int MS_ADPCM_Init(WaveFile *file, size_t datalength)
static int IMA_ADPCM_Decode(WaveFile *file, Uint8 **audio_buf, Uint32 *audio_len)
void SDL_FreeWAV(Uint8 *audio_buf)
static int LAW_Init(WaveFile *file, size_t datalength)
return Display return Display Bool Bool int int int return Display XEvent Bool(*) XPointer return Display return Display Drawable _Xconst char unsigned int unsigned int return Display Pixmap Pixmap XColor XColor unsigned int unsigned int return Display _Xconst char char int char return Display Visual unsigned int int int char unsigned int unsigned int in i)
set set set set set set set macro pixldst1 abits if abits op else op endif endm macro pixldst2 abits if abits op else op endif endm macro pixldst4 abits if abits op else op endif endm macro pixldst0 abits op endm macro pixldst3 mem_operand op endm macro pixldst30 mem_operand op endm macro pixldst abits if abits elseif abits elseif abits elseif abits elseif abits pixldst0 abits else pixldst0 abits pixldst0 abits pixldst0 abits pixldst0 abits endif elseif abits else pixldst0 abits pixldst0 abits endif elseif abits else error unsupported bpp *numpix else pixst endif endm macro pixld1_s mem_operand if asr adds SRC_WIDTH_FIXED bpl add asl mov asr adds SRC_WIDTH_FIXED bpl add asl mov asr adds SRC_WIDTH_FIXED bpl add asl mov asr adds SRC_WIDTH_FIXED bpl add asl elseif asr adds SRC_WIDTH_FIXED bpl add asl mov asr adds SRC_WIDTH_FIXED bpl add asl else error unsupported endif endm macro pixld2_s mem_operand if mov asr add asl add asl mov asr sub UNIT_X add asl mov asr add asl add asl mov asr add UNIT_X add asl else pixld1_s mem_operand pixld1_s mem_operand endif endm macro pixld0_s mem_operand if asr adds SRC_WIDTH_FIXED bpl add asl elseif asr adds SRC_WIDTH_FIXED bpl add asl endif endm macro pixld_s_internal mem_operand if mem_operand pixld2_s mem_operand pixdeinterleave basereg elseif mem_operand elseif mem_operand elseif mem_operand elseif mem_operand pixld0_s mem_operand else pixld0_s mem_operand pixld0_s mem_operand pixld0_s mem_operand pixld0_s mem_operand endif elseif mem_operand else pixld0_s mem_operand pixld0_s mem_operand endif elseif mem_operand else error unsupported mem_operand if bpp mem_operand endif endm macro vuzp8 reg2 vuzp d d ®2 endm macro vzip8 reg2 vzip d d ®2 endm macro pixdeinterleave basereg basereg basereg basereg basereg endif endm macro pixinterleave basereg basereg basereg basereg basereg endif endm macro PF boost_increment endif if endif PF tst PF addne PF subne PF cmp ORIG_W if endif if endif if endif PF subge ORIG_W PF subges if endif if endif if endif endif endm macro cache_preload_simple endif if dst_r_bpp pld[DST_R, #(PREFETCH_DISTANCE_SIMPLE *dst_r_bpp/8)] endif if mask_bpp pld if[MASK, #(PREFETCH_DISTANCE_SIMPLE *mask_bpp/8)] endif endif endm macro fetch_mask_pixblock pixld mask_basereg pixblock_size MASK endm macro ensure_destination_ptr_alignment process_pixblock_tail_head if beq irp skip1(dst_w_bpp<=(lowbit *8)) &&((lowbit *8)<(pixblock_size *dst_w_bpp)) .if lowbit< 16 tst DST_R
set set set set set set set set set set set set set set set set set set set set *set set set macro pixldst op &r &cond WK op &r &cond WK op &r &cond WK else op &m &cond &ia op &r &cond WK else op &m &cond &ia elseif elseif else error unsupported base if elseif elseif else error unsupported unaligned pixldst unaligned endm macro pixst base base else pixldst base endif endm macro PF ptr
struct ADPCM_DecoderState::@15 output
struct ADPCM_DecoderState::@14 block
struct ADPCM_DecoderState::@13 input
WaveFactChunkHint facthint
WaveRiffSizeHint riffhint
WaveTruncationHint trunchint