Removed project files that are generated by "android update project" step.
[openal-soft/android.git] / OpenAL32 / alBuffer.c
blob81e17c5277d5c5d46e80f0cf3bae70e3478b61a8
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(ALfloat *dst, const ALvoid *src, ALint origBytes, ALsizei len);
39 static void ConvertDataRear(ALfloat *dst, const ALvoid *src, ALint origBytes, ALsizei len);
40 static void ConvertDataIMA4(ALfloat *dst, const ALvoid *src, ALint origChans, ALsizei len);
41 static void ConvertDataMULaw(ALfloat *dst, const ALvoid *src, ALsizei len);
42 static void ConvertDataMULawRear(ALfloat *dst, const ALvoid *src, ALsizei len);
44 #define LookupBuffer(m, k) ((ALbuffer*)LookupUIntMapKey(&(m), (k)))
47 * Global Variables
50 static const long g_IMAStep_size[89]={ // IMA ADPCM Stepsize table
51 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, 19, 21, 23, 25, 28, 31,
52 34, 37, 41, 45, 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130, 143,
53 157, 173, 190, 209, 230, 253, 279, 307, 337, 371, 408, 449, 494, 544, 598, 658,
54 724, 796, 876, 963, 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024,
55 3327, 3660, 4026, 4428, 4871, 5358, 5894, 6484, 7132, 7845, 8630, 9493,10442,11487,12635,13899,
56 15289,16818,18500,20350,22358,24633,27086,29794,32767
59 static const long g_IMACodeword_4[16]={ // IMA4 ADPCM Codeword decode table
60 1, 3, 5, 7, 9, 11, 13, 15,
61 -1,-3,-5,-7,-9,-11,-13,-15,
64 static const long g_IMAIndex_adjust_4[16]={ // IMA4 ADPCM Step index adjust decode table
65 -1,-1,-1,-1, 2, 4, 6, 8,
66 -1,-1,-1,-1, 2, 4, 6, 8
69 static const ALshort muLawDecompressionTable[256] = {
70 -32124,-31100,-30076,-29052,-28028,-27004,-25980,-24956,
71 -23932,-22908,-21884,-20860,-19836,-18812,-17788,-16764,
72 -15996,-15484,-14972,-14460,-13948,-13436,-12924,-12412,
73 -11900,-11388,-10876,-10364, -9852, -9340, -8828, -8316,
74 -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140,
75 -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092,
76 -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004,
77 -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980,
78 -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436,
79 -1372, -1308, -1244, -1180, -1116, -1052, -988, -924,
80 -876, -844, -812, -780, -748, -716, -684, -652,
81 -620, -588, -556, -524, -492, -460, -428, -396,
82 -372, -356, -340, -324, -308, -292, -276, -260,
83 -244, -228, -212, -196, -180, -164, -148, -132,
84 -120, -112, -104, -96, -88, -80, -72, -64,
85 -56, -48, -40, -32, -24, -16, -8, 0,
86 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956,
87 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764,
88 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412,
89 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316,
90 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140,
91 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092,
92 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004,
93 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980,
94 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436,
95 1372, 1308, 1244, 1180, 1116, 1052, 988, 924,
96 876, 844, 812, 780, 748, 716, 684, 652,
97 620, 588, 556, 524, 492, 460, 428, 396,
98 372, 356, 340, 324, 308, 292, 276, 260,
99 244, 228, 212, 196, 180, 164, 148, 132,
100 120, 112, 104, 96, 88, 80, 72, 64,
101 56, 48, 40, 32, 24, 16, 8, 0
105 * alGenBuffers(ALsizei n, ALuint *puiBuffers)
107 * Generates n AL Buffers, and stores the Buffers Names in the array pointed to by puiBuffers
109 AL_API ALvoid AL_APIENTRY alGenBuffers(ALsizei n, ALuint *buffers)
111 ALCcontext *Context;
112 ALsizei i=0;
114 Context = GetContextSuspended();
115 if(!Context) return;
117 // Check that we are actually generation some Buffers
118 if(n > 0)
120 ALCdevice *device = Context->Device;
121 ALenum err;
123 // Check the pointer is valid (and points to enough memory to store Buffer Names)
124 if(IsBadWritePtr((void*)buffers, n * sizeof(ALuint)))
125 alSetError(Context, AL_INVALID_VALUE);
126 else
128 // Create all the new Buffers
129 while(i < n)
131 ALbuffer *buffer = calloc(1, sizeof(ALbuffer));
132 if(!buffer)
134 alSetError(Context, AL_OUT_OF_MEMORY);
135 alDeleteBuffers(i, buffers);
136 break;
139 buffer->buffer = (ALuint)ALTHUNK_ADDENTRY(buffer);
140 err = InsertUIntMapEntry(&device->BufferMap, buffer->buffer,
141 buffer);
142 if(err != AL_NO_ERROR)
144 ALTHUNK_REMOVEENTRY(buffer->buffer);
145 memset(buffer, 0, sizeof(ALbuffer));
146 free(buffer);
148 alSetError(Context, err);
149 alDeleteBuffers(i, buffers);
150 break;
152 buffers[i++] = buffer->buffer;
157 ProcessContext(Context);
161 * alDeleteBuffers(ALsizei n, ALuint *puiBuffers)
163 * Deletes the n AL Buffers pointed to by puiBuffers
165 AL_API ALvoid AL_APIENTRY alDeleteBuffers(ALsizei n, const ALuint *puiBuffers)
167 ALCcontext *Context;
168 ALbuffer *ALBuf;
169 ALsizei i;
171 Context = GetContextSuspended();
172 if(!Context) return;
174 // Check we are actually Deleting some Buffers
175 if(n < 0)
176 alSetError(Context, AL_INVALID_VALUE);
177 else
179 ALCdevice *device = Context->Device;
180 ALboolean bFailed = AL_FALSE;
182 // Check that all the buffers are valid and can actually be deleted
183 for (i = 0; i < n; i++)
185 if(!puiBuffers[i])
186 continue;
188 // Check for valid Buffer ID (can be NULL buffer)
189 if((ALBuf=LookupBuffer(device->BufferMap, puiBuffers[i])) != NULL)
191 if(ALBuf->refcount != 0)
193 // Buffer still in use, cannot be deleted
194 alSetError(Context, AL_INVALID_OPERATION);
195 bFailed = AL_TRUE;
196 break;
199 else
201 // Invalid Buffer
202 alSetError(Context, AL_INVALID_NAME);
203 bFailed = AL_TRUE;
204 break;
208 // If all the Buffers were valid (and have Reference Counts of 0), then we can delete them
209 if (!bFailed)
211 for (i = 0; i < n; i++)
213 if((ALBuf=LookupBuffer(device->BufferMap, puiBuffers[i])) != NULL)
215 // Release the memory used to store audio data
216 free(ALBuf->data);
218 // Release buffer structure
219 RemoveUIntMapKey(&device->BufferMap, ALBuf->buffer);
220 ALTHUNK_REMOVEENTRY(ALBuf->buffer);
222 memset(ALBuf, 0, sizeof(ALbuffer));
223 free(ALBuf);
229 ProcessContext(Context);
233 * alIsBuffer(ALuint uiBuffer)
235 * Checks if ulBuffer is a valid Buffer Name
237 AL_API ALboolean AL_APIENTRY alIsBuffer(ALuint buffer)
239 ALCcontext *Context;
240 ALboolean result;
242 Context = GetContextSuspended();
243 if(!Context) return AL_FALSE;
245 result = ((!buffer || LookupBuffer(Context->Device->BufferMap, buffer)) ?
246 AL_TRUE : AL_FALSE);
248 ProcessContext(Context);
250 return result;
254 * alBufferData(ALuint buffer,ALenum format,ALvoid *data,ALsizei size,ALsizei freq)
256 * Fill buffer with audio data
258 AL_API ALvoid AL_APIENTRY alBufferData(ALuint buffer,ALenum format,const ALvoid *data,ALsizei size,ALsizei freq)
260 ALCcontext *Context;
261 ALCdevice *device;
262 ALbuffer *ALBuf;
263 ALvoid *temp;
264 ALenum err;
266 Context = GetContextSuspended();
267 if(!Context) return;
269 device = Context->Device;
270 if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
271 alSetError(Context, AL_INVALID_NAME); /* Invalid Buffer Name */
272 else
274 if(Context->SampleSource)
276 ALintptrEXT offset;
278 if(Context->SampleSource->state == MAPPED)
280 alSetError(Context, AL_INVALID_OPERATION);
281 ProcessContext(Context);
282 return;
285 offset = (const ALubyte*)data - (ALubyte*)NULL;
286 data = Context->SampleSource->data + offset;
289 if(size < 0)
290 alSetError(Context, AL_INVALID_VALUE);
291 else if(ALBuf->refcount != 0)
292 alSetError(Context, AL_INVALID_VALUE);
293 else
295 switch(format)
297 case AL_FORMAT_MONO8:
298 case AL_FORMAT_MONO16:
299 case AL_FORMAT_MONO_FLOAT32:
300 case AL_FORMAT_MONO_DOUBLE_EXT:
301 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_MONO_FLOAT32);
302 if(err != AL_NO_ERROR)
303 alSetError(Context, err);
304 break;
306 case AL_FORMAT_STEREO8:
307 case AL_FORMAT_STEREO16:
308 case AL_FORMAT_STEREO_FLOAT32:
309 case AL_FORMAT_STEREO_DOUBLE_EXT:
310 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_STEREO_FLOAT32);
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 ALenum NewFormat = AL_FORMAT_QUAD32;
319 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
320 ALuint NewBytes = aluBytesFromFormat(NewFormat);
321 ALuint OrigBytes = ((format==AL_FORMAT_REAR8) ? 1 :
322 ((format==AL_FORMAT_REAR16) ? 2 :
323 4));
324 ALuint64 newsize, allocsize;
326 if((size%(OrigBytes*2)) != 0)
328 alSetError(Context, AL_INVALID_VALUE);
329 break;
332 newsize = size / OrigBytes;
333 newsize *= 2;
335 allocsize = (BUFFER_PADDING*NewChannels + newsize)*NewBytes;
336 if(allocsize > INT_MAX)
338 alSetError(Context, AL_OUT_OF_MEMORY);
339 break;
341 temp = realloc(ALBuf->data, allocsize);
342 if(temp)
344 ALBuf->data = temp;
345 ConvertDataRear(ALBuf->data, data, OrigBytes, newsize);
347 ALBuf->format = NewFormat;
348 ALBuf->eOriginalFormat = format;
349 ALBuf->size = newsize*NewBytes;
350 ALBuf->frequency = freq;
352 ALBuf->LoopStart = 0;
353 ALBuf->LoopEnd = newsize / NewChannels;
355 ALBuf->OriginalSize = size;
356 ALBuf->OriginalAlign = OrigBytes * 2;
358 else
359 alSetError(Context, AL_OUT_OF_MEMORY);
360 } break;
362 case AL_FORMAT_QUAD8_LOKI:
363 case AL_FORMAT_QUAD16_LOKI:
364 case AL_FORMAT_QUAD8:
365 case AL_FORMAT_QUAD16:
366 case AL_FORMAT_QUAD32:
367 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_QUAD32);
368 if(err != AL_NO_ERROR)
369 alSetError(Context, err);
370 break;
372 case AL_FORMAT_51CHN8:
373 case AL_FORMAT_51CHN16:
374 case AL_FORMAT_51CHN32:
375 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_51CHN32);
376 if(err != AL_NO_ERROR)
377 alSetError(Context, err);
378 break;
380 case AL_FORMAT_61CHN8:
381 case AL_FORMAT_61CHN16:
382 case AL_FORMAT_61CHN32:
383 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_61CHN32);
384 if(err != AL_NO_ERROR)
385 alSetError(Context, err);
386 break;
388 case AL_FORMAT_71CHN8:
389 case AL_FORMAT_71CHN16:
390 case AL_FORMAT_71CHN32:
391 err = LoadData(ALBuf, data, size, freq, format, AL_FORMAT_71CHN32);
392 if(err != AL_NO_ERROR)
393 alSetError(Context, err);
394 break;
396 case AL_FORMAT_MONO_IMA4:
397 case AL_FORMAT_STEREO_IMA4: {
398 int Channels = ((format==AL_FORMAT_MONO_IMA4) ? 1 : 2);
399 ALenum NewFormat = ((Channels==1) ? AL_FORMAT_MONO_FLOAT32 :
400 AL_FORMAT_STEREO_FLOAT32);
401 ALuint NewBytes = aluBytesFromFormat(NewFormat);
402 ALuint64 newsize, allocsize;
404 // Here is where things vary:
405 // nVidia and Apple use 64+1 samples per channel per block => block_size=36*chans bytes
406 // Most PC sound software uses 2040+1 samples per channel per block -> block_size=1024*chans bytes
407 if((size%(36*Channels)) != 0)
409 alSetError(Context, AL_INVALID_VALUE);
410 break;
413 newsize = size / 36;
414 newsize *= 65;
416 allocsize = (BUFFER_PADDING*Channels + newsize)*NewBytes;
417 if(allocsize > INT_MAX)
419 alSetError(Context, AL_OUT_OF_MEMORY);
420 break;
422 temp = realloc(ALBuf->data, allocsize);
423 if(temp)
425 ALBuf->data = temp;
426 ConvertDataIMA4(ALBuf->data, data, Channels, newsize/(65*Channels));
428 ALBuf->format = NewFormat;
429 ALBuf->eOriginalFormat = format;
430 ALBuf->size = newsize*NewBytes;
431 ALBuf->frequency = freq;
433 ALBuf->LoopStart = 0;
434 ALBuf->LoopEnd = newsize / Channels;
436 ALBuf->OriginalSize = size;
437 ALBuf->OriginalAlign = 36 * Channels;
439 else
440 alSetError(Context, AL_OUT_OF_MEMORY);
441 } break;
443 case AL_FORMAT_MONO_MULAW:
444 case AL_FORMAT_STEREO_MULAW:
445 case AL_FORMAT_QUAD_MULAW:
446 case AL_FORMAT_51CHN_MULAW:
447 case AL_FORMAT_61CHN_MULAW:
448 case AL_FORMAT_71CHN_MULAW: {
449 int Channels = ((format==AL_FORMAT_MONO_MULAW) ? 1 :
450 ((format==AL_FORMAT_STEREO_MULAW) ? 2 :
451 ((format==AL_FORMAT_QUAD_MULAW) ? 4 :
452 ((format==AL_FORMAT_51CHN_MULAW) ? 6 :
453 ((format==AL_FORMAT_61CHN_MULAW) ? 7 : 8)))));
454 ALenum NewFormat = ((Channels==1) ? AL_FORMAT_MONO_FLOAT32 :
455 ((Channels==2) ? AL_FORMAT_STEREO_FLOAT32 :
456 ((Channels==4) ? AL_FORMAT_QUAD32 :
457 ((Channels==6) ? AL_FORMAT_51CHN32 :
458 ((Channels==7) ? AL_FORMAT_61CHN32 :
459 AL_FORMAT_71CHN32)))));
460 ALuint NewBytes = aluBytesFromFormat(NewFormat);
461 ALuint64 allocsize;
463 if((size%(1*Channels)) != 0)
465 alSetError(Context, AL_INVALID_VALUE);
466 break;
469 allocsize = (BUFFER_PADDING*Channels + size)*NewBytes;
470 if(allocsize > INT_MAX)
472 alSetError(Context, AL_OUT_OF_MEMORY);
473 break;
475 temp = realloc(ALBuf->data, allocsize);
476 if(temp)
478 ALBuf->data = temp;
479 ConvertDataMULaw(ALBuf->data, data, size);
481 ALBuf->format = NewFormat;
482 ALBuf->eOriginalFormat = format;
483 ALBuf->size = size*NewBytes;
484 ALBuf->frequency = freq;
486 ALBuf->LoopStart = 0;
487 ALBuf->LoopEnd = size / Channels;
489 ALBuf->OriginalSize = size;
490 ALBuf->OriginalAlign = 1 * Channels;
492 else
493 alSetError(Context, AL_OUT_OF_MEMORY);
494 } break;
496 case AL_FORMAT_REAR_MULAW: {
497 ALenum NewFormat = AL_FORMAT_QUAD32;
498 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
499 ALuint NewBytes = aluBytesFromFormat(NewFormat);
500 ALuint64 newsize, allocsize;
502 if((size%(1*2)) != 0)
504 alSetError(Context, AL_INVALID_VALUE);
505 break;
508 newsize = size * 2;
510 allocsize = (BUFFER_PADDING*NewChannels + newsize)*NewBytes;
511 if(allocsize > INT_MAX)
513 alSetError(Context, AL_OUT_OF_MEMORY);
514 break;
516 temp = realloc(ALBuf->data, allocsize);
517 if(temp)
519 ALBuf->data = temp;
520 ConvertDataMULawRear(ALBuf->data, data, newsize);
522 ALBuf->format = NewFormat;
523 ALBuf->eOriginalFormat = format;
524 ALBuf->size = newsize*NewBytes;
525 ALBuf->frequency = freq;
527 ALBuf->LoopStart = 0;
528 ALBuf->LoopEnd = newsize / NewChannels;
530 ALBuf->OriginalSize = size;
531 ALBuf->OriginalAlign = 1 * 2;
533 else
534 alSetError(Context, AL_OUT_OF_MEMORY);
535 } break;
537 default:
538 alSetError(Context, AL_INVALID_ENUM);
539 break;
544 ProcessContext(Context);
548 * alBufferSubDataEXT(ALuint buffer,ALenum format,ALvoid *data,ALsizei offset,ALsizei length)
550 * Fill buffer with audio data
552 AL_API ALvoid AL_APIENTRY alBufferSubDataEXT(ALuint buffer,ALenum format,const ALvoid *data,ALsizei offset,ALsizei length)
554 ALCcontext *Context;
555 ALCdevice *device;
556 ALbuffer *ALBuf;
558 Context = GetContextSuspended();
559 if(!Context) return;
561 device = Context->Device;
562 if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
563 alSetError(Context, AL_INVALID_NAME);
564 else
566 if(Context->SampleSource)
568 ALintptrEXT offset;
570 if(Context->SampleSource->state == MAPPED)
572 alSetError(Context, AL_INVALID_OPERATION);
573 ProcessContext(Context);
574 return;
577 offset = (const ALubyte*)data - (ALubyte*)NULL;
578 data = Context->SampleSource->data + offset;
581 if(length < 0 || offset < 0 || (length > 0 && data == NULL))
582 alSetError(Context, AL_INVALID_VALUE);
583 else if(ALBuf->eOriginalFormat != format)
584 alSetError(Context, AL_INVALID_ENUM);
585 else if(offset+length < offset ||
586 offset+length > ALBuf->OriginalSize ||
587 (offset%ALBuf->OriginalAlign) != 0 ||
588 (length%ALBuf->OriginalAlign) != 0)
589 alSetError(Context, AL_INVALID_VALUE);
590 else
592 switch(format)
594 case AL_FORMAT_MONO8:
595 case AL_FORMAT_MONO16:
596 case AL_FORMAT_MONO_FLOAT32:
597 case AL_FORMAT_MONO_DOUBLE_EXT:
598 case AL_FORMAT_STEREO8:
599 case AL_FORMAT_STEREO16:
600 case AL_FORMAT_STEREO_FLOAT32:
601 case AL_FORMAT_STEREO_DOUBLE_EXT:
602 case AL_FORMAT_QUAD8_LOKI:
603 case AL_FORMAT_QUAD16_LOKI:
604 case AL_FORMAT_QUAD8:
605 case AL_FORMAT_QUAD16:
606 case AL_FORMAT_QUAD32:
607 case AL_FORMAT_51CHN8:
608 case AL_FORMAT_51CHN16:
609 case AL_FORMAT_51CHN32:
610 case AL_FORMAT_61CHN8:
611 case AL_FORMAT_61CHN16:
612 case AL_FORMAT_61CHN32:
613 case AL_FORMAT_71CHN8:
614 case AL_FORMAT_71CHN16:
615 case AL_FORMAT_71CHN32: {
616 ALuint Bytes = aluBytesFromFormat(format);
618 offset /= Bytes;
619 length /= Bytes;
621 ConvertData(&ALBuf->data[offset], data, Bytes, length);
622 } break;
624 case AL_FORMAT_REAR8:
625 case AL_FORMAT_REAR16:
626 case AL_FORMAT_REAR32: {
627 ALuint Bytes = ((format==AL_FORMAT_REAR8) ? 1 :
628 ((format==AL_FORMAT_REAR16) ? 2 :
629 4));
631 offset /= Bytes;
632 offset *= 2;
633 length /= Bytes;
634 length *= 2;
636 ConvertDataRear(&ALBuf->data[offset], data, Bytes, length);
637 } break;
639 case AL_FORMAT_MONO_IMA4:
640 case AL_FORMAT_STEREO_IMA4: {
641 int Channels = aluChannelsFromFormat(ALBuf->format);
643 // offset -> sample*channel offset, length -> block count
644 offset /= 36;
645 offset *= 65;
646 length /= ALBuf->OriginalAlign;
648 ConvertDataIMA4(&ALBuf->data[offset], data, Channels, length);
649 } break;
651 case AL_FORMAT_MONO_MULAW:
652 case AL_FORMAT_STEREO_MULAW:
653 case AL_FORMAT_QUAD_MULAW:
654 case AL_FORMAT_51CHN_MULAW:
655 case AL_FORMAT_61CHN_MULAW:
656 case AL_FORMAT_71CHN_MULAW:
657 ConvertDataMULaw(&ALBuf->data[offset], data, length);
658 break;
660 case AL_FORMAT_REAR_MULAW:
661 offset *= 2;
662 length *= 2;
663 ConvertDataMULawRear(&ALBuf->data[offset], data, length);
664 break;
666 default:
667 alSetError(Context, AL_INVALID_ENUM);
668 break;
673 ProcessContext(Context);
677 AL_API void AL_APIENTRY alBufferf(ALuint buffer, ALenum eParam, ALfloat flValue)
679 ALCcontext *pContext;
680 ALCdevice *device;
682 (void)flValue;
684 pContext = GetContextSuspended();
685 if(!pContext) return;
687 device = pContext->Device;
688 if(LookupBuffer(device->BufferMap, buffer) == NULL)
689 alSetError(pContext, AL_INVALID_NAME);
691 switch(eParam)
693 default:
694 alSetError(pContext, AL_INVALID_ENUM);
695 break;
699 ProcessContext(pContext);
703 AL_API void AL_APIENTRY alBuffer3f(ALuint buffer, ALenum eParam, ALfloat flValue1, ALfloat flValue2, ALfloat flValue3)
705 ALCcontext *pContext;
706 ALCdevice *device;
708 (void)flValue1;
709 (void)flValue2;
710 (void)flValue3;
712 pContext = GetContextSuspended();
713 if(!pContext) return;
715 device = pContext->Device;
716 if(LookupBuffer(device->BufferMap, buffer) == NULL)
717 alSetError(pContext, AL_INVALID_NAME);
718 else
720 switch(eParam)
722 default:
723 alSetError(pContext, AL_INVALID_ENUM);
724 break;
728 ProcessContext(pContext);
732 AL_API void AL_APIENTRY alBufferfv(ALuint buffer, ALenum eParam, const ALfloat* flValues)
734 ALCcontext *pContext;
735 ALCdevice *device;
737 pContext = GetContextSuspended();
738 if(!pContext) return;
740 device = pContext->Device;
741 if(!flValues)
742 alSetError(pContext, AL_INVALID_VALUE);
743 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
744 alSetError(pContext, AL_INVALID_NAME);
745 else
747 switch(eParam)
749 default:
750 alSetError(pContext, AL_INVALID_ENUM);
751 break;
755 ProcessContext(pContext);
759 AL_API void AL_APIENTRY alBufferi(ALuint buffer, ALenum eParam, ALint lValue)
761 ALCcontext *pContext;
762 ALCdevice *device;
764 (void)lValue;
766 pContext = GetContextSuspended();
767 if(!pContext) return;
769 device = pContext->Device;
770 if(LookupBuffer(device->BufferMap, buffer) == NULL)
771 alSetError(pContext, AL_INVALID_NAME);
772 else
774 switch(eParam)
776 default:
777 alSetError(pContext, AL_INVALID_ENUM);
778 break;
782 ProcessContext(pContext);
786 AL_API void AL_APIENTRY alBuffer3i( ALuint buffer, ALenum eParam, ALint lValue1, ALint lValue2, ALint lValue3)
788 ALCcontext *pContext;
789 ALCdevice *device;
791 (void)lValue1;
792 (void)lValue2;
793 (void)lValue3;
795 pContext = GetContextSuspended();
796 if(!pContext) return;
798 device = pContext->Device;
799 if(LookupBuffer(device->BufferMap, buffer) == NULL)
800 alSetError(pContext, AL_INVALID_NAME);
801 else
803 switch(eParam)
805 default:
806 alSetError(pContext, AL_INVALID_ENUM);
807 break;
811 ProcessContext(pContext);
815 AL_API void AL_APIENTRY alBufferiv(ALuint buffer, ALenum eParam, const ALint* plValues)
817 ALCcontext *pContext;
818 ALCdevice *device;
819 ALbuffer *ALBuf;
821 pContext = GetContextSuspended();
822 if(!pContext) return;
824 device = pContext->Device;
825 if(!plValues)
826 alSetError(pContext, AL_INVALID_VALUE);
827 else if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
828 alSetError(pContext, AL_INVALID_NAME);
829 else
831 switch(eParam)
833 case AL_LOOP_POINTS:
834 if(ALBuf->refcount > 0)
835 alSetError(pContext, AL_INVALID_OPERATION);
836 else if(plValues[0] < 0 || plValues[1] < 0 ||
837 plValues[0] >= plValues[1] || ALBuf->size == 0)
838 alSetError(pContext, AL_INVALID_VALUE);
839 else
841 ALint maxlen = ALBuf->size / aluFrameSizeFromFormat(ALBuf->format);
842 if(plValues[0] > maxlen || plValues[1] > maxlen)
843 alSetError(pContext, AL_INVALID_VALUE);
844 else
846 ALBuf->LoopStart = plValues[0];
847 ALBuf->LoopEnd = plValues[1];
850 break;
852 default:
853 alSetError(pContext, AL_INVALID_ENUM);
854 break;
858 ProcessContext(pContext);
862 AL_API ALvoid AL_APIENTRY alGetBufferf(ALuint buffer, ALenum eParam, ALfloat *pflValue)
864 ALCcontext *pContext;
865 ALCdevice *device;
867 pContext = GetContextSuspended();
868 if(!pContext) return;
870 device = pContext->Device;
871 if(!pflValue)
872 alSetError(pContext, AL_INVALID_VALUE);
873 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
874 alSetError(pContext, AL_INVALID_NAME);
875 else
877 switch(eParam)
879 default:
880 alSetError(pContext, AL_INVALID_ENUM);
881 break;
885 ProcessContext(pContext);
889 AL_API void AL_APIENTRY alGetBuffer3f(ALuint buffer, ALenum eParam, ALfloat* pflValue1, ALfloat* pflValue2, ALfloat* pflValue3)
891 ALCcontext *pContext;
892 ALCdevice *device;
894 pContext = GetContextSuspended();
895 if(!pContext) return;
897 device = pContext->Device;
898 if(!pflValue1 || !pflValue2 || !pflValue3)
899 alSetError(pContext, AL_INVALID_VALUE);
900 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
901 alSetError(pContext, AL_INVALID_NAME);
902 else
904 switch(eParam)
906 default:
907 alSetError(pContext, AL_INVALID_ENUM);
908 break;
912 ProcessContext(pContext);
916 AL_API void AL_APIENTRY alGetBufferfv(ALuint buffer, ALenum eParam, ALfloat* pflValues)
918 ALCcontext *pContext;
919 ALCdevice *device;
921 pContext = GetContextSuspended();
922 if(!pContext) return;
924 device = pContext->Device;
925 if(!pflValues)
926 alSetError(pContext, AL_INVALID_VALUE);
927 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
928 alSetError(pContext, AL_INVALID_NAME);
929 else
931 switch(eParam)
933 default:
934 alSetError(pContext, AL_INVALID_ENUM);
935 break;
939 ProcessContext(pContext);
943 AL_API ALvoid AL_APIENTRY alGetBufferi(ALuint buffer, ALenum eParam, ALint *plValue)
945 ALCcontext *pContext;
946 ALbuffer *pBuffer;
947 ALCdevice *device;
949 pContext = GetContextSuspended();
950 if(!pContext) return;
952 device = pContext->Device;
953 if(!plValue)
954 alSetError(pContext, AL_INVALID_VALUE);
955 else if((pBuffer=LookupBuffer(device->BufferMap, buffer)) == NULL)
956 alSetError(pContext, AL_INVALID_NAME);
957 else
959 switch(eParam)
961 case AL_FREQUENCY:
962 *plValue = pBuffer->frequency;
963 break;
965 case AL_BITS:
966 *plValue = aluBytesFromFormat(pBuffer->format) * 8;
967 break;
969 case AL_CHANNELS:
970 *plValue = aluChannelsFromFormat(pBuffer->format);
971 break;
973 case AL_SIZE:
974 *plValue = pBuffer->size;
975 break;
977 default:
978 alSetError(pContext, AL_INVALID_ENUM);
979 break;
983 ProcessContext(pContext);
987 AL_API void AL_APIENTRY alGetBuffer3i(ALuint buffer, ALenum eParam, ALint* plValue1, ALint* plValue2, ALint* plValue3)
989 ALCcontext *pContext;
990 ALCdevice *device;
992 pContext = GetContextSuspended();
993 if(!pContext) return;
995 device = pContext->Device;
996 if(!plValue1 || !plValue2 || !plValue3)
997 alSetError(pContext, AL_INVALID_VALUE);
998 else if(LookupBuffer(device->BufferMap, buffer) == NULL)
999 alSetError(pContext, AL_INVALID_NAME);
1000 else
1002 switch(eParam)
1004 default:
1005 alSetError(pContext, AL_INVALID_ENUM);
1006 break;
1010 ProcessContext(pContext);
1014 AL_API void AL_APIENTRY alGetBufferiv(ALuint buffer, ALenum eParam, ALint* plValues)
1016 ALCcontext *pContext;
1017 ALCdevice *device;
1018 ALbuffer *ALBuf;
1020 pContext = GetContextSuspended();
1021 if(!pContext) return;
1023 device = pContext->Device;
1024 if(!plValues)
1025 alSetError(pContext, AL_INVALID_VALUE);
1026 else if((ALBuf=LookupBuffer(device->BufferMap, buffer)) == NULL)
1027 alSetError(pContext, AL_INVALID_NAME);
1028 else
1030 switch(eParam)
1032 case AL_FREQUENCY:
1033 case AL_BITS:
1034 case AL_CHANNELS:
1035 case AL_SIZE:
1036 alGetBufferi(buffer, eParam, plValues);
1037 break;
1039 case AL_LOOP_POINTS:
1040 plValues[0] = ALBuf->LoopStart;
1041 plValues[1] = ALBuf->LoopEnd;
1042 break;
1044 default:
1045 alSetError(pContext, AL_INVALID_ENUM);
1046 break;
1050 ProcessContext(pContext);
1054 * LoadData
1056 * Loads the specified data into the buffer, using the specified formats.
1057 * Currently, the new format must be 32-bit float, and must have the same
1058 * channel configuration as the original format. This does NOT handle
1059 * compressed formats (eg. IMA4).
1061 static ALenum LoadData(ALbuffer *ALBuf, const ALvoid *data, ALsizei size, ALuint freq, ALenum OrigFormat, ALenum NewFormat)
1063 ALuint NewBytes = aluBytesFromFormat(NewFormat);
1064 ALuint NewChannels = aluChannelsFromFormat(NewFormat);
1065 ALuint OrigBytes = aluBytesFromFormat(OrigFormat);
1066 ALuint OrigChannels = aluChannelsFromFormat(OrigFormat);
1067 ALuint64 newsize, allocsize;
1068 ALvoid *temp;
1070 assert(NewBytes == 4);
1071 assert(NewChannels == OrigChannels);
1073 if ((size%(OrigBytes*OrigChannels)) != 0)
1074 return AL_INVALID_VALUE;
1076 // Allocate extra padding samples
1077 newsize = size / OrigBytes;
1078 allocsize = (BUFFER_PADDING*NewChannels + newsize)*NewBytes;
1079 if(allocsize > INT_MAX)
1080 return AL_OUT_OF_MEMORY;
1082 temp = realloc(ALBuf->data, allocsize);
1083 if(!temp) return AL_OUT_OF_MEMORY;
1084 ALBuf->data = temp;
1086 // Samples are converted here
1087 ConvertData(ALBuf->data, data, OrigBytes, newsize);
1089 ALBuf->format = NewFormat;
1090 ALBuf->eOriginalFormat = OrigFormat;
1091 ALBuf->size = newsize*NewBytes;
1092 ALBuf->frequency = freq;
1094 ALBuf->LoopStart = 0;
1095 ALBuf->LoopEnd = newsize / NewChannels;
1097 ALBuf->OriginalSize = size;
1098 ALBuf->OriginalAlign = OrigBytes * OrigChannels;
1100 return AL_NO_ERROR;
1103 static void ConvertData(ALfloat *dst, const ALvoid *src, ALint origBytes, ALsizei len)
1105 ALsizei i;
1106 ALint smp;
1107 if(src == NULL)
1108 return;
1109 switch(origBytes)
1111 case 1:
1112 for(i = 0;i < len;i++)
1114 smp = ((ALubyte*)src)[i];
1115 dst[i] = ((smp < 0x80) ? ((smp-128)/128.0f) : ((smp-128)/127.0f));
1117 break;
1119 case 2:
1120 for(i = 0;i < len;i++)
1122 smp = ((ALshort*)src)[i];
1123 dst[i] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1125 break;
1127 case 4:
1128 for(i = 0;i < len;i++)
1129 dst[i] = ((ALfloat*)src)[i];
1130 break;
1132 case 8:
1133 for(i = 0;i < len;i++)
1134 dst[i] = ((ALdouble*)src)[i];
1135 break;
1137 default:
1138 assert(0);
1142 static void ConvertDataRear(ALfloat *dst, const ALvoid *src, ALint origBytes, ALsizei len)
1144 ALsizei i;
1145 ALint smp;
1146 if(src == NULL)
1147 return;
1148 switch(origBytes)
1150 case 1:
1151 for(i = 0;i < len;i+=4)
1153 dst[i+0] = 0;
1154 dst[i+1] = 0;
1155 smp = ((ALubyte*)src)[i/2+0];
1156 dst[i+2] = ((smp < 0x80) ? ((smp-128)/128.0f) : ((smp-128)/127.0f));
1157 smp = ((ALubyte*)src)[i/2+1];
1158 dst[i+3] = ((smp < 0x80) ? ((smp-128)/128.0f) : ((smp-128)/127.0f));
1160 break;
1162 case 2:
1163 for(i = 0;i < len;i+=4)
1165 dst[i+0] = 0;
1166 dst[i+1] = 0;
1167 smp = ((ALshort*)src)[i/2+0];
1168 dst[i+2] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1169 smp = ((ALshort*)src)[i/2+1];
1170 dst[i+3] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1172 break;
1174 case 4:
1175 for(i = 0;i < len;i+=4)
1177 dst[i+0] = 0;
1178 dst[i+1] = 0;
1179 dst[i+2] = ((ALfloat*)src)[i/2+0];
1180 dst[i+3] = ((ALfloat*)src)[i/2+1];
1182 break;
1184 default:
1185 assert(0);
1189 static void ConvertDataIMA4(ALfloat *dst, const ALvoid *src, ALint chans, ALsizei len)
1191 const ALubyte *IMAData;
1192 ALint Sample[2],Index[2];
1193 ALuint IMACode[2];
1194 ALsizei i,j,k,c;
1196 if(src == NULL)
1197 return;
1199 IMAData = src;
1200 for(i = 0;i < len;i++)
1202 for(c = 0;c < chans;c++)
1204 Sample[c] = *(IMAData++);
1205 Sample[c] |= *(IMAData++) << 8;
1206 Sample[c] = (Sample[c]^0x8000) - 32768;
1207 Index[c] = *(IMAData++);
1208 Index[c] |= *(IMAData++) << 8;
1209 Index[c] = (Index[c]^0x8000) - 32768;
1211 Index[c] = ((Index[c]<0) ? 0 : Index[c]);
1212 Index[c] = ((Index[c]>88) ? 88 : Index[c]);
1214 dst[i*65*chans + c] = ((Sample[c] < 0) ? (Sample[c]/32768.0f) : (Sample[c]/32767.0f));
1217 for(j = 1;j < 65;j += 8)
1219 for(c = 0;c < chans;c++)
1221 IMACode[c] = *(IMAData++);
1222 IMACode[c] |= *(IMAData++) << 8;
1223 IMACode[c] |= *(IMAData++) << 16;
1224 IMACode[c] |= *(IMAData++) << 24;
1227 for(k = 0;k < 8;k++)
1229 for(c = 0;c < chans;c++)
1231 Sample[c] += ((g_IMAStep_size[Index[c]]*g_IMACodeword_4[IMACode[c]&15])/8);
1232 Index[c] += g_IMAIndex_adjust_4[IMACode[c]&15];
1234 if(Sample[c] < -32768) Sample[c] = -32768;
1235 else if(Sample[c] > 32767) Sample[c] = 32767;
1237 if(Index[c]<0) Index[c] = 0;
1238 else if(Index[c]>88) Index[c] = 88;
1240 dst[(i*65+j+k)*chans + c] = ((Sample[c] < 0) ? (Sample[c]/32768.0f) : (Sample[c]/32767.0f));
1241 IMACode[c] >>= 4;
1248 static void ConvertDataMULaw(ALfloat *dst, const ALvoid *src, ALsizei len)
1250 ALsizei i;
1251 ALint smp;
1252 if(src == NULL)
1253 return;
1254 for(i = 0;i < len;i++)
1256 smp = muLawDecompressionTable[((ALubyte*)src)[i]];
1257 dst[i] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1261 static void ConvertDataMULawRear(ALfloat *dst, const ALvoid *src, ALsizei len)
1263 ALsizei i;
1264 ALint smp;
1265 if(src == NULL)
1266 return;
1267 for(i = 0;i < len;i+=4)
1269 dst[i+0] = 0;
1270 dst[i+1] = 0;
1271 smp = muLawDecompressionTable[((ALubyte*)src)[i/2+0]];
1272 dst[i+2] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1273 smp = muLawDecompressionTable[((ALubyte*)src)[i/2+1]];
1274 dst[i+3] = ((smp < 0) ? (smp/32768.0f) : (smp/32767.0f));
1279 * ReleaseALBuffers()
1281 * INTERNAL FN : Called by DLLMain on exit to destroy any buffers that still exist
1283 ALvoid ReleaseALBuffers(ALCdevice *device)
1285 ALsizei i;
1286 for(i = 0;i < device->BufferMap.size;i++)
1288 ALbuffer *temp = device->BufferMap.array[i].value;
1289 device->BufferMap.array[i].value = NULL;
1291 // Release sample data
1292 free(temp->data);
1294 // Release Buffer structure
1295 ALTHUNK_REMOVEENTRY(temp->buffer);
1296 memset(temp, 0, sizeof(ALbuffer));
1297 free(temp);