From fa0753f52015f5276d9c8af9f9309d83dc19a582 Mon Sep 17 00:00:00 2001 From: Robbert van der Helm Date: Thu, 31 Dec 2020 14:12:14 +0100 Subject: [PATCH] Use atomic fetch-and-add for unique window classes --- src/wine-host/bridges/vst2.cpp | 8 +------- src/wine-host/bridges/vst3.cpp | 6 +----- src/wine-host/editor.cpp | 13 +++++++++---- src/wine-host/editor.h | 6 +----- 4 files changed, 12 insertions(+), 21 deletions(-) diff --git a/src/wine-host/bridges/vst2.cpp b/src/wine-host/bridges/vst2.cpp index 4ef03eed..0881ead7 100644 --- a/src/wine-host/bridges/vst2.cpp +++ b/src/wine-host/bridges/vst2.cpp @@ -379,13 +379,7 @@ intptr_t Vst2Bridge::dispatch_wrapper(AEffect* plugin, // provided by the host, and let the plugin embed itself into // the Wine window const auto x11_handle = reinterpret_cast(data); - // Win32 window classes have to be unique for the whole application. - // When hosting multiple plugins in a group process, all plugins - // should get a unique window class - const std::string window_class = - "yabridge plugin " + sockets.base_dir.string(); - Editor& editor_instance = - editor.emplace(config, window_class, x11_handle); + Editor& editor_instance = editor.emplace(config, x11_handle); return plugin->dispatcher(plugin, opcode, index, value, editor_instance.get_win32_handle(), diff --git a/src/wine-host/bridges/vst3.cpp b/src/wine-host/bridges/vst3.cpp index 732a1ca5..c5d70007 100644 --- a/src/wine-host/bridges/vst3.cpp +++ b/src/wine-host/bridges/vst3.cpp @@ -397,9 +397,6 @@ void Vst3Bridge::run() { // and if it's actually needed (for instance when the host // resizes the window without informing the plugin) const auto x11_handle = static_cast(request.parent); - const std::string window_class = - "yabridge plugin " + sockets.base_dir.string() + " " + - std::to_string(request.owner_instance_id); // Creating the window and having the plugin embed in it should // be done in the main UI thread @@ -407,8 +404,7 @@ void Vst3Bridge::run() { .run_in_context([&]() { Editor& editor_instance = object_instances[request.owner_instance_id] - .editor.emplace(config, window_class, - x11_handle); + .editor.emplace(config, x11_handle); const tresult result = object_instances[request.owner_instance_id] diff --git a/src/wine-host/editor.cpp b/src/wine-host/editor.cpp index 697e7f7f..073b08eb 100644 --- a/src/wine-host/editor.cpp +++ b/src/wine-host/editor.cpp @@ -45,6 +45,12 @@ constexpr uint32_t xembed_focus_in_msg = 4; constexpr uint32_t xembed_focus_first = 1; +/** + * Used to generate a globally unique identifier for a window class. This is + * needed because every window's window class name should be unique. + */ +std::atomic_size_t window_class_id{}; + /** * Find the topmost window (i.e. the window before the root window in the window * tree) starting from a certain window. @@ -94,13 +100,12 @@ WindowClass::~WindowClass() { UnregisterClass(reinterpret_cast(atom), GetModuleHandle(nullptr)); } -Editor::Editor(const Configuration& config, - const std::string& window_class_name, - const size_t parent_window_handle) +Editor::Editor(const Configuration& config, const size_t parent_window_handle) : use_xembed(config.editor_xembed), x11_connection(xcb_connect(nullptr, nullptr), xcb_disconnect), client_area(get_maximum_screen_dimensions(*x11_connection)), - window_class(window_class_name), + window_class("yabridge plugin " + + std::to_string(window_class_id.fetch_add(1))), // Create a window without any decoratiosn for easy embedding. The // combination of `WS_EX_TOOLWINDOW` and `WS_POPUP` causes the window to // be drawn without any decorations (making resizes behave as you'd diff --git a/src/wine-host/editor.h b/src/wine-host/editor.h index 0ffce84e..6d6826c1 100644 --- a/src/wine-host/editor.h +++ b/src/wine-host/editor.h @@ -97,16 +97,12 @@ class Editor { * * @param config This instance's configuration, used to enable alternative * editor behaviours. - * @param window_class_name The name for the window class for editor - * windows. * @param parent_window_handle The X11 window handle passed by the VST host * for the editor to embed itself into. * * @see win32_handle */ - Editor(const Configuration& config, - const std::string& window_class_name, - const size_t parent_window_handle); + Editor(const Configuration& config, const size_t parent_window_handle); ~Editor();