cmake_minimum_required(VERSION 3.25.1...4.0.0) # Add an interface library with common set of build/linker flags and definitions. set(BUILD_FLAGS_TARGET BuildFlags) add_library(${BUILD_FLAGS_TARGET} INTERFACE) # Enable and require C++20 standard. target_compile_features(${BUILD_FLAGS_TARGET} INTERFACE cxx_std_20) set_target_properties(${BUILD_FLAGS_TARGET} PROPERTIES CXX_STANDARD_REQUIRED ON CXX_EXTENSIONS OFF ) # Settings for build types if(with-lto) include(CheckIPOSupported) check_ipo_supported(RESULT lto_supported OUTPUT lto_supported_error) if(lto_supported) set_target_properties(${BUILD_FLAGS_TARGET} PROPERTIES INTERPROCEDURAL_OPTIMIZATION TRUE ) else() message(WARNING "IPO / LTO not supported: <${lto_supported_error}>") endif() endif() target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE $<$:NDEBUG> $<$:CONFIG_FINAL=1> $<$:DEBUG> ) if(sanitize-address) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=address) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=address) endif() if(sanitize-thread) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=thread) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=thread) endif() if(sanitize-undefined-behaviour) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=undefined) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -fsanitize=undefined) endif() if(mozjs_is_debug_build) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE DEBUG) endif() if(gles) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_GLES=1) endif() if(without-audio) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_AUDIO=0) endif() if(without-nvtt) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_NVTT=0) endif() if(without-lobby) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_LOBBY=0) endif() if(without-miniupnpc) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_MINIUPNPC=0) endif() if(without-dap-interface) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE CONFIG2_DAP_INTERFACE=0) endif() # hide warnings caused by library includes (Nothing to do for gcc/clang) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:/external:W0> ) # various platform-specific build flags if(CMAKE_SYSTEM_NAME STREQUAL "Windows") target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:/MP> # Since KB4088875 Windows 7 has a soft requirement for SSE2. # Windows 8+ and Firefox ESR52 make it hard requirement. # Finally since VS2012 it's enabled implicitely when not set. $<$:/arch:SSE2> # use native wchar_t type (not typedef to unsigned short) $<$:/Zc:wchar_t> $<$:/utf-8> # SpiderMonkey only supports building with MSVC on a best-effort basis, # and the traditional MSVC preprocessor is incompatible with some headers. # Use the modern, standard-compliant MSVC preprocessor instead. $<$:/Zc:preprocessor> # enable most of the standard warnings $<$:/W4> # FIXME: conversion warnings, should add -Wconversion to gcc and clang flags as well $<$:/wd4267> $<$,$>:/O2> ) # disable LNK4221 warning, to avoid spending energy ordering projects in linker invocations target_link_options(${BUILD_FLAGS_TARGET} INTERFACE "/ignore:4221" ) # mozilla 115 linked list destructor in debug build target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE "__PRETTY_FUNCTION__=__FUNCSIG__") # disable Windows debug heap, since it makes malloc/free hugely slower when running inside a debugger set_target_properties(${BUILD_FLAGS_TARGET} PROPERTIES VS_DEBUGGER_ENVIRONMENT "_NO_DEBUG_HEAP=1" ) elseif(UNIX) if(NOT minimal-flags) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE # most of the standard warnings $<$:-Wall> $<$:-Wextra> $<$:-Wpedantic> # $<$:-Wconversion> # FIXME: should seriously consider fixing so this warning can be enabled. # add some other useful warnings that need to be enabled explicitly $<$:-Wunused-parameter> # (useful for finding some multiply-included header files) $<$:-Wredundant-decls> # $<$:-Wformat=2> # (useful sometimes, but a bit noisy, so skip it by default) # $<$:-Wcast-qual> # (useful for checking const-correctness, but a bit noisy, so skip it by default) $<$:-Wnon-virtual-dtor> # (sometimes noisy but finds real bugs) $<$:-Wundef> # (useful for finding macro name typos) # disable some warnings that currently trigger $<$:-Wno-missing-field-initializers> # (this is common in external headers we can't fix) $<$:-Wno-reorder> # order of initialization list in constructors (lots of noise) # enable security features (stack checking etc) that shouldn't have a significant effect on performance and can catch bugs $<$:-fstack-protector-strong> # always enable strict aliasing (useful in debug builds because of the warnings) $<$:-fstrict-aliasing> # don't omit frame pointers (for now), because performance will be impacted negatively by the way this breaks profilers more than it will be impacted positively by the optimisation $<$:-fno-omit-frame-pointer> # FORTIFY_SOURCE needs optimizations to be enabled $<$,$>:-U_FORTIFY_SOURCE> # (avoid redefinition warning if already defined) $<$,$>:-D_FORTIFY_SOURCE=2> ) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:-multiply_defined> $<$:suppress> ) if(NOT without-pch) # do something (?) so that ccache can handle compilation with PCH enabled (ccache 3.1+ also requires CCACHE_SLOPPINESS=time_macros for this to work) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:-fpch-preprocess> ) endif() if(CMAKE_SYSTEM_NAME STREQUAL "Linux" AND CMAKE_SYSTEM_NAME MATCHES ".*BSD*") target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:-fPIC> ) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE "-Wl,--no-undefined" "-Wl,--as-needed" "-Wl,-z,relro" ) endif() if(ARCH STREQUAL "x86") # To support intrinsics like __sync_bool_compare_and_swap on x86 we need to set -march to something that supports them (i686). # We use pentium3 to also enable other features like mmx and sse, while tuning for generic to have good performance on every supported CPU. # Note that all these features are already supported on amd64. target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:-march=pentium3> $<$:-mtune=generic> # This allows x86 operating systems to handle the 2GB+ INTERFACE mod. $<$:-mtune=generic-D_FILE_OFFSET_BITS=64> ) endif() if(ARCH STREQUAL "arm") target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE # disable warnings about va_list ABI change and use compile-time flags for futher configuration. $<$:-Wno-psabi> # Android uses softfp, so we should too. $<$,$>:-mfloat-abi=softfp> ) endif() endif() if(coverage) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE $<$:-fprofile-arcs> $<$:-ftest-coverage> ) target_link_libraries(${BUILD_FLAGS_TARGET} gcov) endif() # MacOS 10.12 only supports intel processors with SSE 4.1, so enable that. if(CMAKE_SYSTEM_NAME STREQUAL "Darwin" AND ARCH STREQUAL "amd64") target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE "-msse4.1" ) endif() # Check if SDK path should be used if(sysroot) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE "-isysroot ${sysroot}" ) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE "-Wl,-syslibroot, ${sysroot}" ) endif() # On OS X, sometimes we need to specify the minimum API version to use if(macosx-version-min) # clang and llvm-gcc look at mmacosx-version-min to determine link target and CRT version, and use it to set the macosx_version_min linker flag target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE "-mmacosx-version-min=${macosx-version-min}" ) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE "-mmacosx-version-min=${macosx-version-min}" ) endif() # Only libc++ is supported on MacOS if(CMAKE_SYSTEM_NAME STREQUAL "Darwin") target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE -stdlib=libc++ ) target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -stdlib=libc++ ) endif() # Hide symbols in dynamic shared objects by default, for efficiency and for equivalence with Windows # - they should be exported explicitly with __attribute__ ((visibility ("default"))) target_compile_options(${BUILD_FLAGS_TARGET} INTERFACE -fvisibility=hidden ) if(bindir) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE INSTALLED_BINDIR=${bindir}) endif() if(datadir) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE INSTALLED_DATADIR=${datadir}) endif() if(libdir) target_compile_definitions(${BUILD_FLAGS_TARGET} INTERFACE INSTALLED_LIBDIR=${libdir}) endif() if(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME MATCHES ".*BSD*") if(libdir) # To use our local shared libraries, they need to be found in the runtime dynamic linker path. Add their path to -rpath. target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -Wl,-rpath,${libdir} ) else() # On FreeBSD we need to allow use of $ORIGIN if(CMAKE_SYSTEM_NAME MATCHES ".*BSD*") target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -Wl,-z,origin ) endif() # Adding the executable path and taking care of correct escaping if(NOT CMAKE_GENERATOR STREQUAL "Ninja") # Checks if any Makefile generator is selected target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -Wl,-rpath,'$$ORIGIN' ) elseif(CMAKE_EXTRA_GENERATOR STREQUAL "CodeBlocks") target_link_options(${BUILD_FLAGS_TARGET} INTERFACE -Wl,-R\\\\$$$ORIGIN ) endif() endif() endif() endif()