Browse Source

Improved CoreAudio handling of USB audio devices being unplugged

tags/2021-05-28
jules 9 years ago
parent
commit
076896d33b
1 changed files with 58 additions and 38 deletions
  1. +58
    -38
      modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp

+ 58
- 38
modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp View File

@@ -388,65 +388,84 @@ public:
return 0;
}
void updateDetailsFromDevice()
int getFrameSizeFromDevice() const
{
stopTimer();
AudioObjectPropertyAddress pa;
pa.mScope = kAudioObjectPropertyScopeWildcard;
pa.mElement = kAudioObjectPropertyElementMaster;
pa.mSelector = kAudioDevicePropertyBufferFrameSize;
if (deviceID == 0)
return;
UInt32 framesPerBuf = (UInt32) bufferSize;
UInt32 size = sizeof (framesPerBuf);
AudioObjectGetPropertyData (deviceID, &pa, 0, nullptr, &size, &framesPerBuf);
return (int) framesPerBuf;
}
// this collects all the new details from the device without any locking, then
// locks + swaps them afterwards.
bool isDeviceAlive() const
{
AudioObjectPropertyAddress pa;
pa.mScope = kAudioObjectPropertyScopeWildcard;
pa.mElement = kAudioObjectPropertyElementMaster;
pa.mSelector = kAudioDevicePropertyDeviceIsAlive;
UInt32 isAlive;
UInt32 isAlive = 0;
UInt32 size = sizeof (isAlive);
pa.mSelector = kAudioDevicePropertyDeviceIsAlive;
if (OK (AudioObjectGetPropertyData (deviceID, &pa, 0, nullptr, &size, &isAlive)) && isAlive == 0)
return;
return deviceID != 0
&& OK (AudioObjectGetPropertyData (deviceID, &pa, 0, nullptr, &size, &isAlive))
&& isAlive != 0;
}
bool updateDetailsFromDevice()
{
stopTimer();
const double currentRate = getNominalSampleRate();
if (currentRate > 0)
sampleRate = currentRate;
if (! isDeviceAlive())
return false;
UInt32 framesPerBuf = (UInt32) bufferSize;
size = sizeof (framesPerBuf);
pa.mSelector = kAudioDevicePropertyBufferFrameSize;
AudioObjectGetPropertyData (deviceID, &pa, 0, nullptr, &size, &framesPerBuf);
// this collects all the new details from the device without any locking, then
// locks + swaps them afterwards.
Array<int> newBufferSizes (getBufferSizesFromDevice());
Array<double> newSampleRates (getSampleRatesFromDevice());
const double newSampleRate = getNominalSampleRate();
const int newBufferSize = getFrameSizeFromDevice();
inputLatency = getLatencyFromDevice (kAudioDevicePropertyScopeInput);
outputLatency = getLatencyFromDevice (kAudioDevicePropertyScopeOutput);
Array<int> newBufferSizes = getBufferSizesFromDevice();
Array<double> newSampleRates = getSampleRatesFromDevice();
const int newInputLatency = getLatencyFromDevice (kAudioDevicePropertyScopeInput);
const int newOutputLatency = getLatencyFromDevice (kAudioDevicePropertyScopeOutput);
Array<CallbackDetailsForChannel> newInChans, newOutChans;
StringArray newInNames (getChannelInfo (true, newInChans));
StringArray newOutNames (getChannelInfo (false, newOutChans));
const int inputBitDepth = getBitDepthFromDevice (kAudioDevicePropertyScopeInput);
const int outputBitDepth = getBitDepthFromDevice (kAudioDevicePropertyScopeOutput);
const int newBitDepth = jmax (getBitDepthFromDevice (kAudioDevicePropertyScopeInput),
getBitDepthFromDevice (kAudioDevicePropertyScopeOutput));
{
const ScopedLock sl (callbackLock);
bitDepth = jmax (inputBitDepth, outputBitDepth);
if (bitDepth <= 0)
bitDepth = 32;
bitDepth = newBitDepth > 0 ? newBitDepth : 32;
// after getting the new values, lock + apply them
const ScopedLock sl (callbackLock);
if (newSampleRate > 0)
sampleRate = newSampleRate;
bufferSize = (int) framesPerBuf;
allocateTempBuffers();
inputLatency = newInputLatency;
outputLatency = newOutputLatency;
bufferSize = newBufferSize;
sampleRates.swapWith (newSampleRates);
bufferSizes.swapWith (newBufferSizes);
sampleRates.swapWith (newSampleRates);
bufferSizes.swapWith (newBufferSizes);
inChanNames.swapWith (newInNames);
outChanNames.swapWith (newOutNames);
inChanNames.swapWith (newInNames);
outChanNames.swapWith (newOutNames);
inputChannelInfo.swapWith (newInChans);
outputChannelInfo.swapWith (newOutChans);
inputChannelInfo.swapWith (newInChans);
outputChannelInfo.swapWith (newOutChans);
allocateTempBuffers();
}
return true;
}
//==============================================================================
@@ -769,9 +788,10 @@ public:
stopTimer();
const double oldSampleRate = sampleRate;
const int oldBufferSize = bufferSize;
updateDetailsFromDevice();
if (oldBufferSize != bufferSize || oldSampleRate != sampleRate)
if (! updateDetailsFromDevice())
owner.stop();
else if (oldBufferSize != bufferSize || oldSampleRate != sampleRate)
owner.restart();
}


Loading…
Cancel
Save