From a756239e727842f2c274208acd8fb93fa745d04a Mon Sep 17 00:00:00 2001 From: Dan Liew Date: Wed, 4 Aug 2021 19:24:56 -0700 Subject: [PATCH] Fix COMPILER_RT_DEBUG build for targets that don't support thread local storage. 022439931f5be77efaf80b44d587666b0c9b13b5 added code that is only enabled when COMPILER_RT_DEBUG is enabled. This code doesn't build on targets that don't support thread local storage because the code added uses the THREADLOCAL macro. Consequently the COMPILER_RT_DEBUG build broke for some Apple targets (e.g. 32-bit iOS simulators). ``` /Volumes/user_data/dev/llvm/llvm.org/main/src/llvm-project/compiler-rt/lib/sanitizer_common/sanitizer_mutex.cpp:216:8: error: thread-local storage is not supported for the current target static THREADLOCAL InternalDeadlockDetector deadlock_detector; ^ /Volumes/user_data/dev/llvm/llvm.org/main/src/llvm-project/compiler-rt/lib/sanitizer_common/sanitizer_internal_defs.h:227:24: note: expanded from macro 'THREADLOCAL' # define THREADLOCAL __thread ^ 1 error generated. ``` To fix this, this patch introduces a `SANITIZER_SUPPORTS_THREADLOCAL` macro that is `1` iff thread local storage is supported by the current target. That condition is then added to `SANITIZER_CHECK_DEADLOCKS` to ensure the code is only enabled when thread local storage is available. The implementation of `SANITIZER_SUPPORTS_THREADLOCAL` currently assumes Clang. See `llvm-project/clang/include/clang/Basic/Features.def` for the definition of the `tls` feature. rdar://81543007 Differential Revision: https://reviews.llvm.org/D107524 --- compiler-rt/lib/sanitizer_common/sanitizer_mutex.h | 3 ++- compiler-rt/lib/sanitizer_common/sanitizer_platform.h | 14 ++++++++++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_mutex.h b/compiler-rt/lib/sanitizer_common/sanitizer_mutex.h index 3fc2d33..709ea1c 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_mutex.h +++ b/compiler-rt/lib/sanitizer_common/sanitizer_mutex.h @@ -95,7 +95,8 @@ enum { // Go linker does not support THREADLOCAL variables, // so we can't use per-thread state. -#define SANITIZER_CHECK_DEADLOCKS (SANITIZER_DEBUG && !SANITIZER_GO) +#define SANITIZER_CHECK_DEADLOCKS \ + (SANITIZER_DEBUG && !SANITIZER_GO && SANITIZER_SUPPORTS_THREADLOCAL) #if SANITIZER_CHECK_DEADLOCKS struct MutexMeta { diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_platform.h b/compiler-rt/lib/sanitizer_common/sanitizer_platform.h index 4d3c088..9b4a0f0 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_platform.h +++ b/compiler-rt/lib/sanitizer_common/sanitizer_platform.h @@ -377,4 +377,18 @@ #define SANITIZER_SUPPORTS_INIT_FOR_DLOPEN 0 #endif +// SANITIZER_SUPPORTS_THREADLOCAL +// 1 - THREADLOCAL macro is supported by target +// 0 - THREADLOCAL macro is not supported by target +#ifndef __has_feature +// TODO: Support other compilers here +# define SANITIZER_SUPPORTS_THREADLOCAL 1 +#else +# if __has_feature(tls) +# define SANITIZER_SUPPORTS_THREADLOCAL 1 +# else +# define SANITIZER_SUPPORTS_THREADLOCAL 0 +# endif +#endif + #endif // SANITIZER_PLATFORM_H -- 2.7.4