-
Notifications
You must be signed in to change notification settings - Fork 11
windows vcpkg support #25
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
base: main
Are you sure you want to change the base?
Conversation
livekit.vcxproj -> D:\workspace\lib-workspace\client-sdk-cpp\build\Release\livekit.lib SimpleDataStream.vcxproj -> D:\workspace\lib-workspace\client-sdk-cpp\build\examples\Release\SimpleDataStream.exe SimpleRoom.vcxproj -> D:\workspace\lib-workspace\client-sdk-cpp\build\examples\Release\SimpleRoom.exe SimpleRpc.vcxproj -> D:\workspace\lib-workspace\client-sdk-cpp\build\examples\Release\SimpleRpc.exe Build Succeeded.
- Fix "file path too long" errors by switching from CMAKE_SOURCE_DIR to CMAKE_CURRENT_SOURCE_DIR for relative path resolution. - Refactor CMakeLists.txt to support nested project usage via LIVEKIT_IS_TOPLEVEL check. - Align MSVC runtime library with Rust static CRT (MultiThreaded) to prevent link-time conflicts. - Implement unified binary output directory (bin/lib/include) with config-specific subfolders. - Add robust cargo build integration using run_cargo.cmake script. - Introduce install logic and full clean targets (clean_all).
- Added CMakePresets.json for unified cross-platform build configurations. - Optimized Rust FFI build logic to prevent unnecessary recompilation when C++ code changes. - Fixed MSVC runtime library (MT/MD) mismatch on Windows. - Added automatic header aggregation to build/include directory. - Refactored CMakeLists.txt to support both top-level and subdirectory integration.
…cies - Add GitHub Actions workflow for Windows, Linux, and macOS - Integrate vcpkg manifest mode with CMake Presets - Fix missing Linux dependencies (libva, alsa, libclang, etc.) - Add CXXFLAGS to ignore deprecated warnings from WebRTC on newer GCC - Synchronize git submodules and fix protocol file paths - Configure build.h template for build metadata injection
- Remove livekit_ffi.h inclusion from public participant.h - Add livekit_ffi.h to room.cpp for internal access to INVALID_HANDLE - Improve header encapsulation by hiding internal FFI definitions from SDK users
…T conflicts
Motivation:
The prebuilt libwebrtc library is strictly compiled with the /MT runtime,
causing severe symbol redefinition and runtime mismatch errors (LNK2038)
when linked against /MD-based Qt applications.
Changes:
1. Architecture Redesign: Refactored livekit-ffi to build as a shared library
(cdylib/DLL) instead of a static library on Windows.
2. Binary Isolation: Leveraged the DLL boundary to encapsulate /MT dependencies,
allowing the consumer layer (livekit.lib) to safely use /MD.
3. CMake Infrastructure Enhancements:
- Explicitly set CMAKE_MSVC_RUNTIME_LIBRARY to MultiThreadedDLL for
MSVC targets.
- Automated the Rust build pipeline with PROTOC environment variable
injection for protobuf generation.
- Added POST_BUILD commands to automatically deploy livekit_ffi.dll and
third-party dependencies (protobuf, abseil) to the output directory.
4. Platform Consistency: Maintained the original static linking logic for
Linux and macOS to preserve performance and simplicity.
Verification:
Validated the generated livekit.lib using `dumpbin /DIRECTIVES`, confirming
the RuntimeLibrary is correctly set to MD_DynamicRelease.
- Automatically copy libprotobuf.lib and abseil_dll.lib to SDK lib
- Replace protobuf_generate with custom add_custom_command - Use --proto_path to ensure correct symbol naming - Linux/macOS use system protobuf (apt/brew) - Windows uses vcpkg - Update documentation for platform-specific dependencies
- Add include paths for all examples (src/, generated/, protobuf) - Copy DLLs to examples output on Windows - Use FetchContent for SDL3 on all platforms - Remove sdl3 from vcpkg.json (not in baseline)
- Add debug-examples and release-examples commands - Update usage help text
|
Great work. I was also hit by the MT / MD issues, the problem seems to be some pre-built libs are using MT and it will cause symbol conflicts, I suspect it was libwebrtc but didn't get time to verify it. I like your approach of workaround the problem:
|
xianshijing-lk
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
from a quick look. Thanks, they are solid code.
| run: | | ||
| [[ -x build.sh ]] && ./build.sh clean-all || true | ||
| if [[ "$RUNNER_OS" == "Windows" ]]; then | ||
| rm -rf build || true |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not sure if it is enough to remove the build folder ? I think "./build.sh clean" also does the "cd client-sdk-rust; cargo clean;"
| run: | | ||
| ./build.sh release | ||
| - name: Configure CMake | ||
| run: cmake --preset ${{ matrix.preset }} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I really like adding the preset.
But I wonder if we should do build.sh on Unix and build.cmd on windows ? so that the CIs and developers are using the same development cmds. What do you think?
| cmake_minimum_required(VERSION 3.20) | ||
|
|
||
| if(NOT DEFINED LIVEKIT_VERSION OR LIVEKIT_VERSION STREQUAL "") | ||
| set(LIVEKIT_VERSION "0.1.0") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit, just use 0.0.0 as default. once your PR is landed, I would like to make the first release.
| TARGET livekit_proto | ||
| PROTOC_OUT_DIR ${PROTO_BINARY_DIR} | ||
| IMPORT_DIRS ${FFI_PROTO_DIR} | ||
| # Manually generate protobuf files to avoid path prefix issues |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Interesting. I am curious what path prefix issues you met. The protobuf worked out of box for me after I installed the protobuf via vcpkg, but likely my workspace wasn't cleaned at all.
| add_custom_command( | ||
| TARGET build_rust_ffi | ||
| POST_BUILD | ||
| COMMAND ${CMAKE_AR} -dv "${RUST_LIB_RELEASE}" protozero_plugin.o |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you will need to rebase my latest change in #21, otherwise the debug build will fail on Linux as it is looking for ${RUST_LIB_RELEASE}
| "displayName": "Windows x64 Debug", | ||
| "description": "Build for Windows x64 Debug (vcpkg)", | ||
| "inherits": "windows-base", | ||
| "binaryDir": "${sourceDir}/build" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should release and debug have different binaryDir ?
like ${sourceDir}/build-release
${sourceDir}/build-debug ?
| "displayName": "Linux Release", | ||
| "description": "Build for Linux Release (system packages)", | ||
| "inherits": "linux-base", | ||
| "binaryDir": "${sourceDir}/build", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
same for Linux and Mac
| } | ||
| }, | ||
| { | ||
| "name": "windows-release", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
is it intentional to have windows-release and windows-debug to be the same ?
if they should be the same, should we just use one windows rather than 2 ?
|
|
||
| :build_only | ||
| echo ==^> Building (%BUILD_TYPE%)... | ||
| cmake --build "%BUILD_DIR%" --config %BUILD_TYPE% -j %VERBOSE% |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
do we need the -j on windows ?
if VERBOSE is empty, will it work ? I am not sure, but doubt if "cmake --build ... -j" is valid
|
|
||
| if "%1"=="debug-examples" ( | ||
| set "BUILD_TYPE=Debug" | ||
| set "PRESET=windows-debug-examples" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I only see windows-release-examples, do we need windows-debug-examples here ?
This PR adjusts the build configuration to handle platform-specific dependency management. #23
Initially, I tried using vcpkg for protobuf and abseil on all platforms. However, I encountered a few issues:
The SDK produces static libraries (
livekit.libandlivekit_ffi.lib). When testing on WSL, I found that users need to link the exact protobuf and abseil versions used during build. On Windows, there's an additional complication: thewebrtc-syscrate inclient-sdk-rustuses pre-built static libraries with/MTruntime (seeconfig.toml:target-feature=+crt-static). Iflivekit.libalso uses/MT, any application using/MDruntime will encounter linking conflicts. Since most Windows applications and frameworks use/MDby default, I changedlivekit_ffito a DLL to isolate the/MTdependency, allowinglivekit.libto use/MDsafely.Linux and macOS don't have the
/MTvs/MDdistinction. Also, vcpkg's library versions don't match what system package managers provide, making it impractical to bundle everything. It's much simpler for users to just install protobuf and abseil via apt or brew.The current approach:
Using the SDK:
livekit.libandlivekit_ffi.dll.lib, copy the DLLs to your executable directorylibprotobuf-devandlibabsl-devvia apt, then linkliblivekit.aandliblivekit_ffi.aprotobufandabseilvia brew, then linkliblivekit.aandliblivekit_ffi.aI'm not sure if this is the best solution, but Windows lacks a system package manager, so bundling dependencies seems necessary for a usable distribution.
Windows output structure:
The CI now builds and runs examples on all platforms to verify the libraries work correctly.