I’m experiencing a strange behaviour in a certain host on Windows for the plugin I’m developing. When opening a project for this host which uses my plugin it makes the host non-responsive. This only happens when opening the project file from the Windows file explorer - it doesn’t happen if I open the host first, then go File->Open to open the file (which works perfectly).
The line of code that is triggering the crash is the assignment operator for the AudioParameterFloat instance.
BensynthpAudioProcessor::processBlock (AudioSampleBuffer& buffer, MidiBuffer& midiMessages){
// Sync macro param values of processor interface with synth
for (size_t m = 0; m < MACRO_COUNT; m++){
if (d->macroData[m].lastInternalValue != d->synth->getMacroParam((unsigned int)m)->getValuePercent()){
// Internal value changed. Update external value
*d->macroData[m].param = d->synth->getMacroParam((unsigned int)m)->getValuePercent(); // THIS LINE ALONE CAUSES THE ISSUE
d->macroData[m].lastExternalValue = d->macroData[m].param->get();
// Record change
d->macroData[m].lastInternalValue = d->synth->getMacroParam((unsigned int)m)->getValuePercent();
}else if (d->macroData[m].lastExternalValue != d->macroData[m].param->get()){
// External value changed. Update internal value
d->synth->getMacroParam((unsigned int)m)->setValuePercent(d->macroData[m].param->get());
d->macroData[m].lastInternalValue = d->synth->getMacroParam((unsigned int)m)->getValuePercent();
// Record change
d->macroData[m].lastExternalValue = d->macroData[m].param->get();
}
}
…
The following is unconditionally run in my AudioProcessor-derived constructor. It’s worth noting the crash never happens if my plugin state is saved with these parameters in their default value.
…
// Expose macro params to host
constexpr float MACRO_DEFAULT_VALUE = 0.5f;
for (size_t i = 0; i < MACRO_COUNT; i++) {
addParameter(d->macroData[i].param = new AudioParameterFloat(String(d->synth->getMacroParam((unsigned int)i)->getName()), String(“M”) + String(d->synth->getMacroParam((unsigned int)i)->getName()), 0.0f, 1.0f, MACRO_DEFAULT_VALUE)); // default value
d->synth->getMacroParam((unsigned int)i)->setValuePercent(MACRO_DEFAULT_VALUE);
d->macroData[i].lastInternalValue = MACRO_DEFAULT_VALUE;
d->macroData[i].lastExternalValue = MACRO_DEFAULT_VALUE;
}
…
Other than this it works properly in at least 4 different hosts, both on Windows and Linux. I strongly suspect I may have done something silly, but I also think it’s a possibility that the host might be doing something naughty. In the AudioParameter float assignment operator implementation has the following:
if (value != newValue)
setValueNotifyingHost (range.convertTo0to1 (newValue));
I’m guessing the ‘if’ statement is why save files don’t crash this host if they’re loading the default value, since the host is never notified. It seems possible the host is unprepared to deal with the notification being sent in processBlock.
If anyone has any ideas on what’s going wrong here I’d be very grateful.