Browse Source

clean up + fix deadlock issue

pull/1639/head
bsp2 6 years ago
parent
commit
f6419ed96a
2 changed files with 30 additions and 50 deletions
  1. +8
    -13
      src/engine.cpp
  2. +22
    -37
      src/vst2_main.cpp

+ 8
- 13
src/engine.cpp View File

@@ -124,6 +124,7 @@ static void engineStep() {
} }
} }


#ifndef USE_VST2
static void engineRun() { static void engineRun() {
#ifdef _MSC_VER #ifdef _MSC_VER
// Set CPU to flush-to-zero (FTZ) and denormals-are-zero (DAZ) mode // Set CPU to flush-to-zero (FTZ) and denormals-are-zero (DAZ) mode
@@ -146,7 +147,6 @@ static void engineRun() {
global->engine.vipMutex.wait(); global->engine.vipMutex.wait();


if (!global->gPaused) { if (!global->gPaused) {
// std::lock_guard<std::mutex> lock(global->engine.mutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
for (int i = 0; i < mutexSteps; i++) { for (int i = 0; i < mutexSteps; i++) {
engineStep(); engineStep();
@@ -179,11 +179,11 @@ void engineStop() {
global->engine.running = false; global->engine.running = false;
global->engine.thread.join(); global->engine.thread.join();
} }
#endif // USE_VST2


void engineAddModule(Module *module) { void engineAddModule(Module *module) {
assert(module); assert(module);
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
// Check that the module is not already added // Check that the module is not already added
auto it = std::find(global->gModules.begin(), global->gModules.end(), module); auto it = std::find(global->gModules.begin(), global->gModules.end(), module);
@@ -197,8 +197,7 @@ void engineAddModule(Module *module) {


void engineRemoveModule(Module *module) { void engineRemoveModule(Module *module) {
assert(module); assert(module);
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
// If a param is being smoothed on this module, stop smoothing it immediately // If a param is being smoothed on this module, stop smoothing it immediately
if (module == global->engine.smoothModule) { if (module == global->engine.smoothModule) {
@@ -235,8 +234,7 @@ static void updateActive() {


void engineAddWire(Wire *wire) { void engineAddWire(Wire *wire) {
assert(wire); assert(wire);
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
// Check wire properties // Check wire properties
assert(wire->outputModule); assert(wire->outputModule);
@@ -253,8 +251,7 @@ void engineAddWire(Wire *wire) {


void engineRemoveWire(Wire *wire) { void engineRemoveWire(Wire *wire) {
assert(wire); assert(wire);
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
// Check that the wire is already added // Check that the wire is already added
auto it = std::find(global->gWires.begin(), global->gWires.end(), wire); auto it = std::find(global->gWires.begin(), global->gWires.end(), wire);
@@ -458,8 +455,7 @@ namespace rack {
#endif // USE_VST2 #endif // USE_VST2


void engineSetParamSmooth(Module *module, int paramId, float value) { void engineSetParamSmooth(Module *module, int paramId, float value) {
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
// Since only one param can be smoothed at a time, if another param is currently being smoothed, skip to its final state // Since only one param can be smoothed at a time, if another param is currently being smoothed, skip to its final state
if (global->engine.smoothModule && !(global->engine.smoothModule == module && global->engine.smoothParamId == paramId)) { if (global->engine.smoothModule && !(global->engine.smoothModule == module && global->engine.smoothParamId == paramId)) {
@@ -471,8 +467,7 @@ void engineSetParamSmooth(Module *module, int paramId, float value) {
} }


void engineSetSampleRate(float newSampleRate) { void engineSetSampleRate(float newSampleRate) {
VIPLock vipLock(global->engine.vipMutex);
// std::lock_guard<std::mutex> lock(global->engine.mutex);
// // VIPLock vipLock(global->engine.vipMutex);
std::lock_guard<std::recursive_mutex> lock(global->engine.mutex); std::lock_guard<std::recursive_mutex> lock(global->engine.mutex);
global->engine.sampleRate = newSampleRate; global->engine.sampleRate = newSampleRate;
global->engine.sampleTime = 1.0 / global->engine.sampleRate; global->engine.sampleTime = 1.0 / global->engine.sampleRate;


+ 22
- 37
src/vst2_main.cpp View File

@@ -870,39 +870,27 @@ public:
bool setSampleRate(float _rate, bool _bLock = true) { bool setSampleRate(float _rate, bool _bLock = true) {
bool r = false; bool r = false;


// Dprintf("xxx setSampleRate: 1 bLock=%d\n", _bLock);
// Dprintf("xxx setSampleRate: ENTER bLock=%d\n", _bLock);


if((_rate >= float(MIN_SAMPLE_RATE)) && (_rate <= float(MAX_SAMPLE_RATE))) if((_rate >= float(MIN_SAMPLE_RATE)) && (_rate <= float(MAX_SAMPLE_RATE)))
{ {
// Dprintf("xxx setSampleRate: 2\n");
if(_bLock) if(_bLock)
{ {
// Dprintf("xxx setSampleRate: 2.1\n");
setGlobals(); setGlobals();
// Dprintf("xxx setSampleRate: 2.2\n");
lockAudio(); lockAudio();
// Dprintf("xxx setSampleRate: 2.3\n");
} }


sample_rate = _rate; sample_rate = _rate;


// Dprintf("xxx setSampleRate: 3\n");

vst2_set_samplerate(sample_rate * oversample.factor); // see engine.cpp vst2_set_samplerate(sample_rate * oversample.factor); // see engine.cpp


// Dprintf("xxx setSampleRate: 4\n");

destroyResamplerStates(); destroyResamplerStates();


// Dprintf("xxx setSampleRate: 5\n");

// Lazy-alloc resampler state // Lazy-alloc resampler state
if(!Dfltequal(oversample.factor, 1.0f)) if(!Dfltequal(oversample.factor, 1.0f))
{ {
int err; int err;


// Dprintf("xxx setSampleRate: 6\n");

oversample.srs_in = speex_resampler_init(NUM_INPUTS, oversample.srs_in = speex_resampler_init(NUM_INPUTS,
sUI(sample_rate), // in rate sUI(sample_rate), // in rate
sUI(sample_rate * oversample.factor), // out rate sUI(sample_rate * oversample.factor), // out rate
@@ -910,8 +898,6 @@ public:
&err &err
); );


// Dprintf("xxx setSampleRate: 7\n");

oversample.srs_out = speex_resampler_init(NUM_OUTPUTS, oversample.srs_out = speex_resampler_init(NUM_OUTPUTS,
sUI(sample_rate * oversample.factor), // in rate sUI(sample_rate * oversample.factor), // in rate
sUI(sample_rate), // out rate sUI(sample_rate), // out rate
@@ -922,16 +908,11 @@ public:
Dprintf("xxx vstrack_plugin: initialize speex resampler (rate=%f factor=%f quality=%d)\n", sample_rate, oversample.factor, oversample.quality); Dprintf("xxx vstrack_plugin: initialize speex resampler (rate=%f factor=%f quality=%d)\n", sample_rate, oversample.factor, oversample.quality);
} }


// Dprintf("xxx setSampleRate: 8\n");

if(_bLock) if(_bLock)
{ {
// Dprintf("xxx setSampleRate: 8.1\n");
unlockAudio(); unlockAudio();
// Dprintf("xxx setSampleRate: 8.2\n");
} }


// Dprintf("xxx setSampleRate: 9\n");
r = true; r = true;
} }


@@ -1067,8 +1048,10 @@ public:
} }


sUI getProgramChunk(uint8_t**_addr) { sUI getProgramChunk(uint8_t**_addr) {
sUI r = 0;
setGlobals(); setGlobals();
vst2_set_shared_plugin_tls_globals(); vst2_set_shared_plugin_tls_globals();
rack::global_ui->app.mtx_param.lock();
if(NULL != last_program_chunk_str) if(NULL != last_program_chunk_str)
{ {
::free(last_program_chunk_str); ::free(last_program_chunk_str);
@@ -1077,9 +1060,10 @@ public:
if(NULL != last_program_chunk_str) if(NULL != last_program_chunk_str)
{ {
*_addr = (uint8_t*)last_program_chunk_str; *_addr = (uint8_t*)last_program_chunk_str;
return (sUI)strlen(last_program_chunk_str) + 1/*ASCIIZ*/;
r = (sUI)strlen(last_program_chunk_str) + 1/*ASCIIZ*/;
} }
return 0;
rack::global_ui->app.mtx_param.unlock();
return r;
} }


bool setBankChunk(size_t _size, uint8_t *_addr) { bool setBankChunk(size_t _size, uint8_t *_addr) {
@@ -1088,28 +1072,23 @@ public:
} }


bool setProgramChunk(size_t _size, uint8_t *_addr) { bool setProgramChunk(size_t _size, uint8_t *_addr) {
// Dprintf("xxx vstrack_plugin:setProgramChunk: 1\n");
Dprintf("xxx vstrack_plugin:setProgramChunk: ENTER\n");
setGlobals(); setGlobals();
// Dprintf("xxx vstrack_plugin:setProgramChunk: 2\n");
rack::global_ui->app.mtx_param.lock();
lockAudio(); lockAudio();
// Dprintf("xxx vstrack_plugin:setProgramChunk: 3\n");
vst2_set_shared_plugin_tls_globals(); vst2_set_shared_plugin_tls_globals();
// Dprintf("xxx vstrack_plugin:setProgramChunk: 4\n");
// std::lock_guard<std::mutex> lock(rack::global->engine.mutex);
std::lock_guard<std::recursive_mutex> lock(rack::global->engine.mutex);
rack::global->engine.mutex.lock();
#if 0 #if 0
Dprintf("xxx vstrack_plugin:setProgramChunk: size=%u\n", _size); Dprintf("xxx vstrack_plugin:setProgramChunk: size=%u\n", _size);
#endif #endif
lglw_glcontext_push(rack::global_ui->window.lglw); lglw_glcontext_push(rack::global_ui->window.lglw);
// Dprintf("xxx vstrack_plugin:setProgramChunk: 5\n");
bool r = rack::global_ui->app.gRackWidget->loadPatchFromString((const char*)_addr); bool r = rack::global_ui->app.gRackWidget->loadPatchFromString((const char*)_addr);
// Dprintf("xxx vstrack_plugin:setProgramChunk: 6\n");
rack::global_ui->ui.gScene->step(); // w/o this the patch is bypassed rack::global_ui->ui.gScene->step(); // w/o this the patch is bypassed
// Dprintf("xxx vstrack_plugin:setProgramChunk: 7\n");
lglw_glcontext_pop(rack::global_ui->window.lglw); lglw_glcontext_pop(rack::global_ui->window.lglw);
// Dprintf("xxx vstrack_plugin:setProgramChunk: 8 r=%d\n", r);
rack::global->engine.mutex.unlock();
unlockAudio(); unlockAudio();
// Dprintf("xxx vstrack_plugin:setProgramChunk: 9\n");
rack::global_ui->app.mtx_param.unlock();
Dprintf("xxx vstrack_plugin:setProgramChunk: LEAVE\n");
return r; return r;
} }


@@ -1273,11 +1252,14 @@ void VSTPluginProcessReplacingFloat32(VSTPlugin *vstPlugin,
// we can get a hold to our C++ class since we stored it in the `object` field (see constructor) // we can get a hold to our C++ class since we stored it in the `object` field (see constructor)
VSTPluginWrapper *wrapper = static_cast<VSTPluginWrapper *>(vstPlugin->object); VSTPluginWrapper *wrapper = static_cast<VSTPluginWrapper *>(vstPlugin->object);
// Dprintf("xxx vstrack_plugin: VSTPluginProcessReplacingFloat32: ENTER\n"); // Dprintf("xxx vstrack_plugin: VSTPluginProcessReplacingFloat32: ENTER\n");
wrapper->lockAudio();

wrapper->setGlobals(); wrapper->setGlobals();
vst2_set_shared_plugin_tls_globals(); vst2_set_shared_plugin_tls_globals();


vst2_handle_queued_params();
wrapper->lockAudio();

if(wrapper->b_check_offline) if(wrapper->b_check_offline)
{ {
// Check if offline rendering state changed and update resampler when necessary // Check if offline rendering state changed and update resampler when necessary
@@ -1287,7 +1269,6 @@ void VSTPluginProcessReplacingFloat32(VSTPlugin *vstPlugin,
// // rack::global->engine.vipMutex.lock(); // // rack::global->engine.vipMutex.lock();
rack::global->engine.mutex.lock(); rack::global->engine.mutex.lock();
rack::global->vst2.last_seen_num_frames = sUI(sampleFrames); rack::global->vst2.last_seen_num_frames = sUI(sampleFrames);
vst2_handle_queued_params();


//Dprintf("xxx vstrack_plugin: VSTPluginProcessReplacingFloat32: lockAudio done\n"); //Dprintf("xxx vstrack_plugin: VSTPluginProcessReplacingFloat32: lockAudio done\n");


@@ -2131,9 +2112,13 @@ float VSTPluginGetParameter(VSTPlugin *vstPlugin,
// we can get a hold to our C++ class since we stored it in the `object` field (see constructor) // we can get a hold to our C++ class since we stored it in the `object` field (see constructor)
VSTPluginWrapper *wrapper = static_cast<VSTPluginWrapper *>(vstPlugin->object); VSTPluginWrapper *wrapper = static_cast<VSTPluginWrapper *>(vstPlugin->object);


wrapper->lockAudio(); // don't query a param while the module is deleted
wrapper->setGlobals(); wrapper->setGlobals();
wrapper->lockAudio();
rack::global->engine.mutex.lock(); // don't query a param while a module is being deleted

float r = vst2_get_param(index); float r = vst2_get_param(index);

rack::global->engine.mutex.unlock();
wrapper->unlockAudio(); wrapper->unlockAudio();


return r; return r;


Loading…
Cancel
Save