[Openal-devel] ALC_ENUMERATE_ALL_EXT and pluggable sound devices
Chris Robinson
chris.kcat at gmail.com
Fri Sep 18 16:41:56 PDT 2009
On Friday 18 September 2009 11:28:49 am Guilherme Balena Versiani wrote:
> Stefanos A. wrote:
> > Besides, why allocate a new string every 5 seconds when you could just
> > say:
> >
> > if (alcGetBoolean(NULL, ALC_DEVICE_LIST_CHANGED))
> > {
> > // retrieve device list
> > }
> >
> > ?
A problem may be in situations where the implementation can't properly
retrieve messages from the OS/sound API about device changes. In such cases,
even getting a boolean about device changes may incur a reprobing of devices
anyway. Sure, you may save on not having to pass the string back to the
program, but I think that's comparatively minor compared to the work already
done.
> 2) Ryan solution ( new memory allocated on the return of
> alcGetString function ): you will broke the behavior of the function, so
> old code implementations will start to leak memory after this change.
The string(s) returned by alcGetString/alGetString are controlled by OpenAL.
When OpenAL frees that memory, it's gone.. the app doesn't need to do anything
to it. And apparently it's already not guaranteed that successive calls to
retrieve the device list will return the same memory.
For languages with GC, I don't see why it wouldn't catch the references to the
old strings being lost when a new set is allocated and given to the app,
initiating a background cleanup of them.
FWIW, I don't think it's that bad of an idea to just retrieve the list every
few seconds. If the cost of alcGetString(NULL, ALC_ALL_DEVICES_SPECIFIER) is
too high, then can't you run it in a background thread? Something like:
volatile bool ListUpdated = false;
thread 1:
...app loop...
if(ListUpdated) {
lock(&device_update_mutex);
copy_strings(MyInternalList, StringsFromAL);
ListUpdated = false;
unlock(&device_update_mutex);
ListUpdated();
}
...end...
thread 2:
while(!KillMeNow) {
lock(&device_update_mutex);
StringsFromAL = alcGetString(NULL, ALC_ALL_DEVICES_SPECIFIER);
ListUpdated = true;
unlock(&device_update_mutex);
Sleep(1000);
}
Then all the reprobing and extra allocation/conversation necessary will happen
away from your main loop, so it should continue on at full speed. The cost to
your main loop would be every second or so just having a copy and whatever
updating you need to do to have the new internal list used.
Additionally, if you wanted, thread 2 could do a compare between the new
strings from AL against MyInternalList, and only mark ListUpdated if they
differ. Then your main loop wouldn't incur any cost unless the devices
actually changed.
More information about the Openal-devel
mailing list