csound / csound

Main repository for Csound
https://csound.com
GNU Lesser General Public License v2.1
1.2k stars 188 forks source link

Q: Issue with dynamic linked csound opcodes #1648

Open docb opened 1 year ago

docb commented 1 year ago

For the vcvrack plugin i have made a static build of the csoundlib64 including the dynamic opcode families (signalflow,doppler etc.) (this static lib is linked then in the plugin.dll for loading in vcvrack, and ensures that the plugin is running without installing csound) This i have done so: added following switches in CMake option(BUILD_STATIC_LIBRARY "Also build a static version of the csound library" ON) option(INIT_STATIC_MODULES "Also build opcodes in a static version of the csound library" ON) -> works: the obj files of the opcodes are in the static lib.

Then in the code i call: init_static_modules(csound->GetCsound());

This works fine but on windows with an installed csound distribution (all 6.18) vcvrack crashed when deleting a csound module. Due to debugger output it crashes somewhere in signalflowgraph.dll. It seems that even if i have linked those opcodes statically the dynamic version is used if installed. But this seems to crash.

Any ideas what else must be done or how is it done correctly?

However i can simply put those modules out. Then they would only work when csound is installed, but not out of the box.

vlazzarini commented 1 year ago

Is this crash strictly on Windows? We might need our Windows experts here (@stekyne ?). I only know about unix-like environments.

docb commented 1 year ago

i only could reproduce it there, on my linux it all works fine. on mac also no problem so far. and also could verify on windows, that if i uninstall csound then the problem is gone.

stekyne commented 1 year ago

It's not that easy to tell what's going on unfortunately. Is there any kind of crash dump, error code, stack trace you can give? I've not experimented with INIT_STATIC_MODULES before so hard to say if they work correctly on Windows normally. It might be worth using a small test app to load them, run some example and close. See if it replicates in a smaller test case.

docb commented 1 year ago

what i wondered about is why the dynamic version of the opcodes is used on windows if present (i.e. csound is installed and there is a plugins64 folder) even if the static ones are there. however this is the only info i have currently, note that this is when i delete the csound instance. win

before spending a lot of time and there is no fast solution, i would rather disable now the opcodes on windows .. they seem to work if csound is installed and i do not init them statically.

stekyne commented 1 year ago

I've managed to reproduce this I think. I built for Windows with INIT_STATIC_MODULES. I notice however that it's not loading the static libs at all or running the correct code paths.

https://github.com/csound/csound/blob/f0bea4d87b49da2be7e9f1fc77826a7327cbc391/Top/csmodule.c#L820

You can see here that the symbol (INIT_STATIC_MODULES) needs to be defined within the csound64 target but it's only being set per file. Not quite sure this was ever working correctly unless I'm misunderstanding something.

https://github.com/csound/csound/blob/7b7661e9a902473e30e98983bc2983f74e37f838/CMakeLists.txt#L963

I added the symbol to the target and the correct code path runs but now I'm getting the crash on unload. It's crashing while in csoundDestroyModules and trying to unload the signalflowgraph.dll. It should probably be avoiding loading these DLLs at all if this flag is set. I'm unsure why it's crashing it though.

Edit: My changes are here: https://github.com/csound/csound/pull/1649/files

docb commented 1 year ago

i think this could be exactly the situation i have, because i call explicitly init_static_modules in my csound init method (this i could change now to set the INIT_STATIC_MODULES for compiling). And this is exactly what i wonder about, that the signalflowgraph.dll is loaded anyway and then crashing on unload.

docb commented 1 year ago

I'm unsure why it's crashing it though.

it may caused somewhere here https://github.com/csound/csound/blob/7b7661e9a902473e30e98983bc2983f74e37f838/Opcodes/signalflowgraph.cpp#L1508 ff.

docb commented 1 year ago

and i guess that here is loaded everything which is found independent of a variable: https://github.com/csound/csound/blob/f0bea4d87b49da2be7e9f1fc77826a7327cbc391/Top/csmodule.c#L565

btw: the crash is also gone if i simple move the plugins64 folder to the desktop.

vlazzarini commented 1 year ago

Csound will load anything it finds in the OPCODE6DIR64, so if the DLL is there it will be loaded. I don't think we have a means to say "don't load this file".

Btw, @stekyne thanks for the fix. Could you apply these changes to the csound6 branch when you are ready?

stekyne commented 1 year ago

Merged to both branches now

vlazzarini commented 1 year ago

if this is still causing bother @rorywalsh has a solution to prevent Csound from loading dynamic opcodes from a different installation on Windows. Maybe he can post it here.

rorywalsh commented 1 year ago

This was happening with the Windows version of Csound that we ship with CsoundUnity. The only solution we found was to stop Csound from loading any plugins by called csoundSetOpcodedir() before compiling Csound. We just point it to the location of the .csd file. It's a little awkward but I think it's the only way we can be sure our embedded version of Csound doesn't conflict with any system installed versions. If users wish to load any plugin libs they can do so manually using the --opcode-lib flag. FWIW, I only got the issue with the plugin libs that ship with Csound. I had no problems using any of the csound plugins that have been moved outside of the main repo.

docb commented 1 year ago

@rorywalsh thanks this seems to work!

jpffitch commented 4 months ago

Victor poiinted out we have ways of loading a module, but no way of ignoring one. Should we implement
--opcode-no-lib=LIBNAME bto block modules?

rorywalsh commented 4 months ago

I'm not sure it's needed John. One can always either point opcodedir someplace else, or simply move the opcode lib in question out of opcodedir.

docEdub commented 4 months ago

There is --opcode-omit in argdecode.c, but I don't think it's implemented.