diff options
| author | Kostya Serebryany <kcc@google.com> | 2013-02-20 14:28:08 +0000 |
|---|---|---|
| committer | Kostya Serebryany <kcc@google.com> | 2013-02-20 14:28:08 +0000 |
| commit | d8c29210e582a053645da0b9431ebe67a410e5b9 (patch) | |
| tree | 13df0699e50e785aafe16123d272f54addec418b /compiler-rt/lib | |
| parent | aadd1f2ad65712a974a1c49997c47adb23e3809d (diff) | |
| download | bcm5719-llvm-d8c29210e582a053645da0b9431ebe67a410e5b9.tar.gz bcm5719-llvm-d8c29210e582a053645da0b9431ebe67a410e5b9.zip | |
[asan] on linux, run __asan_init from .preinit_array (even earlier than before)
llvm-svn: 175623
Diffstat (limited to 'compiler-rt/lib')
| -rw-r--r-- | compiler-rt/lib/asan/asan_internal.h | 4 | ||||
| -rw-r--r-- | compiler-rt/lib/asan/asan_rtl.cc | 4 | ||||
| -rw-r--r-- | compiler-rt/lib/asan/lit_tests/preinit_test.cc | 27 |
3 files changed, 33 insertions, 2 deletions
diff --git a/compiler-rt/lib/asan/asan_internal.h b/compiler-rt/lib/asan/asan_internal.h index b3b1fe709be..1edd8a78fc8 100644 --- a/compiler-rt/lib/asan/asan_internal.h +++ b/compiler-rt/lib/asan/asan_internal.h @@ -91,6 +91,10 @@ # endif #endif +#ifndef ASAN_USE_PREINIT_ARRAY +# define ASAN_USE_PREINIT_ARRAY (ASAN_LINUX && !ASAN_ANDROID) +#endif + // All internal functions in asan reside inside the __asan namespace // to avoid namespace collisions with the user programs. // Seperate namespace also makes it simpler to distinguish the asan run-time diff --git a/compiler-rt/lib/asan/asan_rtl.cc b/compiler-rt/lib/asan/asan_rtl.cc index ad97c77af99..d42c6746860 100644 --- a/compiler-rt/lib/asan/asan_rtl.cc +++ b/compiler-rt/lib/asan/asan_rtl.cc @@ -522,12 +522,12 @@ void __asan_init() { } } -#if defined(ASAN_USE_PREINIT_ARRAY) +#if ASAN_USE_PREINIT_ARRAY // On Linux, we force __asan_init to be called before anyone else // by placing it into .preinit_array section. // FIXME: do we have anything like this on Mac? __attribute__((section(".preinit_array"))) - typeof(__asan_init) *__asan_preinit =__asan_init; + void (*__asan_preinit)(void) =__asan_init; #elif defined(_WIN32) && defined(_DLL) // On Windows, when using dynamic CRT (/MD), we can put a pointer // to __asan_init into the global list of C initializers. diff --git a/compiler-rt/lib/asan/lit_tests/preinit_test.cc b/compiler-rt/lib/asan/lit_tests/preinit_test.cc new file mode 100644 index 00000000000..28e509472c0 --- /dev/null +++ b/compiler-rt/lib/asan/lit_tests/preinit_test.cc @@ -0,0 +1,27 @@ +// RUN: %clangxx -DFUNC=zzzz %s -shared -o %t.so -fPIC +// RUN: %clangxx_asan -DFUNC=main %s -o %t -Wl,-R. %t.so +// RUN: %t + +// This test ensures that we call __asan_init early enough. +// We build a shared library w/o asan instrumentation +// and the binary with asan instrumentation. +// Both files include the same header (emulated by -DFUNC here) +// with C++ template magic which runs global initializer at library load time. +// The function get() is instrumented with asan, but called +// before the usual constructors are run. +// So, we must make sure that __asan_init is executed even earlier. +// +// See http://gcc.gnu.org/bugzilla/show_bug.cgi?id=56393 + +struct A { + int foo() const { return 0; } +}; +A get () { return A(); } +template <class> struct O { + static A const e; +}; +template <class T> A const O <T>::e = get(); +int FUNC() { + return O<int>::e.foo(); +} + |

