Browse Source

Create buffer for vst audio out, fixes dry/wet (inline processing)

Closes #834

Signed-off-by: falkTX <falktx@falktx.com>
tags/v2.1-alpha2
falkTX 6 years ago
parent
commit
5583ba1546
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
2 changed files with 68 additions and 20 deletions
  1. +2
    -0
      source/backend/plugin/CarlaPluginLV2.cpp
  2. +66
    -20
      source/backend/plugin/CarlaPluginVST2.cpp

+ 2
- 0
source/backend/plugin/CarlaPluginLV2.cpp View File

@@ -3902,10 +3902,12 @@ public:
if (pData->audioIn.count > 0) if (pData->audioIn.count > 0)
{ {
CARLA_SAFE_ASSERT_RETURN(audioIn != nullptr, false); CARLA_SAFE_ASSERT_RETURN(audioIn != nullptr, false);
CARLA_SAFE_ASSERT_RETURN(fAudioInBuffers != nullptr, false);
} }
if (pData->audioOut.count > 0) if (pData->audioOut.count > 0)
{ {
CARLA_SAFE_ASSERT_RETURN(audioOut != nullptr, false); CARLA_SAFE_ASSERT_RETURN(audioOut != nullptr, false);
CARLA_SAFE_ASSERT_RETURN(fAudioOutBuffers != nullptr, false);
} }
if (pData->cvIn.count > 0) if (pData->cvIn.count > 0)
{ {


+ 66
- 20
source/backend/plugin/CarlaPluginVST2.cpp View File

@@ -87,6 +87,7 @@ public:
#endif #endif
fFirstActive(true), fFirstActive(true),
fBufferSize(engine->getBufferSize()), fBufferSize(engine->getBufferSize()),
fAudioOutBuffers(nullptr),
fLastTimeInfo(), fLastTimeInfo(),
fEvents(), fEvents(),
fUI(), fUI(),
@@ -639,7 +640,11 @@ public:
if (aOuts > 0) if (aOuts > 0)
{ {
pData->audioOut.createNew(aOuts); pData->audioOut.createNew(aOuts);
fAudioOutBuffers = new float*[aOuts];
needsCtrlIn = true; needsCtrlIn = true;

for (uint32_t i=0; i < aOuts; ++i)
fAudioOutBuffers[i] = nullptr;
} }


if (params > 0) if (params > 0)
@@ -942,7 +947,7 @@ public:
#endif #endif
} }


//bufferSizeChanged(pData->engine->getBufferSize());
bufferSizeChanged(pData->engine->getBufferSize());
reloadPrograms(true); reloadPrograms(true);


if (pData->active) if (pData->active)
@@ -1595,6 +1600,7 @@ public:
if (pData->audioOut.count > 0) if (pData->audioOut.count > 0)
{ {
CARLA_SAFE_ASSERT_RETURN(outBuffer != nullptr, false); CARLA_SAFE_ASSERT_RETURN(outBuffer != nullptr, false);
CARLA_SAFE_ASSERT_RETURN(fAudioOutBuffers != nullptr, false);
} }


// -------------------------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------------------------
@@ -1622,12 +1628,12 @@ public:
// Set audio buffers // Set audio buffers


float* vstInBuffer[pData->audioIn.count]; float* vstInBuffer[pData->audioIn.count];
float* vstOutBuffer[pData->audioOut.count];


for (uint32_t i=0; i < pData->audioIn.count; ++i) for (uint32_t i=0; i < pData->audioIn.count; ++i)
vstInBuffer[i] = const_cast<float*>(inBuffer[i]+timeOffset); vstInBuffer[i] = const_cast<float*>(inBuffer[i]+timeOffset);

for (uint32_t i=0; i < pData->audioOut.count; ++i) for (uint32_t i=0; i < pData->audioOut.count; ++i)
vstOutBuffer[i] = outBuffer[i]+timeOffset;
carla_zeroFloats(fAudioOutBuffers[i], frames);


// -------------------------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------------------------
// Set MIDI events // Set MIDI events
@@ -1646,15 +1652,18 @@ public:


if (pData->hints & PLUGIN_CAN_PROCESS_REPLACING) if (pData->hints & PLUGIN_CAN_PROCESS_REPLACING)
{ {
fEffect->processReplacing(fEffect, (pData->audioIn.count > 0) ? vstInBuffer : nullptr, (pData->audioOut.count > 0) ? vstOutBuffer : nullptr, static_cast<int32_t>(frames));
fEffect->processReplacing(fEffect,
(pData->audioIn.count > 0) ? vstInBuffer : nullptr,
(pData->audioOut.count > 0) ? fAudioOutBuffers : nullptr,
static_cast<int32_t>(frames));
} }
else else
{ {
for (uint32_t i=0; i < pData->audioOut.count; ++i)
carla_zeroFloats(vstOutBuffer[i], frames);

#if ! VST_FORCE_DEPRECATED #if ! VST_FORCE_DEPRECATED
fEffect->process(fEffect, (pData->audioIn.count > 0) ? vstInBuffer : nullptr, (pData->audioOut.count > 0) ? vstOutBuffer : nullptr, static_cast<int32_t>(frames));
fEffect->process(fEffect,
(pData->audioIn.count > 0) ? vstInBuffer : nullptr,
(pData->audioOut.count > 0) ? fAudioOutBuffers : nullptr,
static_cast<int32_t>(frames));
#endif #endif
} }


@@ -1666,9 +1675,9 @@ public:
// Post-processing (dry/wet, volume and balance) // Post-processing (dry/wet, volume and balance)


{ {
const bool doVolume = (pData->hints & PLUGIN_CAN_VOLUME) != 0 && carla_isNotEqual(pData->postProc.volume, 1.0f);
const bool doDryWet = (pData->hints & PLUGIN_CAN_DRYWET) != 0 && carla_isNotEqual(pData->postProc.dryWet, 1.0f); const bool doDryWet = (pData->hints & PLUGIN_CAN_DRYWET) != 0 && carla_isNotEqual(pData->postProc.dryWet, 1.0f);
const bool doBalance = (pData->hints & PLUGIN_CAN_BALANCE) != 0 && ! (carla_isEqual(pData->postProc.balanceLeft, -1.0f) && carla_isEqual(pData->postProc.balanceRight, 1.0f)); const bool doBalance = (pData->hints & PLUGIN_CAN_BALANCE) != 0 && ! (carla_isEqual(pData->postProc.balanceLeft, -1.0f) && carla_isEqual(pData->postProc.balanceRight, 1.0f));
const bool isMono = (pData->audioIn.count == 1);


bool isPair; bool isPair;
float bufValue, oldBufLeft[doBalance ? frames : 1]; float bufValue, oldBufLeft[doBalance ? frames : 1];
@@ -1678,10 +1687,12 @@ public:
// Dry/Wet // Dry/Wet
if (doDryWet) if (doDryWet)
{ {
const uint32_t c = isMono ? 0 : i;

for (uint32_t k=0; k < frames; ++k) for (uint32_t k=0; k < frames; ++k)
{ {
bufValue = inBuffer[(pData->audioIn.count == 1) ? 0 : i][k+timeOffset];
outBuffer[i][k+timeOffset] = (outBuffer[i][k+timeOffset] * pData->postProc.dryWet) + (bufValue * (1.0f - pData->postProc.dryWet));
bufValue = inBuffer[c][k+timeOffset];
fAudioOutBuffers[i][k] = (fAudioOutBuffers[i][k] * pData->postProc.dryWet) + (bufValue * (1.0f - pData->postProc.dryWet));
} }
} }


@@ -1693,7 +1704,7 @@ public:
if (isPair) if (isPair)
{ {
CARLA_ASSERT(i+1 < pData->audioOut.count); CARLA_ASSERT(i+1 < pData->audioOut.count);
carla_copyFloats(oldBufLeft, outBuffer[i]+timeOffset, frames);
carla_copyFloats(oldBufLeft, fAudioOutBuffers[i], frames);
} }


float balRangeL = (pData->postProc.balanceLeft + 1.0f)/2.0f; float balRangeL = (pData->postProc.balanceLeft + 1.0f)/2.0f;
@@ -1704,27 +1715,32 @@ public:
if (isPair) if (isPair)
{ {
// left // left
outBuffer[i][k+timeOffset] = oldBufLeft[k] * (1.0f - balRangeL);
outBuffer[i][k+timeOffset] += outBuffer[i+1][k+timeOffset] * (1.0f - balRangeR);
fAudioOutBuffers[i][k] = oldBufLeft[k] * (1.0f - balRangeL);
fAudioOutBuffers[i][k] += fAudioOutBuffers[i+1][k] * (1.0f - balRangeR);
} }
else else
{ {
// right // right
outBuffer[i][k+timeOffset] = outBuffer[i][k+timeOffset] * balRangeR;
outBuffer[i][k+timeOffset] += oldBufLeft[k] * balRangeL;
fAudioOutBuffers[i][k] = fAudioOutBuffers[i][k] * balRangeR;
fAudioOutBuffers[i][k] += oldBufLeft[k] * balRangeL;
} }
} }
} }


// Volume
if (doVolume)
// Volume (and buffer copy)
{ {
for (uint32_t k=0; k < frames; ++k) for (uint32_t k=0; k < frames; ++k)
outBuffer[i][k+timeOffset] *= pData->postProc.volume;
outBuffer[i][k+timeOffset] = fAudioOutBuffers[i][k] * pData->postProc.volume;
} }
} }


} // End of Post-processing } // End of Post-processing
#else // BUILD_BRIDGE_ALTERNATIVE_ARCH
for (uint32_t i=0; i < pData->audioOut.count; ++i)
{
for (uint32_t k=0; k < frames; ++k)
outBuffer[i][k+timeOffset] = fAudioOutBuffers[i][k];
}
#endif #endif


// -------------------------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------------------------
@@ -1743,6 +1759,13 @@ public:
if (pData->active) if (pData->active)
deactivate(); deactivate();


for (uint32_t i=0; i < pData->audioOut.count; ++i)
{
if (fAudioOutBuffers[i] != nullptr)
delete[] fAudioOutBuffers[i];
fAudioOutBuffers[i] = new float[newBufferSize];
}

#if ! VST_FORCE_DEPRECATED #if ! VST_FORCE_DEPRECATED
dispatcher(effSetBlockSizeAndSampleRate, 0, static_cast<int32_t>(newBufferSize), nullptr, static_cast<float>(pData->engine->getSampleRate())); dispatcher(effSetBlockSizeAndSampleRate, 0, static_cast<int32_t>(newBufferSize), nullptr, static_cast<float>(pData->engine->getSampleRate()));
#endif #endif
@@ -1772,7 +1795,29 @@ public:
// ------------------------------------------------------------------- // -------------------------------------------------------------------
// Plugin buffers // Plugin buffers


// nothing
void clearBuffers() noexcept override
{
carla_debug("CarlaPluginVST2::clearBuffers() - start");

if (fAudioOutBuffers != nullptr)
{
for (uint32_t i=0; i < pData->audioOut.count; ++i)
{
if (fAudioOutBuffers[i] != nullptr)
{
delete[] fAudioOutBuffers[i];
fAudioOutBuffers[i] = nullptr;
}
}

delete[] fAudioOutBuffers;
fAudioOutBuffers = nullptr;
}

CarlaPlugin::clearBuffers();

carla_debug("CarlaPluginVST2::clearBuffers() - end");
}


// ------------------------------------------------------------------- // -------------------------------------------------------------------
// Post-poned UI Stuff // Post-poned UI Stuff
@@ -2443,6 +2488,7 @@ private:


bool fFirstActive; // first process() call after activate() bool fFirstActive; // first process() call after activate()
uint32_t fBufferSize; uint32_t fBufferSize;
float** fAudioOutBuffers;
EngineTimeInfo fLastTimeInfo; EngineTimeInfo fLastTimeInfo;


struct FixedVstEvents { struct FixedVstEvents {


Loading…
Cancel
Save