mstorsjo / llvm-mingw

An LLVM/Clang/LLD based mingw-w64 toolchain
Other
1.93k stars 186 forks source link

Debugging with Wine #441

Open cristianadam opened 3 months ago

cristianadam commented 3 months ago

With Qt Creator 14 one could use the CMAKE_CROSSCOMPILING_EMULATOR set to wine and have a CMake project compiling and running. In my case it was Windows x64 binary running on a Ubuntu 22.04 Arm64.

qtcreator14-cmake-presets-crosscompiling-emulator

I have tried with the 18.1.8 released version, also with lldb-dap, since lldb doesn't work due to missing python bindings in lldb, see https://github.com/mstorsjo/llvm-mingw/issues/359.

But the debugger doesn't work.

CMakeLists.txt ```cmake cmake_minimum_required(VERSION 3.16) project(Hello LANGUAGES CXX) set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON) add_executable(Hello main.cpp) add_custom_command( TARGET Hello POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_SYSROOT}/bin/libc++.dll" ${CMAKE_BINARY_DIR} COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_SYSROOT}/bin/libunwind.dll" ${CMAKE_BINARY_DIR} ) ```
CMakePresets.json ```json { "version": 4, "configurePresets": [ { "name": "llvm-mingw", "displayName": "LLVM MinGW 18.1.8 x64", "generator": "Ninja", "binaryDir": "${sourceDir}/build", "toolchainFile": "llvm-mingw.cmake", "cacheVariables": { "CMAKE_BUILD_TYPE": "Debug", "CMAKE_CROSSCOMPILING_EMULATOR": "/usr/bin/wine64" }, "vendor": { "qt.io/QtCreator/1.0": { "debugger": { "DisplayName": "LLDB Dap 18.1.8 Debugger", "Abis": ["arm-linux-generic-elf-64bit"], "Binary": "$env{HOME}/llvm-mingw/bin/lldb-dap", "EngineType": 1024, "Version": "18.1.8" } } } } ] } ```
llvm-mingw.cmake ```cmake set(_prefix $ENV{HOME}/llvm-mingw/) if(NOT CMAKE_SYSTEM_NAME) set(CMAKE_SYSTEM_NAME Windows) endif() if(NOT CMAKE_SYSTEM_PROCESSOR) set(CMAKE_SYSTEM_PROCESSOR x86_64) endif() set(CMAKE_SYSROOT "${_prefix}${CMAKE_SYSTEM_PROCESSOR}-w64-mingw32" CACHE FILEPATH "" FORCE) set(ENV{PKG_CONFIG_SYSROOT_DIR} "${CMAKE_SYSROOT}") if($ENV{PKG_CONFIG_LIBDIR}) set(ENV{PKG_CONFIG_LIBDIR} "${CMAKE_SYSROOT}/usr/lib/pkgconfig:${CMAKE_SYSROOT}/usr/share/pkgconfig:$ENV{PKG_CONFIG_LIBDIR}") else() set(ENV{PKG_CONFIG_LIBDIR} "${CMAKE_SYSROOT}/usr/lib/pkgconfig:${CMAKE_SYSROOT}/usr/share/pkgconfig") endif() # set these before find_program! set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY) # search tools in prefix, then in system search paths # note that the toolchain will be sourced multiple times and stuff like # CMAKE_C_COMPILER might be cached - use temp variables with find_program set(_linker lld) set(_clang_path) if(CMAKE_HOST_WIN32) set(_clang_path PATH_SUFFIXES LLVM/bin) endif() find_program(_clang_exe clang HINTS "${_prefix}bin" NO_CMAKE_PATH NO_CMAKE_ENVIRONMENT_PATH NO_CACHE ${_clang_path}) find_program(_clangp_exe clang++ HINTS "${_prefix}bin" NO_CMAKE_PATH NO_CMAKE_ENVIRONMENT_PATH NO_CACHE ${_clang_path}) find_program(_llvm_rc llvm-rc HINTS "${_prefix}bin" NO_CMAKE_PATH NO_CMAKE_ENVIRONMENT_PATH NO_CACHE ${_clang_path}) find_program(_ld_linker ld.${_linker} HINTS "${_prefix}bin" NO_CMAKE_PATH NO_CMAKE_ENVIRONMENT_PATH NO_CACHE ${_clang_path}) if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.20") cmake_path(GET _clang_exe PARENT_PATH _clang_path) else() get_filename_component(_clang_path "${_clang_exe}" DIRECTORY) endif() # test if the system compiler is used if(_clang_path STREQUAL "${_prefix}bin") set(CMAKE_ASM_COMPILER "${_clang_exe}") set(CMAKE_C_COMPILER "${_clang_exe}") set(CMAKE_CXX_COMPILER "${_clangp_exe}") else() file(GLOB _respath "${_prefix}lib/clang/*") set(CMAKE_ASM_COMPILER "${_clang_exe}" "-resource-dir=${_respath}") set(CMAKE_C_COMPILER "${_clang_exe}" "-resource-dir=${_respath}") set(CMAKE_CXX_COMPILER "${_clangp_exe}" "-resource-dir=${_respath}") endif() set(CMAKE_RC_COMPILER "${_llvm_rc}") set(CMAKE_LINKER "${_ld_linker}") unset(_clang_path) unset(_prefix) unset(_clang_exe) unset(_clangp_exe) unset(_llvm_rc) unset(_ld_linker) set(CMAKE_C_COMPILER_TARGET ${CMAKE_SYSTEM_PROCESSOR}-w64-mingw32) set(CMAKE_CXX_COMPILER_TARGET ${CMAKE_C_COMPILER_TARGET}) set(CMAKE_ASM_COMPILER_TARGET ${CMAKE_C_COMPILER_TARGET}) set(CMAKE_CXX_FLAGS_INIT "-stdlib=libc++") if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.29") string(TOUPPER ${_linker} CMAKE_LINKER_TYPE) set(_linker) else() set(_linker " -fuse-ld=${_linker}") endif() set(CMAKE_EXE_LINKER_FLAGS_INIT "--start-no-unused-arguments -stdlib=libc++ -rtlib=compiler-rt -unwindlib=libunwind --end-no-unused-arguments${_linker}") set(CMAKE_MODULE_LINKER_FLAGS_INIT "${CMAKE_EXE_LINKER_FLAGS_INIT}") set(CMAKE_SHARED_LINKER_FLAGS_INIT "${CMAKE_EXE_LINKER_FLAGS_INIT}") unset(_linker) ```
main.cpp ```cpp #include #include #if !defined(_M_X64) #error "not a x86_64 compiler" #endif int main() { OSVERSIONINFO info{.dwOSVersionInfoSize = sizeof(OSVERSIONINFO)}; ::GetVersionEx(&info); std::cout << "Hello Windows " << info.dwMajorVersion << "." << info.dwMinorVersion << "." << info.dwBuildNumber << " " << info.szCSDVersion << "\n"; } ```

Apparently one can use lldb to debug applications with wine, as seen at https://werat.dev/blog/debugging-wine-with-lldb-and-vscode/

But patches are required to get things up and running.

I think it would be great if LLVM-MinGW could have Linux and macOS toolchains that would have debugging working with wine!

nolange commented 2 months ago

The IDE will have to understand that wine is not the process to be debugged, and it should "remote connect" to the real process. To date, I haven't found an IDE that covers this transparently, but that's where the work needs to be done.