Don't inline the decompose function
[openal-soft/openal-hmr.git] / OpenAL32 / alBuffer.c
blob4f102439f360d2baa68fec68b23bb76a08d1b427
1 /**
2 * OpenAL cross platform audio library
3 * Copyright (C) 1999-2007 by authors.
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
18 * Or go to http://www.gnu.org/copyleft/lgpl.html
21 #include "config.h"
23 #include <stdlib.h>
24 #include <stdio.h>
25 #include <assert.h>
26 #include <limits.h>
28 #include "alMain.h"
29 #include "AL/al.h"
30 #include "AL/alc.h"
31 #include "alError.h"
32 #include "alBuffer.h"
33 #include "alDatabuffer.h"
34 #include "alThunk.h"
37 static ALenum LoadData(ALbuffer *ALBuf, const ALvoid *data, ALsizei size, ALuint freq, ALenum OrigFormat, ALenum NewFormat);
38 static void ConvertData(ALvoid *dst, const ALvoid *src, enum SrcFmtType srcType, ALsizei len);
39 static void ConvertDataRear(ALvoid *dst, const ALvoid *src, ALint origBytes, ALsizei len);
40 static void ConvertDataIMA4(ALvoid *dst, const ALvoid *src, ALint origChans, ALsizei len);
41 static void ConvertDataMULaw(ALvoid *dst, const ALvoid *src, ALsizei len);
42 static void ConvertDataMULawRear(ALvoid *dst, const ALvoid *src, ALsizei len);
44 #define LookupBuffer(m, k) ((ALbuffer*)LookupUIntMapKey(&(m), (k)))
48 * Global Variables
51 static const long g_IMAStep_size[89]={ // IMA ADPCM Stepsize table
52 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, 19, 21, 23, 25, 28, 31,
53 34, 37, 41, 45, 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130, 143,
54 157, 173, 190, 209, 230, 253, 279, 307, 337, 371, 408, 449, 494, 544, 598, 658,
55 724, 796, 876, 963, 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024,
56 3327, 3660, 4026, 4428, 4871, 5358, 5894, 6484, 7132, 7845, 8630, 9493,10442,11487,12635,13899,
57 15289,16818,18500,20350,22358,24633,27086,29794,32767
60 static const long g_IMACodeword_4[16]={ // IMA4 ADPCM Codeword decode table
61 1, 3, 5, 7, 9, 11, 13, 15,
62 -1,-3,-5,-7,-9,-11,-13,-15,
65 static const long g_IMAIndex_adjust_4[16]={ // IMA4 ADPCM Step index adjust decode table
66 -1,-1,-1,-1, 2, 4, 6, 8,
67 -1,-1,-1,-1, 2, 4, 6, 8
70 static const ALshort muLawDecompressionTable[256] = {
71 -32124,-31100,-30076,-29052,-28028,-27004,-25980,-24956,
72 -23932,-22908,-21884,-20860,-19836,-18812,-17788,-16764,
73 -15996,-15484,-14972,-14460,-13948,-13436,-12924,-12412,
74 -11900,-11388,-10876,-10364, -9852, -9340, -8828, -8316,
75 -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140,
76 -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092,
77 -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004,
78 -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980,
79 -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436,
80 -1372, -1308, -1244, -1180, -1116, -1052, -988, -924,
81 -876, -844, -812, -780, -748, -716, -684, -652,
82 -620, -588, -556, -524, -492, -460, -428, -396,
83 -372, -356, -340, -324, -308, -292, -276, -260,
84 -244, -228, -212, -196, -180, -164, -148, -132,
85 -120, -112, -104, -96, -88, -80, -72, -64,
86 -56, -48, -40, -32, -24, -16, -8, 0,
87 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956,
88 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764,
89 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412,
90 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316,
91 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140,
92 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092,
93 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004,
94 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980,
95 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436,
96 1372, 1308, 1244, 1180, 1116, 1052, 988, 924,
97 876, 844, 812, 780, 748, 716, 684, 652,
98 620, 588, 556, 524, 492, 460, 428, 396,
99 372, 356, 340, 324, 308, 292, 276, 260,
100 244, 228, 212, 196, 180, 164, 148, 132,
101 120, 112, 104, 96, 88, 80, 72, 64,
102 56, 48, 40, 32, 24, 16, 8, 0
106 * alGenBuffers(ALsizei n, ALuint *buffers)
108 * Generates n AL Buffers, and stores the Buffers Names in the array pointed to by buffers
110 AL_API ALvoid AL_APIENTRY alGenBuffers(ALsizei n, ALuint *buffers)
112 ALCcontext *Context;
113 ALsizei i=0;
115 Context = GetContextSuspended();
116 if(!Context) return;
118 // Check that we are actually generating some Buffers
119 if(n < 0 || IsBadWritePtr((void*)buffers, n * sizeof(ALuint)))
120 alSetError(Context, AL_INVALID_VALUE);
121 else
123 ALCdevice *device = Context->Device;
124 ALenum err;
126 // Create all the new Buffers
127 while(i < n)
129 ALbuffer *buffer = calloc(1, sizeof(ALbuffer));
130 if(!buffer)
132 alSetError(Context, AL_OUT_OF_MEMORY);
133 alDeleteBuffers(i, buffers);
134 break;
137 buffer->buffer = (ALuint)ALTHUNK_ADDENTRY(buffer);
138 err = InsertUIntMapEntry(&device->BufferMap, buffer->buffer, buffer);
139 if(err != AL_NO_ERROR)
141 ALTHUNK_REMOVEENTRY(buffer->buffer);
142 memset(buffer, 0, sizeof(ALbuffer));
143 free(buffer);
145 alSetError(Context, err);
146 alDeleteBuffers(i, buffers);
147 break;
149 buffers[i++] = buffer->buffer;
153 ProcessContext(Context);
157 * alDeleteBuffers(ALsizei n, ALuint *buffers)
159 * Deletes the n AL Buffers pointed to by buffers
161 AL_API ALvoid AL_APIENTRY alDeleteBuffers(ALsizei n, const ALuint *buffers)
163 ALCcontext *Context;
164 ALCdevice *device;
165 ALboolean Failed;
166 ALbuffer *ALBuf;
167 ALsizei i;
169 Context = GetContextSuspended();
170 if(!Context) return;
172 Failed = AL_TRUE;
173 device = Context->Device;
174 /* Check we are actually Deleting some Buffers */
175 if(n < 0)
176 alSetError(Context, AL_INVALID_VALUE);
177 else
179 Failed = AL_FALSE;
181 /* Check that all the buffers are valid and can actually be deleted */
182 for(i = 0;i < n;i++)
184 if(!buffers[i])
185 continue;
187 /* Check for valid Buffer ID */
188 if((ALBuf=LookupBuffer(device->BufferMap, buffers[i])) == NULL)
190 alSetError(Context, AL_INVALID_NAME);
191 Failed = AL_TRUE;
192 break;
194 else if(ALBuf->refcount != 0)
196 /* Buffer still in use, cannot be deleted */
197 alSetError(Context, AL_INVALID_OPERATION);
198 Failed = AL_TRUE;
199 break;
204 /* If all the Buffers were valid (and have Reference Counts of 0), then we can delete them */
205 if(!Failed)
207 for(i = 0;i < n;i++)
209 if((ALBuf=LookupBuffer(device->BufferMap, buffers[i])) == NULL)
210 continue;
212 /* Release the memory used to store audio data */
213 free(ALBuf->data);
215 /* Release buffer structure */
216 RemoveUIntMapKey(&device->BufferMap, ALBuf->buffer);
217 ALTHUNK_REMOVEENTRY(ALBuf->buffer);
219 memset(ALBuf, 0, sizeof(ALbuffer));
220 free(ALBuf);
224 ProcessContext(Context);
228 * alIsBuffer(ALuint buffer)
230 * Checks if buffer is a valid Buffer Name
232 AL_API ALboolean AL_APIENTRY alIsBuffer(ALuint buffer)
234 ALCcontext *Context;
235 ALboolean result;
237 Context = GetContextSuspended();
238 if(!Context) return AL_FALSE;
240 result = ((!buffer || LookupBuffer(Context->Device->BufferMap, buffer)) ?
241 AL_TRUE : AL_FALSE);
243 ProcessContext(Context);
245 return result;
249 * alBufferData(ALuint buffer,ALenum format,const ALvoid *data,ALsizei size,ALsizei freq)
251 * Fill buffer with audio data
253 AL_API ALvoid AL_APIENTRY alBufferData(ALuint buffer,ALenum format,const ALvoid *data,ALsizei size,ALsizei freq)
255 ALCcontext *Context;
256 ALCdevice *device;
257 ALbuffer *ALBuf;
258 ALvoid *temp;
259 ALenum err;
261 Context = GetContextSuspended();
262 if(!Context) return;
264 if(Context->SampleSource)
266 ALintptrEXT offset;
268 if(Context->SampleSource->state == MAPPED)
270 alSetError(Context, AL_INVALID_OPERATION);
271 ProcessContext(Context);
272 return;
275 offset = (const ALubyte*)data - (ALubyte*)NULL;
276 data = Context->SampleSource->data + offset;
279 device = Context->Device;
280 if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
281 alSetError(Context, AL_INVALID_NAME);
282 else if(size < 0 || freq < 0)
283 alSetError(Context, AL_INVALID_VALUE);
284 else if(ALBuf->refcount != 0)
285 alSetError(Context, AL_INVALID_VALUE);
286 else switch(format)
288 case AL_FORMAT_MONO8:
289 case AL_FORMAT_MONO16:
290 case AL_FORMAT_MONO_FLOAT32:
291 case AL_FORMAT_MONO_DOUBLE_EXT:
292 case AL_FORMAT_STEREO8:
293 case AL_FORMAT_STEREO16:
294 case AL_FORMAT_STEREO_FLOAT32:
295 case AL_FORMAT_STEREO_DOUBLE_EXT:
296 case AL_FORMAT_QUAD8_LOKI:
297 case AL_FORMAT_QUAD16_LOKI:
298 case AL_FORMAT_QUAD8:
299 case AL_FORMAT_QUAD16:
300 case AL_FORMAT_QUAD32:
301 case AL_FORMAT_51CHN8:
302 case AL_FORMAT_51CHN16:
303 case AL_FORMAT_51CHN32:
304 case AL_FORMAT_61CHN8:
305 case AL_FORMAT_61CHN16:
306 case AL_FORMAT_61CHN32:
307 case AL_FORMAT_71CHN8:
308 case AL_FORMAT_71CHN16:
309 case AL_FORMAT_71CHN32:
310 err = LoadData(ALBuf, data, size, freq, format, format);
311 if(err != AL_NO_ERROR)
312 alSetError(Context, err);
313 break;
315 case AL_FORMAT_REAR8:
316 case AL_FORMAT_REAR16:
317 case AL_FORMAT_REAR32: {
318 ALuint OrigBytes = ((format==AL_FORMAT_REAR8) ? 1 :
319 ((format==AL_FORMAT_REAR16) ? 2 : 4));
320 ALenum NewFormat = ((OrigBytes==4) ? AL_FORMAT_QUAD32 :
321 ((OrigBytes==2) ? AL_FORMAT_QUAD16 :
322 AL_FORMAT_QUAD8));
323 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
324 ALuint NewBytes = aluBytesFromFormat(NewFormat);
325 ALuint64 newsize;
327 if((size%(OrigBytes*2)) != 0)
329 alSetError(Context, AL_INVALID_VALUE);
330 break;
333 newsize = size / OrigBytes;
334 newsize *= 2;
335 newsize *= NewBytes;
337 if(newsize > INT_MAX)
339 alSetError(Context, AL_OUT_OF_MEMORY);
340 break;
342 temp = realloc(ALBuf->data, newsize);
343 if(temp)
345 ALBuf->data = temp;
346 ConvertDataRear(ALBuf->data, data, OrigBytes, newsize/NewBytes);
348 ALBuf->format = NewFormat;
349 ALBuf->eOriginalFormat = format;
350 ALBuf->size = newsize;
351 ALBuf->frequency = freq;
353 ALBuf->LoopStart = 0;
354 ALBuf->LoopEnd = newsize / NewChannels / NewBytes;
356 DecomposeFormat(NewFormat, &ALBuf->FmtType, &ALBuf->FmtChannels);
358 ALBuf->OriginalSize = size;
359 ALBuf->OriginalAlign = OrigBytes * 2;
361 else
362 alSetError(Context, AL_OUT_OF_MEMORY);
363 } break;
365 case AL_FORMAT_MONO_IMA4:
366 case AL_FORMAT_STEREO_IMA4: {
367 ALuint Channels = ((format==AL_FORMAT_MONO_IMA4) ? 1 : 2);
368 ALenum NewFormat = ((Channels==1) ? AL_FORMAT_MONO16 :
369 AL_FORMAT_STEREO16);
370 ALuint NewBytes = aluBytesFromFormat(NewFormat);
371 ALuint64 newsize;
373 /* Here is where things vary:
374 * nVidia and Apple use 64+1 sample frames per block => block_size=36*chans bytes
375 * Most PC sound software uses 2040+1 sample frames per block -> block_size=1024*chans bytes
377 if((size%(36*Channels)) != 0)
379 alSetError(Context, AL_INVALID_VALUE);
380 break;
383 newsize = size / 36;
384 newsize *= 65;
385 newsize *= NewBytes;
387 if(newsize > INT_MAX)
389 alSetError(Context, AL_OUT_OF_MEMORY);
390 break;
392 temp = realloc(ALBuf->data, newsize);
393 if(temp)
395 ALBuf->data = temp;
396 ConvertDataIMA4(ALBuf->data, data, Channels, newsize/(65*Channels*NewBytes));
398 ALBuf->format = NewFormat;
399 ALBuf->eOriginalFormat = format;
400 ALBuf->size = newsize;
401 ALBuf->frequency = freq;
403 ALBuf->LoopStart = 0;
404 ALBuf->LoopEnd = newsize / Channels / NewBytes;
406 DecomposeFormat(NewFormat, &ALBuf->FmtType, &ALBuf->FmtChannels);
408 ALBuf->OriginalSize = size;
409 ALBuf->OriginalAlign = 36 * Channels;
411 else
412 alSetError(Context, AL_OUT_OF_MEMORY);
413 } break;
415 case AL_FORMAT_MONO_MULAW:
416 case AL_FORMAT_STEREO_MULAW:
417 case AL_FORMAT_QUAD_MULAW:
418 case AL_FORMAT_51CHN_MULAW:
419 case AL_FORMAT_61CHN_MULAW:
420 case AL_FORMAT_71CHN_MULAW: {
421 ALuint Channels = ((format==AL_FORMAT_MONO_MULAW) ? 1 :
422 ((format==AL_FORMAT_STEREO_MULAW) ? 2 :
423 ((format==AL_FORMAT_QUAD_MULAW) ? 4 :
424 ((format==AL_FORMAT_51CHN_MULAW) ? 6 :
425 ((format==AL_FORMAT_61CHN_MULAW) ? 7 : 8)))));
426 ALenum NewFormat = ((Channels==1) ? AL_FORMAT_MONO16 :
427 ((Channels==2) ? AL_FORMAT_STEREO16 :
428 ((Channels==4) ? AL_FORMAT_QUAD16 :
429 ((Channels==6) ? AL_FORMAT_51CHN16 :
430 ((Channels==7) ? AL_FORMAT_61CHN16 :
431 AL_FORMAT_71CHN16)))));
432 ALuint NewBytes = aluBytesFromFormat(NewFormat);
433 ALuint64 newsize;
435 if((size%(1*Channels)) != 0)
437 alSetError(Context, AL_INVALID_VALUE);
438 break;
441 newsize = size * NewBytes;
442 if(newsize > INT_MAX)
444 alSetError(Context, AL_OUT_OF_MEMORY);
445 break;
447 temp = realloc(ALBuf->data, newsize);
448 if(temp)
450 ALBuf->data = temp;
451 ConvertDataMULaw(ALBuf->data, data, newsize/NewBytes);
453 ALBuf->format = NewFormat;
454 ALBuf->eOriginalFormat = format;
455 ALBuf->size = newsize;
456 ALBuf->frequency = freq;
458 ALBuf->LoopStart = 0;
459 ALBuf->LoopEnd = newsize / Channels / NewBytes;
461 DecomposeFormat(NewFormat, &ALBuf->FmtType, &ALBuf->FmtChannels);
463 ALBuf->OriginalSize = size;
464 ALBuf->OriginalAlign = 1 * Channels;
466 else
467 alSetError(Context, AL_OUT_OF_MEMORY);
468 } break;
470 case AL_FORMAT_REAR_MULAW: {
471 ALenum NewFormat = AL_FORMAT_QUAD16;
472 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
473 ALuint NewBytes = aluBytesFromFormat(NewFormat);
474 ALuint64 newsize;
476 if((size%(1*2)) != 0)
478 alSetError(Context, AL_INVALID_VALUE);
479 break;
482 newsize = size * 2;
483 newsize *= NewBytes;
485 if(newsize > INT_MAX)
487 alSetError(Context, AL_OUT_OF_MEMORY);
488 break;
490 temp = realloc(ALBuf->data, newsize);
491 if(temp)
493 ALBuf->data = temp;
494 ConvertDataMULawRear(ALBuf->data, data, newsize/NewBytes);
496 ALBuf->format = NewFormat;
497 ALBuf->eOriginalFormat = format;
498 ALBuf->size = newsize;
499 ALBuf->frequency = freq;
501 ALBuf->LoopStart = 0;
502 ALBuf->LoopEnd = newsize / NewChannels / NewBytes;
504 DecomposeFormat(NewFormat, &ALBuf->FmtType, &ALBuf->FmtChannels);
506 ALBuf->OriginalSize = size;
507 ALBuf->OriginalAlign = 1 * 2;
509 else
510 alSetError(Context, AL_OUT_OF_MEMORY);
511 } break;
513 default:
514 alSetError(Context, AL_INVALID_ENUM);
515 break;
518 ProcessContext(Context);
522 * alBufferSubDataSOFT(ALuint buffer,ALenum format,const ALvoid *data,ALsizei offset,ALsizei length)
524 * Update buffer's audio data
526 AL_API ALvoid AL_APIENTRY alBufferSubDataSOFT(ALuint buffer,ALenum format,const ALvoid *data,ALsizei offset,ALsizei length)
528 ALCcontext *Context;
529 ALCdevice *device;
530 ALbuffer *ALBuf;
532 Context = GetContextSuspended();
533 if(!Context) return;
535 if(Context->SampleSource)
537 ALintptrEXT offset;
539 if(Context->SampleSource->state == MAPPED)
541 alSetError(Context, AL_INVALID_OPERATION);
542 ProcessContext(Context);
543 return;
546 offset = (const ALubyte*)data - (ALubyte*)NULL;
547 data = Context->SampleSource->data + offset;
550 device = Context->Device;
551 if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
552 alSetError(Context, AL_INVALID_NAME);
553 else if(length < 0 || offset < 0 || (length > 0 && data == NULL))
554 alSetError(Context, AL_INVALID_VALUE);
555 else if(ALBuf->eOriginalFormat != format)
556 alSetError(Context, AL_INVALID_ENUM);
557 else if(offset > ALBuf->OriginalSize ||
558 length > ALBuf->OriginalSize-offset ||
559 (offset%ALBuf->OriginalAlign) != 0 ||
560 (length%ALBuf->OriginalAlign) != 0)
561 alSetError(Context, AL_INVALID_VALUE);
562 else switch(format)
564 case AL_FORMAT_MONO8:
565 case AL_FORMAT_MONO16:
566 case AL_FORMAT_MONO_FLOAT32:
567 case AL_FORMAT_MONO_DOUBLE_EXT:
568 case AL_FORMAT_STEREO8:
569 case AL_FORMAT_STEREO16:
570 case AL_FORMAT_STEREO_FLOAT32:
571 case AL_FORMAT_STEREO_DOUBLE_EXT:
572 case AL_FORMAT_QUAD8_LOKI:
573 case AL_FORMAT_QUAD16_LOKI:
574 case AL_FORMAT_QUAD8:
575 case AL_FORMAT_QUAD16:
576 case AL_FORMAT_QUAD32:
577 case AL_FORMAT_51CHN8:
578 case AL_FORMAT_51CHN16:
579 case AL_FORMAT_51CHN32:
580 case AL_FORMAT_61CHN8:
581 case AL_FORMAT_61CHN16:
582 case AL_FORMAT_61CHN32:
583 case AL_FORMAT_71CHN8:
584 case AL_FORMAT_71CHN16:
585 case AL_FORMAT_71CHN32: {
586 ALuint OldBytes = aluBytesFromFormat(format);
587 ALuint Bytes = aluBytesFromFormat(ALBuf->format);
588 enum SrcFmtChannels SrcChannels;
589 enum SrcFmtType SrcType;
591 offset /= OldBytes;
592 offset *= Bytes;
593 length /= OldBytes;
595 DecomposeInputFormat(format, &SrcType, &SrcChannels);
596 ConvertData(&((ALubyte*)ALBuf->data)[offset], data, SrcType, length);
597 } break;
599 case AL_FORMAT_REAR8:
600 case AL_FORMAT_REAR16:
601 case AL_FORMAT_REAR32: {
602 ALuint OldBytes = ((format==AL_FORMAT_REAR8) ? 1 :
603 ((format==AL_FORMAT_REAR16) ? 2 : 4));
604 ALuint Bytes = aluBytesFromFormat(ALBuf->format);
606 offset /= OldBytes;
607 offset *= 2;
608 offset *= Bytes;
609 length /= OldBytes;
610 length *= 2;
612 ConvertDataRear(&((ALubyte*)ALBuf->data)[offset], data, Bytes, length);
613 } break;
615 case AL_FORMAT_MONO_IMA4:
616 case AL_FORMAT_STEREO_IMA4: {
617 ALuint Channels = aluChannelsFromFormat(ALBuf->format);
618 ALuint Bytes = aluBytesFromFormat(ALBuf->format);
620 /* offset -> byte offset, length -> block count */
621 offset /= 36;
622 offset *= 65;
623 offset *= Bytes;
624 length /= ALBuf->OriginalAlign;
626 ConvertDataIMA4(&((ALubyte*)ALBuf->data)[offset], data, Channels, length);
627 } break;
629 case AL_FORMAT_MONO_MULAW:
630 case AL_FORMAT_STEREO_MULAW:
631 case AL_FORMAT_QUAD_MULAW:
632 case AL_FORMAT_51CHN_MULAW:
633 case AL_FORMAT_61CHN_MULAW:
634 case AL_FORMAT_71CHN_MULAW: {
635 ALuint Bytes = aluBytesFromFormat(ALBuf->format);
637 offset *= Bytes;
639 ConvertDataMULaw(&((ALubyte*)ALBuf->data)[offset], data, length);
640 } break;
642 case AL_FORMAT_REAR_MULAW: {
643 ALuint Bytes = aluBytesFromFormat(ALBuf->format);
645 offset *= 2;
646 offset *= Bytes;
647 length *= 2;
649 ConvertDataMULawRear(&((ALubyte*)ALBuf->data)[offset], data, length);
650 } break;
652 default:
653 alSetError(Context, AL_INVALID_ENUM);
654 break;
657 ProcessContext(Context);
660 AL_API ALvoid AL_APIENTRY alBufferSubDataEXT(ALuint buffer,ALenum format,const ALvoid *data,ALsizei offset,ALsizei length)
662 alBufferSubDataSOFT(buffer, format, data, offset, length);
666 AL_API void AL_APIENTRY alBufferf(ALuint buffer, ALenum eParam, ALfloat flValue)
668 ALCcontext *pContext;
669 ALCdevice *device;
671 (void)flValue;
673 pContext = GetContextSuspended();
674 if(!pContext) return;
676 device = pContext->Device;
677 if(LookupBuffer(device->BufferMap, buffer) == NULL)
678 alSetError(pContext, AL_INVALID_NAME);
679 else
681 switch(eParam)
683 default:
684 alSetError(pContext, AL_INVALID_ENUM);
685 break;
689 ProcessContext(pContext);
693 AL_API void AL_APIENTRY alBuffer3f(ALuint buffer, ALenum eParam, ALfloat flValue1, ALfloat flValue2, ALfloat flValue3)
695 ALCcontext *pContext;
696 ALCdevice *device;
698 (void)flValue1;
699 (void)flValue2;
700 (void)flValue3;
702 pContext = GetContextSuspended();
703 if(!pContext) return;
705 device = pContext->Device;
706 if(LookupBuffer(device->BufferMap, buffer) == NULL)
707 alSetError(pContext, AL_INVALID_NAME);
708 else
710 switch(eParam)
712 default:
713 alSetError(pContext, AL_INVALID_ENUM);
714 break;
718 ProcessContext(pContext);
722 AL_API void AL_APIENTRY alBufferfv(ALuint buffer, ALenum eParam, const ALfloat* flValues)
724 ALCcontext *pContext;
725 ALCdevice *device;
727 pContext = GetContextSuspended();
728 if(!pContext) return;
730 device = pContext->Device;
731 if(!flValues)
732 alSetError(pContext, AL_INVALID_VALUE);
733 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
734 alSetError(pContext, AL_INVALID_NAME);
735 else
737 switch(eParam)
739 default:
740 alSetError(pContext, AL_INVALID_ENUM);
741 break;
745 ProcessContext(pContext);
749 AL_API void AL_APIENTRY alBufferi(ALuint buffer, ALenum eParam, ALint lValue)
751 ALCcontext *pContext;
752 ALCdevice *device;
754 (void)lValue;
756 pContext = GetContextSuspended();
757 if(!pContext) return;
759 device = pContext->Device;
760 if(LookupBuffer(device->BufferMap, buffer) == NULL)
761 alSetError(pContext, AL_INVALID_NAME);
762 else
764 switch(eParam)
766 default:
767 alSetError(pContext, AL_INVALID_ENUM);
768 break;
772 ProcessContext(pContext);
776 AL_API void AL_APIENTRY alBuffer3i( ALuint buffer, ALenum eParam, ALint lValue1, ALint lValue2, ALint lValue3)
778 ALCcontext *pContext;
779 ALCdevice *device;
781 (void)lValue1;
782 (void)lValue2;
783 (void)lValue3;
785 pContext = GetContextSuspended();
786 if(!pContext) return;
788 device = pContext->Device;
789 if(LookupBuffer(device->BufferMap, buffer) == NULL)
790 alSetError(pContext, AL_INVALID_NAME);
791 else
793 switch(eParam)
795 default:
796 alSetError(pContext, AL_INVALID_ENUM);
797 break;
801 ProcessContext(pContext);
805 AL_API void AL_APIENTRY alBufferiv(ALuint buffer, ALenum eParam, const ALint* plValues)
807 ALCcontext *pContext;
808 ALCdevice *device;
809 ALbuffer *ALBuf;
811 pContext = GetContextSuspended();
812 if(!pContext) return;
814 device = pContext->Device;
815 if(!plValues)
816 alSetError(pContext, AL_INVALID_VALUE);
817 else if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
818 alSetError(pContext, AL_INVALID_NAME);
819 else
821 switch(eParam)
823 case AL_LOOP_POINTS:
824 if(ALBuf->refcount > 0)
825 alSetError(pContext, AL_INVALID_OPERATION);
826 else if(plValues[0] < 0 || plValues[1] < 0 ||
827 plValues[0] >= plValues[1] || ALBuf->size == 0)
828 alSetError(pContext, AL_INVALID_VALUE);
829 else
831 ALint maxlen = ALBuf->size / aluFrameSizeFromFormat(ALBuf->format);
832 if(plValues[0] > maxlen || plValues[1] > maxlen)
833 alSetError(pContext, AL_INVALID_VALUE);
834 else
836 ALBuf->LoopStart = plValues[0];
837 ALBuf->LoopEnd = plValues[1];
840 break;
842 default:
843 alSetError(pContext, AL_INVALID_ENUM);
844 break;
848 ProcessContext(pContext);
852 AL_API ALvoid AL_APIENTRY alGetBufferf(ALuint buffer, ALenum eParam, ALfloat *pflValue)
854 ALCcontext *pContext;
855 ALCdevice *device;
857 pContext = GetContextSuspended();
858 if(!pContext) return;
860 device = pContext->Device;
861 if(!pflValue)
862 alSetError(pContext, AL_INVALID_VALUE);
863 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
864 alSetError(pContext, AL_INVALID_NAME);
865 else
867 switch(eParam)
869 default:
870 alSetError(pContext, AL_INVALID_ENUM);
871 break;
875 ProcessContext(pContext);
879 AL_API void AL_APIENTRY alGetBuffer3f(ALuint buffer, ALenum eParam, ALfloat* pflValue1, ALfloat* pflValue2, ALfloat* pflValue3)
881 ALCcontext *pContext;
882 ALCdevice *device;
884 pContext = GetContextSuspended();
885 if(!pContext) return;
887 device = pContext->Device;
888 if(!pflValue1 || !pflValue2 || !pflValue3)
889 alSetError(pContext, AL_INVALID_VALUE);
890 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
891 alSetError(pContext, AL_INVALID_NAME);
892 else
894 switch(eParam)
896 default:
897 alSetError(pContext, AL_INVALID_ENUM);
898 break;
902 ProcessContext(pContext);
906 AL_API void AL_APIENTRY alGetBufferfv(ALuint buffer, ALenum eParam, ALfloat* pflValues)
908 ALCcontext *pContext;
909 ALCdevice *device;
911 pContext = GetContextSuspended();
912 if(!pContext) return;
914 device = pContext->Device;
915 if(!pflValues)
916 alSetError(pContext, AL_INVALID_VALUE);
917 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
918 alSetError(pContext, AL_INVALID_NAME);
919 else
921 switch(eParam)
923 default:
924 alSetError(pContext, AL_INVALID_ENUM);
925 break;
929 ProcessContext(pContext);
933 AL_API ALvoid AL_APIENTRY alGetBufferi(ALuint buffer, ALenum eParam, ALint *plValue)
935 ALCcontext *pContext;
936 ALbuffer *pBuffer;
937 ALCdevice *device;
939 pContext = GetContextSuspended();
940 if(!pContext) return;
942 device = pContext->Device;
943 if(!plValue)
944 alSetError(pContext, AL_INVALID_VALUE);
945 else if((pBuffer=LookupBuffer(device->BufferMap, buffer)) == NULL)
946 alSetError(pContext, AL_INVALID_NAME);
947 else
949 switch(eParam)
951 case AL_FREQUENCY:
952 *plValue = pBuffer->frequency;
953 break;
955 case AL_BITS:
956 *plValue = aluBytesFromFormat(pBuffer->format) * 8;
957 break;
959 case AL_CHANNELS:
960 *plValue = aluChannelsFromFormat(pBuffer->format);
961 break;
963 case AL_SIZE:
964 *plValue = pBuffer->size;
965 break;
967 default:
968 alSetError(pContext, AL_INVALID_ENUM);
969 break;
973 ProcessContext(pContext);
977 AL_API void AL_APIENTRY alGetBuffer3i(ALuint buffer, ALenum eParam, ALint* plValue1, ALint* plValue2, ALint* plValue3)
979 ALCcontext *pContext;
980 ALCdevice *device;
982 pContext = GetContextSuspended();
983 if(!pContext) return;
985 device = pContext->Device;
986 if(!plValue1 || !plValue2 || !plValue3)
987 alSetError(pContext, AL_INVALID_VALUE);
988 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
989 alSetError(pContext, AL_INVALID_NAME);
990 else
992 switch(eParam)
994 default:
995 alSetError(pContext, AL_INVALID_ENUM);
996 break;
1000 ProcessContext(pContext);
1004 AL_API void AL_APIENTRY alGetBufferiv(ALuint buffer, ALenum eParam, ALint* plValues)
1006 ALCcontext *pContext;
1007 ALCdevice *device;
1008 ALbuffer *ALBuf;
1010 pContext = GetContextSuspended();
1011 if(!pContext) return;
1013 device = pContext->Device;
1014 if(!plValues)
1015 alSetError(pContext, AL_INVALID_VALUE);
1016 else if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
1017 alSetError(pContext, AL_INVALID_NAME);
1018 else
1020 switch(eParam)
1022 case AL_FREQUENCY:
1023 case AL_BITS:
1024 case AL_CHANNELS:
1025 case AL_SIZE:
1026 alGetBufferi(buffer, eParam, plValues);
1027 break;
1029 case AL_LOOP_POINTS:
1030 plValues[0] = ALBuf->LoopStart;
1031 plValues[1] = ALBuf->LoopEnd;
1032 break;
1034 default:
1035 alSetError(pContext, AL_INVALID_ENUM);
1036 break;
1040 ProcessContext(pContext);
1044 * LoadData
1046 * Loads the specified data into the buffer, using the specified formats.
1047 * Currently, the new format must have the same channel configuration as the
1048 * original format, and must have the same sample format (except for double,
1049 * which converts to float). This does NOT handle compressed formats (eg. IMA4
1050 * and muLaw).
1052 static ALenum LoadData(ALbuffer *ALBuf, const ALvoid *data, ALsizei size, ALuint freq, ALenum OrigFormat, ALenum NewFormat)
1054 ALuint NewBytes = aluBytesFromFormat(NewFormat);
1055 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
1056 ALuint OrigBytes = aluBytesFromFormat(OrigFormat);
1057 ALuint OrigChannels = aluChannelsFromFormat(OrigFormat);
1058 enum SrcFmtChannels SrcChannels;
1059 enum FmtChannels DstChannels;
1060 enum SrcFmtType SrcType;
1061 enum FmtType DstType;
1062 ALuint64 newsize;
1063 ALvoid *temp;
1065 assert(NewChannels == OrigChannels);
1066 assert(NewBytes == OrigBytes);
1068 DecomposeInputFormat(OrigFormat, &SrcType, &SrcChannels);
1069 DecomposeFormat(NewFormat, &DstType, &DstChannels);
1071 if((size%(OrigBytes*OrigChannels)) != 0)
1072 return AL_INVALID_VALUE;
1074 newsize = size / OrigBytes;
1075 newsize *= NewBytes;
1076 if(newsize > INT_MAX)
1077 return AL_OUT_OF_MEMORY;
1079 temp = realloc(ALBuf->data, newsize);
1080 if(!temp) return AL_OUT_OF_MEMORY;
1081 ALBuf->data = temp;
1083 // Samples are converted here
1084 ConvertData(ALBuf->data, data, SrcType, newsize/NewBytes);
1086 ALBuf->format = NewFormat;
1087 ALBuf->eOriginalFormat = OrigFormat;
1088 ALBuf->size = newsize;
1089 ALBuf->frequency = freq;
1091 ALBuf->LoopStart = 0;
1092 ALBuf->LoopEnd = newsize / NewChannels / NewBytes;
1094 ALBuf->FmtType = DstType;
1095 ALBuf->FmtChannels = DstChannels;
1097 ALBuf->OriginalSize = size;
1098 ALBuf->OriginalAlign = OrigBytes * OrigChannels;
1100 return AL_NO_ERROR;
1103 static void ConvertData(ALvoid *dst, const ALvoid *src, enum SrcFmtType srcType, ALsizei len)
1105 ALsizei i;
1106 if(src == NULL)
1107 return;
1108 switch(srcType)
1110 case SrcFmtByte: /* signed byte -> unsigned byte */
1111 for(i = 0;i < len;i++)
1112 ((ALubyte*)dst)[i] = ((ALbyte*)src)[i] ^ 0x80;
1113 break;
1115 case SrcFmtUByte:
1116 for(i = 0;i < len;i++)
1117 ((ALubyte*)dst)[i] = ((ALubyte*)src)[i];
1118 break;
1120 case SrcFmtShort:
1121 for(i = 0;i < len;i++)
1122 ((ALshort*)dst)[i] = ((ALshort*)src)[i];
1123 break;
1125 case SrcFmtUShort: /* unsigned short -> signed short */
1126 for(i = 0;i < len;i++)
1127 ((ALshort*)dst)[i] = ((ALushort*)src)[i] ^ 0x8000;
1128 break;
1130 case SrcFmtFloat:
1131 for(i = 0;i < len;i++)
1132 ((ALfloat*)dst)[i] = ((ALfloat*)src)[i];
1133 break;
1135 case SrcFmtDouble:
1136 for(i = 0;i < len;i++)
1137 ((ALdouble*)dst)[i] = ((ALdouble*)src)[i];
1138 break;
1142 static void ConvertDataRear(ALvoid *dst, const ALvoid *src, ALint origBytes, ALsizei len)
1144 ALsizei i;
1145 if(src == NULL)
1146 return;
1147 switch(origBytes)
1149 case 1:
1150 for(i = 0;i < len;i+=4)
1152 ((ALubyte*)dst)[i+0] = 0;
1153 ((ALubyte*)dst)[i+1] = 0;
1154 ((ALubyte*)dst)[i+2] = ((ALubyte*)src)[i/2+0];
1155 ((ALubyte*)dst)[i+3] = ((ALubyte*)src)[i/2+1];
1157 break;
1159 case 2:
1160 for(i = 0;i < len;i+=4)
1162 ((ALshort*)dst)[i+0] = 0;
1163 ((ALshort*)dst)[i+1] = 0;
1164 ((ALshort*)dst)[i+2] = ((ALshort*)src)[i/2+0];
1165 ((ALshort*)dst)[i+3] = ((ALshort*)src)[i/2+1];
1167 break;
1169 case 4:
1170 for(i = 0;i < len;i+=4)
1172 ((ALfloat*)dst)[i+0] = 0.f;
1173 ((ALfloat*)dst)[i+1] = 0.f;
1174 ((ALfloat*)dst)[i+2] = ((ALfloat*)src)[i/2+0];
1175 ((ALfloat*)dst)[i+3] = ((ALfloat*)src)[i/2+1];
1177 break;
1179 default:
1180 assert(0);
1184 static void ConvertDataIMA4(ALvoid *dst, const ALvoid *src, ALint chans, ALsizei len)
1186 const ALubyte *IMAData;
1187 ALint Sample[2],Index[2];
1188 ALuint IMACode[2];
1189 ALsizei i,j,k,c;
1191 if(src == NULL)
1192 return;
1194 IMAData = src;
1195 for(i = 0;i < len;i++)
1197 for(c = 0;c < chans;c++)
1199 Sample[c] = *(IMAData++);
1200 Sample[c] |= *(IMAData++) << 8;
1201 Sample[c] = (Sample[c]^0x8000) - 32768;
1202 Index[c] = *(IMAData++);
1203 Index[c] |= *(IMAData++) << 8;
1204 Index[c] = (Index[c]^0x8000) - 32768;
1206 Index[c] = ((Index[c]<0) ? 0 : Index[c]);
1207 Index[c] = ((Index[c]>88) ? 88 : Index[c]);
1209 ((ALshort*)dst)[i*65*chans + c] = Sample[c];
1212 for(j = 1;j < 65;j += 8)
1214 for(c = 0;c < chans;c++)
1216 IMACode[c] = *(IMAData++);
1217 IMACode[c] |= *(IMAData++) << 8;
1218 IMACode[c] |= *(IMAData++) << 16;
1219 IMACode[c] |= *(IMAData++) << 24;
1222 for(k = 0;k < 8;k++)
1224 for(c = 0;c < chans;c++)
1226 Sample[c] += ((g_IMAStep_size[Index[c]]*g_IMACodeword_4[IMACode[c]&15])/8);
1227 Index[c] += g_IMAIndex_adjust_4[IMACode[c]&15];
1229 if(Sample[c] < -32768) Sample[c] = -32768;
1230 else if(Sample[c] > 32767) Sample[c] = 32767;
1232 if(Index[c]<0) Index[c] = 0;
1233 else if(Index[c]>88) Index[c] = 88;
1235 ((ALshort*)dst)[(i*65+j+k)*chans + c] = Sample[c];
1236 IMACode[c] >>= 4;
1243 static void ConvertDataMULaw(ALvoid *dst, const ALvoid *src, ALsizei len)
1245 ALsizei i;
1246 if(src == NULL)
1247 return;
1248 for(i = 0;i < len;i++)
1249 ((ALshort*)dst)[i] = muLawDecompressionTable[((ALubyte*)src)[i]];
1252 static void ConvertDataMULawRear(ALvoid *dst, const ALvoid *src, ALsizei len)
1254 ALsizei i;
1255 if(src == NULL)
1256 return;
1257 for(i = 0;i < len;i+=4)
1259 ((ALshort*)dst)[i+0] = 0;
1260 ((ALshort*)dst)[i+1] = 0;
1261 ((ALshort*)dst)[i+2] = muLawDecompressionTable[((ALubyte*)src)[i/2+0]];
1262 ((ALshort*)dst)[i+3] = muLawDecompressionTable[((ALubyte*)src)[i/2+1]];
1267 void DecomposeInputFormat(ALenum format, enum SrcFmtType *type,
1268 enum SrcFmtChannels *order)
1270 switch(format)
1272 case AL_FORMAT_MONO8:
1273 *type = SrcFmtUByte;
1274 *order = SrcFmtMono;
1275 break;
1276 case AL_FORMAT_MONO16:
1277 *type = SrcFmtShort;
1278 *order = SrcFmtMono;
1279 break;
1280 case AL_FORMAT_MONO_FLOAT32:
1281 *type = SrcFmtFloat;
1282 *order = SrcFmtMono;
1283 break;
1284 case AL_FORMAT_MONO_DOUBLE_EXT:
1285 *type = SrcFmtDouble;
1286 *order = SrcFmtMono;
1287 break;
1288 case AL_FORMAT_STEREO8:
1289 *type = SrcFmtUByte;
1290 *order = SrcFmtStereo;
1291 break;
1292 case AL_FORMAT_STEREO16:
1293 *type = SrcFmtShort;
1294 *order = SrcFmtStereo;
1295 break;
1296 case AL_FORMAT_STEREO_FLOAT32:
1297 *type = SrcFmtFloat;
1298 *order = SrcFmtStereo;
1299 break;
1300 case AL_FORMAT_STEREO_DOUBLE_EXT:
1301 *type = SrcFmtDouble;
1302 *order = SrcFmtStereo;
1303 break;
1304 case AL_FORMAT_QUAD8_LOKI:
1305 case AL_FORMAT_QUAD8:
1306 *type = SrcFmtUByte;
1307 *order = SrcFmtQuad;
1308 break;
1309 case AL_FORMAT_QUAD16_LOKI:
1310 case AL_FORMAT_QUAD16:
1311 *type = SrcFmtShort;
1312 *order = SrcFmtQuad;
1313 break;
1314 case AL_FORMAT_QUAD32:
1315 *type = SrcFmtFloat;
1316 *order = SrcFmtQuad;
1317 break;
1318 case AL_FORMAT_51CHN8:
1319 *type = SrcFmtUByte;
1320 *order = SrcFmtX51;
1321 break;
1322 case AL_FORMAT_51CHN16:
1323 *type = SrcFmtShort;
1324 *order = SrcFmtX51;
1325 break;
1326 case AL_FORMAT_51CHN32:
1327 *type = SrcFmtFloat;
1328 *order = SrcFmtX51;
1329 break;
1330 case AL_FORMAT_61CHN8:
1331 *type = SrcFmtUByte;
1332 *order = SrcFmtX61;
1333 break;
1334 case AL_FORMAT_61CHN16:
1335 *type = SrcFmtShort;
1336 *order = SrcFmtX61;
1337 break;
1338 case AL_FORMAT_61CHN32:
1339 *type = SrcFmtFloat;
1340 *order = SrcFmtX61;
1341 break;
1342 case AL_FORMAT_71CHN8:
1343 *type = SrcFmtUByte;
1344 *order = SrcFmtX71;
1345 break;
1346 case AL_FORMAT_71CHN16:
1347 *type = SrcFmtShort;
1348 *order = SrcFmtX71;
1349 break;
1350 case AL_FORMAT_71CHN32:
1351 *type = SrcFmtFloat;
1352 *order = SrcFmtX71;
1353 break;
1355 default:
1356 AL_PRINT("Unhandled format specified: 0x%X\n", format);
1357 abort();
1361 void DecomposeFormat(ALenum format, enum FmtType *type, enum FmtChannels *order)
1363 switch(format)
1365 case AL_FORMAT_MONO8:
1366 *type = FmtUByte;
1367 *order = FmtMono;
1368 break;
1369 case AL_FORMAT_MONO16:
1370 *type = FmtShort;
1371 *order = FmtMono;
1372 break;
1373 case AL_FORMAT_MONO_FLOAT32:
1374 *type = FmtFloat;
1375 *order = FmtMono;
1376 break;
1377 case AL_FORMAT_MONO_DOUBLE_EXT:
1378 *type = FmtDouble;
1379 *order = FmtMono;
1380 break;
1381 case AL_FORMAT_STEREO8:
1382 *type = FmtUByte;
1383 *order = FmtStereo;
1384 break;
1385 case AL_FORMAT_STEREO16:
1386 *type = FmtShort;
1387 *order = FmtStereo;
1388 break;
1389 case AL_FORMAT_STEREO_FLOAT32:
1390 *type = FmtFloat;
1391 *order = FmtStereo;
1392 break;
1393 case AL_FORMAT_STEREO_DOUBLE_EXT:
1394 *type = FmtDouble;
1395 *order = FmtStereo;
1396 break;
1397 case AL_FORMAT_QUAD8_LOKI:
1398 case AL_FORMAT_QUAD8:
1399 *type = FmtUByte;
1400 *order = FmtQuad;
1401 break;
1402 case AL_FORMAT_QUAD16_LOKI:
1403 case AL_FORMAT_QUAD16:
1404 *type = FmtShort;
1405 *order = FmtQuad;
1406 break;
1407 case AL_FORMAT_QUAD32:
1408 *type = FmtFloat;
1409 *order = FmtQuad;
1410 break;
1411 case AL_FORMAT_51CHN8:
1412 *type = FmtUByte;
1413 *order = Fmt51ChanWFX;
1414 break;
1415 case AL_FORMAT_51CHN16:
1416 *type = FmtShort;
1417 *order = Fmt51ChanWFX;
1418 break;
1419 case AL_FORMAT_51CHN32:
1420 *type = FmtFloat;
1421 *order = Fmt51ChanWFX;
1422 break;
1423 case AL_FORMAT_61CHN8:
1424 *type = FmtUByte;
1425 *order = Fmt61ChanWFX;
1426 break;
1427 case AL_FORMAT_61CHN16:
1428 *type = FmtShort;
1429 *order = Fmt61ChanWFX;
1430 break;
1431 case AL_FORMAT_61CHN32:
1432 *type = FmtFloat;
1433 *order = Fmt61ChanWFX;
1434 break;
1435 case AL_FORMAT_71CHN8:
1436 *type = FmtUByte;
1437 *order = Fmt71ChanWFX;
1438 break;
1439 case AL_FORMAT_71CHN16:
1440 *type = FmtShort;
1441 *order = Fmt71ChanWFX;
1442 break;
1443 case AL_FORMAT_71CHN32:
1444 *type = FmtFloat;
1445 *order = Fmt71ChanWFX;
1446 break;
1448 default:
1449 AL_PRINT("Unhandled format specified: 0x%X\n", format);
1450 abort();
1456 * ReleaseALBuffers()
1458 * INTERNAL FN : Called by alcCloseDevice to destroy any buffers that still exist
1460 ALvoid ReleaseALBuffers(ALCdevice *device)
1462 ALsizei i;
1463 for(i = 0;i < device->BufferMap.size;i++)
1465 ALbuffer *temp = device->BufferMap.array[i].value;
1466 device->BufferMap.array[i].value = NULL;
1468 // Release sample data
1469 free(temp->data);
1471 // Release Buffer structure
1472 ALTHUNK_REMOVEENTRY(temp->buffer);
1473 memset(temp, 0, sizeof(ALbuffer));
1474 free(temp);