From: Ivan Maidanski Date: Thu, 22 Aug 2019 22:14:25 +0000 (+0300) Subject: Enable multi-threaded builds by CMake X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=54769e69e4c74450cd7cd1e06a9c57fa43f4f7ee;p=gc Enable multi-threaded builds by CMake Now, enable_threads option is on by default. * CMakeLists.txt (enable_threads): Change option default to ON; remove TODO item; set proper option message. * CMakeLists.txt (libatomic_ops/src): Specify include directory only if enable_threads. * CMakeLists.txt (LIBS): Rename to THREADDLLIBS. * CMakeLists.txt [enable_threads]: Change message level and content. * CMakeLists.txt [enable_threads] (THREADDLLIBS): Set to CMAKE_THREAD_LIBS_INIT value (instead of Threads_LIBRARIES). * CMakeLists.txt [enable_threads && !(APPLE || CYGWIN || MSYS || WIN32 || HOST MATCHES mips-.*-irix6.*)] (THREADDLLIBS): Append -ldl; add comment. * CMakeLists.txt [Threads_FOUND]: Remove commented out code. * CMakeLists.txt [CMAKE_USE_PTHREADS_INIT]: Update comments; remove TODO items. * CMakeLists.txt [CMAKE_USE_PTHREADS_INIT && (HOST MATCHES .*-.*-hpux10.*)]: Change message level to fatal error. * CMakeLists.txt [CMAKE_USE_PTHREADS_INIT] (GC_BUILTIN_ATOMIC): Define C macro; add comment. * CMakeLists.txt [CMAKE_USE_PTHREADS_INIT] (GC_THREADS, _REENTRANT): Define C macro unconditionally. * CMakeLists.txt [CMAKE_USE_PTHREADS_INIT && !ANDROID && !MSYS && !APPLE && enable_handle_fork] (HANDLE_FORK): Define C macro. * CMakeLists.txt [CMAKE_USE_WIN32_THREADS_INIT && enable_thread_local_alloc && !enable_parallel_mark] (THREAD_LOCAL_ALLOC): Do not define if BUILD_SHARED_LIBS; add comment. * CMakeLists.txt [CMAKE_HP_PTHREADS_INIT || CMAKE_USE_SPROC_INIT]: Fatal error message. * CMakeLists.txt [enable_gcj_support && enable_threads] (GC_ENABLE_SUSPEND_THREAD): Do not define if enable_thread_local_alloc and host is kfreebsd; add FIXME item. * CMakeLists.txt [enable_threads] (gc): Specify THREADDLLIBS as target link libraries. * CMakeLists.txt [build_tests] (gctest): Likewise. * CMakeLists.txt [build_tests && enable_disclaim] (disclaim_test, disclaim_weakmap_test): Likewise. * CMakeLists.txt [build_tests && enable_threads] (test_atomic_ops, threadleaktest, subthreadcreate_test, initsecondarythread_test): Specify test executable. * CMakeLists.txt [build_tests && enable_threads && !WIN32] (threadkey_test): Likewise. --- diff --git a/CMakeLists.txt b/CMakeLists.txt index 3403bf89..f8ded668 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -36,7 +36,7 @@ include(CTest) option(BUILD_SHARED_LIBS "Build shared libraries" ON) option(build_cord "Build cord library" ON) option(build_tests "Build tests" OFF) -option(enable_threads "TODO" OFF) #TODO Support it +option(enable_threads "Support threads" ON) option(enable_parallel_mark "Parallelize marking and free list construction" ON) option(enable_thread_local_alloc "Turn on thread-local allocation optimization" ON) option(enable_threads_discovery "Enable threads discovery in GC" ON) @@ -92,13 +92,12 @@ else() endif() include_directories(include) -include_directories(libatomic_ops/src) set(SRC alloc.c reclaim.c allchblk.c misc.c mach_dep.c os_dep.c mark_rts.c headers.c mark.c obj_map.c blacklst.c finalize.c new_hblk.c dbg_mlc.c malloc.c dyn_load.c typd_mlc.c ptr_chck.c mallocx.c) -set(LIBS) +set(THREADDLLIBS) set(_HOST ${CMAKE_SYSTEM_PROCESSOR}-unknown-${CMAKE_SYSTEM}) string(TOLOWER ${_HOST} HOST) @@ -106,51 +105,43 @@ message(STATUS "TARGET = ${HOST}") if (enable_threads) find_package(Threads REQUIRED) - message("Thread Model: ${CMAKE_THREAD_LIBS_INIT}" ) + message(STATUS "Thread library: ${CMAKE_THREAD_LIBS_INIT}") + include_directories(libatomic_ops/src) include_directories(${Threads_INCLUDE_DIR}) - set(LIBS ${LIBS} ${Threads_LIBRARIES}) -endif() - -#IF(Threads_FOUND) -# ADD_DEFINITIONS("") -#ELSE -# MESSAGE("Parallel mark requires enable_threads ON" ) -#ENDIF(Threads_FOUND) + set(THREADDLLIBS ${CMAKE_THREAD_LIBS_INIT}) + if (NOT (APPLE OR CYGWIN OR MSYS OR WIN32 OR HOST MATCHES mips-.*-irix6.*)) + set(THREADDLLIBS ${THREADDLLIBS} -ldl) + # The predefined CMAKE_DL_LIBS may be broken. + endif() +endif(enable_threads) -# Thread Detection. Relying on cmake for lib and includes. -#TODO check cmake detection +# Thread support detection. if (CMAKE_USE_PTHREADS_INIT) set(SRC ${SRC} pthread_start.c pthread_support.c pthread_stop_world.c) - # Common defines for most POSIX platforms. - if (ANDROID OR APPLE OR CYGWIN OR MSYS OR HOST MATCHES .*-.*-aix.*|.*-.*-.*freebsd.*|.*-.*-haiku.*|.*-.*-gnu.*|.*-.*-hpux11.*|.*-.*-irix.*|.*-.*-.*linux.*|.*-.*-nacl.*|.*-.*-netbsd.*|.*-.*-openbsd.*|.*-.*-osf.*|.*-.*-solaris.*) - add_definitions("-DGC_THREADS -D_REENTRANT") - if (enable_parallel_mark) - add_definitions("-DPARALLEL_MARK") - endif() - if (enable_thread_local_alloc) - add_definitions("-DTHREAD_LOCAL_ALLOC") - set(SRC ${SRC} thread_local_alloc.c) - endif() - message("Explicit GC_INIT() calls may be required.") + if (HOST MATCHES .*-.*-hpux10.*) + message(FATAL_ERROR "HP/UX 10 POSIX threads are not supported.") + endif() + # Assume the compiler supports C11 (GCC) atomic intrinsics. + add_definitions("-DGC_BUILTIN_ATOMIC") + # Common defines for POSIX platforms. + add_definitions("-DGC_THREADS -D_REENTRANT") + if (enable_parallel_mark) + add_definitions("-DPARALLEL_MARK") endif() + if (enable_thread_local_alloc) + add_definitions("-DTHREAD_LOCAL_ALLOC") + set(SRC ${SRC} thread_local_alloc.c) + endif() + message("Explicit GC_INIT() calls may be required.") if (HOST MATCHES .*-.*-hpux11.*) message("Only HP/UX 11 POSIX threads are supported.") add_definitions("-D_POSIX_C_SOURCE=199506L") - #TODO test -DVAR=value. Alternative is COMPILE_DEFINITIONS property - endif() - if (HOST MATCHES .*-.*-hpux10.*) - message("HP/UX 10 POSIX threads are not supported.") - endif() - if (HOST MATCHES .*-.*-netbsd.*) + elseif (HOST MATCHES .*-.*-netbsd.*) message("Only on NetBSD 2.0 or later.") add_definitions("-D_PTHREADS") endif() - if (ANDROID) # ANDROID variable is defined by CMake v3.7.0+. + if (ANDROID OR MSYS) # ANDROID variable is defined by CMake v3.7.0+. # Android NDK does not provide pthread_atfork. - elseif (CYGWIN OR HOST MATCHES .*-.*-aix.*|.*-.*-freebsd.*|.*-.*-haiku.*|.*-.*-hpux11.*|.*-.*-irix.*|.*-.*-kfreebsd.*-gnu|.*-.*-.*linux.*|.*-.*-netbsd.*|.*-.*-openbsd.*|.*-.*-osf.*|.*-.*-solaris.*) - if (enable_handle_fork) - add_definitions("-DHANDLE_FORK") - endif(enable_handle_fork) elseif (APPLE) if (enable_handle_fork) # The incremental mode conflicts with fork handling. @@ -159,6 +150,8 @@ if (CMAKE_USE_PTHREADS_INIT) endif() endif(enable_handle_fork) set(SRC ${SRC} darwin_stop_world.c) + elseif (enable_handle_fork) + add_definitions("-DHANDLE_FORK") endif() if (enable_sigrt_signals) add_definitions("-DGC_USESIGRT_SIGNALS") @@ -166,24 +159,27 @@ if (CMAKE_USE_PTHREADS_INIT) if (CYGWIN OR MSYS) set(SRC ${SRC} win32_threads.c) endif() -endif(CMAKE_USE_PTHREADS_INIT) - -if (CMAKE_USE_WIN32_THREADS_INIT) +elseif (CMAKE_USE_WIN32_THREADS_INIT) add_definitions("-DGC_THREADS") if (enable_parallel_mark) add_definitions("-DPARALLEL_MARK") - if (enable_thread_local_alloc) - add_definitions("-DTHREAD_LOCAL_ALLOC") - set(SRC ${SRC} thread_local_alloc.c) - endif() - endif(enable_parallel_mark) + endif() + if (enable_thread_local_alloc AND (enable_parallel_mark OR NOT BUILD_SHARED_LIBS)) + # Imply THREAD_LOCAL_ALLOC unless GC_DLL. + add_definitions("-DTHREAD_LOCAL_ALLOC") + set(SRC ${SRC} thread_local_alloc.c) + endif() add_definitions("-DEMPTY_GETENV_RESULTS") set(SRC ${SRC} win32_threads.c) -endif(CMAKE_USE_WIN32_THREADS_INIT) +elseif (CMAKE_HP_PTHREADS_INIT OR CMAKE_USE_SPROC_INIT) + message(FATAL_ERROR "Unsupported thread package") +endif() if (enable_gcj_support) add_definitions("-DGC_GCJ_SUPPORT") - if (enable_threads) + if (enable_threads AND NOT (enable_thread_local_alloc AND HOST MATCHES .*-.*-kfreebsd.*-gnu)) + # FIXME: For a reason, gctest hangs up on kFreeBSD if both of + # THREAD_LOCAL_ALLOC and GC_ENABLE_SUSPEND_THREAD are defined. add_definitions("-DGC_ENABLE_SUSPEND_THREAD") endif() set(SRC ${SRC} gcj_mlc.c) @@ -309,6 +305,9 @@ if (DEFINED CFLAGS_EXTRA) endif() add_library(gc ${SRC}) +if (enable_threads) + target_link_libraries(gc PRIVATE ${THREADDLLIBS}) +endif() if (enable_cplusplus) add_library(gccpp gc_cpp.cc) @@ -397,7 +396,7 @@ if (build_tests) endif(enable_cplusplus) add_executable(gctest WIN32 tests/test.c) - target_link_libraries(gctest PRIVATE gc) + target_link_libraries(gctest PRIVATE gc ${THREADDLLIBS}) add_test(NAME gctest COMMAND gctest) if (WATCOM) # Suppress "conditional expression in if statement is always true/false" @@ -445,6 +444,30 @@ if (build_tests) add_test(NAME tracetest COMMAND tracetest) endif() + if (enable_threads) + add_executable(test_atomic_ops tests/test_atomic_ops.c) + target_link_libraries(test_atomic_ops PRIVATE gc) + add_test(NAME test_atomic_ops COMMAND test_atomic_ops) + + add_executable(threadleaktest tests/thread_leak_test.c) + target_link_libraries(threadleaktest PRIVATE gc ${THREADDLLIBS}) + add_test(NAME threadleaktest COMMAND threadleaktest) + + if (NOT WIN32) + add_executable(threadkey_test tests/threadkey_test.c) + target_link_libraries(threadkey_test PRIVATE gc ${THREADDLLIBS}) + add_test(NAME threadkey_test COMMAND threadkey_test) + endif() + + add_executable(subthreadcreate_test tests/subthread_create.c) + target_link_libraries(subthreadcreate_test PRIVATE gc ${THREADDLLIBS}) + add_test(NAME subthreadcreate_test COMMAND subthreadcreate_test) + + add_executable(initsecondarythread_test tests/initsecondarythread.c) + target_link_libraries(initsecondarythread_test PRIVATE gc ${THREADDLLIBS}) + add_test(NAME initsecondarythread_test COMMAND initsecondarythread_test) + endif(enable_threads) + if (enable_cplusplus) add_executable(test_cpp WIN32 tests/test_cpp.cc) target_link_libraries(test_cpp PRIVATE gc gccpp) @@ -457,11 +480,11 @@ if (build_tests) add_test(NAME disclaim_bench COMMAND disclaim_bench) add_executable(disclaim_test tests/disclaim_test.c) - target_link_libraries(disclaim_test PRIVATE gc) + target_link_libraries(disclaim_test PRIVATE gc ${THREADDLLIBS}) add_test(NAME disclaim_test COMMAND disclaim_test) add_executable(disclaim_weakmap_test tests/disclaim_weakmap_test.c) - target_link_libraries(disclaim_weakmap_test PRIVATE gc) + target_link_libraries(disclaim_weakmap_test PRIVATE gc ${THREADDLLIBS}) add_test(NAME disclaim_weakmap_test COMMAND disclaim_weakmap_test) endif() endif(build_tests)