diff options
-rw-r--r-- | Alc/ALc.c | 15 | ||||
-rw-r--r-- | Alc/ALu.c | 32 | ||||
-rw-r--r-- | OpenAL32/Include/alMain.h | 4 | ||||
-rw-r--r-- | OpenAL32/alSource.c | 45 |
4 files changed, 82 insertions, 14 deletions
@@ -892,6 +892,7 @@ static ALvoid InitContext(ALCcontext *pContext) //Validate pContext pContext->LastError = AL_NO_ERROR; pContext->Suspended = AL_FALSE; + pContext->ActiveSourceCount = 0; InitUIntMap(&pContext->SourceMap); //Set globals @@ -1613,8 +1614,15 @@ ALC_API ALCcontext* ALC_APIENTRY alcCreateContext(ALCdevice *device, const ALCin device->Contexts = temp; ALContext = calloc(1, sizeof(ALCcontext)); - if(!ALContext) + if(ALContext) { + ALContext->MaxActiveSources = 256; + ALContext->ActiveSources = malloc(sizeof(*ALContext->ActiveSources) * + ALContext->MaxActiveSources); + } + if(!ALContext || !ALContext->ActiveSources) + { + free(ALContext); alcSetError(device, ALC_OUT_OF_MEMORY); ProcessContext(NULL); return NULL; @@ -1693,6 +1701,11 @@ ALC_API ALCvoid ALC_APIENTRY alcDestroyContext(ALCcontext *context) } ResetUIntMap(&context->EffectSlotMap); + free(context->ActiveSources); + context->ActiveSources = NULL; + context->MaxActiveSources = 0; + context->ActiveSourceCount = 0; + list = &g_pContextList; while(*list != context) list = &(*list)->next; @@ -939,23 +939,27 @@ static void MixSomeSources(ALCcontext *ALContext, float (*DryBuffer)[OUTPUTCHANN ALenum State; ALsizei pos; - if(ALContext->SourceMap.size <= 0) - return; - DuplicateStereo = ALContext->Device->DuplicateStereo; DeviceFreq = ALContext->Device->Frequency; rampLength = DeviceFreq * MIN_RAMP_LENGTH / 1000; rampLength = max(rampLength, SamplesToDo); - pos = ALContext->SourceMap.size; + pos = 0; next_source: - do { - if(pos-- <= 0) - return; - ALSource = ALContext->SourceMap.array[pos].value; - } while(ALSource->state != AL_PLAYING); - j = 0; + while(ALContext->ActiveSourceCount > pos) + { + ALsizei end; + + ALSource = ALContext->ActiveSources[pos]; + if(ALSource->state == AL_PLAYING) + break; + + end = --(ALContext->ActiveSourceCount); + ALContext->ActiveSources[pos] = ALContext->ActiveSources[end]; + } + if(pos >= ALContext->ActiveSourceCount) + return; /* Find buffer format */ Frequency = 0; @@ -1028,8 +1032,8 @@ next_source: for(i = 0;i < BuffersPlayed && BufferListItem;i++) BufferListItem = BufferListItem->next; - while(State == AL_PLAYING && j < SamplesToDo) - { + j = 0; + do { ALfloat *Data = NULL; ALuint LoopStart = 0; ALuint LoopEnd = 0; @@ -1397,7 +1401,7 @@ next_source: DataPosFrac = 0; } } - } + } while(State == AL_PLAYING && j < SamplesToDo); /* Update source info */ ALSource->state = State; @@ -1413,6 +1417,8 @@ next_source: ALSource->FirstStart = AL_FALSE; + if(ALSource->state == AL_PLAYING) + pos++; goto next_source; } diff --git a/OpenAL32/Include/alMain.h b/OpenAL32/Include/alMain.h index afc94da2..4d963563 100644 --- a/OpenAL32/Include/alMain.h +++ b/OpenAL32/Include/alMain.h @@ -433,6 +433,10 @@ struct ALCcontext_struct ALfloat DopplerVelocity; ALfloat flSpeedOfSound; + struct ALsource **ActiveSources; + ALsizei ActiveSourceCount; + ALsizei MaxActiveSources; + ALCdevice *Device; const ALCchar *ExtensionList; diff --git a/OpenAL32/alSource.c b/OpenAL32/alSource.c index d470f027..5d7ceced 100644 --- a/OpenAL32/alSource.c +++ b/OpenAL32/alSource.c @@ -145,6 +145,16 @@ AL_API ALvoid AL_APIENTRY alDeleteSources(ALsizei n, const ALuint *sources) // Recheck that the Source is valid, because there could be duplicated Source names if((Source=LookupSource(Context->SourceMap, sources[i])) != NULL) { + for(j = 0;j < Context->ActiveSourceCount;j++) + { + if(Context->ActiveSources[j] == Source) + { + ALsizei end = --(Context->ActiveSourceCount); + Context->ActiveSources[j] = Context->ActiveSources[end]; + break; + } + } + // For each buffer in the source's queue, decrement its reference counter and remove it while(Source->queue != NULL) { @@ -1310,6 +1320,31 @@ AL_API ALvoid AL_APIENTRY alSourcePlayv(ALsizei n, const ALuint *sources) } } + if(Context->ActiveSourceCount+n < n) + { + alSetError(Context, AL_OUT_OF_MEMORY); + goto done; + } + + while(Context->MaxActiveSources < Context->ActiveSourceCount+n) + { + void *temp = NULL; + ALsizei newcount; + + newcount = Context->MaxActiveSources << 1; + if(newcount > 0) + temp = realloc(Context->ActiveSources, + sizeof(*Context->ActiveSources) * newcount); + if(!temp) + { + alSetError(Context, AL_OUT_OF_MEMORY); + goto done; + } + + Context->ActiveSources = temp; + Context->MaxActiveSources = newcount; + } + for(i = 0;i < n;i++) { Source = (ALsource*)ALTHUNK_LOOKUPENTRY(sources[i]); @@ -1364,6 +1399,16 @@ AL_API ALvoid AL_APIENTRY alSourcePlayv(ALsizei n, const ALuint *sources) Source->position = 0; Source->position_fraction = 0; } + else + { + for(j = 0;j < Context->ActiveSourceCount;j++) + { + if(Context->ActiveSources[j] == Source) + break; + } + if(j == Context->ActiveSourceCount) + Context->ActiveSources[Context->ActiveSourceCount++] = Source; + } } done: |