mirror of
https://github.com/robbert-vdh/yabridge.git
synced 2026-05-09 20:29:10 +02:00
Further reduce allocations by reusing responses
On the plugin's side, still need to do a lot of work on the Wine side of things.
This commit is contained in:
@@ -50,14 +50,14 @@ class DefaultDataConverter {
|
|||||||
const intptr_t value) const;
|
const intptr_t value) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Write the reponse back to the `data` pointer.
|
* Write the response back to the `data` pointer.
|
||||||
*/
|
*/
|
||||||
virtual void write(const int opcode,
|
virtual void write(const int opcode,
|
||||||
void* data,
|
void* data,
|
||||||
const EventResult& response) const;
|
const EventResult& response) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Write the reponse back to the `value` pointer. This is only used during
|
* Write the response back to the `value` pointer. This is only used during
|
||||||
* the `effGetSpeakerArrangement` event.
|
* the `effGetSpeakerArrangement` event.
|
||||||
*/
|
*/
|
||||||
virtual void write_value(const int opcode,
|
virtual void write_value(const int opcode,
|
||||||
|
|||||||
@@ -462,6 +462,24 @@ class Vst3Sockets : public Sockets {
|
|||||||
audio_processor_buffers.at(object_ref.get().instance_id));
|
audio_processor_buffers.at(object_ref.get().instance_id));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Alternative to `send_audio_processor_message()` for use with
|
||||||
|
* `MessageReference<T>`, where we also want deserialize into an existing
|
||||||
|
* object to prevent allocations. Used during audio processing.q
|
||||||
|
*
|
||||||
|
* TODO: Think of a better name for this
|
||||||
|
*/
|
||||||
|
template <typename T>
|
||||||
|
typename T::Response& receive_audio_processor_message_into(
|
||||||
|
const MessageReference<T>& request_ref,
|
||||||
|
typename T::Response& response_ref,
|
||||||
|
std::optional<std::pair<Vst3Logger&, bool>> logging) {
|
||||||
|
return audio_processor_sockets.at(request_ref.get().instance_id)
|
||||||
|
.receive_into(
|
||||||
|
request_ref, response_ref, logging,
|
||||||
|
audio_processor_buffers.at(request_ref.get().instance_id));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* For sending messages from the host to the plugin. After we have a better
|
* For sending messages from the host to the plugin. After we have a better
|
||||||
* idea of what our communication model looks like we'll probably want to
|
* idea of what our communication model looks like we'll probably want to
|
||||||
|
|||||||
@@ -220,12 +220,15 @@ Vst3PluginProxyImpl::process(Steinberg::Vst::ProcessData& data) {
|
|||||||
process_request.data.repopulate(data);
|
process_request.data.repopulate(data);
|
||||||
process_request.new_realtime_priority = new_realtime_priority;
|
process_request.new_realtime_priority = new_realtime_priority;
|
||||||
|
|
||||||
ProcessResponse response = bridge.send_audio_processor_message(
|
// We'll also receive the response into an existing object so we can also
|
||||||
MessageReference<YaAudioProcessor::Process>(process_request));
|
// avoid heap allocations there
|
||||||
|
bridge.receive_audio_processor_message_into(
|
||||||
|
MessageReference<YaAudioProcessor::Process>(process_request),
|
||||||
|
process_response);
|
||||||
|
|
||||||
response.output_data.write_back_outputs(data);
|
process_response.output_data.write_back_outputs(data);
|
||||||
|
|
||||||
return response.result;
|
return process_response.result;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32 PLUGIN_API Vst3PluginProxyImpl::getTailSamples() {
|
uint32 PLUGIN_API Vst3PluginProxyImpl::getTailSamples() {
|
||||||
|
|||||||
@@ -489,6 +489,13 @@ class Vst3PluginProxyImpl : public Vst3PluginProxy {
|
|||||||
*/
|
*/
|
||||||
YaAudioProcessor::Process process_request;
|
YaAudioProcessor::Process process_request;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The response object we'll get in return when we send the
|
||||||
|
* `process_request` object above to the Wine plugin host. This object also
|
||||||
|
* contains heap data, so we also want to reuse this.
|
||||||
|
*/
|
||||||
|
YaAudioProcessor::ProcessResponse process_response;
|
||||||
|
|
||||||
// Caches
|
// Caches
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -121,6 +121,21 @@ class Vst3PluginBridge : PluginBridge<Vst3Sockets<std::jthread>> {
|
|||||||
object, std::pair<Vst3Logger&, bool>(logger, true));
|
object, std::pair<Vst3Logger&, bool>(logger, true));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Send an `IAudioProcessor` or `IComponent` control message to a specific
|
||||||
|
* plugin instance, receiving the results into an existing object. This is
|
||||||
|
* similar to the `send_audio_processor_message()` above, but this lets us
|
||||||
|
* avoid allocations in response objects that contain heap data.
|
||||||
|
*/
|
||||||
|
template <typename T>
|
||||||
|
typename T::Response& receive_audio_processor_message_into(
|
||||||
|
const T& object,
|
||||||
|
typename T::Response& response_object) {
|
||||||
|
return sockets.receive_audio_processor_message_into(
|
||||||
|
object, response_object,
|
||||||
|
std::pair<Vst3Logger&, bool>(logger, true));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The logging facility used for this instance of yabridge. Wraps around
|
* The logging facility used for this instance of yabridge. Wraps around
|
||||||
* `PluginBridge::generic_logger`.
|
* `PluginBridge::generic_logger`.
|
||||||
|
|||||||
Reference in New Issue
Block a user