annotate audio/EffectWrapper.cpp @ 750:e7c77c366360

Fix #1978 Overload message says auditioning plugin disabled, even if no auditioning plugin present
author Chris Cannam
date Wed, 22 Apr 2020 17:10:52 +0100
parents 54393ed09d65
children
rev   line source
Chris@739 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
Chris@739 2
Chris@739 3 /*
Chris@739 4 Sonic Visualiser
Chris@739 5 An audio file viewer and annotation editor.
Chris@739 6 Centre for Digital Music, Queen Mary, University of London.
Chris@739 7
Chris@739 8 This program is free software; you can redistribute it and/or
Chris@739 9 modify it under the terms of the GNU General Public License as
Chris@739 10 published by the Free Software Foundation; either version 2 of the
Chris@739 11 License, or (at your option) any later version. See the file
Chris@739 12 COPYING included with this distribution for more information.
Chris@739 13 */
Chris@739 14
Chris@739 15 #include "EffectWrapper.h"
Chris@739 16
Chris@739 17 #include <rubberband/RubberBandStretcher.h>
Chris@739 18
Chris@739 19 #include "base/Debug.h"
Chris@739 20
Chris@740 21 //#define DEBUG_EFFECT_WRAPPER 1
Chris@740 22
Chris@739 23 using namespace std;
Chris@739 24
Chris@739 25 static const int DEFAULT_RING_BUFFER_SIZE = 131071;
Chris@739 26
Chris@739 27 EffectWrapper::EffectWrapper(ApplicationPlaybackSource *source) :
Chris@739 28 m_source(source),
Chris@739 29 m_bypassed(false),
Chris@739 30 m_failed(false),
Chris@739 31 m_channelCount(0)
Chris@739 32 {
Chris@739 33 }
Chris@739 34
Chris@739 35 EffectWrapper::~EffectWrapper()
Chris@739 36 {
Chris@739 37 }
Chris@739 38
Chris@739 39 void
Chris@739 40 EffectWrapper::setEffect(weak_ptr<RealTimePluginInstance> effect)
Chris@739 41 {
Chris@739 42 lock_guard<mutex> guard(m_mutex);
Chris@739 43
Chris@740 44 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 45 SVCERR << "EffectWrapper[" << this
Chris@740 46 << "]::setEffect(" << effect.lock() << ")" << endl;
Chris@740 47 #endif
Chris@740 48
Chris@739 49 m_effect = effect;
Chris@739 50 m_failed = false;
Chris@739 51 }
Chris@739 52
Chris@749 53 bool
Chris@749 54 EffectWrapper::haveEffect() const
Chris@749 55 {
Chris@749 56 return m_effect.lock() != nullptr;
Chris@749 57 }
Chris@749 58
Chris@749 59 void
Chris@749 60 EffectWrapper::clearEffect()
Chris@749 61 {
Chris@749 62 m_effect = {};
Chris@749 63 }
Chris@749 64
Chris@739 65 void
Chris@739 66 EffectWrapper::setBypassed(bool bypassed)
Chris@739 67 {
Chris@739 68 lock_guard<mutex> guard(m_mutex);
Chris@739 69
Chris@740 70 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 71 SVCERR << "EffectWrapper[" << this
Chris@740 72 << "]::setBypassed(" << bypassed << ")" << endl;
Chris@740 73 #endif
Chris@740 74
Chris@739 75 m_bypassed = bypassed;
Chris@739 76 }
Chris@739 77
Chris@739 78 bool
Chris@739 79 EffectWrapper::isBypassed() const
Chris@739 80 {
Chris@739 81 lock_guard<mutex> guard(m_mutex);
Chris@739 82
Chris@739 83 return m_bypassed;
Chris@739 84 }
Chris@739 85
Chris@739 86 void
Chris@739 87 EffectWrapper::reset()
Chris@739 88 {
Chris@739 89 lock_guard<mutex> guard(m_mutex);
Chris@739 90
Chris@740 91 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 92 SVCERR << "EffectWrapper[" << this << "]::reset" << endl;
Chris@740 93 #endif
Chris@740 94
Chris@739 95 for (auto &rb: m_effectOutputBuffers) {
Chris@739 96 rb.reset();
Chris@739 97 }
Chris@740 98
Chris@740 99 m_failed = false;
Chris@739 100 }
Chris@739 101
Chris@739 102 int
Chris@739 103 EffectWrapper::getSourceSamples(float *const *samples,
Chris@739 104 int nchannels, int nframes)
Chris@739 105 {
Chris@739 106 lock_guard<mutex> guard(m_mutex);
Chris@739 107
Chris@740 108 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 109 SVCERR << "EffectWrapper[" << this << "]::getSourceSamples: " << nframes
Chris@740 110 << " frames across " << nchannels << " channels" << endl;
Chris@740 111 #endif
Chris@740 112
Chris@739 113 auto effect(m_effect.lock());
Chris@739 114
Chris@740 115 if (!effect) {
Chris@740 116 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 117 SVCERR << "EffectWrapper::getSourceSamples: "
Chris@740 118 << "no effect is set" << endl;
Chris@740 119 #endif
Chris@739 120 return m_source->getSourceSamples(samples, nchannels, nframes);
Chris@739 121 }
Chris@739 122
Chris@740 123 if (m_bypassed || m_failed) {
Chris@740 124 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 125 SVCERR << "EffectWrapper::getSourceSamples: "
Chris@740 126 << "effect is bypassed or has failed" << endl;
Chris@740 127 #endif
Chris@740 128 return m_source->getSourceSamples(samples, nchannels, nframes);
Chris@740 129 }
Chris@740 130
Chris@739 131 static int warnings = 0;
Chris@739 132 if (nchannels != m_channelCount) {
Chris@739 133 if (warnings >= 0) {
Chris@740 134 SVCERR << "WARNING: EffectWrapper::getSourceSamples called for a number of channels different from that set with setSystemPlaybackChannelCount ("
Chris@739 135 << nchannels << " vs " << m_channelCount << ")" << endl;
Chris@739 136 if (++warnings == 6) {
Chris@739 137 SVCERR << "(further warnings will be suppressed)" << endl;
Chris@739 138 warnings = -1;
Chris@739 139 }
Chris@739 140 }
Chris@739 141 return 0;
Chris@739 142 }
Chris@739 143
Chris@739 144 if ((int)effect->getAudioInputCount() != m_channelCount) {
Chris@739 145 if (!m_failed) {
Chris@739 146 SVCERR << "EffectWrapper::getSourceSamples: "
Chris@739 147 << "Can't run plugin: plugin input count "
Chris@739 148 << effect->getAudioInputCount()
Chris@739 149 << " != our channel count " << m_channelCount
Chris@739 150 << " (future errors for this plugin will be suppressed)"
Chris@739 151 << endl;
Chris@739 152 m_failed = true;
Chris@739 153 }
Chris@739 154 }
Chris@739 155 if ((int)effect->getAudioOutputCount() != m_channelCount) {
Chris@739 156 if (!m_failed) {
Chris@739 157 SVCERR << "EffectWrapper::getSourceSamples: "
Chris@739 158 << "Can't run plugin: plugin output count "
Chris@739 159 << effect->getAudioOutputCount()
Chris@739 160 << " != our channel count " << m_channelCount
Chris@739 161 << " (future errors for this plugin will be suppressed)"
Chris@739 162 << endl;
Chris@739 163 m_failed = true;
Chris@739 164 }
Chris@739 165 }
Chris@739 166
Chris@739 167 if (m_failed) {
Chris@739 168 return m_source->getSourceSamples(samples, nchannels, nframes);
Chris@739 169 }
Chris@739 170
Chris@739 171 float **ib = effect->getAudioInputBuffers();
Chris@739 172 float **ob = effect->getAudioOutputBuffers();
Chris@739 173 int blockSize = effect->getBufferSize();
Chris@739 174
Chris@739 175 int got = 0;
Chris@739 176
Chris@739 177 while (got < nframes) {
Chris@739 178
Chris@739 179 int read = 0;
Chris@739 180 for (int c = 0; c < nchannels; ++c) {
Chris@740 181 read = m_effectOutputBuffers[c].read(samples[c] + got,
Chris@740 182 nframes - got);
Chris@739 183 }
Chris@739 184
Chris@739 185 got += read;
Chris@739 186
Chris@739 187 if (got < nframes) {
Chris@739 188
Chris@739 189 int toRun = m_source->getSourceSamples(ib, nchannels, blockSize);
Chris@739 190 if (toRun <= 0) break;
Chris@739 191
Chris@740 192 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 193 SVCERR << "EffectWrapper::getSourceSamples: Running effect "
Chris@740 194 << "for " << toRun << " frames" << endl;
Chris@740 195 #endif
Chris@739 196 effect->run(Vamp::RealTime::zeroTime, toRun);
Chris@739 197
Chris@739 198 for (int c = 0; c < nchannels; ++c) {
Chris@739 199 m_effectOutputBuffers[c].write(ob[c], toRun);
Chris@739 200 }
Chris@739 201 }
Chris@739 202 }
Chris@739 203
Chris@739 204 return got;
Chris@739 205 }
Chris@739 206
Chris@739 207 void
Chris@739 208 EffectWrapper::setSystemPlaybackChannelCount(int count)
Chris@739 209 {
Chris@739 210 {
Chris@739 211 lock_guard<mutex> guard(m_mutex);
Chris@740 212 #ifdef DEBUG_EFFECT_WRAPPER
Chris@740 213 SVCERR << "EffectWrapper[" << this
Chris@740 214 << "]::setSystemPlaybackChannelCount(" << count << ")" << endl;
Chris@740 215 #endif
Chris@739 216 m_effectOutputBuffers.resize
Chris@739 217 (count, RingBuffer<float>(DEFAULT_RING_BUFFER_SIZE));
Chris@739 218 m_channelCount = count;
Chris@739 219 }
Chris@739 220 m_source->setSystemPlaybackChannelCount(count);
Chris@739 221 }
Chris@739 222
Chris@739 223 void
Chris@739 224 EffectWrapper::setSystemPlaybackSampleRate(int rate)
Chris@739 225 {
Chris@739 226 m_source->setSystemPlaybackSampleRate(rate);
Chris@739 227 }
Chris@739 228
Chris@739 229 std::string
Chris@739 230 EffectWrapper::getClientName() const
Chris@739 231 {
Chris@739 232 return m_source->getClientName();
Chris@739 233 }
Chris@739 234
Chris@739 235 int
Chris@739 236 EffectWrapper::getApplicationSampleRate() const
Chris@739 237 {
Chris@739 238 return m_source->getApplicationSampleRate();
Chris@739 239 }
Chris@739 240
Chris@739 241 int
Chris@739 242 EffectWrapper::getApplicationChannelCount() const
Chris@739 243 {
Chris@739 244 return m_source->getApplicationChannelCount();
Chris@739 245 }
Chris@739 246
Chris@739 247 void
Chris@739 248 EffectWrapper::setSystemPlaybackBlockSize(int sz)
Chris@739 249 {
Chris@739 250 SVDEBUG << "NOTE: EffectWrapper::setSystemPlaybackBlockSize called "
Chris@739 251 << "with size = " << sz << "; not passing to wrapped source, as "
Chris@739 252 << "actual block size will vary" << endl;
Chris@739 253 }
Chris@739 254
Chris@739 255 void
Chris@739 256 EffectWrapper::setSystemPlaybackLatency(int latency)
Chris@739 257 {
Chris@739 258 m_source->setSystemPlaybackLatency(latency);
Chris@739 259 }
Chris@739 260
Chris@739 261 void
Chris@739 262 EffectWrapper::setOutputLevels(float left, float right)
Chris@739 263 {
Chris@739 264 m_source->setOutputLevels(left, right);
Chris@739 265 }
Chris@739 266
Chris@739 267 void
Chris@739 268 EffectWrapper::audioProcessingOverload()
Chris@739 269 {
Chris@739 270 m_source->audioProcessingOverload();
Chris@739 271 }