diff --git a/src/common/logging/vst3.cpp b/src/common/logging/vst3.cpp index 50f3da77..dd55ac0e 100644 --- a/src/common/logging/vst3.cpp +++ b/src/common/logging/vst3.cpp @@ -216,6 +216,14 @@ bool Vst3Logger::log_request(bool is_host_vst, }); } +bool Vst3Logger::log_request(bool is_host_vst, + const YaComponent::GetControllerClassId& request) { + return log_request_base(is_host_vst, [&](auto& message) { + message << request.instance_id + << ": IComponent::getControllerClassId(&classId)"; + }); +} + bool Vst3Logger::log_request(bool is_host_vst, const YaComponent::SetIoMode& request) { return log_request_base(is_host_vst, [&](auto& message) { @@ -583,6 +591,19 @@ void Vst3Logger::log_response( }); } +void Vst3Logger::log_response( + bool is_host_vst, + const YaComponent::GetControllerClassIdResponse& response) { + log_response_base(is_host_vst, [&](auto& message) { + message << response.result.string(); + if (response.result == Steinberg::kResultOk) { + message << ", " + << format_uid(Steinberg::FUID::fromTUID( + response.editor_cid.data())); + } + }); +} + void Vst3Logger::log_response(bool is_host_vst, const YaComponent::GetBusInfoResponse& response) { log_response_base(is_host_vst, [&](auto& message) { diff --git a/src/common/logging/vst3.h b/src/common/logging/vst3.h index ee7e2544..2ee16a8f 100644 --- a/src/common/logging/vst3.h +++ b/src/common/logging/vst3.h @@ -76,6 +76,8 @@ class Vst3Logger { bool log_request(bool is_host_vst, const YaAudioProcessor::SetProcessing&); bool log_request(bool is_host_vst, const YaAudioProcessor::Process&); bool log_request(bool is_host_vst, const YaAudioProcessor::GetTailSamples&); + bool log_request(bool is_host_vst, + const YaComponent::GetControllerClassId&); bool log_request(bool is_host_vst, const YaComponent::SetIoMode&); bool log_request(bool is_host_vst, const YaComponent::GetBusCount&); bool log_request(bool is_host_vst, const YaComponent::GetBusInfo&); @@ -127,6 +129,8 @@ class Vst3Logger { const YaAudioProcessor::GetBusArrangementResponse&); void log_response(bool is_host_vst, const YaAudioProcessor::ProcessResponse&); + void log_response(bool is_host_vst, + const YaComponent::GetControllerClassIdResponse&); void log_response(bool is_host_vst, const YaComponent::GetBusInfoResponse&); void log_response(bool is_host_vst, const YaComponent::GetRoutingInfoResponse&); diff --git a/src/common/serialization/vst3.h b/src/common/serialization/vst3.h index 955b2c6e..4908cff3 100644 --- a/src/common/serialization/vst3.h +++ b/src/common/serialization/vst3.h @@ -71,6 +71,7 @@ using ControlRequest = std::variant object) - : supported(false) { - if (auto component = - Steinberg::FUnknownPtr(object)) { - supported = true; - - // `IComponent::getControllerClassId` - Steinberg::TUID cid; - if (component->getControllerClassId(cid) == Steinberg::kResultOk) { - edit_controller_cid = std::to_array(cid); - } - } -} + : supported(Steinberg::FUnknownPtr(object)) {} YaComponent::YaComponent(const ConstructArgs&& args) : arguments(std::move(args)) {} - -tresult PLUGIN_API YaComponent::getControllerClassId(Steinberg::TUID classId) { - // TODO: This is now not being logged at all. It's probably better if we - // just drop these two functions that output cached data directly. - // They'll only be used once or twice anyways. - if (arguments.edit_controller_cid) { - std::copy(arguments.edit_controller_cid->begin(), - arguments.edit_controller_cid->end(), classId); - return Steinberg::kResultOk; - } else { - return Steinberg::kNotImplemented; - } -} diff --git a/src/common/serialization/vst3/plugin/component.h b/src/common/serialization/vst3/plugin/component.h index 60b73b7a..9449e6fb 100644 --- a/src/common/serialization/vst3/plugin/component.h +++ b/src/common/serialization/vst3/plugin/component.h @@ -52,17 +52,9 @@ class YaComponent : public Steinberg::Vst::IComponent { */ bool supported; - /** - * The class ID of this component's corresponding editor controller. You - * can't use C-style array in `std::optional`s. - */ - std::optional edit_controller_cid; - template void serialize(S& s) { s.value1b(supported); - s.ext(edit_controller_cid, bitsery::ext::StdOptional{}, - [](S& s, auto& cid) { s.container1b(cid); }); } }; @@ -74,7 +66,38 @@ class YaComponent : public Steinberg::Vst::IComponent { inline bool supported() const { return arguments.supported; } - tresult PLUGIN_API getControllerClassId(Steinberg::TUID classId) override; + /** + * The response code and returned CID for a call to + * `IComponent::getControllerClassId()`. + */ + struct GetControllerClassIdResponse { + UniversalTResult result; + ArrayUID editor_cid; + + template + void serialize(S& s) { + s.object(result); + s.container1b(editor_cid); + } + }; + + /** + * Message to pass through a call to `IComponent::getControllerClassId()` to + * the Wine plugin host. + */ + struct GetControllerClassId { + using Response = GetControllerClassIdResponse; + + native_size_t instance_id; + + template + void serialize(S& s) { + s.value8b(instance_id); + } + }; + + virtual tresult PLUGIN_API + getControllerClassId(Steinberg::TUID classId) override = 0; /** * Message to pass through a call to `IComponent::setIoMode(mode)` to the diff --git a/src/plugin/bridges/vst3-impls/plugin-proxy.cpp b/src/plugin/bridges/vst3-impls/plugin-proxy.cpp index cabe7b61..e7050085 100644 --- a/src/plugin/bridges/vst3-impls/plugin-proxy.cpp +++ b/src/plugin/bridges/vst3-impls/plugin-proxy.cpp @@ -116,6 +116,16 @@ uint32 PLUGIN_API Vst3PluginProxyImpl::getTailSamples() { YaAudioProcessor::GetTailSamples{.instance_id = instance_id()}); } +tresult PLUGIN_API +Vst3PluginProxyImpl::getControllerClassId(Steinberg::TUID classId) { + const GetControllerClassIdResponse response = bridge.send_message( + YaComponent::GetControllerClassId{.instance_id = instance_id()}); + + std::copy(response.editor_cid.begin(), response.editor_cid.end(), classId); + + return response.result; +} + tresult PLUGIN_API Vst3PluginProxyImpl::setIoMode(Steinberg::Vst::IoMode mode) { return bridge.send_message( YaComponent::SetIoMode{.instance_id = instance_id(), .mode = mode}); diff --git a/src/plugin/bridges/vst3-impls/plugin-proxy.h b/src/plugin/bridges/vst3-impls/plugin-proxy.h index e406f968..0d6e856f 100644 --- a/src/plugin/bridges/vst3-impls/plugin-proxy.h +++ b/src/plugin/bridges/vst3-impls/plugin-proxy.h @@ -56,6 +56,7 @@ class Vst3PluginProxyImpl : public Vst3PluginProxy { uint32 PLUGIN_API getTailSamples() override; // From `IComponent` + tresult PLUGIN_API getControllerClassId(Steinberg::TUID classId) override; tresult PLUGIN_API setIoMode(Steinberg::Vst::IoMode mode) override; int32 PLUGIN_API getBusCount(Steinberg::Vst::MediaType type, Steinberg::Vst::BusDirection dir) override; diff --git a/src/wine-host/bridges/vst3.cpp b/src/wine-host/bridges/vst3.cpp index 1d3f0358..5a1767d5 100644 --- a/src/wine-host/bridges/vst3.cpp +++ b/src/wine-host/bridges/vst3.cpp @@ -210,6 +210,16 @@ void Vst3Bridge::run() { return object_instances[request.instance_id] .audio_processor->getTailSamples(); }, + [&](const YaComponent::GetControllerClassId& request) + -> YaComponent::GetControllerClassId::Response { + Steinberg::TUID cid; + const tresult result = + object_instances[request.instance_id] + .component->getControllerClassId(cid); + + return YaComponent::GetControllerClassIdResponse{ + .result = result, .editor_cid = std::to_array(cid)}; + }, [&](const YaComponent::SetIoMode& request) -> YaComponent::SetIoMode::Response { return object_instances[request.instance_id]