From 40e21a0c1b5fc222d236e35e994bc3a4aba49f64 Mon Sep 17 00:00:00 2001 From: KHeartz Date: Fri, 12 Jun 2026 23:57:47 -0400 Subject: [PATCH] feat: build RakVoice into the core library Move RakVoice from DependentExtensions into the core MafiaNet library so voice support is always built, instead of being gated behind MAFIANET_BUILD_SAMPLES. - Move RakVoice.{h,cpp} to Source/include/mafianet and Source/src, and add them to the core source/header lists. - Add cmake/FetchVoiceDependencies.cmake to fetch Opus and RNNoise unconditionally, included before the Source subdirectory. The core targets link them via $ so the install/export set is unaffected. - Drop Opus/RNNoise from FetchDependencies.cmake (now sample-only: bzip2, miniupnpc, jansson) and remove the standalone RakVoice target. - Repoint the RakVoice samples at the MafiaNet target and the mafianet/RakVoice.h header. Fix the RNNoise target source list while here: it omitted parse_lpcnet_weights.c and the model rnnoise_data.c, leaving rnn_parse_weights/init_rnnoise/rnnoise_arrays unresolved when linking a shared library or executable. --- CMakeLists.txt | 13 +- DependentExtensions/CMakeLists.txt | 8 +- Samples/RakVoice/CMakeLists.txt | 1 - Samples/RakVoice/main.cpp | 2 +- Samples/RakVoiceDSound/CMakeLists.txt | 1 - Samples/RakVoiceDSound/DSoundVoiceAdapter.h | 2 +- Samples/RakVoiceDSound/main.cpp | 2 +- Samples/RakVoiceFMOD/CMakeLists.txt | 1 - Samples/RakVoiceFMOD/FMODVoiceAdapter.h | 2 +- Samples/RakVoiceFMOD/main.cpp | 2 +- Source/CMakeLists.txt | 20 +++ .../include/mafianet}/RakVoice.h | 0 .../src}/RakVoice.cpp | 2 +- cmake/FetchDependencies.cmake | 84 +------------ cmake/FetchVoiceDependencies.cmake | 119 ++++++++++++++++++ 15 files changed, 164 insertions(+), 95 deletions(-) rename {DependentExtensions => Source/include/mafianet}/RakVoice.h (100%) rename {DependentExtensions => Source/src}/RakVoice.cpp (96%) create mode 100644 cmake/FetchVoiceDependencies.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 0422e89c8..e6a6e55da 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -45,11 +45,22 @@ find_package(Threads REQUIRED) list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake") include(MafiaNetHelpers) +# RakVoice is built into the core library, so its dependencies (Opus, RNNoise) +# are always fetched, before the Source subdirectory that consumes them. +include(FetchVoiceDependencies) + # Platform-specific settings if(WIN32) add_compile_definitions( _CRT_SECURE_NO_DEPRECATE _CRT_NONSTDC_NO_DEPRECATE + # Suppress the legacy Winsock 1.1 header. Several samples include + # before the MafiaNet headers that pull in ; + # without this, windows.h drags in winsock.h first and winsock2.h then + # redefines sockaddr/fd_set/etc. (C2011/C2375). winsock2.h itself + # defines _WINSOCKAPI_ for the same reason, so predefining it globally + # is consistent and harmless for the core library. + _WINSOCKAPI_ ) endif() @@ -58,7 +69,7 @@ add_subdirectory(Source) # Samples and extensions if(MAFIANET_BUILD_SAMPLES) - # Fetch dependencies (bzip2, miniupnpc, opus, rnnoise) + # Fetch sample/extension dependencies (bzip2, miniupnpc, jansson) include(FetchDependencies) add_subdirectory(Samples) add_subdirectory(DependentExtensions) diff --git a/DependentExtensions/CMakeLists.txt b/DependentExtensions/CMakeLists.txt index e586f0105..ff88e41fc 100644 --- a/DependentExtensions/CMakeLists.txt +++ b/DependentExtensions/CMakeLists.txt @@ -1,6 +1,6 @@ # MafiaNet Dependent Extensions # -# Dependencies (bzip2, miniupnpc, opus, rnnoise) are fetched via FetchContent +# Dependencies (bzip2, miniupnpc, jansson) are fetched via FetchContent # in cmake/FetchDependencies.cmake # # Copyright (c) 2024, MafiaHub @@ -12,10 +12,8 @@ add_subdirectory(Autopatcher) # Lobby2 extension (matchmaking and lobby system) add_subdirectory(Lobby2) -# RakVoice - voice compression and transmission (uses opus, rnnoise from FetchContent) -add_library(RakVoice STATIC RakVoice.cpp RakVoice.h) -target_link_libraries(RakVoice PUBLIC MafiaNet PRIVATE opus rnnoise) -target_include_directories(RakVoice PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) +# RakVoice (voice compression using Opus + RNNoise) is built into the core +# MafiaNet library; see Source/CMakeLists.txt. # Optional extensions based on available dependencies diff --git a/Samples/RakVoice/CMakeLists.txt b/Samples/RakVoice/CMakeLists.txt index 3a55dd678..ca6dc401c 100644 --- a/Samples/RakVoice/CMakeLists.txt +++ b/Samples/RakVoice/CMakeLists.txt @@ -61,7 +61,6 @@ if(PORTAUDIO_FOUND) add_executable(RakVoiceSample main.cpp) target_link_libraries(RakVoiceSample PRIVATE MafiaNet - RakVoice ${PORTAUDIO_LIBRARIES} ) target_include_directories(RakVoiceSample PRIVATE diff --git a/Samples/RakVoice/main.cpp b/Samples/RakVoice/main.cpp index 2b737ac30..646ddbcad 100644 --- a/Samples/RakVoice/main.cpp +++ b/Samples/RakVoice/main.cpp @@ -22,7 +22,7 @@ #include "mafianet/peerinterface.h" #include "mafianet/MessageIdentifiers.h" -#include "RakVoice.h" +#include "mafianet/RakVoice.h" #include "mafianet/statistics.h" #include "mafianet/NatPunchthroughClient.h" #include "mafianet/BitStream.h" diff --git a/Samples/RakVoiceDSound/CMakeLists.txt b/Samples/RakVoiceDSound/CMakeLists.txt index 80e1ca2e1..c701f15f5 100644 --- a/Samples/RakVoiceDSound/CMakeLists.txt +++ b/Samples/RakVoiceDSound/CMakeLists.txt @@ -43,7 +43,6 @@ if(DSOUND_INCLUDE_DIR AND DSOUND_LIBRARY) target_link_libraries(RakVoiceDSoundSample PRIVATE MafiaNet - RakVoice ${DSOUND_LIBRARY} ${DXERR_LIBRARY} winmm diff --git a/Samples/RakVoiceDSound/DSoundVoiceAdapter.h b/Samples/RakVoiceDSound/DSoundVoiceAdapter.h index f6d0cd014..04713dbbc 100644 --- a/Samples/RakVoiceDSound/DSoundVoiceAdapter.h +++ b/Samples/RakVoiceDSound/DSoundVoiceAdapter.h @@ -31,7 +31,7 @@ of each frame. #ifndef __DSOUNDVOICEADAPTER_H #define __DSOUNDVOICEADAPTER_H -#include "RakVoice.h" +#include "mafianet/RakVoice.h" // If you get: // Error 1 fatal error C1083: Cannot open include file: 'dsound.h': No such file or directory diff --git a/Samples/RakVoiceDSound/main.cpp b/Samples/RakVoiceDSound/main.cpp index 1889702e7..54076ca2d 100644 --- a/Samples/RakVoiceDSound/main.cpp +++ b/Samples/RakVoiceDSound/main.cpp @@ -27,7 +27,7 @@ #include "mafianet/MessageIdentifiers.h" #include "mafianet/sleep.h" -#include "RakVoice.h" +#include "mafianet/RakVoice.h" #include "mafianet/statistics.h" #include "mafianet/GetTime.h" #include "mafianet/assert.h" diff --git a/Samples/RakVoiceFMOD/CMakeLists.txt b/Samples/RakVoiceFMOD/CMakeLists.txt index 374a5000e..52ab021a6 100644 --- a/Samples/RakVoiceFMOD/CMakeLists.txt +++ b/Samples/RakVoiceFMOD/CMakeLists.txt @@ -34,7 +34,6 @@ if(FMOD_INCLUDE_DIR AND FMOD_LIBRARY) target_link_libraries(RakVoiceFMODSample PRIVATE MafiaNet - RakVoice ${FMOD_LIBRARY} ) diff --git a/Samples/RakVoiceFMOD/FMODVoiceAdapter.h b/Samples/RakVoiceFMOD/FMODVoiceAdapter.h index ec790a54c..2723a2544 100644 --- a/Samples/RakVoiceFMOD/FMODVoiceAdapter.h +++ b/Samples/RakVoiceFMOD/FMODVoiceAdapter.h @@ -20,7 +20,7 @@ #ifndef __FMODVOICEBRIDGE_H #define __FMODVOICEBRIDGE_H -#include "RakVoice.h" +#include "mafianet/RakVoice.h" // If you get: // Error 1 fatal error C1083: Cannot open include file: 'fmod.hpp': No such file or directory c:\raknet\samples\rakvoicefmod\fmodvoiceadapter.h 9 diff --git a/Samples/RakVoiceFMOD/main.cpp b/Samples/RakVoiceFMOD/main.cpp index 88a480469..a25702a73 100644 --- a/Samples/RakVoiceFMOD/main.cpp +++ b/Samples/RakVoiceFMOD/main.cpp @@ -27,7 +27,7 @@ #include "mafianet/Gets.h" #include "mafianet/sleep.h" -#include "RakVoice.h" +#include "mafianet/RakVoice.h" #include "mafianet/statistics.h" #include "mafianet/GetTime.h" #include "mafianet/assert.h" diff --git a/Source/CMakeLists.txt b/Source/CMakeLists.txt index bfaca360d..bc2586bef 100644 --- a/Source/CMakeLists.txt +++ b/Source/CMakeLists.txt @@ -77,6 +77,7 @@ set(MAFIANET_SOURCES src/RakSleep.cpp src/RakString.cpp src/RakThread.cpp + src/RakVoice.cpp src/RakWString.cpp src/Rand.cpp src/RandSync.cpp @@ -222,6 +223,7 @@ set(MAFIANET_HEADERS include/mafianet/PS3Includes.h include/mafianet/PS4Includes.h include/mafianet/Rackspace.h + include/mafianet/RakVoice.h include/mafianet/Rand.h include/mafianet/RandSync.h include/mafianet/ReadyEvent.h @@ -319,6 +321,12 @@ function(mafianet_configure_target target_name) PRIVATE Threads::Threads $<$:ws2_32> + # RakVoice (built into the core library) requires the Opus codec and + # RNNoise noise suppression, fetched in FetchVoiceDependencies. These + # are bundled into the MafiaNet export set (see Installation below) so + # installed static-library consumers can resolve the symbols. + opus + rnnoise ) target_compile_definitions(${target_name} @@ -402,6 +410,18 @@ install(TARGETS ${MAFIANET_INSTALL_TARGETS} INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} ) +# RakVoice links the Opus and RNNoise static libraries into the core library. +# Bundle them into the MafiaNet export so installed static-library consumers can +# resolve opus_*/rnnoise_* symbols (neither dependency ships its own CMake config +# package here). Opus also self-exports to its own OpusTargets set, which is +# harmless: a target may belong to multiple export sets. +install(TARGETS opus rnnoise + EXPORT MafiaNetTargets + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} +) + # Install headers install(DIRECTORY include/ DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} diff --git a/DependentExtensions/RakVoice.h b/Source/include/mafianet/RakVoice.h similarity index 100% rename from DependentExtensions/RakVoice.h rename to Source/include/mafianet/RakVoice.h diff --git a/DependentExtensions/RakVoice.cpp b/Source/src/RakVoice.cpp similarity index 96% rename from DependentExtensions/RakVoice.cpp rename to Source/src/RakVoice.cpp index af741aa8b..dbc5d76a8 100644 --- a/DependentExtensions/RakVoice.cpp +++ b/Source/src/RakVoice.cpp @@ -14,7 +14,7 @@ * license found in the license.txt file in the root directory of this source tree. */ -#include "RakVoice.h" +#include "mafianet/RakVoice.h" #include #include #include "mafianet/BitStream.h" diff --git a/cmake/FetchDependencies.cmake b/cmake/FetchDependencies.cmake index f6fcc2959..e3219e01d 100644 --- a/cmake/FetchDependencies.cmake +++ b/cmake/FetchDependencies.cmake @@ -62,87 +62,14 @@ set(UPNPC_BUILD_TESTS OFF CACHE BOOL "" FORCE) set(UPNPC_BUILD_SAMPLE OFF CACHE BOOL "" FORCE) set(UPNPC_NO_INSTALL ON CACHE BOOL "" FORCE) -# ----------------------------------------------------------------------------- -# Opus - audio codec for RakVoice -# ----------------------------------------------------------------------------- -FetchContent_Declare( - Opus - GIT_REPOSITORY https://github.com/xiph/opus.git - GIT_TAG v1.6.1 - GIT_SHALLOW TRUE -) - -# Opus configuration -set(OPUS_BUILD_SHARED_LIBRARY OFF CACHE BOOL "" FORCE) -set(OPUS_BUILD_TESTING OFF CACHE BOOL "" FORCE) -set(OPUS_BUILD_PROGRAMS OFF CACHE BOOL "" FORCE) -set(OPUS_INSTALL_PKG_CONFIG_MODULE OFF CACHE BOOL "" FORCE) -set(OPUS_INSTALL_CMAKE_CONFIG_MODULE OFF CACHE BOOL "" FORCE) - -# ----------------------------------------------------------------------------- -# RNNoise - neural network noise suppression for RakVoice -# ----------------------------------------------------------------------------- -# RNNoise doesn't have a proper CMake build, so we fetch and build manually -FetchContent_Declare( - rnnoise - GIT_REPOSITORY https://github.com/xiph/rnnoise.git - GIT_TAG v0.2 - GIT_SHALLOW TRUE -) - -# RNNoise model data (neural network weights) -set(RNNOISE_MODEL_VERSION "0b50c45") -FetchContent_Declare( - rnnoise_model - URL https://media.xiph.org/rnnoise/models/rnnoise_data-${RNNOISE_MODEL_VERSION}.tar.gz - URL_HASH SHA256=4ac81c5c0884ec4bd5907026aaae16209b7b76cd9d7f71af582094a2f98f4b43 -) +# Note: Opus and RNNoise (used by RakVoice, which is built into the core +# library) are fetched separately in FetchVoiceDependencies.cmake so they are +# always available, independent of MAFIANET_BUILD_SAMPLES. # ----------------------------------------------------------------------------- # Fetch all dependencies # ----------------------------------------------------------------------------- -FetchContent_MakeAvailable(bzip2 miniupnpc Opus jansson) - -# Fetch rnnoise separately (needs manual target creation) -FetchContent_GetProperties(rnnoise) -if(NOT rnnoise_POPULATED) - FetchContent_Populate(rnnoise) -endif() - -# Fetch rnnoise model data -FetchContent_GetProperties(rnnoise_model) -if(NOT rnnoise_model_POPULATED) - FetchContent_Populate(rnnoise_model) -endif() - -# ----------------------------------------------------------------------------- -# RNNoise - manual target creation (no upstream CMakeLists.txt) -# ----------------------------------------------------------------------------- -if(NOT TARGET rnnoise) - add_library(rnnoise STATIC - ${rnnoise_SOURCE_DIR}/src/denoise.c - ${rnnoise_SOURCE_DIR}/src/rnn.c - ${rnnoise_SOURCE_DIR}/src/rnnoise_tables.c - ${rnnoise_SOURCE_DIR}/src/nnet.c - ${rnnoise_SOURCE_DIR}/src/nnet_default.c - ${rnnoise_SOURCE_DIR}/src/pitch.c - ${rnnoise_SOURCE_DIR}/src/kiss_fft.c - ${rnnoise_SOURCE_DIR}/src/celt_lpc.c - ) - # Get Opus source directory for celt headers (needed by vec_neon.h) - FetchContent_GetProperties(Opus) - target_include_directories(rnnoise - PUBLIC - ${rnnoise_SOURCE_DIR}/include - PRIVATE - ${rnnoise_SOURCE_DIR}/src - ${rnnoise_model_SOURCE_DIR}/src # Contains rnnoise_data.h - ${opus_SOURCE_DIR}/celt # Contains os_support.h - ${opus_SOURCE_DIR}/include # Contains opus_defines.h - ) - target_compile_definitions(rnnoise PRIVATE COMPILE_OPUS=1) - set_target_properties(rnnoise PROPERTIES FOLDER "Dependencies") -endif() +FetchContent_MakeAvailable(bzip2 miniupnpc jansson) # ----------------------------------------------------------------------------- # Create aliases for compatibility with existing target names @@ -164,9 +91,6 @@ endif() if(TARGET libminiupnpc-static) set_target_properties(libminiupnpc-static PROPERTIES FOLDER "Dependencies") endif() -if(TARGET opus) - set_target_properties(opus PROPERTIES FOLDER "Dependencies") -endif() if(TARGET jansson) set_target_properties(jansson PROPERTIES FOLDER "Dependencies") endif() diff --git a/cmake/FetchVoiceDependencies.cmake b/cmake/FetchVoiceDependencies.cmake new file mode 100644 index 000000000..05911d7e3 --- /dev/null +++ b/cmake/FetchVoiceDependencies.cmake @@ -0,0 +1,119 @@ +# MafiaNet Voice Dependency Fetching +# +# Fetches the Opus codec and RNNoise noise suppression used by RakVoice. +# RakVoice is built into the core MafiaNet library, so these dependencies are +# always fetched (no system package fallback) for reproducible builds. +# +# Copyright (c) 2024, MafiaHub +# Licensed under MIT-style license + +include(FetchContent) + +message(STATUS "Fetching MafiaNet voice dependencies (Opus, RNNoise)...") + +# ----------------------------------------------------------------------------- +# Opus - audio codec for RakVoice +# ----------------------------------------------------------------------------- +FetchContent_Declare( + Opus + GIT_REPOSITORY https://github.com/xiph/opus.git + GIT_TAG v1.6.1 + GIT_SHALLOW TRUE +) + +# Opus configuration +set(OPUS_BUILD_SHARED_LIBRARY OFF CACHE BOOL "" FORCE) +set(OPUS_BUILD_TESTING OFF CACHE BOOL "" FORCE) +set(OPUS_BUILD_PROGRAMS OFF CACHE BOOL "" FORCE) +set(OPUS_INSTALL_PKG_CONFIG_MODULE OFF CACHE BOOL "" FORCE) +set(OPUS_INSTALL_CMAKE_CONFIG_MODULE OFF CACHE BOOL "" FORCE) + +# ----------------------------------------------------------------------------- +# RNNoise - neural network noise suppression for RakVoice +# ----------------------------------------------------------------------------- +# RNNoise doesn't have a proper CMake build, so we fetch and build manually +FetchContent_Declare( + rnnoise + GIT_REPOSITORY https://github.com/xiph/rnnoise.git + GIT_TAG v0.2 + GIT_SHALLOW TRUE +) + +# RNNoise model data (neural network weights) +set(RNNOISE_MODEL_VERSION "0b50c45") +FetchContent_Declare( + rnnoise_model + URL https://media.xiph.org/rnnoise/models/rnnoise_data-${RNNOISE_MODEL_VERSION}.tar.gz + URL_HASH SHA256=4ac81c5c0884ec4bd5907026aaae16209b7b76cd9d7f71af582094a2f98f4b43 +) + +# ----------------------------------------------------------------------------- +# Fetch dependencies +# ----------------------------------------------------------------------------- +FetchContent_MakeAvailable(Opus) + +# Fetch rnnoise separately (needs manual target creation) +FetchContent_GetProperties(rnnoise) +if(NOT rnnoise_POPULATED) + FetchContent_Populate(rnnoise) +endif() + +# Fetch rnnoise model data +FetchContent_GetProperties(rnnoise_model) +if(NOT rnnoise_model_POPULATED) + FetchContent_Populate(rnnoise_model) +endif() + +# ----------------------------------------------------------------------------- +# RNNoise - manual target creation (no upstream CMakeLists.txt) +# ----------------------------------------------------------------------------- +if(NOT TARGET rnnoise) + add_library(rnnoise STATIC + ${rnnoise_SOURCE_DIR}/src/denoise.c + ${rnnoise_SOURCE_DIR}/src/rnn.c + ${rnnoise_SOURCE_DIR}/src/rnnoise_tables.c + ${rnnoise_SOURCE_DIR}/src/nnet.c + ${rnnoise_SOURCE_DIR}/src/nnet_default.c + ${rnnoise_SOURCE_DIR}/src/pitch.c + ${rnnoise_SOURCE_DIR}/src/kiss_fft.c + ${rnnoise_SOURCE_DIR}/src/celt_lpc.c + # Weight parser (parse_weights -> rnn_parse_weights via nnet.h) + ${rnnoise_SOURCE_DIR}/src/parse_lpcnet_weights.c + # Model weight data (rnnoise_arrays, init_rnnoise) + ${rnnoise_model_SOURCE_DIR}/src/rnnoise_data.c + ) + # Get Opus source directory for celt headers (needed by vec_neon.h) + FetchContent_GetProperties(Opus) + target_include_directories(rnnoise + PUBLIC + # Build-interface only: rnnoise is bundled into the MafiaNet export, + # but its headers are not installed (RakVoice.h forward-declares the + # RNNoise types), so this build-tree path must not leak into the + # exported/installed interface. + $ + PRIVATE + ${rnnoise_SOURCE_DIR}/src + ${rnnoise_model_SOURCE_DIR}/src # Contains rnnoise_data.h + ${opus_SOURCE_DIR}/celt # Contains os_support.h + ${opus_SOURCE_DIR}/include # Contains opus_defines.h + ) + target_compile_definitions(rnnoise PRIVATE COMPILE_OPUS=1) + # Built static but linked into the shared libmafianet.so, so every object + # must be position-independent (otherwise: "relocation R_X86_64_PC32 ... + # can not be used when making a shared object; recompile with -fPIC"). + set_target_properties(rnnoise PROPERTIES + FOLDER "Dependencies" + POSITION_INDEPENDENT_CODE ON + ) +endif() + +if(TARGET opus) + # Same reason as rnnoise above: PIC is required to link the static opus + # archive into the shared MafiaNet library. + set_target_properties(opus PROPERTIES + FOLDER "Dependencies" + POSITION_INDEPENDENT_CODE ON + ) +endif() + +message(STATUS "MafiaNet voice dependencies fetched successfully")