Browse Source

Fixed some data races in the CoreAudio audio device

tags/2021-05-28
Tom Poole 8 years ago
parent
commit
ceb0afd861
4 changed files with 29 additions and 17 deletions
  1. +24
    -12
      modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp
  2. +1
    -1
      modules/juce_audio_plugin_client/Standalone/juce_StandaloneFilterWindow.h
  3. +2
    -2
      modules/juce_core/threads/juce_Thread.cpp
  4. +2
    -2
      modules/juce_core/threads/juce_Thread.h

+ 24
- 12
modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp View File

@@ -1292,8 +1292,11 @@ public:
}
fifos.setSize (chanIndex, fifoSize);
fifoReadPointers = fifos.getArrayOfReadPointers();
fifoWritePointers = fifos.getArrayOfWritePointers();
fifos.clear();
startThread (9);
threadInitialised.wait();
return {};
}
@@ -1401,6 +1404,9 @@ private:
bool active = false;
String lastError;
AudioBuffer<float> fifos;
const float** fifoReadPointers = nullptr;
float** fifoWritePointers = nullptr;
WaitableEvent threadInitialised;
void run() override
{
@@ -1428,6 +1434,8 @@ private:
jassert (numInputChans + numOutputChans == buffer.getNumChannels());
threadInitialised.signal();
while (! threadShouldExit())
{
readInput (buffer, numSamples, blockSizeMs);
@@ -1679,7 +1687,7 @@ private:
{
auto index = inputIndex + i;
auto dest = destBuffer.getWritePointer (index);
auto src = owner.fifos.getReadPointer (index);
auto src = owner.fifoReadPointers[index];
if (size1 > 0) FloatVectorOperations::copy (dest, src + start1, size1);
if (size2 > 0) FloatVectorOperations::copy (dest + size1, src + start2, size2);
@@ -1704,7 +1712,7 @@ private:
for (int i = 0; i < numOutputChans; ++i)
{
auto index = outputIndex + i;
auto dest = owner.fifos.getWritePointer (index);
auto dest = owner.fifoWritePointers[index];
auto src = srcBuffer.getReadPointer (index);
if (size1 > 0) FloatVectorOperations::copy (dest + start1, src, size1);
@@ -1718,8 +1726,6 @@ private:
float** outputChannelData, int numOutputChannels,
int numSamples) override
{
auto& buf = owner.fifos;
if (numInputChannels > 0)
{
int start1, size1, start2, size2;
@@ -1733,19 +1739,22 @@ private:
for (int i = 0; i < numInputChannels; ++i)
{
auto dest = buf.getWritePointer (inputIndex + i);
auto dest = owner.fifoWritePointers[inputIndex + i];
auto src = inputChannelData[i];
if (size1 > 0) FloatVectorOperations::copy (dest + start1, src, size1);
if (size2 > 0) FloatVectorOperations::copy (dest + start2, src + size1, size2);
}
inputFifo.finishedWrite (size1 + size2);
auto totalSize = size1 + size2;
inputFifo.finishedWrite (totalSize);
if (numSamples > size1 + size2)
if (numSamples > totalSize)
{
auto samplesRemaining = numSamples - totalSize;
for (int i = 0; i < numInputChans; ++i)
buf.clear (inputIndex + i, size1 + size2, numSamples - (size1 + size2));
FloatVectorOperations::clear (owner.fifoWritePointers[inputIndex + i] + totalSize, samplesRemaining);
owner.underrun();
}
@@ -1765,18 +1774,21 @@ private:
for (int i = 0; i < numOutputChannels; ++i)
{
auto dest = outputChannelData[i];
auto src = buf.getReadPointer (outputIndex + i);
auto src = owner.fifoReadPointers[outputIndex + i];
if (size1 > 0) FloatVectorOperations::copy (dest, src + start1, size1);
if (size2 > 0) FloatVectorOperations::copy (dest + size1, src + start2, size2);
}
outputFifo.finishedRead (size1 + size2);
auto totalSize = size1 + size2;
outputFifo.finishedRead (totalSize);
if (numSamples > size1 + size2)
if (numSamples > totalSize)
{
auto samplesRemaining = numSamples - totalSize;
for (int i = 0; i < numOutputChannels; ++i)
FloatVectorOperations::clear (outputChannelData[i] + (size1 + size2), numSamples - (size1 + size2));
FloatVectorOperations::clear (outputChannelData[i] + totalSize, samplesRemaining);
owner.underrun();
}


+ 1
- 1
modules/juce_audio_plugin_client/Standalone/juce_StandaloneFilterWindow.h View File

@@ -295,7 +295,7 @@ public:
if (settings != nullptr)
{
savedState = settings->getXmlValue ("audioSetup");
savedState = settings->getXmlValue ("audioSetup");
#if ! (JUCE_IOS || JUCE_ANDROID)
shouldMuteInput.setValue (settings->getBoolValue ("shouldMuteInput", true));


+ 2
- 2
modules/juce_core/threads/juce_Thread.cpp View File

@@ -123,7 +123,7 @@ void Thread::startThread()
{
const ScopedLock sl (startStopLock);
shouldExit = false;
shouldExit = 0;
if (threadHandle.get() == nullptr)
{
@@ -170,7 +170,7 @@ Thread* JUCE_CALLTYPE Thread::getCurrentThread()
//==============================================================================
void Thread::signalThreadShouldExit()
{
shouldExit = true;
shouldExit = 1;
listeners.call ([] (Listener& l) { l.exitSignalSent(); });
}


+ 2
- 2
modules/juce_core/threads/juce_Thread.h View File

@@ -153,7 +153,7 @@ public:
@see signalThreadShouldExit, currentThreadShouldExit
*/
bool threadShouldExit() const { return shouldExit; }
bool threadShouldExit() const { return shouldExit.get() != 0; }
/** Checks whether the current thread has been told to stop running.
On the message thread, this will always return false, otherwise
@@ -333,7 +333,7 @@ private:
size_t threadStackSize;
uint32 affinityMask = 0;
bool deleteOnThreadEnd = false;
bool volatile shouldExit = false;
Atomic<int32> shouldExit { 0 };
ListenerList<Listener, Array<Listener*, CriticalSection>> listeners;
#if JUCE_ANDROID


Loading…
Cancel
Save