Pergunta

In my app, I'm typically using 5 buffers and 5 sources, but it varies up and down some. Everything works fine from the beginning, but after some time there seems to be some type of resource leak, so fewer and fewer sounds are played. After about 15 minutes of running, all sounds are gone. I’ve searched for a bug in my code for a couple of days, and I’m guessing the resource leak is elsewhere. Pseudo:

    context = alcCreateContext(device, attributes);
    alcMakeContextCurrent(context);
    alutInitWithoutContext(0, 0);
    ...
10: buffer = alutCreateBufferFromFileImage(data, len);
    ...
    alGenSources(1, &sid);
    alSourcei(sid, AL_SOURCE_RELATIVE, AL_FALSE);
    alSourcef(sid, AL_ROLLOFF_FACTOR, 0.2f);
    alSourcei(sid, AL_BUFFER, buffer);
    ...
    alSourceStop(sid);
    ...
    alDeleteSources(1, &sid);
    alDeleteBuffers(1, &buffer);
    ...
    goto 10

After each call I’m checking for OpenAL errors, but none are ever reported. I’ve also tried adding suspend/resume code when moving the app to/from background, like so:

// -> background
alcMakeContextCurrent(0);
alcSuspendContext(context);
// -> foreground
alcMakeContextCurrent(context);
alcProcessContext(context);

But that doesn’t have any noticeable effect (when I push application to background, then pull it back up again). The bug is the same on iPad2 with a recent iOS version as on iPhone3GS running an old iOS version. What to do, what to do?

Edit: In debug build I'm getting -1 returned from alSourcePlay(sid=5260). For one, -1 is not one of the valid return codes as far as I can tell. Some old implementation seems to define AL_INVALID as -1. Disregarding that, depending on the implementation, if the sid from alGenSources() is recycled when doing alDeleteSources(), 5260 is very high. Does anybody know if the sample ID is recycled when deleting, or is it just a counter?

Foi útil?

Solução

I found no way to fix this, it seems to be a resource leak within the OpenAL implementation on iOS. My way to circumvent is to shutdown and reinitialize OpenAL, which worked pretty ok with some glitches, but the alternative is far worse. Repair code:

if OpenALIrreparableLeakState:
    for sound in resources_of_type("sound"):
        sound.release()
    openal.shutdown()
    openal.initialize()
    for sound in resources_of_type("sound"):
        sound.load()
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top