Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Linking of VST3 plugin fails on Clang + MinGW due to CheckSettingMacros undefining JucePlugin_Build_VST3 #993

Closed
Birch-san opened this issue Jan 11, 2022 · 1 comment

Comments

@Birch-san
Copy link

Birch-san commented Jan 11, 2022

I've been attempting to use a Linux Docker container to cross-compile my audio plugin for Windows x86_64, using Clang and MinGW.

The problem only occurs when you use JUCE_VST3_CAN_REPLACE_VST2=1 (so, to repro this you'll need a VST2 SDK).

It fails at link-time; juce_VST3_Wrapper.cpp fails to find symbol getUUIDForVST2ID.

/opt/llvm-mingw/bin/x86_64-w64-mingw32-clang++ -DJUCE_DISABLE_ASSERTIONS -g -shared -o "AudioPluginExample_artefacts/Debug/VST3/Audio Plugin Example.vst3/Contents/x86_64-win/Audio Plugin Example.vst3" -Wl,--major-image-version,0,--minor-image-version,0 -Wl,--whole-archive CMakeFiles/AudioPluginExample_VST3.dir/objects.a -Wl,--no-whole-archive @CMakeFiles/AudioPluginExample_VST3.dir/linklibs.rsp
ld.lld: error: undefined symbol: juce::getUUIDForVST2ID(bool, unsigned char*)
>>> referenced by /linux_native/include/JUCE-6.1.2/modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp:3572
>>>               objects.a(juce_audio_plugin_client_VST3.cpp.obj):(juce::getFUIDForVST2ID(bool))
clang-13: error: linker command failed with exit code 1 (use -v to see invocation)
CMakeFiles/AudioPluginExample_VST3.dir/build.make:256: recipe for target 'AudioPluginExample_artefacts/Debug/VST3/Audio Plugin Example.vst3/Contents/x86_64-win/Audio Plugin Example.vst3' failed

The symbol is supposed to be created in juce_PluginUtilities.cpp, provided JucePlugin_Build_VST3 is defined.

But juce_CheckSettingMacros.h undefines it since our toolchain is not whitelisted.

As a result: juce_audio_plugin_client_utils.cpp.obj (the file responsible for including juce_PluginUtilities.cpp) gets created without the symbol juce::getUUIDForVST2ID(bool, unsigned char*) .

here's how to reproduce the problem inside a Linux Docker container (cross-compiling for Windows):

# I assume that you have a VST2_SDK installed at ~/SDKs/VST_SDK/VST2_SDK/, and mount it into the container
docker run -it --rm --name=mingw-repro -v "$HOME/SDKs/VST_SDK/VST2_SDK/:/VST2_SDK/:ro" mstorsjo/llvm-mingw

# now you're inside the container
# install juceaide dependencies:
apt-get update -qq && \
apt-get install -qqy --no-install-recommends libx11-dev libxrandr-dev libxinerama-dev libxcursor-dev libfreetype6-dev && \
apt-get clean -y && \
rm -rf /var/lib/apt/lists/*

TOOLCHAIN=x86_64
TOOLCHAIN_FILE="/${TOOLCHAIN}_toolchain.cmake"
MINGW_REPO=clang64

# define CMake toolchain for cross-compiling to x86_64 Windows via MinGW:
cat >"$TOOLCHAIN_FILE" <<EOF
# the name of the target operating system
set(CMAKE_SYSTEM_NAME Windows)

# which compilers to use for C and C++
set(CMAKE_C_COMPILER   $TOOLCHAIN-w64-mingw32-clang)
set(CMAKE_CXX_COMPILER $TOOLCHAIN-w64-mingw32-clang++)

# where is the target environment located
# https://cmake.org/cmake/help/latest/command/find_library.html
set(CMAKE_FIND_ROOT_PATH  /$MINGW_REPO;/opt/llvm-mingw/$TOOLCHAIN-w64-mingw32)

# adjust the default behavior of the FIND_XXX() commands:
# search programs in the host environment
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)

# search headers and libraries in the target environment
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
EOF

# clone last-known-good JUCE
# we cannot use a newer JUCE due to https://github.com/juce-framework/JUCE/issues/985
git clone --branch 6.1.2 --depth 1 https://github.com/juce-framework/JUCE.git

cd JUCE

# build juceaide (we will *not* cross-compile this for Windows; we build natively for the build machine)
cmake -B build -DCMAKE_INSTALL_PREFIX="/linux_native"
cmake --build build --target install

cd examples/CMake/AudioPlugin
# uncomment find_package line
sed -i '/^# find_package(JUCE/ s/# //' CMakeLists.txt
# enable JUCE_VST3_CAN_REPLACE_VST2
sed -i '/JUCE_VST3_CAN_REPLACE_VST2=0/ s/0/1/' CMakeLists.txt
# set VST2_SDK path
sed -i '/^juce_add_plugin/i juce_set_vst2_sdk_path(/VST2_SDK)' CMakeLists.txt

# I've disabled assertions because of an unrelated issue (compiling asm on Clang):
#   https://github.com/juce-framework/JUCE/issues/986
VERBOSE=1 cmake -Bbuild \
-DCMAKE_VERBOSE_MAKEFILE:BOOL=ON \
-DCMAKE_PREFIX_PATH="/linux_native" \
-DCMAKE_INSTALL_PREFIX="/$MINGW_REPO" \
-DCMAKE_CXX_FLAGS='-DJUCE_DISABLE_ASSERTIONS' \
-DCMAKE_TOOLCHAIN_FILE="$TOOLCHAIN_FILE" \
-DCMAKE_BUILD_TYPE=Debug
# will encounter link failure in juce_VST3_Wrapper.cpp
cmake --build build --target AudioPluginExample_VST3

cd build
# the reason for the link failure is because the symbol is missing:
llvm-nm -gU CMakeFiles/AudioPluginExample.dir/linux_native/include/JUCE-6.1.2/modules/juce_audio_plugin_client/juce_audio_plugin_client_utils.cpp.obj
# no symbols printed at all!

I'm currently working around this with the following patch:
Birch-san@7182e6e

In my branch (Birch-san/juicysfplugin#32), build and link succeed. I get the following symbols returned:

llvm-nm -gU CMakeFiles/JuicySFPlugin.dir/linux_native/include/JUCE-6.1.2/modules/juce_audio_plugin_client/juce_audio_plugin_client_utils.cpp.obj
00001200 T _ZN4juce16getUUIDForVST2IDEbPh
000019c0 T _ZN4juce36handleManufacturerSpecificVST2OpcodeEixPvf
00000000 T _ZN4juce9ByteOrder12bigEndianIntEPKv
00000000 T _ZN4juce9ByteOrder7makeIntEhhhh

With my patch: this successfully builds & links a VST3 plugin, which runs fine in FL Studio.
perhaps Clang+MinGW should be added to the whitelist of supported toolchains in juce_CheckSettingMacros.h?

@Birch-san Birch-san changed the title Compilation of VST3 plugin fails on Clang + MinGW due to macro undefining JucePlugin_Build_VST3 Compilation of VST3 plugin fails on Clang + MinGW due to CheckSettingMacros undefining JucePlugin_Build_VST3 Jan 11, 2022
@Birch-san Birch-san changed the title Compilation of VST3 plugin fails on Clang + MinGW due to CheckSettingMacros undefining JucePlugin_Build_VST3 Linking of VST3 plugin fails on Clang + MinGW due to CheckSettingMacros undefining JucePlugin_Build_VST3 Jan 11, 2022
@reuk
Copy link
Member

reuk commented Jan 18, 2022

I've recently spent some time fixing JUCE builds for MinGW-W64 8.1.0+ (that's the version that ships in the most recent CodeBlocks).

The relevant changes are f429647 and 640194c

Please try building with JUCE from the most recent develop branch and let us know if you run into any further issues.

I'm closing this issue for now, but I'll reopen it if you discover that the issue has not been satisfactorily resolved.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants