This prevents animated textures that are still a valid size from stop animating. Off screen textures will stop so if turned fast, there may be a slight stutter until the face's virtual size has been updated.
The mac audio device manager was being "helpful" by restarting
playout and recording if the Default device was changed, assuming
the application wouldn't care.
However, we received an update of device change, and attempted to
stop and start playout anyway, causing a conflict.
The fix was simply to not deploy new devices when the device id didn't
change.
Changed iWebRTCUpdateDevices and iAudioDeviceMutex to gWebRTCUpdateDevicesand gAudioDeviceMutex to follow Firestorm coding standards.
They are global static variables.
Added three FMOD specific changes based upon reading the FMOD manual.
See: https://www.fmod.com/docs/2.00/api/platforms-win.html
As well, switched to using the FMOD log version of the library and found one error on the get advanced features.
Also, the call back method should be a static method. Just being cautious.
As with the previous change, this is to address the issue FIRE-36022 where users who remove their USB headsets with microphones are having the viewer lock up.
This introduces a new inline mutex called iAudioDeviceMutex. This is stored in a shared header file located on llcommon. iAudioDeviceMutex is a timed_mutex which allows for a time limit to be placed on a wait for a lock. Once the time runs out or the lock is achiveved the code moves on. With a check after the lock, if the owner is the current thread, then the lock was successful, otherwise it's still being used by another thread and the function should exit to try again later on.
This logic is wrapping WebRTC, FMOD and Vinvox calls to the audio hardware by the Viewer. OpenAL does not currently support changing of audio hardware and always defaults to the default audio hardware.
Added exceptions handling for the new unique_lock with the timed_mutex as they can throw 2 exceptions if the thread is already locked by the current thread and if the mutex is invalid.
Further testing may reveal other areas which would need the timed_mutex added to protect from threads locking up.
This is created to address the issue of USB headsets being removed or Bluetooth headsets with bad connections causing the viewer to lock up.
First Part: WebRTC
WebRTC now has an added inline atomic bool used to track when the worker thread is accessing the audio hardware. If the coroutine that is always running detects 10 consecutive true flag values, it will set WebRTC to exit and exit itself.
This coroutine was what was locking up the viewer as it spammed the mMainQueue with messages every update, but the worker thread was locked up and unable to receive the messages. Once the queue reached 1024 messages, it would lock up.
Underlying issue is the Windows Core Audio driver system crashes if too many threads have requests to get audio updates upon hardware changes. And with a USB headset having 2 devices in 1, it multiples the updates by 2x. The WebRTC audio system itself locks a mutex as it calls the core audio system to get set the input, but if it is already being processed by another thread, it then gets an exception to try again. The audio driver is not handling the message and crashes and does not return leaving the WebRTC worker thread locked.
Commented out a block of new code recently added which was also being called by one of the callback functions.
This had the side effect of having 2 LLWebRTCDevicesObserver listening to the hardware removal events and cause both to trigger events at the same time, which may be the source of the queue being locked up in a race condition.
Was able to reproduce issue 2x without code change by moving mouse around a lot while on rezing and then pulling USB headset out of the USB port. Direct motherboard USB port seemed to work the best as could not trigger while headset was in USB hub.