We currently version `__asan_init` and when the ABI version doesn't match, the linker gives a `undefined reference to '__asan_init_v5'` message. From this, it might not be obvious that it's actually a version mismatch error. This patch makes the error message much clearer by changing the name of the undefined symbol to be `__asan_version_mismatch_check_xxx` (followed by the version string). We obviously don't want the initializer to be named like that, so it's a separate symbol that is used only for the purpose of version checking.
Reviewed at http://reviews.llvm.org/D11004
llvm-svn: 243004
// v3=>v4: added '__asan_global_source_location' to __asan_global.
// v4=>v5: changed the semantics and format of __asan_stack_malloc_ and
// __asan_stack_free_ functions.
- #define __asan_init __asan_init_v5
- #define __asan_init_name "__asan_init_v5"
+ // v5=>v6: changed the name of the version check symbol
+ #define __asan_version_mismatch_check __asan_version_mismatch_check_v6
}
#endif // ASAN_INIT_VERSION_H
extern "C" {
// This function should be called at the very beginning of the process,
// before any instrumented code is executed and before any call to malloc.
- // Please note that __asan_init is a macro that is replaced with
- // __asan_init_vXXX at compile-time.
SANITIZER_INTERFACE_ATTRIBUTE void __asan_init();
+ // This function exists purely to get a linker/loader error when using
+ // incompatible versions of instrumentation and runtime library. Please note
+ // that __asan_version_mismatch_check is a macro that is replaced with
+ // __asan_version_mismatch_check_vXXX at compile-time.
+ SANITIZER_INTERFACE_ATTRIBUTE void __asan_version_mismatch_check();
+
// This structure is used to describe the source location of a place where
// global was defined.
struct __asan_global_source_location {
AsanActivate();
AsanInitInternal();
}
+
+void __asan_version_mismatch_check() {
+ // Do nothing.
+}
// __asan_init is expected to be called by only one thread.
if (fn) return;
- fn = (fntype)getRealProcAddressOrDie(__asan_init_name);
+ fn = (fntype)getRealProcAddressOrDie("__asan_init");
fn();
__asan_option_detect_stack_use_after_return =
(__asan_should_detect_stack_use_after_return() != 0);
// RUN: nm -g `%clang_asan %s -fsanitize=address -### 2>&1 | grep "libclang_rt.asan_osx_dynamic.dylib" | sed -e 's/.*"\(.*libclang_rt.asan_osx_dynamic.dylib\)".*/\1/'` \
// RUN: | grep " T " | sed "s/.* T //" \
// RUN: | grep "__asan_" | sed "s/___asan_/__asan_/" \
-// RUN: | sed -E "s/__asan_init_v[0-9]+/__asan_init/" \
+// RUN: | sed -E "s/__asan_version_mismatch_check_v[0-9]+/__asan_version_mismatch_check/" \
// RUN: | grep -v "__asan_default_options" \
// RUN: | grep -v "__asan_on_error" > %t.symbols
// RUN: %clang_asan -O2 %s -o %t.exe
// RUN: nm -D %t.exe | grep " T " | sed "s/.* T //" \
// RUN: | grep "__asan_" | sed "s/___asan_/__asan_/" \
-// RUN: | sed -E "s/__asan_init_v[0-9]+/__asan_init/" \
+// RUN: | sed -E "s/__asan_version_mismatch_check_v[0-9]+/__asan_version_mismatch_check/" \
// RUN: | grep -v "__asan_default_options" \
// RUN: | grep -v "__asan_stack_" \
// RUN: | grep -v "__asan_on_error" > %t.symbols