#pragma once #include #include #include #include #include "preferences/usersettings.h" #include "engine/sidechain/sidechainworker.h" #include "soundio/soundmanagerutil.h" #include "util/fifo.h" #include "util/mutex.h" #include "util/types.h" class EngineSideChain : public QThread, public AudioDestination { Q_OBJECT public: EngineSideChain(UserSettingsPointer pConfig, CSAMPLE* sidechainMix); ~EngineSideChain() override; // Not thread-safe, wait-free. Submit buffer of samples to the sidechain for // processing. Should only be called from a single writer thread (typically // the engine callback). void writeSamples(const CSAMPLE* pBuffer, int iFrames); // Thin wrapper around writeSamples that is used by SoundManager when receiving // from a sound card input instead of the engine void receiveBuffer(const AudioInput& input, const CSAMPLE* pBuffer, unsigned int iFrames) override; // Thread-safe, blocking. void addSideChainWorker(SideChainWorker* pWorker); static const int SIDECHAIN_BUFFER_SIZE = 65536; private: void run() override; UserSettingsPointer m_pConfig; // Indicates that the thread should exit. volatile bool m_bStopThread; FIFO m_sampleFifo; CSAMPLE* m_pWorkBuffer; CSAMPLE* m_pSidechainMix; // Provides thread safety around the wait condition below. QMutex m_waitLock; // Allows sleeping until we have samples to process. QWaitCondition m_waitForSamples; // Sidechain workers registered with EngineSideChain. MMutex m_workerLock; QList m_workers GUARDED_BY(m_workerLock); };