Skip to content

Commit

Permalink
[sanitizer] Bail out with warning if user dlopens shared library with…
Browse files Browse the repository at this point in the history
… RTLD_DEEPBIND flag

People keep hitting on spurious failures in malloc/free routines when using sanitizers
with shared libraries dlopened with RTLD_DEEPBIND (see google/sanitizers#611 for details).
Let's check for this flag and bail out with warning message instead of failing in random places.

Differential Revision: https://reviews.llvm.org/D30504

llvm-svn: 297370
  • Loading branch information
chefmax7 committed Mar 9, 2017
1 parent 49b112f commit 76630d4
Show file tree
Hide file tree
Showing 7 changed files with 41 additions and 4 deletions.
8 changes: 5 additions & 3 deletions compiler-rt/lib/asan/asan_interceptors.cc
Original file line number Diff line number Diff line change
Expand Up @@ -228,9 +228,11 @@ DECLARE_REAL_AND_INTERCEPTOR(void, free, void *)
// Strict init-order checking is dlopen-hostile:
// https://github.com/google/sanitizers/issues/178
#define COMMON_INTERCEPTOR_ON_DLOPEN(filename, flag) \
if (flags()->strict_init_order) { \
StopInitOrderChecking(); \
}
do { \
if (flags()->strict_init_order) \
StopInitOrderChecking(); \
CheckNoDeepBind(filename, flag); \
} while (false)
#define COMMON_INTERCEPTOR_ON_EXIT(ctx) OnExit()
#define COMMON_INTERCEPTOR_LIBRARY_LOADED(filename, handle) \
CoverageUpdateMapping()
Expand Down
2 changes: 2 additions & 0 deletions compiler-rt/lib/sanitizer_common/sanitizer_common.h
Original file line number Diff line number Diff line change
Expand Up @@ -911,6 +911,8 @@ struct StackDepotStats {
// indicate that sanitizer allocator should not attempt to release memory to OS.
const s32 kReleaseToOSIntervalNever = -1;

void CheckNoDeepBind(const char *filename, int flag);

} // namespace __sanitizer

inline void *operator new(__sanitizer::operator_new_size_type size,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,8 @@ bool PlatformHasDifferentMemcpyAndMemmove();
COMMON_INTERCEPTOR_READ_STRING_OF_LEN((ctx), (s), REAL(strlen)(s), (n))

#ifndef COMMON_INTERCEPTOR_ON_DLOPEN
#define COMMON_INTERCEPTOR_ON_DLOPEN(filename, flag) {}
#define COMMON_INTERCEPTOR_ON_DLOPEN(filename, flag) \
CheckNoDeepBind(filename, flag);
#endif

#ifndef COMMON_INTERCEPTOR_GET_TLS_RANGE
Expand Down
13 changes: 13 additions & 0 deletions compiler-rt/lib/sanitizer_common/sanitizer_linux.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1460,6 +1460,19 @@ void MaybeReexec() {

void PrintModuleMap() { }

void CheckNoDeepBind(const char *filename, int flag) {
if (flag & RTLD_DEEPBIND) {
Report(
"You are trying to dlopen a %s shared library with RTLD_DEEPBIND flag"
" which is incompatibe with sanitizer runtime "
"(see https://github.com/google/sanitizers/issues/611 for details"
"). If you want to run %s library under sanitizers please remove "
"RTLD_DEEPBIND from dlopen flags.\n",
filename, filename);
Die();
}
}

uptr FindAvailableMemoryRange(uptr size, uptr alignment, uptr left_padding) {
UNREACHABLE("FindAvailableMemoryRange is not available");
return 0;
Expand Down
4 changes: 4 additions & 0 deletions compiler-rt/lib/sanitizer_common/sanitizer_mac.cc
Original file line number Diff line number Diff line change
Expand Up @@ -886,6 +886,10 @@ void PrintModuleMap() {
Printf("End of module map.\n");
}

void CheckNoDeepBind(const char *filename, int flag) {
// Do nothing.
}

} // namespace __sanitizer

#endif // SANITIZER_MAC
3 changes: 3 additions & 0 deletions compiler-rt/lib/sanitizer_common/sanitizer_win.cc
Original file line number Diff line number Diff line change
Expand Up @@ -990,6 +990,9 @@ int WaitForProcess(pid_t pid) { return -1; }
// FIXME implement on this platform.
void GetMemoryProfile(fill_profile_f cb, uptr *stats, uptr stats_size) { }

void CheckNoDeepBind(const char *filename, int flag) {
// Do nothing.
}

} // namespace __sanitizer

Expand Down
12 changes: 12 additions & 0 deletions compiler-rt/test/sanitizer_common/TestCases/Linux/deepbind.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// RUN: %clangxx %s -o %t && %run not %t 1 2>&1 | FileCheck %s
// UNSUPPORTED: lsan, android

#include <dlfcn.h>
#include <stdio.h>
#include <string>

int main (int argc, char *argv[]) {
// CHECK: You are trying to dlopen a <arbitrary path> shared library with RTLD_DEEPBIND flag
void *lib = dlopen("<arbitrary path>", RTLD_NOW | RTLD_DEEPBIND);
return 0;
}

0 comments on commit 76630d4

Please sign in to comment.