aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2017-06-10 13:44:32 +0000
committerDimitry Andric <dim@FreeBSD.org>2017-06-10 13:44:32 +0000
commit7edd24de96f22ad70fd3ca16a3c51723383cd58b (patch)
tree1bd9c96401fc2098358ab3ab9f14255e2eabd1ac
parent25091d6bd042c6bf2709eaab2bd1a88f3f2d9fda (diff)
downloadsrc-7edd24de96f22ad70fd3ca16a3c51723383cd58b.tar.gz
src-7edd24de96f22ad70fd3ca16a3c51723383cd58b.zip
Vendor import of compiler-rt trunk r305145:vendor/compiler-rt/compiler-rt-trunk-r305145
Notes
Notes: svn path=/vendor/compiler-rt/dist/; revision=319784 svn path=/vendor/compiler-rt/compiler-rt-trunk-r305145/; revision=319785; tag=vendor/compiler-rt/compiler-rt-trunk-r305145
-rw-r--r--CMakeLists.txt2
-rw-r--r--lib/asan/asan_allocator.cc4
-rw-r--r--lib/asan/asan_allocator.h2
-rw-r--r--lib/asan/asan_interceptors.cc17
-rw-r--r--lib/asan/asan_malloc_linux.cc22
-rw-r--r--lib/lsan/lsan_common.cc3
-rw-r--r--lib/lsan/lsan_common_linux.cc23
-rw-r--r--lib/lsan/lsan_interceptors.cc24
-rw-r--r--lib/msan/msan_allocator.cc96
-rw-r--r--lib/msan/msan_allocator.h97
-rw-r--r--lib/msan/msan_interceptors.cc2
-rw-r--r--lib/sanitizer_common/sanitizer_common_interceptors.inc5
-rw-r--r--lib/sanitizer_common/sanitizer_linux.cc10
-rw-r--r--lib/sanitizer_common/sanitizer_platform.h9
-rwxr-xr-xlib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh3
-rw-r--r--lib/tsan/rtl/tsan_rtl_thread.cc1
-rw-r--r--test/asan/TestCases/Darwin/atos-symbolizer.cc2
-rw-r--r--test/asan/TestCases/Linux/asan_preload_test-3.cc33
-rw-r--r--test/asan/TestCases/Posix/halt_on_error-torture.cc6
-rw-r--r--test/msan/Linux/strerror_r.cc18
-rw-r--r--test/profile/Linux/instrprof-alloc.test4
-rw-r--r--test/profile/Linux/instrprof-value-prof-warn.test2
-rw-r--r--test/sanitizer_common/TestCases/Linux/allocator_fork_no_hang.cc118
-rw-r--r--test/sanitizer_common/TestCases/sanitizer_coverage_inline8bit_counter.cc2
-rw-r--r--test/tsan/strerror_r.cc29
25 files changed, 223 insertions, 311 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index b522c340d669..51769088a992 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -255,7 +255,7 @@ if(EXISTS ${COMPILER_RT_LLD_PATH}/ AND LLVM_TOOL_LLD_BUILD)
set(COMPILER_RT_HAS_LLD TRUE)
else()
set(COMPILER_RT_LLD_PATH ${LLVM_MAIN_SRC_DIR}/../lld)
- if(EXISTS ${COMPILER_RT_LLD_PATH}/)
+ if(EXISTS ${COMPILER_RT_LLD_PATH}/ AND LLVM_TOOL_LLD_BUILD)
set(COMPILER_RT_HAS_LLD TRUE)
else()
set(COMPILER_RT_HAS_LLD FALSE)
diff --git a/lib/asan/asan_allocator.cc b/lib/asan/asan_allocator.cc
index db5a683e283d..7010b6023614 100644
--- a/lib/asan/asan_allocator.cc
+++ b/lib/asan/asan_allocator.cc
@@ -47,6 +47,8 @@ static u32 RZSize2Log(u32 rz_size) {
return res;
}
+static AsanAllocator &get_allocator();
+
// The memory chunk allocated from the underlying allocator looks like this:
// L L L L L L H H U U U U U U R R
// L -- left redzone words (0 or more bytes)
@@ -717,7 +719,7 @@ struct Allocator {
static Allocator instance(LINKER_INITIALIZED);
-AsanAllocator &get_allocator() {
+static AsanAllocator &get_allocator() {
return instance.allocator;
}
diff --git a/lib/asan/asan_allocator.h b/lib/asan/asan_allocator.h
index ce3e25dc5094..ad1aeb58a86b 100644
--- a/lib/asan/asan_allocator.h
+++ b/lib/asan/asan_allocator.h
@@ -213,7 +213,5 @@ void asan_mz_force_unlock();
void PrintInternalAllocatorStats();
void AsanSoftRssLimitExceededCallback(bool exceeded);
-AsanAllocator &get_allocator();
-
} // namespace __asan
#endif // ASAN_ALLOCATOR_H
diff --git a/lib/asan/asan_interceptors.cc b/lib/asan/asan_interceptors.cc
index 4682fba3392c..264d5aee8ceb 100644
--- a/lib/asan/asan_interceptors.cc
+++ b/lib/asan/asan_interceptors.cc
@@ -22,7 +22,6 @@
#include "asan_stats.h"
#include "asan_suppressions.h"
#include "lsan/lsan_common.h"
-#include "sanitizer_common/sanitizer_stackdepot.h"
#include "sanitizer_common/sanitizer_libc.h"
#if SANITIZER_POSIX
@@ -705,25 +704,9 @@ INTERCEPTOR(int, __cxa_atexit, void (*func)(void *), void *arg,
#endif // ASAN_INTERCEPT___CXA_ATEXIT
#if ASAN_INTERCEPT_FORK
-static void BeforeFork() {
- if (SANITIZER_LINUX) {
- get_allocator().ForceLock();
- StackDepotLockAll();
- }
-}
-
-static void AfterFork() {
- if (SANITIZER_LINUX) {
- StackDepotUnlockAll();
- get_allocator().ForceUnlock();
- }
-}
-
INTERCEPTOR(int, fork, void) {
ENSURE_ASAN_INITED();
- BeforeFork();
int pid = REAL(fork)();
- AfterFork();
return pid;
}
#endif // ASAN_INTERCEPT_FORK
diff --git a/lib/asan/asan_malloc_linux.cc b/lib/asan/asan_malloc_linux.cc
index 8c99d3bc9257..fd40f47db1c4 100644
--- a/lib/asan/asan_malloc_linux.cc
+++ b/lib/asan/asan_malloc_linux.cc
@@ -60,36 +60,42 @@ INTERCEPTOR(void, cfree, void *ptr) {
#endif // SANITIZER_INTERCEPT_CFREE
INTERCEPTOR(void*, malloc, uptr size) {
- if (UNLIKELY(!asan_inited))
+ if (UNLIKELY(asan_init_is_running))
// Hack: dlsym calls malloc before REAL(malloc) is retrieved from dlsym.
return AllocateFromLocalPool(size);
+ ENSURE_ASAN_INITED();
GET_STACK_TRACE_MALLOC;
return asan_malloc(size, &stack);
}
INTERCEPTOR(void*, calloc, uptr nmemb, uptr size) {
- if (UNLIKELY(!asan_inited))
+ if (UNLIKELY(asan_init_is_running))
// Hack: dlsym calls calloc before REAL(calloc) is retrieved from dlsym.
return AllocateFromLocalPool(nmemb * size);
+ ENSURE_ASAN_INITED();
GET_STACK_TRACE_MALLOC;
return asan_calloc(nmemb, size, &stack);
}
INTERCEPTOR(void*, realloc, void *ptr, uptr size) {
- GET_STACK_TRACE_MALLOC;
if (UNLIKELY(IsInDlsymAllocPool(ptr))) {
- uptr offset = (uptr)ptr - (uptr)alloc_memory_for_dlsym;
- uptr copy_size = Min(size, kDlsymAllocPoolSize - offset);
+ const uptr offset = (uptr)ptr - (uptr)alloc_memory_for_dlsym;
+ const uptr copy_size = Min(size, kDlsymAllocPoolSize - offset);
void *new_ptr;
- if (UNLIKELY(!asan_inited)) {
+ if (UNLIKELY(asan_init_is_running)) {
new_ptr = AllocateFromLocalPool(size);
} else {
- copy_size = size;
- new_ptr = asan_malloc(copy_size, &stack);
+ ENSURE_ASAN_INITED();
+ GET_STACK_TRACE_MALLOC;
+ new_ptr = asan_malloc(size, &stack);
}
internal_memcpy(new_ptr, ptr, copy_size);
return new_ptr;
}
+ if (UNLIKELY(asan_init_is_running))
+ return AllocateFromLocalPool(size);
+ ENSURE_ASAN_INITED();
+ GET_STACK_TRACE_MALLOC;
return asan_realloc(ptr, size, &stack);
}
diff --git a/lib/lsan/lsan_common.cc b/lib/lsan/lsan_common.cc
index d4f670681fa5..a5ffc6835f5f 100644
--- a/lib/lsan/lsan_common.cc
+++ b/lib/lsan/lsan_common.cc
@@ -408,9 +408,6 @@ static void MarkInvalidPCCb(uptr chunk, void *arg) {
// On Linux, handles dynamically allocated TLS blocks by treating all chunks
// allocated from ld-linux.so as reachable.
-// On Linux, treats all chunks allocated from ld-linux.so as reachable, which
-// covers dynamically allocated TLS blocks, internal dynamic loader's loaded
-// modules accounting etc.
// Dynamic TLS blocks contain the TLS variables of dynamically loaded modules.
// They are allocated with a __libc_memalign() call in allocate_and_init()
// (elf/dl-tls.c). Glibc won't tell us the address ranges occupied by those
diff --git a/lib/lsan/lsan_common_linux.cc b/lib/lsan/lsan_common_linux.cc
index 2e4095b495fe..c903be42d1e7 100644
--- a/lib/lsan/lsan_common_linux.cc
+++ b/lib/lsan/lsan_common_linux.cc
@@ -23,10 +23,6 @@
#include "sanitizer_common/sanitizer_linux.h"
#include "sanitizer_common/sanitizer_stackdepot.h"
-#if SANITIZER_USE_GETAUXVAL
-#include <sys/auxv.h>
-#endif // SANITIZER_USE_GETAUXVAL
-
namespace __lsan {
static const char kLinkerName[] = "ld";
@@ -34,12 +30,8 @@ static const char kLinkerName[] = "ld";
static char linker_placeholder[sizeof(LoadedModule)] ALIGNED(64);
static LoadedModule *linker = nullptr;
-static bool IsLinker(const LoadedModule& module) {
-#if SANITIZER_USE_GETAUXVAL
- return module.base_address() == getauxval(AT_BASE);
-#else
- return LibraryNameIs(module.full_name(), kLinkerName);
-#endif // SANITIZER_USE_GETAUXVAL
+static bool IsLinker(const char* full_name) {
+ return LibraryNameIs(full_name, kLinkerName);
}
__attribute__((tls_model("initial-exec")))
@@ -57,25 +49,22 @@ void InitializePlatformSpecificModules() {
ListOfModules modules;
modules.init();
for (LoadedModule &module : modules) {
- if (!IsLinker(module))
- continue;
+ if (!IsLinker(module.full_name())) continue;
if (linker == nullptr) {
linker = reinterpret_cast<LoadedModule *>(linker_placeholder);
*linker = module;
module = LoadedModule();
} else {
VReport(1, "LeakSanitizer: Multiple modules match \"%s\". "
- "TLS and other allocations originating from linker might be "
- "falsely reported as leaks.\n", kLinkerName);
+ "TLS will not be handled correctly.\n", kLinkerName);
linker->clear();
linker = nullptr;
return;
}
}
if (linker == nullptr) {
- VReport(1, "LeakSanitizer: Dynamic linker not found. TLS and other "
- "allocations originating from linker might be falsely reported "
- "as leaks.\n");
+ VReport(1, "LeakSanitizer: Dynamic linker not found. "
+ "TLS will not be handled correctly.\n");
}
}
diff --git a/lib/lsan/lsan_interceptors.cc b/lib/lsan/lsan_interceptors.cc
index a0a59daa07ae..9e39a7d1944d 100644
--- a/lib/lsan/lsan_interceptors.cc
+++ b/lib/lsan/lsan_interceptors.cc
@@ -22,7 +22,6 @@
#include "sanitizer_common/sanitizer_platform_interceptors.h"
#include "sanitizer_common/sanitizer_platform_limits_posix.h"
#include "sanitizer_common/sanitizer_posix.h"
-#include "sanitizer_common/sanitizer_stackdepot.h"
#include "sanitizer_common/sanitizer_tls_get_addr.h"
#include "lsan.h"
#include "lsan_allocator.h"
@@ -98,28 +97,6 @@ INTERCEPTOR(void*, valloc, uptr size) {
}
#endif
-static void BeforeFork() {
- if (SANITIZER_LINUX) {
- LockAllocator();
- StackDepotLockAll();
- }
-}
-
-static void AfterFork() {
- if (SANITIZER_LINUX) {
- StackDepotUnlockAll();
- UnlockAllocator();
- }
-}
-
-INTERCEPTOR(int, fork, void) {
- ENSURE_LSAN_INITED;
- BeforeFork();
- int pid = REAL(fork)();
- AfterFork();
- return pid;
-}
-
#if SANITIZER_INTERCEPT_MEMALIGN
INTERCEPTOR(void*, memalign, uptr alignment, uptr size) {
ENSURE_LSAN_INITED;
@@ -359,7 +336,6 @@ void InitializeInterceptors() {
LSAN_MAYBE_INTERCEPT_MALLOPT;
INTERCEPT_FUNCTION(pthread_create);
INTERCEPT_FUNCTION(pthread_join);
- INTERCEPT_FUNCTION(fork);
if (pthread_key_create(&g_thread_finalize_key, &thread_finalize)) {
Report("LeakSanitizer: failed to create thread key.\n");
diff --git a/lib/msan/msan_allocator.cc b/lib/msan/msan_allocator.cc
index f76b01de0924..1be573faa412 100644
--- a/lib/msan/msan_allocator.cc
+++ b/lib/msan/msan_allocator.cc
@@ -12,6 +12,8 @@
// MemorySanitizer allocator.
//===----------------------------------------------------------------------===//
+#include "sanitizer_common/sanitizer_allocator.h"
+#include "sanitizer_common/sanitizer_allocator_interface.h"
#include "msan.h"
#include "msan_allocator.h"
#include "msan_origin.h"
@@ -20,12 +22,102 @@
namespace __msan {
+struct Metadata {
+ uptr requested_size;
+};
+
+struct MsanMapUnmapCallback {
+ void OnMap(uptr p, uptr size) const {}
+ void OnUnmap(uptr p, uptr size) const {
+ __msan_unpoison((void *)p, size);
+
+ // We are about to unmap a chunk of user memory.
+ // Mark the corresponding shadow memory as not needed.
+ uptr shadow_p = MEM_TO_SHADOW(p);
+ ReleaseMemoryPagesToOS(shadow_p, shadow_p + size);
+ if (__msan_get_track_origins()) {
+ uptr origin_p = MEM_TO_ORIGIN(p);
+ ReleaseMemoryPagesToOS(origin_p, origin_p + size);
+ }
+ }
+};
+
+#if defined(__mips64)
+ static const uptr kMaxAllowedMallocSize = 2UL << 30;
+ static const uptr kRegionSizeLog = 20;
+ static const uptr kNumRegions = SANITIZER_MMAP_RANGE_SIZE >> kRegionSizeLog;
+ typedef TwoLevelByteMap<(kNumRegions >> 12), 1 << 12> ByteMap;
+
+ struct AP32 {
+ static const uptr kSpaceBeg = 0;
+ static const u64 kSpaceSize = SANITIZER_MMAP_RANGE_SIZE;
+ static const uptr kMetadataSize = sizeof(Metadata);
+ typedef __sanitizer::CompactSizeClassMap SizeClassMap;
+ static const uptr kRegionSizeLog = __msan::kRegionSizeLog;
+ typedef __msan::ByteMap ByteMap;
+ typedef MsanMapUnmapCallback MapUnmapCallback;
+ static const uptr kFlags = 0;
+ };
+ typedef SizeClassAllocator32<AP32> PrimaryAllocator;
+#elif defined(__x86_64__)
+#if SANITIZER_LINUX && !defined(MSAN_LINUX_X86_64_OLD_MAPPING)
+ static const uptr kAllocatorSpace = 0x700000000000ULL;
+#else
+ static const uptr kAllocatorSpace = 0x600000000000ULL;
+#endif
+ static const uptr kMaxAllowedMallocSize = 8UL << 30;
+
+ struct AP64 { // Allocator64 parameters. Deliberately using a short name.
+ static const uptr kSpaceBeg = kAllocatorSpace;
+ static const uptr kSpaceSize = 0x40000000000; // 4T.
+ static const uptr kMetadataSize = sizeof(Metadata);
+ typedef DefaultSizeClassMap SizeClassMap;
+ typedef MsanMapUnmapCallback MapUnmapCallback;
+ static const uptr kFlags = 0;
+ };
+
+ typedef SizeClassAllocator64<AP64> PrimaryAllocator;
+
+#elif defined(__powerpc64__)
+ static const uptr kMaxAllowedMallocSize = 2UL << 30; // 2G
+
+ struct AP64 { // Allocator64 parameters. Deliberately using a short name.
+ static const uptr kSpaceBeg = 0x300000000000;
+ static const uptr kSpaceSize = 0x020000000000; // 2T.
+ static const uptr kMetadataSize = sizeof(Metadata);
+ typedef DefaultSizeClassMap SizeClassMap;
+ typedef MsanMapUnmapCallback MapUnmapCallback;
+ static const uptr kFlags = 0;
+ };
+
+ typedef SizeClassAllocator64<AP64> PrimaryAllocator;
+#elif defined(__aarch64__)
+ static const uptr kMaxAllowedMallocSize = 2UL << 30; // 2G
+ static const uptr kRegionSizeLog = 20;
+ static const uptr kNumRegions = SANITIZER_MMAP_RANGE_SIZE >> kRegionSizeLog;
+ typedef TwoLevelByteMap<(kNumRegions >> 12), 1 << 12> ByteMap;
+
+ struct AP32 {
+ static const uptr kSpaceBeg = 0;
+ static const u64 kSpaceSize = SANITIZER_MMAP_RANGE_SIZE;
+ static const uptr kMetadataSize = sizeof(Metadata);
+ typedef __sanitizer::CompactSizeClassMap SizeClassMap;
+ static const uptr kRegionSizeLog = __msan::kRegionSizeLog;
+ typedef __msan::ByteMap ByteMap;
+ typedef MsanMapUnmapCallback MapUnmapCallback;
+ static const uptr kFlags = 0;
+ };
+ typedef SizeClassAllocator32<AP32> PrimaryAllocator;
+#endif
+typedef SizeClassAllocatorLocalCache<PrimaryAllocator> AllocatorCache;
+typedef LargeMmapAllocator<MsanMapUnmapCallback> SecondaryAllocator;
+typedef CombinedAllocator<PrimaryAllocator, AllocatorCache,
+ SecondaryAllocator> Allocator;
+
static Allocator allocator;
static AllocatorCache fallback_allocator_cache;
static SpinMutex fallback_mutex;
-Allocator &get_allocator() { return allocator; }
-
void MsanAllocatorInit() {
allocator.Init(
common_flags()->allocator_may_return_null,
diff --git a/lib/msan/msan_allocator.h b/lib/msan/msan_allocator.h
index abd4ea678523..407942e54c1a 100644
--- a/lib/msan/msan_allocator.h
+++ b/lib/msan/msan_allocator.h
@@ -15,106 +15,9 @@
#define MSAN_ALLOCATOR_H
#include "sanitizer_common/sanitizer_common.h"
-#include "sanitizer_common/sanitizer_allocator.h"
-#include "sanitizer_common/sanitizer_allocator_interface.h"
namespace __msan {
-struct Metadata {
- uptr requested_size;
-};
-
-struct MsanMapUnmapCallback {
- void OnMap(uptr p, uptr size) const {}
- void OnUnmap(uptr p, uptr size) const {
- __msan_unpoison((void *)p, size);
-
- // We are about to unmap a chunk of user memory.
- // Mark the corresponding shadow memory as not needed.
- uptr shadow_p = MEM_TO_SHADOW(p);
- ReleaseMemoryPagesToOS(shadow_p, shadow_p + size);
- if (__msan_get_track_origins()) {
- uptr origin_p = MEM_TO_ORIGIN(p);
- ReleaseMemoryPagesToOS(origin_p, origin_p + size);
- }
- }
-};
-
-#if defined(__mips64)
- static const uptr kMaxAllowedMallocSize = 2UL << 30;
- static const uptr kRegionSizeLog = 20;
- static const uptr kNumRegions = SANITIZER_MMAP_RANGE_SIZE >> kRegionSizeLog;
- typedef TwoLevelByteMap<(kNumRegions >> 12), 1 << 12> ByteMap;
-
- struct AP32 {
- static const uptr kSpaceBeg = 0;
- static const u64 kSpaceSize = SANITIZER_MMAP_RANGE_SIZE;
- static const uptr kMetadataSize = sizeof(Metadata);
- typedef __sanitizer::CompactSizeClassMap SizeClassMap;
- static const uptr kRegionSizeLog = __msan::kRegionSizeLog;
- typedef __msan::ByteMap ByteMap;
- typedef MsanMapUnmapCallback MapUnmapCallback;
- static const uptr kFlags = 0;
- };
- typedef SizeClassAllocator32<AP32> PrimaryAllocator;
-#elif defined(__x86_64__)
-#if SANITIZER_LINUX && !defined(MSAN_LINUX_X86_64_OLD_MAPPING)
- static const uptr kAllocatorSpace = 0x700000000000ULL;
-#else
- static const uptr kAllocatorSpace = 0x600000000000ULL;
-#endif
- static const uptr kMaxAllowedMallocSize = 8UL << 30;
-
- struct AP64 { // Allocator64 parameters. Deliberately using a short name.
- static const uptr kSpaceBeg = kAllocatorSpace;
- static const uptr kSpaceSize = 0x40000000000; // 4T.
- static const uptr kMetadataSize = sizeof(Metadata);
- typedef DefaultSizeClassMap SizeClassMap;
- typedef MsanMapUnmapCallback MapUnmapCallback;
- static const uptr kFlags = 0;
- };
-
- typedef SizeClassAllocator64<AP64> PrimaryAllocator;
-
-#elif defined(__powerpc64__)
- static const uptr kMaxAllowedMallocSize = 2UL << 30; // 2G
-
- struct AP64 { // Allocator64 parameters. Deliberately using a short name.
- static const uptr kSpaceBeg = 0x300000000000;
- static const uptr kSpaceSize = 0x020000000000; // 2T.
- static const uptr kMetadataSize = sizeof(Metadata);
- typedef DefaultSizeClassMap SizeClassMap;
- typedef MsanMapUnmapCallback MapUnmapCallback;
- static const uptr kFlags = 0;
- };
-
- typedef SizeClassAllocator64<AP64> PrimaryAllocator;
-#elif defined(__aarch64__)
- static const uptr kMaxAllowedMallocSize = 2UL << 30; // 2G
- static const uptr kRegionSizeLog = 20;
- static const uptr kNumRegions = SANITIZER_MMAP_RANGE_SIZE >> kRegionSizeLog;
- typedef TwoLevelByteMap<(kNumRegions >> 12), 1 << 12> ByteMap;
-
- struct AP32 {
- static const uptr kSpaceBeg = 0;
- static const u64 kSpaceSize = SANITIZER_MMAP_RANGE_SIZE;
- static const uptr kMetadataSize = sizeof(Metadata);
- typedef __sanitizer::CompactSizeClassMap SizeClassMap;
- static const uptr kRegionSizeLog = __msan::kRegionSizeLog;
- typedef __msan::ByteMap ByteMap;
- typedef MsanMapUnmapCallback MapUnmapCallback;
- static const uptr kFlags = 0;
- };
- typedef SizeClassAllocator32<AP32> PrimaryAllocator;
-#endif
-typedef SizeClassAllocatorLocalCache<PrimaryAllocator> AllocatorCache;
-typedef LargeMmapAllocator<MsanMapUnmapCallback> SecondaryAllocator;
-typedef CombinedAllocator<PrimaryAllocator, AllocatorCache,
- SecondaryAllocator> Allocator;
-
-
-Allocator &get_allocator();
-
struct MsanThreadLocalMallocStorage {
uptr quarantine_cache[16];
// Allocator cache contains atomic_uint64_t which must be 8-byte aligned.
diff --git a/lib/msan/msan_interceptors.cc b/lib/msan/msan_interceptors.cc
index fbc2ea4fec9d..0f50693441be 100644
--- a/lib/msan/msan_interceptors.cc
+++ b/lib/msan/msan_interceptors.cc
@@ -1201,7 +1201,6 @@ INTERCEPTOR(void *, shmat, int shmid, const void *shmaddr, int shmflg) {
}
static void BeforeFork() {
- get_allocator().ForceLock();
StackDepotLockAll();
ChainedOriginDepotLockAll();
}
@@ -1209,7 +1208,6 @@ static void BeforeFork() {
static void AfterFork() {
ChainedOriginDepotUnlockAll();
StackDepotUnlockAll();
- get_allocator().ForceUnlock();
}
INTERCEPTOR(int, fork, void) {
diff --git a/lib/sanitizer_common/sanitizer_common_interceptors.inc b/lib/sanitizer_common/sanitizer_common_interceptors.inc
index c0c08a031e9b..6ca431d8ad82 100644
--- a/lib/sanitizer_common/sanitizer_common_interceptors.inc
+++ b/lib/sanitizer_common/sanitizer_common_interceptors.inc
@@ -3395,7 +3395,10 @@ INTERCEPTOR(char *, strerror_r, int errnum, char *buf, SIZE_T buflen) {
// its metadata. See
// https://github.com/google/sanitizers/issues/321.
char *res = REAL(strerror_r)(errnum, buf, buflen);
- COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
+ if (res == buf)
+ COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
+ else
+ COMMON_INTERCEPTOR_INITIALIZE_RANGE(res, REAL(strlen)(res) + 1);
return res;
}
#endif //(_POSIX_C_SOURCE >= 200112L || _XOPEN_SOURCE >= 600) && !_GNU_SOURCE ||
diff --git a/lib/sanitizer_common/sanitizer_linux.cc b/lib/sanitizer_common/sanitizer_linux.cc
index 7bc7682dd962..cec2f264cbc4 100644
--- a/lib/sanitizer_common/sanitizer_linux.cc
+++ b/lib/sanitizer_common/sanitizer_linux.cc
@@ -75,6 +75,16 @@ extern char **environ; // provided by crt1
#include <sys/signal.h>
#endif
+#ifndef __GLIBC_PREREQ
+#define __GLIBC_PREREQ(x, y) 0
+#endif
+
+#if SANITIZER_LINUX && __GLIBC_PREREQ(2, 16)
+# define SANITIZER_USE_GETAUXVAL 1
+#else
+# define SANITIZER_USE_GETAUXVAL 0
+#endif
+
#if SANITIZER_USE_GETAUXVAL
#include <sys/auxv.h>
#endif
diff --git a/lib/sanitizer_common/sanitizer_platform.h b/lib/sanitizer_common/sanitizer_platform.h
index 8fa3f7ab66fc..49732aa32323 100644
--- a/lib/sanitizer_common/sanitizer_platform.h
+++ b/lib/sanitizer_common/sanitizer_platform.h
@@ -269,14 +269,5 @@
# define SANITIZER_SUPPRESS_LEAK_ON_PTHREAD_EXIT 0
#endif
-#ifndef __GLIBC_PREREQ
-#define __GLIBC_PREREQ(x, y) 0
-#endif
-
-#if SANITIZER_LINUX && __GLIBC_PREREQ(2, 16)
-# define SANITIZER_USE_GETAUXVAL 1
-#else
-# define SANITIZER_USE_GETAUXVAL 0
-#endif
#endif // SANITIZER_PLATFORM_H
diff --git a/lib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh b/lib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh
index 4a0fb03c4c70..c5865ecfee6c 100755
--- a/lib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh
+++ b/lib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh
@@ -129,7 +129,7 @@ if [[ ! -d ${LLVM_BUILD} ]]; then
$LLVM_SRC
fi
cd ${LLVM_BUILD}
-ninja LLVMSymbolize LLVMObject LLVMDebugInfoDWARF LLVMSupport LLVMDebugInfoPDB LLVMMC
+ninja LLVMSymbolize LLVMObject LLVMBinaryFormat LLVMDebugInfoDWARF LLVMSupport LLVMDebugInfoPDB LLVMMC
cd ${BUILD_DIR}
rm -rf ${SYMBOLIZER_BUILD}
@@ -148,6 +148,7 @@ $SCRIPT_DIR/ar_to_bc.sh $LIBCXX_BUILD/lib/libc++.a \
$LIBCXX_BUILD/lib/libc++abi.a \
$LLVM_BUILD/lib/libLLVMSymbolize.a \
$LLVM_BUILD/lib/libLLVMObject.a \
+ $LLVM_BUILD/lib/libLLVMBinaryFormat.a \
$LLVM_BUILD/lib/libLLVMDebugInfoDWARF.a \
$LLVM_BUILD/lib/libLLVMSupport.a \
$LLVM_BUILD/lib/libLLVMDebugInfoPDB.a \
diff --git a/lib/tsan/rtl/tsan_rtl_thread.cc b/lib/tsan/rtl/tsan_rtl_thread.cc
index edb60980c76f..67eebf5d0c38 100644
--- a/lib/tsan/rtl/tsan_rtl_thread.cc
+++ b/lib/tsan/rtl/tsan_rtl_thread.cc
@@ -345,6 +345,7 @@ void MemoryAccessRange(ThreadState *thr, uptr pc, uptr addr,
StatInc(thr, StatMopRange);
if (*shadow_mem == kShadowRodata) {
+ DCHECK(!is_write);
// Access to .rodata section, no races here.
// Measurements show that it can be 10-20% of all memory accesses.
StatInc(thr, StatMopRangeRodata);
diff --git a/test/asan/TestCases/Darwin/atos-symbolizer.cc b/test/asan/TestCases/Darwin/atos-symbolizer.cc
index 7b091c4d681c..e7d7e7a17fb7 100644
--- a/test/asan/TestCases/Darwin/atos-symbolizer.cc
+++ b/test/asan/TestCases/Darwin/atos-symbolizer.cc
@@ -4,7 +4,7 @@
// RUN: %env_asan_opts=verbosity=2 ASAN_SYMBOLIZER_PATH=$(which atos) not %run %t 2>&1 | FileCheck %s
// Path returned by `which atos` is invalid on iOS.
-// UNSUPPORTED: ios
+// UNSUPPORTED: ios, i386-darwin
#include <stdlib.h>
#include <string.h>
diff --git a/test/asan/TestCases/Linux/asan_preload_test-3.cc b/test/asan/TestCases/Linux/asan_preload_test-3.cc
new file mode 100644
index 000000000000..041669b56a45
--- /dev/null
+++ b/test/asan/TestCases/Linux/asan_preload_test-3.cc
@@ -0,0 +1,33 @@
+// Regression test for PR33206
+//
+// RUN: %clang -DDYN=1 -DMALLOC=1 -fPIC -shared %s -o %t-dso1.so
+// RUN: %clang -DDYN=1 -DMALLOC=1 -fPIC -shared %s -o %t-dso2.so %t-dso1.so
+// RUN: %clang %s -o %t-1 %t-dso2.so
+// RUN: env LD_PRELOAD=%shared_libasan %run %t-1 2>&1 | FileCheck %s
+// RUN: %clang -DDYN=1 -DREALLOC=1 -fPIC -shared %s -o %t-dso3.so
+// RUN: %clang -DDYN=1 -DREALLOC=1 -fPIC -shared %s -o %t-dso4.so %t-dso3.so
+// RUN: %clang %s -o %t-2 %t-dso4.so
+// RUN: env LD_PRELOAD=%shared_libasan %run %t-2 2>&1 | FileCheck %s
+// REQUIRES: asan-dynamic-runtime
+
+#include <stdlib.h>
+#include <stdio.h>
+
+#ifdef DYN
+__attribute__((constructor)) void foo() {
+ void *p;
+#ifdef MALLOC
+ p = malloc(1 << 20);
+#endif
+#ifdef REALLOC
+ p = realloc (0, 1 << 20);
+#endif
+ free(p);
+}
+#else
+int main() {
+ // CHECK: Success
+ printf("Success\n");
+ return 0;
+}
+#endif
diff --git a/test/asan/TestCases/Posix/halt_on_error-torture.cc b/test/asan/TestCases/Posix/halt_on_error-torture.cc
index 1b26173d713f..829568e2682b 100644
--- a/test/asan/TestCases/Posix/halt_on_error-torture.cc
+++ b/test/asan/TestCases/Posix/halt_on_error-torture.cc
@@ -10,12 +10,12 @@
//
// Collisions are unlikely but still possible so we need the ||.
// RUN: rm -f 10.txt
-// RUN: %env_asan_opts=halt_on_error=false:suppress_equal_pcs=false %run %t 10 20 >>10.txt 2>&1 || true
+// RUN: %env_asan_opts=halt_on_error=false:suppress_equal_pcs=false:exitcode=0 %run %t 10 20 2>&1 | cat > 10.txt
// RUN: FileCheck --check-prefix=CHECK-COLLISION %s < 10.txt || FileCheck --check-prefix=CHECK-NO-COLLISION %s < 10.txt
//
// Collisions are unlikely but still possible so we need the ||.
// RUN: rm -f 20.txt
-// RUN: %env_asan_opts=halt_on_error=false %run %t 10 20 >>20.txt 2>&1 || true
+// RUN: %env_asan_opts=halt_on_error=false:exitcode=0 %run %t 10 20 2>&1 | cat > 20.txt
// RUN: FileCheck --check-prefix=CHECK-COLLISION %s < 20.txt || FileCheck --check-prefix=CHECK-NO-COLLISION %s < 20.txt
#include <stdio.h>
@@ -38,7 +38,7 @@ void *run(void *arg) {
unsigned seed = (unsigned)(size_t)arg;
volatile char tmp[2];
- __asan_poison_memory_region(&tmp, sizeof(tmp));
+ __asan_poison_memory_region(&tmp, sizeof(tmp));
for (size_t i = 0; i < niter; ++i) {
random_delay(&seed);
diff --git a/test/msan/Linux/strerror_r.cc b/test/msan/Linux/strerror_r.cc
new file mode 100644
index 000000000000..aec653f9c025
--- /dev/null
+++ b/test/msan/Linux/strerror_r.cc
@@ -0,0 +1,18 @@
+// RUN: %clang_msan -O0 -g %s -o %t && %run %t
+
+#include <assert.h>
+#include <errno.h>
+#include <string.h>
+
+int main() {
+ char buf[1000];
+ char *res = strerror_r(EINVAL, buf, sizeof(buf));
+ assert(res);
+ volatile int z = strlen(res);
+
+ res = strerror_r(-1, buf, sizeof(buf));
+ assert(res);
+ z = strlen(res);
+
+ return 0;
+}
diff --git a/test/profile/Linux/instrprof-alloc.test b/test/profile/Linux/instrprof-alloc.test
index 752b10892170..4db764704adb 100644
--- a/test/profile/Linux/instrprof-alloc.test
+++ b/test/profile/Linux/instrprof-alloc.test
@@ -1,6 +1,6 @@
-// RUN: %clang_profgen -Xclang -fprofile-instrument=llvm -fuse-ld=gold -Wl,-wrap,malloc -Wl,-wrap,calloc -o %t -O3 %S/../Inputs/instrprof-alloc.c
+// RUN: %clang_pgogen -fuse-ld=gold -Wl,-wrap,malloc -Wl,-wrap,calloc -o %t -O3 %S/../Inputs/instrprof-alloc.c
// RUN: env LLVM_PROFILE_FILE=%t.profraw %run %t
-// RUN: %clang_profgen -Xclang -fprofile-instrument=llvm -mllvm -vp-static-alloc=false -fuse-ld=gold -Wl,-wrap,malloc -Wl,-wrap,calloc -o %t.dyn -O3 %S/../Inputs/instrprof-alloc.c
+// RUN: %clang_pgogen -mllvm -vp-static-alloc=false -fuse-ld=gold -Wl,-wrap,malloc -Wl,-wrap,calloc -o %t.dyn -O3 %S/../Inputs/instrprof-alloc.c
// RUN: env LLVM_PROFILE_FILE=%t.profraw not %run %t.dyn
diff --git a/test/profile/Linux/instrprof-value-prof-warn.test b/test/profile/Linux/instrprof-value-prof-warn.test
index 26502cc900dc..6ca1603fb244 100644
--- a/test/profile/Linux/instrprof-value-prof-warn.test
+++ b/test/profile/Linux/instrprof-value-prof-warn.test
@@ -1,4 +1,4 @@
-RUN: %clang_profgen -O2 -mllvm -disable-vp=false -Xclang -fprofile-instrument=llvm -mllvm -vp-static-alloc=true -DSTRESS=1 -o %t.ir.warn %S/../Inputs/instrprof-value-prof-real.c
+RUN: %clang_pgogen -O2 -mllvm -disable-vp=false -mllvm -vp-static-alloc=true -DSTRESS=1 -o %t.ir.warn %S/../Inputs/instrprof-value-prof-real.c
RUN: env LLVM_PROFILE_FILE=%t.ir.profraw LLVM_VP_MAX_NUM_VALS_PER_SITE=255 %run %t.ir.warn 2>&1 |FileCheck --check-prefix=WARNING %s
# Test that enough static counters have been allocated
RUN: env LLVM_PROFILE_FILE=%t.ir.profraw LLVM_VP_MAX_NUM_VALS_PER_SITE=150 %run %t.ir.warn 2>&1 |FileCheck --check-prefix=NOWARNING --allow-empty %s
diff --git a/test/sanitizer_common/TestCases/Linux/allocator_fork_no_hang.cc b/test/sanitizer_common/TestCases/Linux/allocator_fork_no_hang.cc
deleted file mode 100644
index d159d85ee2d6..000000000000
--- a/test/sanitizer_common/TestCases/Linux/allocator_fork_no_hang.cc
+++ /dev/null
@@ -1,118 +0,0 @@
-// https://github.com/google/sanitizers/issues/774
-// Test that sanitizer allocator is fork-safe.
-// Run a number of threads that perform memory allocation/deallocation, then fork
-// and verify that malloc/free do not deadlock in the child process.
-
-// RUN: %clangxx -std=c++11 -O0 %s -o %t
-// RUN: ASAN_OPTIONS=detect_leaks=0 %run %t 2>&1 | FileCheck %s
-
-// Fun fact: if test output is redirected to a file (as opposed to
-// being piped directly to FileCheck), we may lose some "done"s due to
-// a kernel bug:
-// https://lkml.org/lkml/2014/2/17/324
-
-// UNSUPPORTED: tsan
-
-// Flaky on PPC64.
-// UNSUPPORTED: powerpc64-target-arch
-// UNSUPPORTED: powerpc64le-target-arch
-
-#include <pthread.h>
-#include <unistd.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <sys/time.h>
-#include <signal.h>
-#include <errno.h>
-
-int done;
-
-void *worker(void *arg) {
- while (true) {
- void *p = malloc(4);
- if (__atomic_load_n(&done, __ATOMIC_RELAXED))
- return 0;
- }
- return 0;
-}
-
-// Run through malloc/free in the child process.
-// This can deadlock on allocator cache refilling.
-void child() {
- for (int i = 0; i < 10000; ++i) {
- void *p = malloc(4);
- }
- write(2, "done\n", 5);
-}
-
-void test() {
- const int kThreads = 10;
- pthread_t t[kThreads];
- for (int i = 0; i < kThreads; ++i)
- pthread_create(&t[i], NULL, worker, (void*)(long)i);
- usleep(100000);
- pid_t pid = fork();
- if (pid) {
- // parent
- __atomic_store_n(&done, 1, __ATOMIC_RELAXED);
- pid_t p;
- while ((p = wait(NULL)) == -1) { }
- } else {
- // child
- child();
- }
-}
-
-int main() {
- const int kChildren = 30;
- for (int i = 0; i < kChildren; ++i) {
- pid_t pid = fork();
- if (pid) {
- // parent
- } else {
- test();
- exit(0);
- }
- }
-
- for (int i = 0; i < kChildren; ++i) {
- pid_t p;
- while ((p = wait(NULL)) == -1) { }
- }
-
- return 0;
-}
-
-// Expect 30 (== kChildren) "done" messages.
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
-// CHECK: done
diff --git a/test/sanitizer_common/TestCases/sanitizer_coverage_inline8bit_counter.cc b/test/sanitizer_common/TestCases/sanitizer_coverage_inline8bit_counter.cc
index b7246ebf2751..1a4ad1f066d9 100644
--- a/test/sanitizer_common/TestCases/sanitizer_coverage_inline8bit_counter.cc
+++ b/test/sanitizer_common/TestCases/sanitizer_coverage_inline8bit_counter.cc
@@ -1,7 +1,7 @@
// Tests -fsanitize-coverage=inline-8bit-counters
//
// REQUIRES: has_sancovcc,stable-runtime
-// UNSUPPORTED: i386-darwin
+// UNSUPPORTED: i386-darwin, x86_64-darwin, x86_64h-darwin
//
// RUN: %clangxx -O0 %s -fsanitize-coverage=inline-8bit-counters 2>&1
diff --git a/test/tsan/strerror_r.cc b/test/tsan/strerror_r.cc
new file mode 100644
index 000000000000..06c92d3bb641
--- /dev/null
+++ b/test/tsan/strerror_r.cc
@@ -0,0 +1,29 @@
+// RUN: %clangxx_tsan -O1 -DTEST_ERROR=ERANGE %s -o %t && %run %t 2>&1 | FileCheck --check-prefixes=CHECK,CHECK-SYS %s
+// RUN: %clangxx_tsan -O1 -DTEST_ERROR=-1 %s -o %t && not %run %t 2>&1 | FileCheck --check-prefixes=CHECK,CHECK-USER %s
+// UNSUPPORTED: darwin
+
+#include <assert.h>
+#include <errno.h>
+#include <pthread.h>
+#include <stdio.h>
+#include <string.h>
+
+char buffer[1000];
+
+void *Thread(void *p) {
+ return strerror_r(TEST_ERROR, buffer, sizeof(buffer));
+}
+
+int main() {
+ pthread_t th[2];
+ pthread_create(&th[0], 0, Thread, 0);
+ pthread_create(&th[1], 0, Thread, 0);
+ pthread_join(th[0], 0);
+ pthread_join(th[1], 0);
+ fprintf(stderr, "DONE\n");
+}
+
+// CHECK-USER: WARNING: ThreadSanitizer: data race
+// CHECK-SYS-NOT: WARNING: ThreadSanitizer: data race
+
+// CHECK: DONE