Index: compiler-rt/trunk/lib/asan/asan_interceptors.h =================================================================== --- compiler-rt/trunk/lib/asan/asan_interceptors.h +++ compiler-rt/trunk/lib/asan/asan_interceptors.h @@ -46,11 +46,13 @@ # define ASAN_INTERCEPT__LONGJMP 1 # define ASAN_INTERCEPT_INDEX 1 # define ASAN_INTERCEPT_PTHREAD_CREATE 1 +# define ASAN_INTERCEPT_VFORK 1 #else # define ASAN_INTERCEPT_ATOLL_AND_STRTOLL 0 # define ASAN_INTERCEPT__LONGJMP 0 # define ASAN_INTERCEPT_INDEX 0 # define ASAN_INTERCEPT_PTHREAD_CREATE 0 +# define ASAN_INTERCEPT_VFORK 0 #endif #if SANITIZER_FREEBSD || SANITIZER_LINUX || SANITIZER_NETBSD || \ Index: compiler-rt/trunk/lib/asan/asan_interceptors.cc =================================================================== --- compiler-rt/trunk/lib/asan/asan_interceptors.cc +++ compiler-rt/trunk/lib/asan/asan_interceptors.cc @@ -572,6 +572,13 @@ } #endif // ASAN_INTERCEPT___CXA_ATEXIT +#if ASAN_INTERCEPT_VFORK +extern "C" int fork(void); +INTERCEPTOR(int, vfork, void) { + return fork(); +} +#endif // ASAN_INTERCEPT_VFORK + // ---------------------- InitializeAsanInterceptors ---------------- {{{1 namespace __asan { void InitializeAsanInterceptors() { @@ -649,6 +656,10 @@ ASAN_INTERCEPT_FUNC(__cxa_atexit); #endif +#if ASAN_INTERCEPT_VFORK + ASAN_INTERCEPT_FUNC(vfork); +#endif + InitializePlatformInterceptors(); VReport(1, "AddressSanitizer: libc interceptors initialized\n"); Index: compiler-rt/trunk/test/asan/TestCases/Posix/vfork.cc =================================================================== --- compiler-rt/trunk/test/asan/TestCases/Posix/vfork.cc +++ compiler-rt/trunk/test/asan/TestCases/Posix/vfork.cc @@ -0,0 +1,30 @@ +// Test that vfork() is fork(). +// https://github.com/google/sanitizers/issues/925 + +// RUN: %clangxx_asan -O0 %s -o %t && %run %t 2>&1 + +#include +#include +#include +#include + +int volatile global; + +int main(int argc, char **argv) { + pid_t pid = vfork(); + if (pid) { + // parent + int status; + int res; + do { + res = waitpid(pid, &status, 0); + } while (res >= 0 && !WIFEXITED(status) && !WIFSIGNALED(status)); + assert(global == 0); + } else { + // child + global = 42; + _exit(0); + } + + return 0; +}