Commit Graph

612 Commits

Author SHA1 Message Date
Robbert van der Helm 49750575bc Fix xcb assertion failures in Ardour for good
Hopefully. Checking mapped state apparently wasn't enough to prevent
spurious assertion failures on `is_child_window_or_same()`. Now we'll
just use exceptions instead of assertions so we catch them and ignore
them.
2021-05-02 20:40:59 +02:00
Robbert van der Helm 2fd453e747 Repeat the window mapped check for Ardour
This is probably a better idea than trying to be efficient. If we get
two events in a row, then it can be that the map status has changed
between the two events.
2021-05-02 18:33:05 +02:00
Robbert van der Helm 5c88140c54 Also use mutual recursion for program list changes
The VST3 version of Voxengo TEOTE would deadlock in Ardour when Ardour
calls `IEditController::setState()`, the plugin calls
`IUnitHandler::notifyProgramListChange()` in response, and then when
Ardour calls `IUnitInfo::getProgramName()` while handling that callback.
All of these functions have to be called from the same thread in Voxengo
plugins.
2021-05-02 00:41:28 +02:00
Robbert van der Helm fd29c7d825 Skip X11 events when the window is not mapped
This fixes potential assertion failures in Ardour when Ardour unmaps
editor windows.
2021-05-01 23:22:59 +02:00
Robbert van der Helm 7bcc9ac181 Cancel group host shutdown timer with new request
Or else we will still shut down the host when loading the new plugin
takes a while.
2021-05-01 22:10:51 +02:00
Robbert van der Helm 448bfca0bc Reduce the initial shutdown timer on group hosts
This five seconds matches the five seconds on the first watchdog timer
proc.
2021-05-01 22:09:34 +02:00
Robbert van der Helm f3f2bfdc24 Fix deadlock caused by do_mutual_recursion_on_off_thread
Apparently the destructor for C++17/20 conditional initializers are only
run after the else branch, so this would keep the mutex locked while
executing `do_call()`.
2021-05-01 21:01:47 +02:00
Robbert van der Helm b103723df2 Make the watchdog much more aggressive
For individually hosted plugins this will behave the same. For plugin
groups it would have been nice if we could shut down individual plugins,
but dangling threads are apparently a real issue. This should be
equivalent in all use cases.

This also reverts commit bda9a0b75f.
2021-05-01 19:05:55 +02:00
Robbert van der Helm bbc93d7413 Catch all exceptions during initialization 2021-05-01 18:48:46 +02:00
Robbert van der Helm 5c2da36ecd Use a shorter delay for the first watchdog check 2021-05-01 18:47:45 +02:00
Robbert van der Helm 4ff538c7e1 Let group hosts shut down on their own if unused
We would never try to shut the group host down if nothing ever tried to
connect to it. This could happen when the native host gets killed after
initializing the yabridge plugin but before it gets the chance to
request the group host process to host a plugin.
2021-05-01 18:38:18 +02:00
Robbert van der Helm 56afefeb53 Terminate all threads when initialization fails
With this the watchdog can correctly terminate VST2 bridges that get
stuck during initialization.
2021-05-01 17:58:46 +02:00
Robbert van der Helm bda9a0b75f Catch exceptions in failing host callbacks
This will let us more or less gracefully handle failing host callbacks
during initialization. We cannot catch this from anywhere else since
this these functions get called from unmanaged code.
2021-05-01 17:57:41 +02:00
Robbert van der Helm 832089d4d1 Implement the Wine host process watchdog
This will shut down a bridge's sockets when the connected native host
process exits, to prevent dangling Wine processes.
2021-05-01 17:54:22 +02:00
Robbert van der Helm e912bdd302 Also make sure that all group host threads exit
I actually don't know if this is necessary, but it was necessary for
individually hosted plugins, so presumably it's also needed here.
2021-05-01 17:20:13 +02:00
Robbert van der Helm 757fb6d372 Pass the PID of the native host to the Wine hosts
We need this for our watchdog.
2021-05-01 17:13:16 +02:00
Robbert van der Helm 131d749ba6 Register the Wine host bridge watchdog
It doesn't do anything yet.
2021-05-01 16:52:05 +02:00
Robbert van der Helm d8ca4022d1 Add universal way to shutdown sockets on Wine side 2021-05-01 16:51:55 +02:00
Robbert van der Helm 0f2db64aeb Add the pieces for a watchdog for dangling plugins
Once we register our plugins here, we should be able to gracefully shut
down any plugins whose remote process got killed.
2021-05-01 16:51:55 +02:00
Robbert van der Helm aeca37d795 Rearrange src/wine-host/utils.h
We're going to need to spawn a Win32Thread in the MainContext to act as
a watchdog.
2021-05-01 15:46:27 +02:00
Robbert van der Helm b22f207aee Move the MainContext to HostBridge
We'll use this to create a watchdog timer that shuts down the sockets
when the native host gets terminated.
2021-05-01 15:06:13 +02:00
Robbert van der Helm 177431e202 Fix performEdit() deadlock in Ardour/Mixbus
Those DAWs would immediately call `IEditController::performEdit()` with
the same parameter change the plugin has just announced, which would
result in a deadlock. Hopefully this helps with #100.
2021-04-30 20:50:54 +02:00
Robbert van der Helm 2fe6b1c48d Clean up the main VST3 mutual recursion function 2021-04-30 20:44:50 +02:00
Robbert van der Helm 36b3636072 Handle mutual recursion in context menus
REAPER will call `getState()` while the context menu is open, and that
also has to be handled from the GUI thread.
2021-04-30 02:49:54 +02:00
Robbert van der Helm cb07fd07a2 Handle mutual recursion while loading presets 2021-04-29 23:40:42 +02:00
Robbert van der Helm 0f506f75e4 Bypass connection point proxies when possible
This greatly improves compatibility with VST3 plugins in Ardour and
Mixbus. Most notably the FabFilter plugins would previously freeze when
having the GUI open while duplicating or inserting new instances.
2021-04-29 15:36:28 +02:00
Robbert van der Helm e4177f2856 Avoid IAudioProcessor::isActive() on GUI thread
I haven't seen this cause any issues this way, and I could imagine that
this could cause some hangs when initializing a second instance of a
plugin while you're interacting with the GUI of the first instance.
2021-04-29 14:29:15 +02:00
Robbert van der Helm a56e4b337f Rename the VST3 mutual recursion functions 2021-04-29 14:03:15 +02:00
Robbert van der Helm 45d83ad9a1 Revert "Separate mutual recursion on GUI and other threads"
This reverts commit a495f1a67f.

This ended up not being an issue. What we _do_ have to do, sadly, is to
have a mutual recursion context stack per plugin. Otherwise multiple
plugin instances can deadlock eachother.
2021-04-29 13:54:48 +02:00
Robbert van der Helm a495f1a67f Separate mutual recursion on GUI and other threads
I wasn't able to get this to clash, but this way we can be 100% sure
that there aren't any weird issues.
2021-04-29 12:07:11 +02:00
Robbert van der Helm 8b168b310c Fix mutual recursion with latency in Ardour/Mixbus
This would cause Ardour and Mixbus to freeze when inserting a latency
introducing (JUCE based) VST3 plugin. As mentioned in #98.
2021-04-29 03:13:53 +02:00
Robbert van der Helm 6f6e6c5b94 Reword caching to prefetching
Since that makes it much clearer what we're actually doing. With old
`cache_time_info` was actually caching the response, but now we're
querying it before the plugin has even requested the information.
2021-04-29 01:07:14 +02:00
Robbert van der Helm c82eb35243 Also cache audioMasterGetCurrentProcessLevel()
Melda plugins seem to call this during every processing cycle.
2021-04-29 01:02:10 +02:00
Robbert van der Helm b8f8dd7236 Log cached audioMasterGetTime() calls
Just like we log cached VST3 function calls.
2021-04-29 00:41:56 +02:00
Robbert van der Helm 1deb4cf664 Send the VST2 transport info along with processing
And cache it during the processing cycle. This greatly reduces the
overhead of bridging VST2 plugins.
2021-04-29 00:32:25 +02:00
Robbert van der Helm 6a3c726acf Get rid of spurious accessibility label 2021-04-29 00:31:11 +02:00
Robbert van der Helm 6cd1b664d3 Rearrange fields in Vst2Bridge 2021-04-29 00:31:11 +02:00
Robbert van der Helm 70adf5493e Add a logger to the Wine VST2 bridge 2021-04-29 00:31:11 +02:00
Robbert van der Helm 32db921b9b Move generic logger on the Wine side to common.h
We'll also need this for VST2 plugins when we start caching the time
info.
2021-04-29 00:31:11 +02:00
Robbert van der Helm 14b0ba0c62 Clarify the definition of empty_arrangement
This is the same thing of course, but it's a bitfield so just a single 0
may seem a bit odd if you don't already know that.
2021-04-28 13:41:24 +02:00
Robbert van der Helm 216c6bc4f2 Always provide at least some speaker arrangement
This works around a bug in the VST3 version of W. A. Production
Imperfect as mentioned in #97. Even if it's a synth and numInputs is 0,
the plugin will still try to read the input arrangement.
2021-04-28 13:35:15 +02:00
Robbert van der Helm 23f94b35d0 Fix move semantics in Win32Thread and Win32Timer
I was sure that moving an `std::optional<T>` would reset the object you
moved from, but apparently not.
2021-04-28 12:56:49 +02:00
Robbert van der Helm 93f089eca7 Always set FTZ instead of gating it behind a flag
After a quick round of testing it seems like REAPER doesn't always
enable this on the audio thread, but Bitwig, Ardour, Carla and Renoise
do. So it should be safe to just get rid of the option and to leave this
enabled all the time.
2021-04-28 12:07:14 +02:00
Robbert van der Helm 2be41da9b6 Add compatibility option to force flushing to zero
This prevents Kush Audio REDDI from taking down the DAW when the host
passes it denormalized audio to process. I've discovered that the issue
with this plugin had to do with denormals in the issue linked below, but
I didn't realize that we can just enable the FTZ flag for plugins that
don't already do so.

https://github.com/osxmidi/LinVst/issues/174
2021-04-27 23:33:50 +02:00
Robbert van der Helm 73d9f5f9b8 Remove unnecessary include 2021-04-27 20:46:08 +02:00
Robbert van der Helm b52362e698 Fix time info cache being applied to other opcodes
I don't know how I've never noticed this, but we should of course only
be handling `audioMasterGetTime()` this way. This also explains why
enabling this permanently in the past broke some plugins.
2021-04-27 17:32:32 +02:00
Robbert van der Helm 5a68b8b39d Flush the reparent from 0c7dbe8
This should add a root reparent to prevent that X11 error, but it should
still prevent flickering by doing it just before closing the window.
2021-04-27 03:43:45 +02:00
Robbert van der Helm 0c7dbe8a4a Reparent to the root window before deferring close
We did this before implementing the deferred close in yabridge 3.0.0. It
didn't seem necessary anymore so we got rid of it, but without this
closing an iZotope Rx plugin's editor in Renoise was guaranteed to
trigger an X11 error and crash Renoise. Doing this reparent doesn't seem
to cause any slowdown but it does at least fix the specific combination
of iZotope Rx and Renoise.
2021-04-26 18:47:58 +02:00
Robbert van der Helm 0d53f03b28 Get rid of an incorrect comment
This probably ended up here during a refactor.
2021-04-26 18:32:50 +02:00
Robbert van der Helm f6cf1a7dd2 Use explicit narrowing for SetWindowLongPtr() 2021-04-26 18:32:50 +02:00