Hey,
I’m making the voice processing of my synth multi-threaded. I’ve been advised before that this has limited benefits in a DAW, but since it’s for iOS and Android this shouldn’t be an issue.
I’m using this multi producer, multi consumer queue.
The threads (one for each core) are setup before hand like below. voicesRemaining is a std::atomic int.
numThreads = SystemStats::getNumCpus();
for (int i = 0; i < numThreads; i++) {
processThreads.push_back(thread([&]() {
VoiceProcessTask task;
while (true) {
processQueue.wait_dequeue(task);
task.process();
voicesRemaining.fetch_add(-1, std::memory_order_release);
}
}));
}
Then every call to renderVoices does something like this:
voicesRemaining = voices.size();
for (int i = 0; i < voices.size(); ++i) { //add all voices to the queue
processQueue.enqueue(
VoiceProcessTask(voices.getUnchecked(i), &buffer, startSample, numSamples));
}
VoiceProcessTask task;
while (voicesRemaining.load(std::memory_order_acquire) != 0) { //while the threads do their biz, help out with the queue
if (!processQueue.try_dequeue(task)) {
continue;
}
task.process();
voicesRemaining.fetch_add(-1, std::memory_order_release);
}
I’m seeing big benefits already in terms of performance, but I’m wondering if anyone’s got any tips to improve it further? One issue is how to destroy the queue while the threads are in the wait_dequeue state. I never need to destroy them during the lifetime of the app though so many it’s not so important. I guess they get brutally terminated when the app closes.
Thanks