From e02ebca2c9aeafb2a3d6f71f9c24bb5b1f1d8803 Mon Sep 17 00:00:00 2001 From: Jupeyy Date: Fri, 25 Mar 2022 09:19:18 +0100 Subject: [PATCH 1/2] Rename lib generation scripts --- scripts/{android => compile_libs}/cmake_lib_compile.sh | 0 scripts/{android/gen_android_libs.sh => compile_libs/gen_libs.sh} | 0 .../make_android_openssl.sh => compile_libs/make_lib_openssl.sh} | 0 .../make_lib_opusfile.sh} | 0 .../make_android_sqlite3.sh => compile_libs/make_lib_sqlite3.sh} | 0 5 files changed, 0 insertions(+), 0 deletions(-) rename scripts/{android => compile_libs}/cmake_lib_compile.sh (100%) rename scripts/{android/gen_android_libs.sh => compile_libs/gen_libs.sh} (100%) rename scripts/{android/make_android_openssl.sh => compile_libs/make_lib_openssl.sh} (100%) rename scripts/{android/make_android_opusfile.sh => compile_libs/make_lib_opusfile.sh} (100%) rename scripts/{android/make_android_sqlite3.sh => compile_libs/make_lib_sqlite3.sh} (100%) diff --git a/scripts/android/cmake_lib_compile.sh b/scripts/compile_libs/cmake_lib_compile.sh similarity index 100% rename from scripts/android/cmake_lib_compile.sh rename to scripts/compile_libs/cmake_lib_compile.sh diff --git a/scripts/android/gen_android_libs.sh b/scripts/compile_libs/gen_libs.sh similarity index 100% rename from scripts/android/gen_android_libs.sh rename to scripts/compile_libs/gen_libs.sh diff --git a/scripts/android/make_android_openssl.sh b/scripts/compile_libs/make_lib_openssl.sh similarity index 100% rename from scripts/android/make_android_openssl.sh rename to scripts/compile_libs/make_lib_openssl.sh diff --git a/scripts/android/make_android_opusfile.sh b/scripts/compile_libs/make_lib_opusfile.sh similarity index 100% rename from scripts/android/make_android_opusfile.sh rename to scripts/compile_libs/make_lib_opusfile.sh diff --git a/scripts/android/make_android_sqlite3.sh b/scripts/compile_libs/make_lib_sqlite3.sh similarity index 100% rename from scripts/android/make_android_sqlite3.sh rename to scripts/compile_libs/make_lib_sqlite3.sh From bb1ed45c3d389baf96cf7d3b66faa46d4a088bb8 Mon Sep 17 00:00:00 2001 From: Jupeyy Date: Fri, 25 Mar 2022 09:26:37 +0100 Subject: [PATCH 2/2] Emscripten support --- CMakeLists.txt | 29 ++- README.md | 28 +++ cmake/FindCrypto.cmake | 2 +- cmake/FindZLIB.cmake | 29 +++ cmake/toolchains/Emscripten.toolchain | 37 +++ other/emscripten/minimal.html | 44 ++++ scripts/android/README.md | 2 +- scripts/compile_libs/cmake_lib_compile.sh | 96 +++++--- scripts/compile_libs/gen_libs.sh | 216 ++++++++++++------ scripts/compile_libs/make_lib_openssl.sh | 31 ++- scripts/compile_libs/make_lib_opusfile.sh | 38 ++- scripts/compile_libs/make_lib_sqlite3.sh | 42 +++- src/base/detect.h | 6 +- .../client/backend/opengl/backend_opengl3.cpp | 36 +-- src/engine/client/backend_sdl.cpp | 7 + src/engine/client/client.cpp | 2 + src/engine/client/notifications.cpp | 2 +- src/engine/shared/config_variables.h | 4 + 18 files changed, 504 insertions(+), 147 deletions(-) create mode 100644 cmake/toolchains/Emscripten.toolchain create mode 100644 other/emscripten/minimal.html diff --git a/CMakeLists.txt b/CMakeLists.txt index 44827a97f..f20fecf58 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -70,7 +70,7 @@ endif() if(CMAKE_SYSTEM_NAME STREQUAL "Windows") set(TARGET_OS "windows") -elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux") +elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "Emscripten") set(TARGET_OS "linux") elseif(CMAKE_SYSTEM_NAME STREQUAL "Darwin") set(TARGET_OS "mac") @@ -83,7 +83,9 @@ endif() include(CheckCCompilerFlag) include(CheckCXXCompilerFlag) include(CheckSymbolExists) -include(CheckAtomic) +if(NOT (CMAKE_SYSTEM_NAME STREQUAL "Emscripten")) + include(CheckAtomic) +endif() check_symbol_exists(__i386 "" TARGET_ARCH_X86_i386) if(TARGET_ARCH_X86_i386) @@ -125,6 +127,10 @@ option(VULKAN "Enable the vulkan backend" ${AUTO_VULKAN_BACKEND}) option(EXCEPTION_HANDLING "Enable exception handling (only works with Windows as of now)" OFF) +if(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + include(${PROJECT_SOURCE_DIR}/cmake/toolchains/Emscripten.toolchain) +endif() + if(TEST_MYSQL) set(MYSQL ON) endif() @@ -358,6 +364,8 @@ endif() if(FAT) set(LIB_DIR "${TARGET_OS}/libfat") +elseif(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + set(LIB_DIR "webasm/libwasm") elseif(TARGET_CPU_ARCHITECTURE STREQUAL "arm" OR TARGET_CPU_ARCHITECTURE STREQUAL "arm64") set(LIB_DIR "${TARGET_OS}/lib${TARGET_CPU_ARCHITECTURE}") else() @@ -384,12 +392,16 @@ function(set_extra_dirs_include VARIABLE NAME LIBRARY) set("HINTS_${VARIABLE}_INCLUDEDIR" PARENT_SCOPE) is_bundled(IS_BUNDLED "${LIBRARY}") if(IS_BUNDLED) - set("HINTS_${VARIABLE}_INCLUDEDIR" "ddnet-libs/${NAME}/include" "ddnet-libs/${NAME}/include/${TARGET_OS}" PARENT_SCOPE) + set(TMP_TARGET_OS ${TARGET_OS}) + if(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + set(TMP_TARGET_OS webasm) + endif() + set("HINTS_${VARIABLE}_INCLUDEDIR" "ddnet-libs/${NAME}/include" "ddnet-libs/${NAME}/include/${TMP_TARGET_OS}" PARENT_SCOPE) endif() endfunction() if(CMAKE_CROSSCOMPILING) - if(TARGET_OS STREQUAL "android") + if(TARGET_OS STREQUAL "android" OR CMAKE_SYSTEM_NAME STREQUAL "Emscripten") # be more aggressive with android toolchain set(CROSSCOMPILING_NO_CMAKE_SYSTEM_PATH NO_CMAKE_SYSTEM_PATH NO_DEFAULT_PATH NO_CMAKE_FIND_ROOT_PATH) else() @@ -656,6 +668,12 @@ else() endif() endif() +if(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + set(PLATFORM_CLIENT_LIBS GL) + set(PLATFORM_CLIENT_INCLUDE_DIRS "") + set(CMAKE_EXECUTABLE_SUFFIX ".html") +endif() + ######################################################################## # DOWNLOAD GTEST ######################################################################## @@ -2961,6 +2979,9 @@ foreach(target ${TARGETS_OWN}) if(VERSION) target_compile_definitions(${target} PRIVATE GAME_RELEASE_VERSION="${VERSION}") endif() + if(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + target_compile_definitions(${target} PRIVATE CONF_WEBASM) + endif() endforeach() foreach(target ${TARGETS_DEP}) diff --git a/README.md b/README.md index ed682068f..09df1fc8d 100644 --- a/README.md +++ b/README.md @@ -189,6 +189,34 @@ Install MinGW cross-compilers of the form `i686-w64-mingw32-gcc` (32 bit) or Then add `-DCMAKE_TOOLCHAIN_FILE=../cmake/toolchains/mingw64.toolchain` to the **initial** CMake command line. +Cross-compiling on Linux to Web Assembler vis Emscripten +-------------------------------------------------------- + +Install Emscripten cross-compilers (e.g. `sudo apt install emscripten`) on a modern linux distro. + +Then run `emcmake cmake .. -DVIDEORECORDER=OFF -DVULKAN=OFF -DSERVER=OFF -DTOOLS=OFF -DPREFER_BUNDLED_LIBS=ON` in your build directory. + +To test the compiled code locally, just use `emrun --browser firefox DDNet.html` + +To host the compiled .html file copy all `.data`, `.html`, `.js`, `.wasm` files to the web server. (see /other/emscripten/minimal.html for a minimal html example) + +Then enable cross origin policies. Example for apache2 on debian based distros: +```bash +sudo a2enmod header + +# edit the apache2 config to allow .htaccess files +sudo nano /etc/apache2/apache2.conf + +# set AllowOverride to All for your directory +# then create a .htaccess file on the web server (where the .html is) +# and add these lines +Header add Cross-Origin-Embedder-Policy "require-corp" +Header add Cross-Origin-Opener-Policy "same-origin" + +# now restart apache2 +sudo service apache2 restart +``` + Cross-compiling on Linux to macOS --------------------------------- diff --git a/cmake/FindCrypto.cmake b/cmake/FindCrypto.cmake index 138e08996..eaa4aa14f 100644 --- a/cmake/FindCrypto.cmake +++ b/cmake/FindCrypto.cmake @@ -8,7 +8,7 @@ if(NOT PREFER_BUNDLED_LIBS) endif() endif() -if(PREFER_BUNDLED_LIBS AND TARGET_OS STREQUAL "android") +if(PREFER_BUNDLED_LIBS AND (TARGET_OS STREQUAL "android" OR CMAKE_SYSTEM_NAME STREQUAL "Emscripten")) set_extra_dirs_lib(CRYPTO openssl) find_library(CRYPTO_LIBRARY1 NAMES crypto diff --git a/cmake/FindZLIB.cmake b/cmake/FindZLIB.cmake index 87cbd89ea..35f68b201 100644 --- a/cmake/FindZLIB.cmake +++ b/cmake/FindZLIB.cmake @@ -8,6 +8,35 @@ if(NOT PREFER_BUNDLED_LIBS) endif() endif() +if(CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + set_extra_dirs_lib(ZLIB zlib) + find_library(ZLIB_LIBRARY + NAMES z + HINTS ${HINTS_ZLIB_LIBDIR} ${PC_ZLIB_LIBDIR} ${PC_ZLIB_LIBRARY_DIRS} + PATHS ${PATHS_ZLIB_LIBDIR} + ${CROSSCOMPILING_NO_CMAKE_SYSTEM_PATH} + ) + set_extra_dirs_include(ZLIB zlib "${ZLIB_LIBRARY}") + find_path(ZLIB_INCLUDEDIR1 zlib.h + PATH_SUFFIXES zlib + HINTS ${HINTS_ZLIB_INCLUDEDIR} ${PC_ZLIB_INCLUDEDIR} ${PC_ZLIB_INCLUDE_DIRS} + PATHS ${PATHS_ZLIB_INCLUDEDIR} + ${CROSSCOMPILING_NO_CMAKE_SYSTEM_PATH} + ) + find_path(ZLIB_INCLUDEDIR2 zconf.h + PATH_SUFFIXES zlib + HINTS ${HINTS_ZLIB_INCLUDEDIR} ${PC_ZLIB_INCLUDEDIR} ${PC_ZLIB_INCLUDE_DIRS} + PATHS ${PATHS_ZLIB_INCLUDEDIR} + ${CROSSCOMPILING_NO_CMAKE_SYSTEM_PATH} + ) + + if(ZLIB_LIBRARY AND ZLIB_INCLUDEDIR1 AND ZLIB_INCLUDEDIR2) + set(ZLIB_INCLUDE_DIRS ${ZLIB_INCLUDEDIR1} ${ZLIB_INCLUDEDIR2}) + set(ZLIB_LIBRARIES ${ZLIB_LIBRARY}) + set(ZLIB_FOUND TRUE) + endif() +endif() + if(NOT ZLIB_FOUND) set(ZLIB_BUNDLED ON) set(ZLIB_SRC_DIR src/engine/external/zlib) diff --git a/cmake/toolchains/Emscripten.toolchain b/cmake/toolchains/Emscripten.toolchain new file mode 100644 index 000000000..0ed57443b --- /dev/null +++ b/cmake/toolchains/Emscripten.toolchain @@ -0,0 +1,37 @@ +set(WASM_CXX_ENGINE_FLAGS "") +set(WASM_ENGINE_FLAGS "") +set(WASM_ENGINE_FLAGS "-s LLD_REPORT_UNDEFINED -s USE_PTHREADS=1") +# needed for loading files in a c-like style +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s FILESYSTEM=1 -s FORCE_FILESYSTEM=1") +# load data directory to the filesystem +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} --preload-file data") +# remove some annoyance for now, TODO +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} --allow-multiple-definition -Wl,--shared-memory,--no-check-features") +# TODO +#set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -lwebsocket.js -s PROXY_POSIX_SOCKETS=1") +# use Web Assmebly & a WebGL2 comptatible GLES3 implementation +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s WASM=1") +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s USE_WEBGL2=1") +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s FULL_ES3=1") +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s DEFAULT_LIBRARY_FUNCS_TO_INCLUDE=[\"$autoResumeAudioContext, $dynCall\"]") +# this flag is the most important one. It tells SDL2 to call emscripten functions when polling event +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s ASYNCIFY=1") +# TODO, has to be fixed in SDL2, can improve responsivness of the site +#set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s PROXY_TO_PTHREAD=1") +# SDL2 is compiled by the gen_libs.sh script for easy up to date code +#set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s USE_SDL=2") +#set(WASM_CXX_ENGINE_FLAGS "${WASM_CXX_ENGINE_FLAGS} -s USE_SDL=2") +# even if slower, memory growth has the advantage of using less resources, keep it on for now (instead of a static memory pool) +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s ALLOW_MEMORY_GROWTH=1") +#set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s INITIAL_MEMORY=2000MB") +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s MAXIMUM_MEMORY=2000MB") +# not optimal but required so that threads are created on fly (instead of delayed when the next javascript calls come in) +set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -s PTHREAD_POOL_SIZE=10") +if(NOT (CMAKE_BUILD_TYPE STREQUAL "Debug")) + # will drastically reduce code size + set(WASM_ENGINE_FLAGS "${WASM_ENGINE_FLAGS} -flto") +endif() +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -pthread -D_REENTRANT -g -O3 ${WASM_CXX_ENGINE_FLAGS}") +set(CMAKE_C_FLAGS "${CMAKE_CXX_FLAGS} -pthread -D_REENTRANT -g -O3 ${WASM_CXX_ENGINE_FLAGS}") +set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -pthread ${WASM_ENGINE_FLAGS}") +set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} ${WASM_ENGINE_FLAGS}") diff --git a/other/emscripten/minimal.html b/other/emscripten/minimal.html new file mode 100644 index 000000000..2a5e51c57 --- /dev/null +++ b/other/emscripten/minimal.html @@ -0,0 +1,44 @@ + + + + + + + + +

+ + + + diff --git a/scripts/android/README.md b/scripts/android/README.md index 6a046cf22..985ea15fb 100644 --- a/scripts/android/README.md +++ b/scripts/android/README.md @@ -47,7 +47,7 @@ How to build: How to build the ddnet-libs for Android: ======================================== - There is a script to automatically download and build all repositories, this requires an active internet connection: - `scripts/android/gen_android_libs.sh ` + `scripts/compile_libs/gen_libs.sh android` Warning!: DO NOT CHOOSE A DIRECTORY INSIDE THE SOURCE TREE After the script finished executing it should have created a ddnet-libs directory which created all libs in the right directory format and can be merged with ddnet-libs in the source directory diff --git a/scripts/compile_libs/cmake_lib_compile.sh b/scripts/compile_libs/cmake_lib_compile.sh index c0c6298b7..ba11a4a19 100755 --- a/scripts/compile_libs/cmake_lib_compile.sh +++ b/scripts/compile_libs/cmake_lib_compile.sh @@ -6,36 +6,76 @@ echo "$ANDROID_NDK" export MAKEFLAGS=-j32 +if [[ "${2}" == "webasm" ]]; then + COMPILEFLAGS="-pthread -O3 -g -s USE_PTHREADS=1" + LINKFLAGS="-pthread -O3 -g -s USE_PTHREADS=1 -s ASYNCIFY=1" +fi + +COMPILEFLAGS=$3 +LINKFLAGS=$4 + function compile_source() { - cmake \ - -H. \ - -G "Unix Makefiles" \ - -DCMAKE_BUILD_TYPE=Release \ - -DANDROID_NATIVE_API_LEVEL="android-$1" \ - -DCMAKE_TOOLCHAIN_FILE="$ANDROID_NDK/build/cmake/android.toolchain.cmake" \ - -DANDROID_ABI="${3}" \ - -DANDROID_ARM_NEON=TRUE \ - -B"$2" \ - -DBUILD_SHARED_LIBS=OFF \ - -DHIDAPI_SKIP_LIBUSB=TRUE \ - -DCURL_USE_OPENSSL=ON \ - -DSDL_HIDAPI=OFF \ - -DOP_DISABLE_HTTP=ON \ - -DOP_DISABLE_EXAMPLES=ON \ - -DOP_DISABLE_DOCS=ON \ - -DOPENSSL_ROOT_DIR="$PWD"/../openssl/"$2" \ - -DOPENSSL_CRYPTO_LIBRARY="$PWD"/../openssl/"$2"/libcrypto.a \ - -DOPENSSL_SSL_LIBRARY="$PWD"/../openssl/"$2"/libssl.a \ - -DOPENSSL_INCLUDE_DIR="${PWD}/../openssl/include;${PWD}/../openssl/${2}/include" - ( - cd "$2" || exit 1 - cmake --build . - ) + if [[ "${4}" == "android" ]]; then + cmake \ + -H. \ + -G "Unix Makefiles" \ + -DCMAKE_BUILD_TYPE=Release \ + -DANDROID_NATIVE_API_LEVEL="android-$1" \ + -DCMAKE_TOOLCHAIN_FILE="$ANDROID_NDK/build/cmake/android.toolchain.cmake" \ + -DANDROID_ABI="${3}" \ + -DANDROID_ARM_NEON=TRUE \ + -B"$2" \ + -DBUILD_SHARED_LIBS=OFF \ + -DHIDAPI_SKIP_LIBUSB=TRUE \ + -DCURL_USE_OPENSSL=ON \ + -DSDL_HIDAPI=OFF \ + -DOP_DISABLE_HTTP=ON \ + -DOP_DISABLE_EXAMPLES=ON \ + -DOP_DISABLE_DOCS=ON \ + -DOPENSSL_ROOT_DIR="$PWD"/../openssl/"$2" \ + -DOPENSSL_CRYPTO_LIBRARY="$PWD"/../openssl/"$2"/libcrypto.a \ + -DOPENSSL_SSL_LIBRARY="$PWD"/../openssl/"$2"/libssl.a \ + -DOPENSSL_INCLUDE_DIR="${PWD}/../openssl/include;${PWD}/../openssl/${2}/include" + ( + cd "$2" || exit 1 + cmake --build . + ) + else + ${5} cmake \ + -H. \ + -DCMAKE_BUILD_TYPE=Release \ + -B"$2" \ + -DSDL_STATIC=TRUE \ + -DFT_DISABLE_HARFBUZZ=ON \ + -DFT_DISABLE_BZIP2=ON \ + -DFT_DISABLE_BROTLI=ON \ + -DFT_REQUIRE_ZLIB=TRUE \ + -DCMAKE_C_FLAGS="$COMPILEFLAGS -DGLEW_STATIC" -DCMAKE_CXX_FLAGS="$COMPILEFLAGS" -DCMAKE_CXX_FLAGS_RELEASE="$COMPILEFLAGS" -DCMAKE_C_FLAGS_RELEASE="$COMPILEFLAGS" \ + -DCMAKE_SHARED_LINKER_FLAGS="$LINKFLAGS" -DCMAKE_SHARED_LINKER_FLAGS_RELEASE="$LINKFLAGS" \ + -DSDL_PTHREADS=ON -DSDL_THREADS=ON \ + -DCURL_USE_OPENSSL=ON \ + -DOPUS_HARDENING=OFF \ + -DOPUS_STACK_PROTECTOR=OFF \ + -DOPENSSL_ROOT_DIR="$PWD"/../openssl/"$2" \ + -DOPENSSL_CRYPTO_LIBRARY="$PWD"/../openssl/"$2"/libcrypto.a \ + -DOPENSSL_SSL_LIBRARY="$PWD"/../openssl/"$2"/libssl.a \ + -DOPENSSL_INCLUDE_DIR="${PWD}/../openssl/include;${PWD}/../openssl/${2}/include" \ + -DZLIB_LIBRARY="${PWD}/../zlib/${2}/libz.a" -DZLIB_INCLUDE_DIR="${PWD}/../zlib;${PWD}/../zlib/${2}" + ( + cd "$2" || exit 1 + cmake --build . + ) + fi } -compile_source "$1" build_android_arm armeabi-v7a & -compile_source "$1" build_android_arm64 arm64-v8a & -compile_source "$1" build_android_x86 x86 & -compile_source "$1" build_android_x86_64 x86_64 & +if [[ "${2}" == "android" ]]; then + compile_source "$1" build_"$2"_arm armeabi-v7a "$2" "" & + compile_source "$1" build_"$2"_arm64 arm64-v8a "$2" "" & + compile_source "$1" build_"$2"_x86 x86 "$2" "" & + compile_source "$1" build_"$2"_x86_64 x86_64 "$2" "" & +elif [[ "${2}" == "webasm" ]]; then + sed -i "s/include(CheckSizes)//g" CMakeLists.txt + compile_source "$1" build_"$2"_wasm wasm "$2" emcmake & +fi wait diff --git a/scripts/compile_libs/gen_libs.sh b/scripts/compile_libs/gen_libs.sh index a01eed19d..e41bdf53a 100755 --- a/scripts/compile_libs/gen_libs.sh +++ b/scripts/compile_libs/gen_libs.sh @@ -6,6 +6,50 @@ if [ -z ${1+x} ]; then exit 1 fi +if [ -z ${2+x} ]; then + echo "Specify the target system" + exit 1 +fi + +OS_NAME=$2 + +COMPILEFLAGS="-fPIC" +LINKFLAGS="-fPIC" +if [[ "${OS_NAME}" == "webasm" ]]; then + COMPILEFLAGS="-pthread -O3 -g -s USE_PTHREADS=1" + LINKFLAGS="-pthread -O3 -g -s USE_PTHREADS=1 -s ASYNCIFY=1 -s WASM=1" +fi + +if [[ "${OS_NAME}" == "android" ]]; then + OS_NAME_PATH="android" +elif [[ "${OS_NAME}" == "windows" ]]; then + OS_NAME_PATH="windows" +elif [[ "${OS_NAME}" == "linux" ]]; then + OS_NAME_PATH="linux" +elif [[ "${OS_NAME}" == "webasm" ]]; then + OS_NAME_PATH="webasm" +fi + +COMP_HAS_ARM32=0 +COMP_HAS_ARM64=0 +COMP_HAS_x86=0 +COMP_HAS_x64=0 +COMP_HAS_WEBASM=0 + +if [[ "${OS_NAME}" == "android" ]]; then + COMP_HAS_ARM32=1 + COMP_HAS_ARM64=1 + COMP_HAS_x86=1 + COMP_HAS_x64=1 +elif [[ "${OS_NAME}" == "linux" ]]; then + COMP_HAS_x64=1 +elif [[ "${OS_NAME}" == "windows" ]]; then + COMP_HAS_x86=1 + COMP_HAS_x64=1 +elif [[ "${OS_NAME}" == "webasm" ]]; then + COMP_HAS_WEBASM=1 +fi + mkdir -p "$1" cd "$1" || exit 1 @@ -15,15 +59,15 @@ function build_cmake_lib() { fi ( cd "${1}" || exit 1 - cp "${CURDIR}"/scripts/android/cmake_lib_compile.sh cmake_lib_compile.sh - ./cmake_lib_compile.sh "$_ANDROID_ABI_LEVEL" + cp "${CURDIR}"/scripts/compile_libs/cmake_lib_compile.sh cmake_lib_compile.sh + ./cmake_lib_compile.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS" ) } _ANDROID_ABI_LEVEL=24 -mkdir -p android_libs -cd android_libs || exit 1 +mkdir -p compile_libs +cd compile_libs || exit 1 # start with openssl ( @@ -37,16 +81,19 @@ cd android_libs || exit 1 if [[ "$_WAS_THERE_SSLFILE" == 0 ]]; then ./autogen.sh fi - cp "${CURDIR}"/scripts/android/make_android_openssl.sh make_android_openssl.sh - ./make_android_openssl.sh "$_ANDROID_ABI_LEVEL" + cp "${CURDIR}"/scripts/compile_libs/make_lib_openssl.sh make_lib_openssl.sh + ./make_lib_openssl.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS" ) ) +build_cmake_lib zlib https://github.com/madler/zlib +build_cmake_lib png https://github.com/glennrp/libpng build_cmake_lib curl https://github.com/curl/curl build_cmake_lib freetype2 https://gitlab.freedesktop.org/freetype/freetype build_cmake_lib sdl https://github.com/libsdl-org/SDL build_cmake_lib ogg https://github.com/xiph/ogg build_cmake_lib opus https://github.com/xiph/opus + ( _WAS_THERE_OPUSFILE=1 if [ ! -d "opusfile" ]; then @@ -57,8 +104,8 @@ build_cmake_lib opus https://github.com/xiph/opus if [[ "$_WAS_THERE_OPUSFILE" == 0 ]]; then ./autogen.sh fi - cp "${CURDIR}"/scripts/android/make_android_opusfile.sh make_android_opusfile.sh - ./make_android_opusfile.sh "$_ANDROID_ABI_LEVEL" + cp "${CURDIR}"/scripts/compile_libs/make_lib_opusfile.sh make_lib_opusfile.sh + ./make_lib_opusfile.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS" ) # SQLite, just download and built by hand @@ -69,111 +116,138 @@ fi ( cd sqlite3 || exit 1 - cp "${CURDIR}"/scripts/android/make_android_sqlite3.sh make_android_sqlite3.sh - ./make_android_sqlite3.sh "$_ANDROID_ABI_LEVEL" + cp "${CURDIR}"/scripts/compile_libs/make_lib_sqlite3.sh make_lib_sqlite3.sh + ./make_lib_sqlite3.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS" ) cd .. -mkdir ddnet-libs -function _copy_curl() { - mkdir -p ddnet-libs/curl/android/lib"$2" - cp android_libs/curl/build_android_"$1"/lib/libcurl.a ddnet-libs/curl/android/lib"$2"/libcurl.a +function copy_arches_for_lib() { + if [[ "$COMP_HAS_ARM32" == "1" ]]; then + ${1} arm arm + fi + if [[ "$COMP_HAS_ARM64" == "1" ]]; then + ${1} arm64 arm64 + fi + if [[ "$COMP_HAS_x86" == "1" ]]; then + ${1} x86 32 + fi + if [[ "$COMP_HAS_x64" == "1" ]]; then + ${1} x86_64 64 + fi + if [[ "$COMP_HAS_WEBASM" == "1" ]]; then + ${1} wasm wasm + fi } -_copy_curl arm arm -_copy_curl arm64 arm64 -_copy_curl x86 32 -_copy_curl x86_64 64 +mkdir ddnet-libs +function _copy_curl() { + mkdir -p ddnet-libs/curl/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/curl/build_"$OS_NAME"_"$1"/lib/libcurl.a ddnet-libs/curl/"$OS_NAME_PATH"/lib"$2"/libcurl.a +} + +copy_arches_for_lib _copy_curl mkdir ddnet-libs function _copy_freetype2() { - mkdir -p ddnet-libs/freetype/android/lib"$2" - cp android_libs/freetype2/build_android_"$1"/libfreetype.a ddnet-libs/freetype/android/lib"$2"/libfreetype.a + mkdir -p ddnet-libs/freetype/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/freetype2/build_"$OS_NAME"_"$1"/libfreetype.a ddnet-libs/freetype/"$OS_NAME_PATH"/lib"$2"/libfreetype.a } -_copy_freetype2 arm arm -_copy_freetype2 arm64 arm64 -_copy_freetype2 x86 32 -_copy_freetype2 x86_64 64 +copy_arches_for_lib _copy_freetype2 mkdir ddnet-libs function _copy_sdl() { - mkdir -p ddnet-libs/sdl/android/lib"$2" - cp android_libs/sdl/build_android_"$1"/libSDL2.a ddnet-libs/sdl/android/lib"$2"/libSDL2.a - cp android_libs/sdl/build_android_"$1"/libSDL2main.a ddnet-libs/sdl/android/lib"$2"/libSDL2main.a - if [ ! -d "ddnet-libs/sdl/include/android" ]; then - mkdir -p ddnet-libs/sdl/include/android + mkdir -p ddnet-libs/sdl/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/sdl/build_"$OS_NAME"_"$1"/libSDL2.a ddnet-libs/sdl/"$OS_NAME_PATH"/lib"$2"/libSDL2.a + cp compile_libs/sdl/build_"$OS_NAME"_"$1"/libSDL2main.a ddnet-libs/sdl/"$OS_NAME_PATH"/lib"$2"/libSDL2main.a + if [ ! -d "ddnet-libs/sdl/include/$OS_NAME_PATH" ]; then + mkdir -p ddnet-libs/sdl/include/"$OS_NAME_PATH" fi - cp -R android_libs/sdl/include/* ddnet-libs/sdl/include/android + cp -R compile_libs/sdl/include/* ddnet-libs/sdl/include/"$OS_NAME_PATH" } -_copy_sdl arm arm -_copy_sdl arm64 arm64 -_copy_sdl x86 32 -_copy_sdl x86_64 64 +copy_arches_for_lib _copy_sdl # copy java code from SDL2 -rm -R ddnet-libs/sdl/java -mkdir -p ddnet-libs/sdl/java -cp -R android_libs/sdl/android-project/app/src/main/java/org ddnet-libs/sdl/java/ +if [[ "$OS_NAME" == "android" ]]; then + rm -R ddnet-libs/sdl/java + mkdir -p ddnet-libs/sdl/java + cp -R compile_libs/sdl/android-project/app/src/main/java/org ddnet-libs/sdl/java/ +fi mkdir ddnet-libs function _copy_ogg() { - mkdir -p ddnet-libs/opus/android/lib"$2" - cp android_libs/ogg/build_android_"$1"/libogg.a ddnet-libs/opus/android/lib"$2"/libogg.a + mkdir -p ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/ogg/build_"$OS_NAME"_"$1"/libogg.a ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2"/libogg.a } -_copy_ogg arm arm -_copy_ogg arm64 arm64 -_copy_ogg x86 32 -_copy_ogg x86_64 64 +copy_arches_for_lib _copy_ogg mkdir ddnet-libs function _copy_opus() { - mkdir -p ddnet-libs/opus/android/lib"$2" - cp android_libs/opus/build_android_"$1"/libopus.a ddnet-libs/opus/android/lib"$2"/libopus.a + mkdir -p ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/opus/build_"$OS_NAME"_"$1"/libopus.a ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2"/libopus.a } -_copy_opus arm arm -_copy_opus arm64 arm64 -_copy_opus x86 32 -_copy_opus x86_64 64 +copy_arches_for_lib _copy_opus mkdir ddnet-libs function _copy_opusfile() { - mkdir -p ddnet-libs/opus/android/lib"$2" - cp android_libs/opusfile/build_"$1"/libopusfile.a ddnet-libs/opus/android/lib"$2"/libopusfile.a + mkdir -p ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/opusfile/build_"$OS_NAME"_"$1"/libopusfile.a ddnet-libs/opus/"$OS_NAME_PATH"/lib"$2"/libopusfile.a } -_copy_opusfile arm arm -_copy_opusfile arm64 arm64 -_copy_opusfile x86 32 -_copy_opusfile x86_64 64 +copy_arches_for_lib _copy_opusfile mkdir ddnet-libs function _copy_sqlite3() { - mkdir -p ddnet-libs/sqlite3/android/lib"$2" - cp android_libs/sqlite3/build_"$1"/sqlite3.a ddnet-libs/sqlite3/android/lib"$2"/libsqlite3.a + mkdir -p ddnet-libs/sqlite3/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/sqlite3/build_"$OS_NAME"_"$1"/sqlite3.a ddnet-libs/sqlite3/"$OS_NAME_PATH"/lib"$2"/libsqlite3.a } -_copy_sqlite3 arm arm -_copy_sqlite3 arm64 arm64 -_copy_sqlite3 x86 32 -_copy_sqlite3 x86_64 64 +copy_arches_for_lib _copy_sqlite3 mkdir ddnet-libs function _copy_openssl() { - mkdir -p ddnet-libs/openssl/android/lib"$2" + mkdir -p ddnet-libs/openssl/"$OS_NAME_PATH"/lib"$2" mkdir -p ddnet-libs/openssl/include - mkdir -p ddnet-libs/openssl/include/android - cp android_libs/openssl/build_android_"$1"/libcrypto.a ddnet-libs/openssl/android/lib"$2"/libcrypto.a - cp android_libs/openssl/build_android_"$1"/libssl.a ddnet-libs/openssl/android/lib"$2"/libssl.a - cp -R android_libs/openssl/build_android_"$1"/include/* ddnet-libs/openssl/include/android - cp -R android_libs/openssl/include/* ddnet-libs/openssl/include + mkdir -p ddnet-libs/openssl/include/"$OS_NAME_PATH" + cp compile_libs/openssl/build_"$OS_NAME"_"$1"/libcrypto.a ddnet-libs/openssl/"$OS_NAME_PATH"/lib"$2"/libcrypto.a + cp compile_libs/openssl/build_"$OS_NAME"_"$1"/libssl.a ddnet-libs/openssl/"$OS_NAME_PATH"/lib"$2"/libssl.a + cp -R compile_libs/openssl/build_"$OS_NAME"_"$1"/include/* ddnet-libs/openssl/include/"$OS_NAME_PATH" + cp -R compile_libs/openssl/include/* ddnet-libs/openssl/include } -_copy_openssl arm arm -_copy_openssl arm64 arm64 -_copy_openssl x86 32 -_copy_openssl x86_64 64 +copy_arches_for_lib _copy_openssl + +mkdir ddnet-libs +function _copy_zlib() { + # copy headers + ( + cd compile_libs/zlib || exit 1 + find . -maxdepth 1 -iname '*.h' -print0 | while IFS= read -r -d $'\0' file; do + mkdir -p ../../ddnet-libs/zlib/include/"$(dirname "$file")" + cp "$file" ../../ddnet-libs/zlib/include/"$(dirname "$file")" + done + + cd build_"$OS_NAME"_"$1" || exit 1 + find . -maxdepth 1 -iname '*.h' -print0 | while IFS= read -r -d $'\0' file; do + mkdir -p ../../../ddnet-libs/zlib/include/"$OS_NAME_PATH"/"$(dirname "$file")" + cp "$file" ../../../ddnet-libs/zlib/include/"$OS_NAME_PATH"/"$(dirname "$file")" + done + ) + + mkdir -p ddnet-libs/zlib/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/zlib/build_"$OS_NAME"_"$1"/libz.a ddnet-libs/zlib/"$OS_NAME_PATH"/lib"$2"/libz.a +} + +copy_arches_for_lib _copy_zlib + +mkdir ddnet-libs +function _copy_png() { + mkdir -p ddnet-libs/png/"$OS_NAME_PATH"/lib"$2" + cp compile_libs/png/build_"$OS_NAME"_"$1"/libpng16.a ddnet-libs/png/"$OS_NAME_PATH"/lib"$2"/libpng16.a +} + +copy_arches_for_lib _copy_png diff --git a/scripts/compile_libs/make_lib_openssl.sh b/scripts/compile_libs/make_lib_openssl.sh index cdbddf21b..39e803fe6 100755 --- a/scripts/compile_libs/make_lib_openssl.sh +++ b/scripts/compile_libs/make_lib_openssl.sh @@ -5,6 +5,11 @@ ANDROID_NDK="$(find "$ANDROID_HOME/ndk" -maxdepth 1 | sort -n | tail -1)" export MAKEFLAGS=-j32 +export CXXFLAGS="$3" +export CFLAGS="$3" +export CPPFLAGS="$4" +export LDFLAGS="$4" + export ANDROID_NDK_ROOT=$ANDROID_NDK PATH=$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin:$ANDROID_NDK_ROOT/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin:$PATH @@ -18,16 +23,26 @@ function buid_openssl() { ( cd "$1" || exit 1 if [[ "$_EXISTS_PROJECT" == "0" ]]; then - ../Configure "$2" no-asm no-shared + if [[ "${4}" == "webasm" ]]; then + emconfigure ../Configure "$2" -no-tests -no-asm -static -no-afalgeng -DOPENSSL_SYS_NETWARE -DSIG_DFL=0 -DSIG_IGN=0 -DHAVE_FORK=0 -DOPENSSL_NO_AFALGENG=1 --with-rand-seed=getrandom + + sed -i 's|^CROSS_COMPILE.*$|CROSS_COMPILE=|g' Makefile + else + ../Configure "$2" no-asm no-shared + fi fi - make $MAKEFLAGS build_generated - make $MAKEFLAGS libcrypto.a - make $MAKEFLAGS libssl.a + ${5} make $MAKEFLAGS build_generated + ${5} make $MAKEFLAGS libcrypto.a + ${5} make $MAKEFLAGS libssl.a cd .. ) } -buid_openssl build_android_arm android-arm "$1" -buid_openssl build_android_arm64 android-arm64 "$1" -buid_openssl build_android_x86 android-x86 "$1" -buid_openssl build_android_x86_64 android-x86_64 "$1" +if [[ "${2}" == "android" ]]; then + buid_openssl build_"$2"_arm android-arm "$1" "$2" "" + buid_openssl build_"$2"_arm64 android-arm64 "$1" "$2" "" + buid_openssl build_"$2"_x86 android-x86 "$1" "$2" "" + buid_openssl build_"$2"_x86_64 android-x86_64 "$1" "$2" "" +elif [[ "${2}" == "webasm" ]]; then + buid_openssl build_"$2"_wasm linux-generic64 "$1" "$2" emmake +fi diff --git a/scripts/compile_libs/make_lib_opusfile.sh b/scripts/compile_libs/make_lib_opusfile.sh index 6de769c96..87c62784f 100755 --- a/scripts/compile_libs/make_lib_opusfile.sh +++ b/scripts/compile_libs/make_lib_opusfile.sh @@ -5,6 +5,11 @@ ANDROID_NDK="$(find "$ANDROID_HOME/ndk" -maxdepth 1 | sort -n | tail -1)" export MAKEFLAGS=-j32 +export CXXFLAGS="$3" +export CFLAGS="$3" +export CPPFLAGS="$4" +export LDFLAGS="$4" + export ANDROID_NDK_ROOT="$ANDROID_NDK" function make_opusfile() { @@ -24,7 +29,18 @@ function make_opusfile() { cp ../../ogg/"$2"/libogg.a libogg.a cp ../../opus/"$2"/libopus.a libopus.a fi - "$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/$3$4-clang" \ + + TMP_COMPILER="" + TMP_AR="" + if [[ "${5}" == "android" ]]; then + TMP_COMPILER="$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/$3$4-clang" + TMP_AR="$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-ar" + elif [[ "${5}" == "webasm" ]]; then + TMP_COMPILER="emcc" + TMP_AR="emar" + fi + + ${TMP_COMPILER} \ -c \ -fPIC \ -I"${PWD}"/../include \ @@ -32,16 +48,14 @@ function make_opusfile() { ../src/opusfile.c \ ../src/info.c \ ../src/internal.c - "$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/$3$4-clang" \ + ${TMP_COMPILER} \ -c \ -fPIC \ -I"${PWD}"/../include \ -I"${PWD}"/include \ -include stdio.h \ - -Dftello=ftell \ - -Dfseek=fseek \ ../src/stream.c - "$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-ar" \ + ${TMP_AR} \ rvs \ libopusfile.a \ opusfile.o \ @@ -52,11 +66,15 @@ function make_opusfile() { } function compile_all_opusfile() { - make_opusfile build_arm build_android_arm armv7a-linux-androideabi "$1" - make_opusfile build_arm64 build_android_arm64 aarch64-linux-android "$1" - make_opusfile build_x86 build_android_x86 i686-linux-android "$1" - make_opusfile build_x86_64 build_android_x86_64 x86_64-linux-android "$1" + if [[ "${2}" == "android" ]]; then + make_opusfile build_"$2"_arm build_"$2"_arm armv7a-linux-androideabi "$1" "$2" + make_opusfile build_"$2"_arm64 build_"$2"_arm64 aarch64-linux-android "$1" "$2" + make_opusfile build_"$2"_x86 build_"$2"_x86 i686-linux-android "$1" "$2" + make_opusfile build_"$2"_x86_64 build_"$2"_x86_64 x86_64-linux-android "$1" "$2" + elif [[ "${2}" == "webasm" ]]; then + make_opusfile build_"$2"_wasm build_"$2"_wasm "" "$1" "$2" + fi } -compile_all_opusfile "$1" +compile_all_opusfile "$1" "$2" diff --git a/scripts/compile_libs/make_lib_sqlite3.sh b/scripts/compile_libs/make_lib_sqlite3.sh index 2acc36033..2e8eb75d0 100755 --- a/scripts/compile_libs/make_lib_sqlite3.sh +++ b/scripts/compile_libs/make_lib_sqlite3.sh @@ -5,6 +5,11 @@ ANDROID_NDK="$(find "$ANDROID_HOME/ndk" -maxdepth 1 | sort -n | tail -1)" export MAKEFLAGS=-j32 +export CXXFLAGS="$3" +export CFLAGS="$3" +export CPPFLAGS="$4" +LINKER_FLAGS="$4" + export ANDROID_NDK_ROOT="$ANDROID_NDK" PATH="$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin:$ANDROID_NDK_ROOT/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin:$PATH" _LD_LIBRARY_PATH=".:$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin:$ANDROID_NDK_ROOT/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin:$LD_LIBRARY_PATH" @@ -13,17 +18,32 @@ function make_sqlite3() { ( mkdir -p "$1" cd "$1" || exit 1 - LDFLAGS="-L./" \ + + TMP_COMPILER="" + TMP_AR="" + if [[ "${5}" == "android" ]]; then + TMP_COMPILER="$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/$3$4-clang" + TMP_AR="$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-ar" + elif [[ "${5}" == "webasm" ]]; then + TMP_COMPILER="emcc" + TMP_AR="emar" + fi + + LDFLAGS="${LINKER_FLAGS} -L./" \ LD_LIBRARY_PATH="$_LD_LIBRARY_PATH" \ - "$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/$3$4-clang" \ + ${TMP_COMPILER} \ -c \ -fPIC \ + -DSQLITE_ENABLE_ATOMIC_WRITE=1 \ + -DSQLITE_ENABLE_BATCH_ATOMIC_WRITE=1 \ + -DSQLITE_ENABLE_MULTITHREADED_CHECKS=1 \ + -DSQLITE_THREADSAFE=1 \ ../sqlite3.c \ -o sqlite3.o - LDFLAGS="-L./" \ + LDFLAGS="${LINKER_FLAGS} -L./" \ LD_LIBRARY_PATH="$_LD_LIBRARY_PATH" \ - "$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-ar" \ + ${TMP_AR} \ rvs \ sqlite3.a \ sqlite3.o @@ -31,11 +51,15 @@ function make_sqlite3() { } function compile_all_sqlite3() { - make_sqlite3 build_arm build_android_arm armv7a-linux-androideabi "$1" - make_sqlite3 build_arm64 build_android_arm64 aarch64-linux-android "$1" - make_sqlite3 build_x86 build_android_x86 i686-linux-android "$1" - make_sqlite3 build_x86_64 build_android_x86_64 x86_64-linux-android "$1" + if [[ "${2}" == "android" ]]; then + make_sqlite3 build_"$2"_arm build_"$2"_arm armv7a-linux-androideabi "$1" "$2" + make_sqlite3 build_"$2"_arm64 build_"$2"_arm64 aarch64-linux-android "$1" "$2" + make_sqlite3 build_"$2"_x86 build_"$2"_x86 i686-linux-android "$1" "$2" + make_sqlite3 build_"$2"_x86_64 build_"$2"_x86_64 x86_64-linux-android "$1" "$2" + elif [[ "${2}" == "webasm" ]]; then + make_sqlite3 build_"$2"_wasm build_"$2"_wasm "" "$1" "$2" + fi } -compile_all_sqlite3 "$1" +compile_all_sqlite3 "$1" "$2" diff --git a/src/base/detect.h b/src/base/detect.h index ce530c375..90eeeae78 100644 --- a/src/base/detect.h +++ b/src/base/detect.h @@ -46,12 +46,16 @@ #define PLATFORM_STRING "openbsd" #endif -#if(defined(__LINUX__) || defined(__linux__)) && !defined(__ANDROID__) +#if(defined(__LINUX__) || defined(__linux__) || defined(CONF_WEBASM)) && !defined(__ANDROID__) #define CONF_FAMILY_UNIX 1 #define CONF_FAMILY_STRING "unix" #define CONF_PLATFORM_LINUX 1 #define PLATFORM_STRING "linux" #define CONF_BACKEND_OPENGL_ES3 1 +#ifdef CONF_WEBASM +// GLES only +#define CONF_BACKEND_OPENGL_ES 1 +#endif #endif #if defined(__ANDROID__) diff --git a/src/engine/client/backend/opengl/backend_opengl3.cpp b/src/engine/client/backend/opengl/backend_opengl3.cpp index 26043783e..5ad001768 100644 --- a/src/engine/client/backend/opengl/backend_opengl3.cpp +++ b/src/engine/client/backend/opengl/backend_opengl3.cpp @@ -17,6 +17,16 @@ #include +#ifdef CONF_WEBASM +// WebGL2 defines the type of a buffer at the first bind to a buffer target +// this is different to GLES 3 (https://www.khronos.org/registry/webgl/specs/latest/2.0/#5.1) +static constexpr GLenum BUFFER_INIT_INDEX_TARGET = GL_ELEMENT_ARRAY_BUFFER; +static constexpr GLenum BUFFER_INIT_VERTEX_TARGET = GL_ARRAY_BUFFER; +#else +static constexpr GLenum BUFFER_INIT_INDEX_TARGET = GL_COPY_WRITE_BUFFER; +static constexpr GLenum BUFFER_INIT_VERTEX_TARGET = GL_COPY_WRITE_BUFFER; +#endif + // ------------ CCommandProcessorFragment_OpenGL3_3 int CCommandProcessorFragment_OpenGL3_3::TexFormatToNewOpenGLFormat(int TexFormat) { @@ -458,7 +468,7 @@ bool CCommandProcessorFragment_OpenGL3_3::Cmd_Init(const SCommand_Init *pCommand glBindVertexArray(0); glGenBuffers(1, &m_QuadDrawIndexBufferID); - glBindBuffer(GL_COPY_WRITE_BUFFER, m_QuadDrawIndexBufferID); + glBindBuffer(BUFFER_INIT_INDEX_TARGET, m_QuadDrawIndexBufferID); unsigned int Indices[CCommandBuffer::MAX_VERTICES / 4 * 6]; int Primq = 0; @@ -472,7 +482,7 @@ bool CCommandProcessorFragment_OpenGL3_3::Cmd_Init(const SCommand_Init *pCommand Indices[i + 5] = Primq + 3; Primq += 4; } - glBufferData(GL_COPY_WRITE_BUFFER, sizeof(unsigned int) * CCommandBuffer::MAX_VERTICES / 4 * 6, Indices, GL_STATIC_DRAW); + glBufferData(BUFFER_INIT_INDEX_TARGET, sizeof(unsigned int) * CCommandBuffer::MAX_VERTICES / 4 * 6, Indices, GL_STATIC_DRAW); m_CurrentIndicesInBuffer = CCommandBuffer::MAX_VERTICES / 4 * 6; @@ -944,12 +954,12 @@ void CCommandProcessorFragment_OpenGL3_3::AppendIndices(unsigned int NewIndicesC glBindBuffer(GL_COPY_READ_BUFFER, m_QuadDrawIndexBufferID); GLuint NewIndexBufferID; glGenBuffers(1, &NewIndexBufferID); - glBindBuffer(GL_COPY_WRITE_BUFFER, NewIndexBufferID); + glBindBuffer(BUFFER_INIT_INDEX_TARGET, NewIndexBufferID); GLsizeiptr size = sizeof(unsigned int); - glBufferData(GL_COPY_WRITE_BUFFER, (GLsizeiptr)NewIndicesCount * size, NULL, GL_STATIC_DRAW); - glCopyBufferSubData(GL_COPY_READ_BUFFER, GL_COPY_WRITE_BUFFER, 0, 0, (GLsizeiptr)m_CurrentIndicesInBuffer * size); - glBufferSubData(GL_COPY_WRITE_BUFFER, (GLsizeiptr)m_CurrentIndicesInBuffer * size, (GLsizeiptr)AddCount * size, Indices); - glBindBuffer(GL_COPY_WRITE_BUFFER, 0); + glBufferData(BUFFER_INIT_INDEX_TARGET, (GLsizeiptr)NewIndicesCount * size, NULL, GL_STATIC_DRAW); + glCopyBufferSubData(GL_COPY_READ_BUFFER, BUFFER_INIT_INDEX_TARGET, 0, 0, (GLsizeiptr)m_CurrentIndicesInBuffer * size); + glBufferSubData(BUFFER_INIT_INDEX_TARGET, (GLsizeiptr)m_CurrentIndicesInBuffer * size, (GLsizeiptr)AddCount * size, Indices); + glBindBuffer(BUFFER_INIT_INDEX_TARGET, 0); glBindBuffer(GL_COPY_READ_BUFFER, 0); glDeleteBuffers(1, &m_QuadDrawIndexBufferID); @@ -982,8 +992,8 @@ void CCommandProcessorFragment_OpenGL3_3::Cmd_CreateBufferObject(const CCommandB GLuint VertBufferID = 0; glGenBuffers(1, &VertBufferID); - glBindBuffer(GL_COPY_WRITE_BUFFER, VertBufferID); - glBufferData(GL_COPY_WRITE_BUFFER, (GLsizeiptr)(pCommand->m_DataSize), pUploadData, GL_STATIC_DRAW); + glBindBuffer(BUFFER_INIT_VERTEX_TARGET, VertBufferID); + glBufferData(BUFFER_INIT_VERTEX_TARGET, (GLsizeiptr)(pCommand->m_DataSize), pUploadData, GL_STATIC_DRAW); m_BufferObjectIndices[Index] = VertBufferID; @@ -996,8 +1006,8 @@ void CCommandProcessorFragment_OpenGL3_3::Cmd_RecreateBufferObject(const CComman void *pUploadData = pCommand->m_pUploadData; int Index = pCommand->m_BufferIndex; - glBindBuffer(GL_COPY_WRITE_BUFFER, m_BufferObjectIndices[Index]); - glBufferData(GL_COPY_WRITE_BUFFER, (GLsizeiptr)(pCommand->m_DataSize), pUploadData, GL_STATIC_DRAW); + glBindBuffer(BUFFER_INIT_VERTEX_TARGET, m_BufferObjectIndices[Index]); + glBufferData(BUFFER_INIT_VERTEX_TARGET, (GLsizeiptr)(pCommand->m_DataSize), pUploadData, GL_STATIC_DRAW); if(pCommand->m_DeletePointer) free(pUploadData); @@ -1008,8 +1018,8 @@ void CCommandProcessorFragment_OpenGL3_3::Cmd_UpdateBufferObject(const CCommandB void *pUploadData = pCommand->m_pUploadData; int Index = pCommand->m_BufferIndex; - glBindBuffer(GL_COPY_WRITE_BUFFER, m_BufferObjectIndices[Index]); - glBufferSubData(GL_COPY_WRITE_BUFFER, (GLintptr)(pCommand->m_pOffset), (GLsizeiptr)(pCommand->m_DataSize), pUploadData); + glBindBuffer(BUFFER_INIT_VERTEX_TARGET, m_BufferObjectIndices[Index]); + glBufferSubData(BUFFER_INIT_VERTEX_TARGET, (GLintptr)(pCommand->m_pOffset), (GLsizeiptr)(pCommand->m_DataSize), pUploadData); if(pCommand->m_DeletePointer) free(pUploadData); diff --git a/src/engine/client/backend_sdl.cpp b/src/engine/client/backend_sdl.cpp index e87e261a8..0168e0dd0 100644 --- a/src/engine/client/backend_sdl.cpp +++ b/src/engine/client/backend_sdl.cpp @@ -123,11 +123,16 @@ void CGraphicsBackend_Threaded::StopProcessor() void CGraphicsBackend_Threaded::RunBuffer(CCommandBuffer *pBuffer) { +#ifdef CONF_WEBASM + // run everything single threaded for now, context binding in a thread seems to not work as of now + RunBufferSingleThreadedUnsafe(pBuffer); +#else WaitForIdle(); std::unique_lock Lock(m_BufferSwapMutex); m_pBuffer = pBuffer; m_BufferInProcess.store(true, std::memory_order_relaxed); m_BufferSwapCond.notify_all(); +#endif } void CGraphicsBackend_Threaded::RunBufferSingleThreadedUnsafe(CCommandBuffer *pBuffer) @@ -668,6 +673,7 @@ bool CGraphicsBackend_SDL_GL::GetDriverVersion(EGraphicsDriverAgeType DriverAgeT if(BackendType == BACKEND_TYPE_OPENGL) { pName = "OpenGL"; +#ifndef CONF_BACKEND_OPENGL_ES if(DriverAgeType == GRAPHICS_DRIVER_AGE_TYPE_LEGACY) { Major = 1; @@ -689,6 +695,7 @@ bool CGraphicsBackend_SDL_GL::GetDriverVersion(EGraphicsDriverAgeType DriverAgeT Patch = 0; return true; } +#endif } else if(BackendType == BACKEND_TYPE_OPENGL_ES) { diff --git a/src/engine/client/client.cpp b/src/engine/client/client.cpp index 59ed9efe6..a427753e7 100644 --- a/src/engine/client/client.cpp +++ b/src/engine/client/client.cpp @@ -2888,6 +2888,7 @@ void CClient::Run() CVideo::Init(); #endif +#ifndef CONF_WEBASM // open socket { NETADDR BindAddr; @@ -2910,6 +2911,7 @@ void CClient::Run() } } } +#endif // init font rendering Kernel()->RequestInterface()->Init(); diff --git a/src/engine/client/notifications.cpp b/src/engine/client/notifications.cpp index b38e53353..8153815d7 100644 --- a/src/engine/client/notifications.cpp +++ b/src/engine/client/notifications.cpp @@ -4,7 +4,7 @@ #if defined(CONF_PLATFORM_MACOS) // Code is in src/macos/notification.mm. -#elif defined(CONF_FAMILY_UNIX) && !defined(CONF_PLATFORM_ANDROID) && !defined(CONF_PLATFORM_HAIKU) +#elif defined(CONF_FAMILY_UNIX) && !defined(CONF_PLATFORM_ANDROID) && !defined(CONF_PLATFORM_HAIKU) && !defined(CONF_WEBASM) #include void NotificationsInit() { diff --git a/src/engine/shared/config_variables.h b/src/engine/shared/config_variables.h index 4647c7348..60f3edcb1 100644 --- a/src/engine/shared/config_variables.h +++ b/src/engine/shared/config_variables.h @@ -103,8 +103,12 @@ MACRO_CONFIG_INT(GfxDesktopWidth, gfx_desktop_width, 0, 0, 0, CFGFLAG_SAVE | CFG MACRO_CONFIG_INT(GfxDesktopHeight, gfx_desktop_height, 0, 0, 0, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Desktop resolution height for detecting display changes (not recommended to change manually)") #if !defined(CONF_PLATFORM_MACOS) MACRO_CONFIG_INT(GfxBorderless, gfx_borderless, 0, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Borderless window (not to be used with fullscreen)") +#if !defined(CONF_WEBASM) MACRO_CONFIG_INT(GfxFullscreen, gfx_fullscreen, 1, 0, 3, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Set fullscreen mode: 0=no fullscreen, 1=pure fullscreen, 2=desktop fullscreen, 3=windowed fullscreen") #else +MACRO_CONFIG_INT(GfxFullscreen, gfx_fullscreen, 0, 0, 3, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Set fullscreen mode: 0=no fullscreen, 1=pure fullscreen, 2=desktop fullscreen, 3=windowed fullscreen") +#endif +#else MACRO_CONFIG_INT(GfxBorderless, gfx_borderless, 1, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Borderless window (not to be used with fullscreen)") MACRO_CONFIG_INT(GfxFullscreen, gfx_fullscreen, 0, 0, 3, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Set fullscreen mode: 0=no fullscreen, 1=pure fullscreen, 2=desktop fullscreen, 3=windowed fullscreen") #endif