Yeah, taking the address of main doesn't conform to standard anyway.<div>I've submitted a fix for this in r164115.</div><div>Sorry!</div><div><br><div class="gmail_quote">On Tue, Sep 18, 2012 at 1:05 AM, David Blaikie <span dir="ltr"><<a href="mailto:dblaikie@gmail.com" target="_blank">dblaikie@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">On Mon, Sep 17, 2012 at 3:02 AM, Alexey Samsonov <<a href="mailto:samsonov@google.com">samsonov@google.com</a>> wrote:<br>

> Author: samsonov<br>
> Date: Mon Sep 17 05:02:17 2012<br>
> New Revision: <a href="tel:164022" value="+49164022">164022</a><br>
><br>
> URL: <a href="http://llvm.org/viewvc/llvm-project?rev=164022&view=rev" target="_blank">http://llvm.org/viewvc/llvm-project?rev=164022&view=rev</a><br>
> Log:<br>
> [TSan] move: rtl_tests->tests/rtl unit_tests->tests/unit to make a single root for gtest-based tests. Support running these tests from lit via check-tsan command.<br>
><br>
> Added:<br>
>     compiler-rt/trunk/lib/tsan/lit_tests/<br>
>     compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/lit_tests/Unit/<br>
>     compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg<br>
>     compiler-rt/trunk/lib/tsan/lit_tests/Unit/<a href="http://lit.site.cfg.in" target="_blank">lit.site.cfg.in</a><br>
>     compiler-rt/trunk/lib/tsan/tests/<br>
>     compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc<br>
>     compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc<br>
> Removed:<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc<br>
>     compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc<br>
>     compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc<br>
> Modified:<br>
>     compiler-rt/trunk/lib/tsan/CMakeLists.txt<br>
>     compiler-rt/trunk/lib/tsan/Makefile.old<br>
><br>
> Modified: compiler-rt/trunk/lib/tsan/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/CMakeLists.txt?rev=164022&r1=164021&r2=164022&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/CMakeLists.txt?rev=164022&r1=164021&r2=164022&view=diff</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/CMakeLists.txt (original)<br>
> +++ compiler-rt/trunk/lib/tsan/CMakeLists.txt Mon Sep 17 05:02:17 2012<br>
> @@ -17,31 +17,6 @@<br>
>  add_subdirectory(rtl)<br>
><br>
>  if(LLVM_INCLUDE_TESTS)<br>
> -  add_custom_target(TsanUnitTests)<br>
> -  set_target_properties(TsanUnitTests PROPERTIES<br>
> -    FOLDER "TSan unittests")<br>
> -<br>
> -  function(add_tsan_unittest testname)<br>
> -    # Build unit tests only on 64-bit Linux.<br>
> -    if(UNIX AND NOT APPLE<br>
> -            AND CAN_TARGET_X86_64<br>
> -            AND CMAKE_SIZEOF_VOID_P EQUAL 8<br>
> -            AND NOT LLVM_BUILD_32_BITS)<br>
> -      add_unittest(TsanUnitTests ${testname} ${ARGN})<br>
> -      # Link with TSan runtime.<br>
> -      target_link_libraries(${testname} clang_rt.tsan-x86_64)<br>
> -      # Build tests with PIE and debug info.<br>
> -      set_property(TARGET ${testname} APPEND_STRING<br>
> -        PROPERTY COMPILE_FLAGS " -fPIE -g")<br>
> -      set_property(TARGET ${testname} APPEND_STRING<br>
> -        PROPERTY LINK_FLAGS " -pie")<br>
> -    endif()<br>
> -  endfunction()<br>
> -<br>
> -  include_directories(rtl)<br>
> -  # There are two groups of unit tests: rtl_tests and unit_tests.<br>
> -  add_subdirectory(rtl_tests)<br>
> -  add_subdirectory(unit_tests)<br>
> +  add_subdirectory(tests)<br>
>  endif()<br>
> -<br>
> -# FIXME: Support TSan runtime tests, unit tests and output tests.<br>
> +add_subdirectory(lit_tests)<br>
><br>
> Modified: compiler-rt/trunk/lib/tsan/Makefile.old<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/Makefile.old?rev=164022&r1=164021&r2=164022&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/Makefile.old?rev=164022&r1=164021&r2=164022&view=diff</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/Makefile.old (original)<br>
> +++ compiler-rt/trunk/lib/tsan/Makefile.old Mon Sep 17 05:02:17 2012<br>
> @@ -19,9 +19,9 @@<br>
><br>
>  SANITIZER_COMMON_TESTS_SRC=$(wildcard ../sanitizer_common/tests/*_test.cc)<br>
>  SANITIZER_COMMON_TESTS_OBJ=$(patsubst %.cc,%.o,$(SANITIZER_COMMON_TESTS_SRC))<br>
> -RTL_TEST_SRC=$(wildcard rtl_tests/*.cc)<br>
> +RTL_TEST_SRC=$(wildcard tests/rtl/*.cc)<br>
>  RTL_TEST_OBJ=$(patsubst %.cc,%.o,$(RTL_TEST_SRC))<br>
> -UNIT_TEST_SRC=$(wildcard unit_tests/*_test.cc)<br>
> +UNIT_TEST_SRC=$(wildcard tests/unit/*_test.cc)<br>
>  UNIT_TEST_OBJ=$(patsubst %.cc,%.o,$(UNIT_TEST_SRC))<br>
>  UNIT_TEST_HDR=$(wildcard rtl/*.h) $(wildcard ../sanitizer_common/*.h)<br>
><br>
><br>
> Added: compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt (added)<br>
> +++ compiler-rt/trunk/lib/tsan/lit_tests/CMakeLists.txt Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,12 @@<br>
> +configure_lit_site_cfg(<br>
> +  ${CMAKE_CURRENT_SOURCE_DIR}/Unit/<a href="http://lit.site.cfg.in" target="_blank">lit.site.cfg.in</a><br>
> +  ${CMAKE_CURRENT_BINARY_DIR}/Unit/lit.site.cfg<br>
> +  )<br>
> +<br>
> +# Run TSan unit tests.<br>
> +if(LLVM_INCLUDE_TESTS)<br>
> +  add_lit_testsuite(check-tsan "Running ThreadSanitizer tests"<br>
> +    ${CMAKE_CURRENT_BINARY_DIR}/Unit<br>
> +    DEPENDS TsanUnitTests)<br>
> +  set_target_properties(check-tsan PROPERTIES FOLDER "TSan unittests")<br>
> +endif()<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg (added)<br>
> +++ compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.cfg Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,29 @@<br>
> +# -*- Python -*-<br>
> +<br>
> +import os<br>
> +<br>
> +def get_required_attr(config, attr_name):<br>
> +  attr_value = getattr(config, attr_name, None)<br>
> +  if not attr_value:<br>
> +    lit.fatal("No attribute %r in test configuration! You may need to run "<br>
> +              "tests from your build directory or add this attribute "<br>
> +              "to lit.site.cfg " % attr_name)<br>
> +  return attr_value<br>
> +<br>
> +# Setup attributes common for all compiler-rt projects.<br>
> +llvm_src_root = get_required_attr(config, 'llvm_src_root')<br>
> +compiler_rt_lit_unit_cfg = os.path.join(llvm_src_root, "projects",<br>
> +                                        "compiler-rt", "lib",<br>
> +                                        "lit.common.unit.cfg")<br>
> +lit.load_config(config, compiler_rt_lit_unit_cfg)<br>
> +<br>
> +# Setup config name.<br>
> +<a href="http://config.name" target="_blank">config.name</a> = 'ThreadSanitizer-Unit'<br>
> +<br>
> +# Setup test source and exec root. For unit tests, we define<br>
> +# it as build directory with TSan unit tests.<br>
> +llvm_obj_root = get_required_attr(config, "llvm_obj_root")<br>
> +config.test_exec_root = os.path.join(llvm_obj_root, "projects",<br>
> +                                     "compiler-rt", "lib",<br>
> +                                     "tsan", "tests")<br>
> +config.test_source_root = config.test_exec_root<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/lit_tests/Unit/<a href="http://lit.site.cfg.in" target="_blank">lit.site.cfg.in</a><br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.site.cfg.in?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/lit_tests/Unit/lit.site.cfg.in?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/lit_tests/Unit/<a href="http://lit.site.cfg.in" target="_blank">lit.site.cfg.in</a> (added)<br>
> +++ compiler-rt/trunk/lib/tsan/lit_tests/Unit/<a href="http://lit.site.cfg.in" target="_blank">lit.site.cfg.in</a> Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,9 @@<br>
> +## Autogenerated by LLVM/Clang configuration.<br>
> +# Do not edit!<br>
> +<br>
> +config.build_type = "@CMAKE_BUILD_TYPE@"<br>
> +config.llvm_obj_root = "@LLVM_BINARY_DIR@"<br>
> +config.llvm_src_root = "@LLVM_SOURCE_DIR@"<br>
> +<br>
> +# Let the main config do the real work.<br>
> +lit.load_config(config, "@CMAKE_CURRENT_SOURCE_DIR@/Unit/lit.cfg")<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/CMakeLists.txt (removed)<br>
> @@ -1,15 +0,0 @@<br>
> -set(TSAN_RTL_TESTS<br>
> -  tsan_bench.cc<br>
> -  tsan_mop.cc<br>
> -  tsan_mutex.cc<br>
> -  tsan_posix.cc<br>
> -  tsan_string.cc<br>
> -  tsan_test.cc<br>
> -  tsan_thread.cc<br>
> -  )<br>
> -<br>
> -if(UNIX AND NOT APPLE)<br>
> -  list(APPEND TSAN_RTL_TESTS tsan_test_util_linux.cc)<br>
> -endif()<br>
> -<br>
> -add_tsan_unittest(TsanRtlTest ${TSAN_RTL_TESTS})<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_bench.cc (removed)<br>
> @@ -1,105 +0,0 @@<br>
> -//===-- tsan_bench.cc -----------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_test_util.h"<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_defs.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <stdint.h><br>
> -<br>
> -const int kSize = 128;<br>
> -const int kRepeat = 2*1024*1024;<br>
> -<br>
> -void noinstr(void *p) {}<br>
> -<br>
> -template<typename T, void(*__tsan_mop)(void *p)><br>
> -static void Benchmark() {<br>
> -  volatile T data[kSize];<br>
> -  for (int i = 0; i < kRepeat; i++) {<br>
> -    for (int j = 0; j < kSize; j++) {<br>
> -      __tsan_mop((void*)&data[j]);<br>
> -      data[j]++;<br>
> -    }<br>
> -  }<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop1) {<br>
> -  Benchmark<uint8_t, noinstr>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop1Read) {<br>
> -  Benchmark<uint8_t, __tsan_read1>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop1Write) {<br>
> -  Benchmark<uint8_t, __tsan_write1>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop2) {<br>
> -  Benchmark<uint16_t, noinstr>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop2Read) {<br>
> -  Benchmark<uint16_t, __tsan_read2>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop2Write) {<br>
> -  Benchmark<uint16_t, __tsan_write2>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop4) {<br>
> -  Benchmark<uint32_t, noinstr>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop4Read) {<br>
> -  Benchmark<uint32_t, __tsan_read4>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop4Write) {<br>
> -  Benchmark<uint32_t, __tsan_write4>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop8) {<br>
> -  Benchmark<uint8_t, noinstr>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop8Read) {<br>
> -  Benchmark<uint64_t, __tsan_read8>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, Mop8Write) {<br>
> -  Benchmark<uint64_t, __tsan_write8>();<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, FuncCall) {<br>
> -  for (int i = 0; i < kRepeat; i++) {<br>
> -    for (int j = 0; j < kSize; j++)<br>
> -      __tsan_func_entry((void*)(uintptr_t)j);<br>
> -    for (int j = 0; j < kSize; j++)<br>
> -      __tsan_func_exit();<br>
> -  }<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH, MutexLocal) {<br>
> -  Mutex m;<br>
> -  ScopedThread().Create(m);<br>
> -  for (int i = 0; i < 50; i++) {<br>
> -    ScopedThread t;<br>
> -    t.Lock(m);<br>
> -    t.Unlock(m);<br>
> -  }<br>
> -  for (int i = 0; i < 16*1024*1024; i++) {<br>
> -    m.Lock();<br>
> -    m.Unlock();<br>
> -  }<br>
> -  ScopedThread().Destroy(m);<br>
> -}<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mop.cc (removed)<br>
> @@ -1,233 +0,0 @@<br>
> -//===-- tsan_mop.cc -------------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <stddef.h><br>
> -#include <stdint.h><br>
> -<br>
> -TEST(ThreadSanitizer, SimpleWrite) {<br>
> -  ScopedThread t;<br>
> -  MemLoc l;<br>
> -  t.Write1(l);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, SimpleWriteWrite) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l1, l2;<br>
> -  t1.Write1(l1);<br>
> -  t2.Write1(l2);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, WriteWriteRace) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Write1(l);<br>
> -  t2.Write1(l, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, ReadWriteRace) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Read1(l);<br>
> -  t2.Write1(l, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, WriteReadRace) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Write1(l);<br>
> -  t2.Read1(l, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, ReadReadNoRace) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Read1(l);<br>
> -  t2.Read1(l);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, WriteThenRead) {<br>
> -  MemLoc l;<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Write1(l);<br>
> -  t1.Read1(l);<br>
> -  t2.Read1(l, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, WriteThenLockedRead) {<br>
> -  Mutex m(Mutex::RW);<br>
> -  MainThread t0;<br>
> -  t0.Create(m);<br>
> -  MemLoc l;<br>
> -  {<br>
> -    ScopedThread t1, t2;<br>
> -<br>
> -    t1.Write8(l);<br>
> -<br>
> -    t1.Lock(m);<br>
> -    t1.Read8(l);<br>
> -    t1.Unlock(m);<br>
> -<br>
> -    t2.Read8(l, true);<br>
> -  }<br>
> -  t0.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, LockedWriteThenRead) {<br>
> -  Mutex m(Mutex::RW);<br>
> -  MainThread t0;<br>
> -  t0.Create(m);<br>
> -  MemLoc l;<br>
> -  {<br>
> -    ScopedThread t1, t2;<br>
> -<br>
> -    t1.Lock(m);<br>
> -    t1.Write8(l);<br>
> -    t1.Unlock(m);<br>
> -<br>
> -    t1.Read8(l);<br>
> -<br>
> -    t2.Read8(l, true);<br>
> -  }<br>
> -  t0.Destroy(m);<br>
> -}<br>
> -<br>
> -<br>
> -TEST(ThreadSanitizer, RaceWithOffset) {<br>
> -  ScopedThread t1, t2;<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access(l.loc(), true, 8, false);<br>
> -    t2.Access((char*)l.loc() + 4, true, 4, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access(l.loc(), true, 8, false);<br>
> -    t2.Access((char*)l.loc() + 7, true, 1, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 4, true, 4, false);<br>
> -    t2.Access((char*)l.loc() + 4, true, 2, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 4, true, 4, false);<br>
> -    t2.Access((char*)l.loc() + 6, true, 2, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 3, true, 2, false);<br>
> -    t2.Access((char*)l.loc() + 4, true, 1, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 1, true, 8, false);<br>
> -    t2.Access((char*)l.loc() + 3, true, 1, true);<br>
> -  }<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, RaceWithOffset2) {<br>
> -  ScopedThread t1, t2;<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc(), true, 4, false);<br>
> -    t2.Access((char*)l.loc() + 2, true, 1, true);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 2, true, 1, false);<br>
> -    t2.Access((char*)l.loc(), true, 4, true);<br>
> -  }<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, NoRaceWithOffset) {<br>
> -  ScopedThread t1, t2;<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access(l.loc(), true, 4, false);<br>
> -    t2.Access((char*)l.loc() + 4, true, 4, false);<br>
> -  }<br>
> -  {<br>
> -    MemLoc l;<br>
> -    t1.Access((char*)l.loc() + 3, true, 2, false);<br>
> -    t2.Access((char*)l.loc() + 1, true, 2, false);<br>
> -    t2.Access((char*)l.loc() + 5, true, 2, false);<br>
> -  }<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, RaceWithDeadThread) {<br>
> -  MemLoc l;<br>
> -  ScopedThread t;<br>
> -  ScopedThread().Write1(l);<br>
> -  t.Write1(l, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, BenignRaceOnVptr) {<br>
> -  void *vptr_storage;<br>
> -  MemLoc vptr(&vptr_storage), val;<br>
> -  vptr_storage = val.loc();<br>
> -  ScopedThread t1, t2;<br>
> -  t1.VptrUpdate(vptr, val);<br>
> -  t2.Read8(vptr);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, HarmfulRaceOnVptr) {<br>
> -  void *vptr_storage;<br>
> -  MemLoc vptr(&vptr_storage), val1, val2;<br>
> -  vptr_storage = val1.loc();<br>
> -  ScopedThread t1, t2;<br>
> -  t1.VptrUpdate(vptr, val2);<br>
> -  t2.Read8(vptr, true);<br>
> -}<br>
> -<br>
> -static void foo() {<br>
> -  volatile int x = 42;<br>
> -  int x2 = x;<br>
> -  (void)x2;<br>
> -}<br>
> -<br>
> -static void bar() {<br>
> -  volatile int x = 43;<br>
> -  int x2 = x;<br>
> -  (void)x2;<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, ReportDeadThread) {<br>
> -  MemLoc l;<br>
> -  ScopedThread t1;<br>
> -  {<br>
> -    ScopedThread t2;<br>
> -    t2.Call(&foo);<br>
> -    t2.Call(&bar);<br>
> -    t2.Write1(l);<br>
> -  }<br>
> -  t1.Write1(l, true);<br>
> -}<br>
> -<br>
> -struct ClassWithStatic {<br>
> -  static int Data[4];<br>
> -};<br>
> -<br>
> -int ClassWithStatic::Data[4];<br>
> -<br>
> -static void foobarbaz() {}<br>
> -<br>
> -TEST(ThreadSanitizer, ReportRace) {<br>
> -  ScopedThread t1;<br>
> -  MainThread().Access(&ClassWithStatic::Data, true, 4, false);<br>
> -  t1.Call(&foobarbaz);<br>
> -  t1.Access(&ClassWithStatic::Data, true, 2, true);<br>
> -  t1.Return();<br>
> -}<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_mutex.cc (removed)<br>
> @@ -1,221 +0,0 @@<br>
> -//===-- tsan_mutex.cc -----------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "sanitizer_common/sanitizer_atomic.h"<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_interface_ann.h"<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <stdint.h><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(ThreadSanitizer, BasicMutex) {<br>
> -  ScopedThread t;<br>
> -  Mutex m;<br>
> -  t.Create(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  t.Unlock(m);<br>
> -<br>
> -  CHECK(t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  CHECK(!t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, BasicSpinMutex) {<br>
> -  ScopedThread t;<br>
> -  Mutex m(Mutex::Spin);<br>
> -  t.Create(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  t.Unlock(m);<br>
> -<br>
> -  CHECK(t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  CHECK(!t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, BasicRwMutex) {<br>
> -  ScopedThread t;<br>
> -  Mutex m(Mutex::RW);<br>
> -  t.Create(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  t.Unlock(m);<br>
> -<br>
> -  CHECK(t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  CHECK(!t.TryLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.ReadLock(m);<br>
> -  t.ReadUnlock(m);<br>
> -<br>
> -  CHECK(t.TryReadLock(m));<br>
> -  t.ReadUnlock(m);<br>
> -<br>
> -  t.Lock(m);<br>
> -  CHECK(!t.TryReadLock(m));<br>
> -  t.Unlock(m);<br>
> -<br>
> -  t.ReadLock(m);<br>
> -  CHECK(!t.TryLock(m));<br>
> -  t.ReadUnlock(m);<br>
> -<br>
> -  t.ReadLock(m);<br>
> -  CHECK(t.TryReadLock(m));<br>
> -  t.ReadUnlock(m);<br>
> -  t.ReadUnlock(m);<br>
> -<br>
> -  t.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, Mutex) {<br>
> -  Mutex m;<br>
> -  MainThread t0;<br>
> -  t0.Create(m);<br>
> -<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Lock(m);<br>
> -  t1.Write1(l);<br>
> -  t1.Unlock(m);<br>
> -  t2.Lock(m);<br>
> -  t2.Write1(l);<br>
> -  t2.Unlock(m);<br>
> -  t2.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, SpinMutex) {<br>
> -  Mutex m(Mutex::Spin);<br>
> -  MainThread t0;<br>
> -  t0.Create(m);<br>
> -<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Lock(m);<br>
> -  t1.Write1(l);<br>
> -  t1.Unlock(m);<br>
> -  t2.Lock(m);<br>
> -  t2.Write1(l);<br>
> -  t2.Unlock(m);<br>
> -  t2.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, RwMutex) {<br>
> -  Mutex m(Mutex::RW);<br>
> -  MainThread t0;<br>
> -  t0.Create(m);<br>
> -<br>
> -  ScopedThread t1, t2, t3;<br>
> -  MemLoc l;<br>
> -  t1.Lock(m);<br>
> -  t1.Write1(l);<br>
> -  t1.Unlock(m);<br>
> -  t2.Lock(m);<br>
> -  t2.Write1(l);<br>
> -  t2.Unlock(m);<br>
> -  t1.ReadLock(m);<br>
> -  t3.ReadLock(m);<br>
> -  t1.Read1(l);<br>
> -  t3.Read1(l);<br>
> -  t1.ReadUnlock(m);<br>
> -  t3.ReadUnlock(m);<br>
> -  t2.Lock(m);<br>
> -  t2.Write1(l);<br>
> -  t2.Unlock(m);<br>
> -  t2.Destroy(m);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, StaticMutex) {<br>
> -  // Emulates statically initialized mutex.<br>
> -  Mutex m;<br>
> -  m.StaticInit();<br>
> -  {<br>
> -    ScopedThread t1, t2;<br>
> -    t1.Lock(m);<br>
> -    t1.Unlock(m);<br>
> -    t2.Lock(m);<br>
> -    t2.Unlock(m);<br>
> -  }<br>
> -  MainThread().Destroy(m);<br>
> -}<br>
> -<br>
> -static void *singleton_thread(void *param) {<br>
> -  atomic_uintptr_t *singleton = (atomic_uintptr_t *)param;<br>
> -  for (int i = 0; i < 4*1024*1024; i++) {<br>
> -    int *val = (int *)atomic_load(singleton, memory_order_acquire);<br>
> -    __tsan_acquire(singleton);<br>
> -    __tsan_read4(val);<br>
> -    CHECK_EQ(*val, 42);<br>
> -  }<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH_ThreadSanitizer, Singleton) {<br>
> -  const int kClockSize = 100;<br>
> -  const int kThreadCount = 8;<br>
> -<br>
> -  // Puff off thread's clock.<br>
> -  for (int i = 0; i < kClockSize; i++) {<br>
> -    ScopedThread t1;<br>
> -    (void)t1;<br>
> -  }<br>
> -  // Create the singleton.<br>
> -  int val = 42;<br>
> -  __tsan_write4(&val);<br>
> -  atomic_uintptr_t singleton;<br>
> -  __tsan_release(&singleton);<br>
> -  atomic_store(&singleton, (uintptr_t)&val, memory_order_release);<br>
> -  // Create reader threads.<br>
> -  pthread_t threads[kThreadCount];<br>
> -  for (int t = 0; t < kThreadCount; t++)<br>
> -    pthread_create(&threads[t], 0, singleton_thread, &singleton);<br>
> -  for (int t = 0; t < kThreadCount; t++)<br>
> -    pthread_join(threads[t], 0);<br>
> -}<br>
> -<br>
> -TEST(DISABLED_BENCH_ThreadSanitizer, StopFlag) {<br>
> -  const int kClockSize = 100;<br>
> -  const int kIters = 16*1024*1024;<br>
> -<br>
> -  // Puff off thread's clock.<br>
> -  for (int i = 0; i < kClockSize; i++) {<br>
> -    ScopedThread t1;<br>
> -    (void)t1;<br>
> -  }<br>
> -  // Create the stop flag.<br>
> -  atomic_uintptr_t flag;<br>
> -  __tsan_release(&flag);<br>
> -  atomic_store(&flag, 0, memory_order_release);<br>
> -  // Read it a lot.<br>
> -  for (int i = 0; i < kIters; i++) {<br>
> -    uptr v = atomic_load(&flag, memory_order_acquire);<br>
> -    __tsan_acquire(&flag);<br>
> -    CHECK_EQ(v, 0);<br>
> -  }<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_posix.cc (removed)<br>
> @@ -1,146 +0,0 @@<br>
> -//===-- tsan_posix.cc -----------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <pthread.h><br>
> -<br>
> -struct thread_key {<br>
> -  pthread_key_t key;<br>
> -  pthread_mutex_t *mtx;<br>
> -  int val;<br>
> -  int *cnt;<br>
> -  thread_key(pthread_key_t key, pthread_mutex_t *mtx, int val, int *cnt)<br>
> -    : key(key)<br>
> -    , mtx(mtx)<br>
> -    , val(val)<br>
> -    , cnt(cnt) {<br>
> -  }<br>
> -};<br>
> -<br>
> -static void thread_secific_dtor(void *v) {<br>
> -  thread_key *k = (thread_key *)v;<br>
> -  EXPECT_EQ(pthread_mutex_lock(k->mtx), 0);<br>
> -  (*k->cnt)++;<br>
> -  __tsan_write4(&k->cnt);<br>
> -  EXPECT_EQ(pthread_mutex_unlock(k->mtx), 0);<br>
> -  if (k->val == 42) {<br>
> -    delete k;<br>
> -  } else if (k->val == 43 || k->val == 44) {<br>
> -    k->val--;<br>
> -    EXPECT_EQ(pthread_setspecific(k->key, k), 0);<br>
> -  } else {<br>
> -    ASSERT_TRUE(false);<br>
> -  }<br>
> -}<br>
> -<br>
> -static void *dtors_thread(void *p) {<br>
> -  thread_key *k = (thread_key *)p;<br>
> -  EXPECT_EQ(pthread_setspecific(k->key, k), 0);<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(Posix, ThreadSpecificDtors) {<br>
> -  int cnt = 0;<br>
> -  pthread_key_t key;<br>
> -  EXPECT_EQ(pthread_key_create(&key, thread_secific_dtor), 0);<br>
> -  pthread_mutex_t mtx;<br>
> -  EXPECT_EQ(pthread_mutex_init(&mtx, 0), 0);<br>
> -  pthread_t th[3];<br>
> -  thread_key *k[3];<br>
> -  k[0] = new thread_key(key, &mtx, 42, &cnt);<br>
> -  k[1] = new thread_key(key, &mtx, 43, &cnt);<br>
> -  k[2] = new thread_key(key, &mtx, 44, &cnt);<br>
> -  EXPECT_EQ(pthread_create(&th[0], 0, dtors_thread, k[0]), 0);<br>
> -  EXPECT_EQ(pthread_create(&th[1], 0, dtors_thread, k[1]), 0);<br>
> -  EXPECT_EQ(pthread_join(th[0], 0), 0);<br>
> -  EXPECT_EQ(pthread_create(&th[2], 0, dtors_thread, k[2]), 0);<br>
> -  EXPECT_EQ(pthread_join(th[1], 0), 0);<br>
> -  EXPECT_EQ(pthread_join(th[2], 0), 0);<br>
> -  EXPECT_EQ(pthread_key_delete(key), 0);<br>
> -  EXPECT_EQ(6, cnt);<br>
> -}<br>
> -<br>
> -static __thread int local_var;<br>
> -<br>
> -static void *local_thread(void *p) {<br>
> -  __tsan_write1(&local_var);<br>
> -  __tsan_write1(&p);<br>
> -  if (p == 0)<br>
> -    return 0;<br>
> -  const int kThreads = 4;<br>
> -  pthread_t th[kThreads];<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    EXPECT_EQ(pthread_create(&th[i], 0, local_thread,<br>
> -              (void*)((long)p - 1)), 0);  // NOLINT<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    EXPECT_EQ(pthread_join(th[i], 0), 0);<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(Posix, ThreadLocalAccesses) {<br>
> -  local_thread((void*)2);<br>
> -}<br>
> -<br>
> -struct CondContext {<br>
> -  pthread_mutex_t m;<br>
> -  pthread_cond_t c;<br>
> -  int data;<br>
> -};<br>
> -<br>
> -static void *cond_thread(void *p) {<br>
> -  CondContext &ctx = *static_cast<CondContext*>(p);<br>
> -<br>
> -  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> -  EXPECT_EQ(ctx.data, 0);<br>
> -  ctx.data = 1;<br>
> -  EXPECT_EQ(pthread_cond_signal(&ctx.c), 0);<br>
> -  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> -<br>
> -  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> -  while (ctx.data != 2)<br>
> -    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> -  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> -<br>
> -  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> -  ctx.data = 3;<br>
> -  EXPECT_EQ(pthread_cond_broadcast(&ctx.c), 0);<br>
> -  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> -<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(Posix, CondBasic) {<br>
> -  CondContext ctx;<br>
> -  EXPECT_EQ(pthread_mutex_init(&ctx.m, 0), 0);<br>
> -  EXPECT_EQ(pthread_cond_init(&ctx.c, 0), 0);<br>
> -  ctx.data = 0;<br>
> -  pthread_t th;<br>
> -  EXPECT_EQ(pthread_create(&th, 0, cond_thread, &ctx), 0);<br>
> -<br>
> -  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> -  while (ctx.data != 1)<br>
> -    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> -  ctx.data = 2;<br>
> -  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> -  EXPECT_EQ(pthread_cond_broadcast(&ctx.c), 0);<br>
> -<br>
> -  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> -  while (ctx.data != 3)<br>
> -    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> -  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> -<br>
> -  EXPECT_EQ(pthread_join(th, 0), 0);<br>
> -  EXPECT_EQ(pthread_cond_destroy(&ctx.c), 0);<br>
> -  EXPECT_EQ(pthread_mutex_destroy(&ctx.m), 0);<br>
> -}<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_string.cc (removed)<br>
> @@ -1,82 +0,0 @@<br>
> -//===-- tsan_string.cc ----------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <string.h><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(ThreadSanitizer, Memcpy) {<br>
> -  char data0[7] = {1, 2, 3, 4, 5, 6, 7};<br>
> -  char data[7] = {42, 42, 42, 42, 42, 42, 42};<br>
> -  MainThread().Memcpy(data+1, data0+1, 5);<br>
> -  EXPECT_EQ(data[0], 42);<br>
> -  EXPECT_EQ(data[1], 2);<br>
> -  EXPECT_EQ(data[2], 3);<br>
> -  EXPECT_EQ(data[3], 4);<br>
> -  EXPECT_EQ(data[4], 5);<br>
> -  EXPECT_EQ(data[5], 6);<br>
> -  EXPECT_EQ(data[6], 42);<br>
> -  MainThread().Memset(data+1, 13, 5);<br>
> -  EXPECT_EQ(data[0], 42);<br>
> -  EXPECT_EQ(data[1], 13);<br>
> -  EXPECT_EQ(data[2], 13);<br>
> -  EXPECT_EQ(data[3], 13);<br>
> -  EXPECT_EQ(data[4], 13);<br>
> -  EXPECT_EQ(data[5], 13);<br>
> -  EXPECT_EQ(data[6], 42);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, MemcpyRace1) {<br>
> -  char *data = new char[10];<br>
> -  char *data1 = new char[10];<br>
> -  char *data2 = new char[10];<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Memcpy(data, data1, 10);<br>
> -  t2.Memcpy(data, data2, 10, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, MemcpyRace2) {<br>
> -  char *data = new char[10];<br>
> -  char *data1 = new char[10];<br>
> -  char *data2 = new char[10];<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Memcpy(data+5, data1, 1);<br>
> -  t2.Memcpy(data+3, data2, 4, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, MemcpyRace3) {<br>
> -  char *data = new char[10];<br>
> -  char *data1 = new char[10];<br>
> -  char *data2 = new char[10];<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Memcpy(data, data1, 10);<br>
> -  t2.Memcpy(data1, data2, 10, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, MemcpyStack) {<br>
> -  char *data = new char[10];<br>
> -  char *data1 = new char[10];<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Memcpy(data, data1, 10);<br>
> -  t2.Memcpy(data, data1, 10, true);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, MemsetRace1) {<br>
> -  char *data = new char[10];<br>
> -  ScopedThread t1, t2;<br>
> -  t1.Memset(data, 1, 10);<br>
> -  t2.Memset(data, 2, 10, true);<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test.cc (removed)<br>
> @@ -1,44 +0,0 @@<br>
> -//===-- tsan_test.cc ------------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -static void foo() {}<br>
> -static void bar() {}<br>
> -<br>
> -TEST(ThreadSanitizer, FuncCall) {<br>
> -  ScopedThread t1, t2;<br>
> -  MemLoc l;<br>
> -  t1.Write1(l);<br>
> -  t2.Call(foo);<br>
> -  t2.Call(bar);<br>
> -  t2.Write1(l, true);<br>
> -  t2.Return();<br>
> -  t2.Return();<br>
> -}<br>
> -<br>
> -int main(int argc, char **argv) {<br>
> -  TestMutexBeforeInit();  // Mutexes must be usable before __tsan_init();<br>
> -  __tsan_init();<br>
> -  __tsan_func_entry(__builtin_return_address(0));<br>
> -  __tsan_func_entry((char*)&main + 1);<br>
> -<br>
> -  testing::GTEST_FLAG(death_test_style) = "threadsafe";<br>
> -  testing::InitGoogleTest(&argc, argv);<br>
> -  int res = RUN_ALL_TESTS();<br>
> -<br>
> -  __tsan_func_exit();<br>
> -  __tsan_func_exit();<br>
> -  return res;<br>
> -}<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util.h (removed)<br>
> @@ -1,122 +0,0 @@<br>
> -//===-- tsan_test_util.h ----------------------------------------*- C++ -*-===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -// Test utils.<br>
> -//===----------------------------------------------------------------------===//<br>
> -#ifndef TSAN_TEST_UTIL_H<br>
> -#define TSAN_TEST_UTIL_H<br>
> -<br>
> -void TestMutexBeforeInit();<br>
> -<br>
> -// A location of memory on which a race may be detected.<br>
> -class MemLoc {<br>
> - public:<br>
> -  explicit MemLoc(int offset_from_aligned = 0);<br>
> -  explicit MemLoc(void *const real_addr) : loc_(real_addr) { }<br>
> -  ~MemLoc();<br>
> -  void *loc() const { return loc_; }<br>
> - private:<br>
> -  void *const loc_;<br>
> -  MemLoc(const MemLoc&);<br>
> -  void operator = (const MemLoc&);<br>
> -};<br>
> -<br>
> -class Mutex {<br>
> - public:<br>
> -  enum Type { Normal, Spin, RW };<br>
> -<br>
> -  explicit Mutex(Type type = Normal);<br>
> -  ~Mutex();<br>
> -<br>
> -  void Init();<br>
> -  void StaticInit();  // Emulates static initalization (tsan invisible).<br>
> -  void Destroy();<br>
> -  void Lock();<br>
> -  bool TryLock();<br>
> -  void Unlock();<br>
> -  void ReadLock();<br>
> -  bool TryReadLock();<br>
> -  void ReadUnlock();<br>
> -<br>
> - private:<br>
> -  // Placeholder for pthread_mutex_t, CRITICAL_SECTION or whatever.<br>
> -  void *mtx_[128];<br>
> -  bool alive_;<br>
> -  const Type type_;<br>
> -<br>
> -  Mutex(const Mutex&);<br>
> -  void operator = (const Mutex&);<br>
> -};<br>
> -<br>
> -// A thread is started in CTOR and joined in DTOR.<br>
> -class ScopedThread {<br>
> - public:<br>
> -  explicit ScopedThread(bool detached = false, bool main = false);<br>
> -  ~ScopedThread();<br>
> -  void Detach();<br>
> -<br>
> -  void Access(void *addr, bool is_write, int size, bool expect_race);<br>
> -  void Read(const MemLoc &ml, int size, bool expect_race = false) {<br>
> -    Access(ml.loc(), false, size, expect_race);<br>
> -  }<br>
> -  void Write(const MemLoc &ml, int size, bool expect_race = false) {<br>
> -    Access(ml.loc(), true, size, expect_race);<br>
> -  }<br>
> -  void Read1(const MemLoc &ml, bool expect_race = false) {<br>
> -    Read(ml, 1, expect_race); }<br>
> -  void Read2(const MemLoc &ml, bool expect_race = false) {<br>
> -    Read(ml, 2, expect_race); }<br>
> -  void Read4(const MemLoc &ml, bool expect_race = false) {<br>
> -    Read(ml, 4, expect_race); }<br>
> -  void Read8(const MemLoc &ml, bool expect_race = false) {<br>
> -    Read(ml, 8, expect_race); }<br>
> -  void Write1(const MemLoc &ml, bool expect_race = false) {<br>
> -    Write(ml, 1, expect_race); }<br>
> -  void Write2(const MemLoc &ml, bool expect_race = false) {<br>
> -    Write(ml, 2, expect_race); }<br>
> -  void Write4(const MemLoc &ml, bool expect_race = false) {<br>
> -    Write(ml, 4, expect_race); }<br>
> -  void Write8(const MemLoc &ml, bool expect_race = false) {<br>
> -    Write(ml, 8, expect_race); }<br>
> -<br>
> -  void VptrUpdate(const MemLoc &vptr, const MemLoc &new_val,<br>
> -                  bool expect_race = false);<br>
> -<br>
> -  void Call(void(*pc)());<br>
> -  void Return();<br>
> -<br>
> -  void Create(const Mutex &m);<br>
> -  void Destroy(const Mutex &m);<br>
> -  void Lock(const Mutex &m);<br>
> -  bool TryLock(const Mutex &m);<br>
> -  void Unlock(const Mutex &m);<br>
> -  void ReadLock(const Mutex &m);<br>
> -  bool TryReadLock(const Mutex &m);<br>
> -  void ReadUnlock(const Mutex &m);<br>
> -<br>
> -  void Memcpy(void *dst, const void *src, int size, bool expect_race = false);<br>
> -  void Memset(void *dst, int val, int size, bool expect_race = false);<br>
> -<br>
> - private:<br>
> -  struct Impl;<br>
> -  Impl *impl_;<br>
> -  ScopedThread(const ScopedThread&);  // Not implemented.<br>
> -  void operator = (const ScopedThread&);  // Not implemented.<br>
> -};<br>
> -<br>
> -class MainThread : public ScopedThread {<br>
> - public:<br>
> -  MainThread()<br>
> -    : ScopedThread(false, true) {<br>
> -  }<br>
> -};<br>
> -<br>
> -#endif  // #ifndef TSAN_TEST_UTIL_H<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_test_util_linux.cc (removed)<br>
> @@ -1,465 +0,0 @@<br>
> -<br>
> -//===-- tsan_test_util_linux.cc -------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -// Test utils, linux implementation.<br>
> -//===----------------------------------------------------------------------===//<br>
> -<br>
> -#include "sanitizer_common/sanitizer_atomic.h"<br>
> -#include "tsan_interface.h"<br>
> -#include "tsan_test_util.h"<br>
> -#include "tsan_report.h"<br>
> -<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -#include <assert.h><br>
> -#include <pthread.h><br>
> -#include <stdio.h><br>
> -#include <stdint.h><br>
> -#include <string.h><br>
> -#include <unistd.h><br>
> -#include <errno.h><br>
> -<br>
> -using namespace __tsan;  // NOLINT<br>
> -<br>
> -static __thread bool expect_report;<br>
> -static __thread bool expect_report_reported;<br>
> -static __thread ReportType expect_report_type;<br>
> -<br>
> -extern "C" void *__interceptor_memcpy(void*, const void*, uptr);<br>
> -extern "C" void *__interceptor_memset(void*, int, uptr);<br>
> -<br>
> -static void *BeforeInitThread(void *param) {<br>
> -  (void)param;<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -static void AtExit() {<br>
> -}<br>
> -<br>
> -void TestMutexBeforeInit() {<br>
> -  // Mutexes must be usable before __tsan_init();<br>
> -  pthread_mutex_t mtx = PTHREAD_MUTEX_INITIALIZER;<br>
> -  pthread_mutex_lock(&mtx);<br>
> -  pthread_mutex_unlock(&mtx);<br>
> -  pthread_mutex_destroy(&mtx);<br>
> -  pthread_t thr;<br>
> -  pthread_create(&thr, 0, BeforeInitThread, 0);<br>
> -  pthread_join(thr, 0);<br>
> -  atexit(AtExit);<br>
> -}<br>
> -<br>
> -namespace __tsan {<br>
> -bool OnReport(const ReportDesc *rep, bool suppressed) {<br>
> -  if (expect_report) {<br>
> -    if (rep->typ != expect_report_type) {<br>
> -      printf("Expected report of type %d, got type %d\n",<br>
> -             (int)expect_report_type, (int)rep->typ);<br>
> -      EXPECT_FALSE("Wrong report type");<br>
> -      return false;<br>
> -    }<br>
> -  } else {<br>
> -    EXPECT_FALSE("Unexpected report");<br>
> -    return false;<br>
> -  }<br>
> -  expect_report_reported = true;<br>
> -  return true;<br>
> -}<br>
> -}<br>
> -<br>
> -static void* allocate_addr(int size, int offset_from_aligned = 0) {<br>
> -  static uintptr_t foo;<br>
> -  static atomic_uintptr_t uniq = {(uintptr_t)&foo};  // Some real address.<br>
> -  const int kAlign = 16;<br>
> -  CHECK(offset_from_aligned < kAlign);<br>
> -  size = (size + 2 * kAlign) & ~(kAlign - 1);<br>
> -  uintptr_t addr = atomic_fetch_add(&uniq, size, memory_order_relaxed);<br>
> -  return (void*)(addr + offset_from_aligned);<br>
> -}<br>
> -<br>
> -MemLoc::MemLoc(int offset_from_aligned)<br>
> -  : loc_(allocate_addr(16, offset_from_aligned)) {<br>
> -}<br>
> -<br>
> -MemLoc::~MemLoc() {<br>
> -}<br>
> -<br>
> -Mutex::Mutex(Type type)<br>
> -  : alive_()<br>
> -  , type_(type) {<br>
> -}<br>
> -<br>
> -Mutex::~Mutex() {<br>
> -  CHECK(!alive_);<br>
> -}<br>
> -<br>
> -void Mutex::Init() {<br>
> -  CHECK(!alive_);<br>
> -  alive_ = true;<br>
> -  if (type_ == Normal)<br>
> -    CHECK_EQ(pthread_mutex_init((pthread_mutex_t*)mtx_, 0), 0);<br>
> -  else if (type_ == Spin)<br>
> -    CHECK_EQ(pthread_spin_init((pthread_spinlock_t*)mtx_, 0), 0);<br>
> -  else if (type_ == RW)<br>
> -    CHECK_EQ(pthread_rwlock_init((pthread_rwlock_t*)mtx_, 0), 0);<br>
> -  else<br>
> -    CHECK(0);<br>
> -}<br>
> -<br>
> -void Mutex::StaticInit() {<br>
> -  CHECK(!alive_);<br>
> -  CHECK(type_ == Normal);<br>
> -  alive_ = true;<br>
> -  pthread_mutex_t tmp = PTHREAD_MUTEX_INITIALIZER;<br>
> -  memcpy(mtx_, &tmp, sizeof(tmp));<br>
> -}<br>
> -<br>
> -void Mutex::Destroy() {<br>
> -  CHECK(alive_);<br>
> -  alive_ = false;<br>
> -  if (type_ == Normal)<br>
> -    CHECK_EQ(pthread_mutex_destroy((pthread_mutex_t*)mtx_), 0);<br>
> -  else if (type_ == Spin)<br>
> -    CHECK_EQ(pthread_spin_destroy((pthread_spinlock_t*)mtx_), 0);<br>
> -  else if (type_ == RW)<br>
> -    CHECK_EQ(pthread_rwlock_destroy((pthread_rwlock_t*)mtx_), 0);<br>
> -}<br>
> -<br>
> -void Mutex::Lock() {<br>
> -  CHECK(alive_);<br>
> -  if (type_ == Normal)<br>
> -    CHECK_EQ(pthread_mutex_lock((pthread_mutex_t*)mtx_), 0);<br>
> -  else if (type_ == Spin)<br>
> -    CHECK_EQ(pthread_spin_lock((pthread_spinlock_t*)mtx_), 0);<br>
> -  else if (type_ == RW)<br>
> -    CHECK_EQ(pthread_rwlock_wrlock((pthread_rwlock_t*)mtx_), 0);<br>
> -}<br>
> -<br>
> -bool Mutex::TryLock() {<br>
> -  CHECK(alive_);<br>
> -  if (type_ == Normal)<br>
> -    return pthread_mutex_trylock((pthread_mutex_t*)mtx_) == 0;<br>
> -  else if (type_ == Spin)<br>
> -    return pthread_spin_trylock((pthread_spinlock_t*)mtx_) == 0;<br>
> -  else if (type_ == RW)<br>
> -    return pthread_rwlock_trywrlock((pthread_rwlock_t*)mtx_) == 0;<br>
> -  return false;<br>
> -}<br>
> -<br>
> -void Mutex::Unlock() {<br>
> -  CHECK(alive_);<br>
> -  if (type_ == Normal)<br>
> -    CHECK_EQ(pthread_mutex_unlock((pthread_mutex_t*)mtx_), 0);<br>
> -  else if (type_ == Spin)<br>
> -    CHECK_EQ(pthread_spin_unlock((pthread_spinlock_t*)mtx_), 0);<br>
> -  else if (type_ == RW)<br>
> -    CHECK_EQ(pthread_rwlock_unlock((pthread_rwlock_t*)mtx_), 0);<br>
> -}<br>
> -<br>
> -void Mutex::ReadLock() {<br>
> -  CHECK(alive_);<br>
> -  CHECK(type_ == RW);<br>
> -  CHECK_EQ(pthread_rwlock_rdlock((pthread_rwlock_t*)mtx_), 0);<br>
> -}<br>
> -<br>
> -bool Mutex::TryReadLock() {<br>
> -  CHECK(alive_);<br>
> -  CHECK(type_ == RW);<br>
> -  return pthread_rwlock_tryrdlock((pthread_rwlock_t*)mtx_) ==  0;<br>
> -}<br>
> -<br>
> -void Mutex::ReadUnlock() {<br>
> -  CHECK(alive_);<br>
> -  CHECK(type_ == RW);<br>
> -  CHECK_EQ(pthread_rwlock_unlock((pthread_rwlock_t*)mtx_), 0);<br>
> -}<br>
> -<br>
> -struct Event {<br>
> -  enum Type {<br>
> -    SHUTDOWN,<br>
> -    READ,<br>
> -    WRITE,<br>
> -    VPTR_UPDATE,<br>
> -    CALL,<br>
> -    RETURN,<br>
> -    MUTEX_CREATE,<br>
> -    MUTEX_DESTROY,<br>
> -    MUTEX_LOCK,<br>
> -    MUTEX_TRYLOCK,<br>
> -    MUTEX_UNLOCK,<br>
> -    MUTEX_READLOCK,<br>
> -    MUTEX_TRYREADLOCK,<br>
> -    MUTEX_READUNLOCK,<br>
> -    MEMCPY,<br>
> -    MEMSET<br>
> -  };<br>
> -  Type type;<br>
> -  void *ptr;<br>
> -  uptr arg;<br>
> -  uptr arg2;<br>
> -  bool res;<br>
> -  bool expect_report;<br>
> -  ReportType report_type;<br>
> -<br>
> -  Event(Type type, const void *ptr = 0, uptr arg = 0, uptr arg2 = 0)<br>
> -    : type(type)<br>
> -    , ptr(const_cast<void*>(ptr))<br>
> -    , arg(arg)<br>
> -    , arg2(arg2)<br>
> -    , res()<br>
> -    , expect_report()<br>
> -    , report_type() {<br>
> -  }<br>
> -<br>
> -  void ExpectReport(ReportType type) {<br>
> -    expect_report = true;<br>
> -    report_type = type;<br>
> -  }<br>
> -};<br>
> -<br>
> -struct ScopedThread::Impl {<br>
> -  pthread_t thread;<br>
> -  bool main;<br>
> -  bool detached;<br>
> -  atomic_uintptr_t event;  // Event*<br>
> -<br>
> -  static void *ScopedThreadCallback(void *arg);<br>
> -  void send(Event *ev);<br>
> -  void HandleEvent(Event *ev);<br>
> -};<br>
> -<br>
> -void ScopedThread::Impl::HandleEvent(Event *ev) {<br>
> -  CHECK_EQ(expect_report, false);<br>
> -  expect_report = ev->expect_report;<br>
> -  expect_report_reported = false;<br>
> -  expect_report_type = ev->report_type;<br>
> -  switch (ev->type) {<br>
> -  case Event::READ:<br>
> -  case Event::WRITE: {<br>
> -    void (*tsan_mop)(void *addr) = 0;<br>
> -    if (ev->type == Event::READ) {<br>
> -      switch (ev->arg /*size*/) {<br>
> -        case 1: tsan_mop = __tsan_read1; break;<br>
> -        case 2: tsan_mop = __tsan_read2; break;<br>
> -        case 4: tsan_mop = __tsan_read4; break;<br>
> -        case 8: tsan_mop = __tsan_read8; break;<br>
> -        case 16: tsan_mop = __tsan_read16; break;<br>
> -      }<br>
> -    } else {<br>
> -      switch (ev->arg /*size*/) {<br>
> -        case 1: tsan_mop = __tsan_write1; break;<br>
> -        case 2: tsan_mop = __tsan_write2; break;<br>
> -        case 4: tsan_mop = __tsan_write4; break;<br>
> -        case 8: tsan_mop = __tsan_write8; break;<br>
> -        case 16: tsan_mop = __tsan_write16; break;<br>
> -      }<br>
> -    }<br>
> -    CHECK_NE(tsan_mop, 0);<br>
> -    errno = ECHRNG;<br>
> -    tsan_mop(ev->ptr);<br>
> -    CHECK_EQ(errno, ECHRNG);  // In no case must errno be changed.<br>
> -    break;<br>
> -  }<br>
> -  case Event::VPTR_UPDATE:<br>
> -    __tsan_vptr_update((void**)ev->ptr, (void*)ev->arg);<br>
> -    break;<br>
> -  case Event::CALL:<br>
> -    __tsan_func_entry((void*)((uptr)ev->ptr));<br>
> -    break;<br>
> -  case Event::RETURN:<br>
> -    __tsan_func_exit();<br>
> -    break;<br>
> -  case Event::MUTEX_CREATE:<br>
> -    static_cast<Mutex*>(ev->ptr)->Init();<br>
> -    break;<br>
> -  case Event::MUTEX_DESTROY:<br>
> -    static_cast<Mutex*>(ev->ptr)->Destroy();<br>
> -    break;<br>
> -  case Event::MUTEX_LOCK:<br>
> -    static_cast<Mutex*>(ev->ptr)->Lock();<br>
> -    break;<br>
> -  case Event::MUTEX_TRYLOCK:<br>
> -    ev->res = static_cast<Mutex*>(ev->ptr)->TryLock();<br>
> -    break;<br>
> -  case Event::MUTEX_UNLOCK:<br>
> -    static_cast<Mutex*>(ev->ptr)->Unlock();<br>
> -    break;<br>
> -  case Event::MUTEX_READLOCK:<br>
> -    static_cast<Mutex*>(ev->ptr)->ReadLock();<br>
> -    break;<br>
> -  case Event::MUTEX_TRYREADLOCK:<br>
> -    ev->res = static_cast<Mutex*>(ev->ptr)->TryReadLock();<br>
> -    break;<br>
> -  case Event::MUTEX_READUNLOCK:<br>
> -    static_cast<Mutex*>(ev->ptr)->ReadUnlock();<br>
> -    break;<br>
> -  case Event::MEMCPY:<br>
> -    __interceptor_memcpy(ev->ptr, (void*)ev->arg, ev->arg2);<br>
> -    break;<br>
> -  case Event::MEMSET:<br>
> -    __interceptor_memset(ev->ptr, ev->arg, ev->arg2);<br>
> -    break;<br>
> -  default: CHECK(0);<br>
> -  }<br>
> -  if (expect_report && !expect_report_reported) {<br>
> -    printf("Missed expected report of type %d\n", (int)ev->report_type);<br>
> -    EXPECT_FALSE("Missed expected race");<br>
> -  }<br>
> -  expect_report = false;<br>
> -}<br>
> -<br>
> -void *ScopedThread::Impl::ScopedThreadCallback(void *arg) {<br>
> -  __tsan_func_entry(__builtin_return_address(0));<br>
> -  Impl *impl = (Impl*)arg;<br>
> -  for (;;) {<br>
> -    Event* ev = (Event*)atomic_load(&impl->event, memory_order_acquire);<br>
> -    if (ev == 0) {<br>
> -      pthread_yield();<br>
> -      continue;<br>
> -    }<br>
> -    if (ev->type == Event::SHUTDOWN) {<br>
> -      atomic_store(&impl->event, 0, memory_order_release);<br>
> -      break;<br>
> -    }<br>
> -    impl->HandleEvent(ev);<br>
> -    atomic_store(&impl->event, 0, memory_order_release);<br>
> -  }<br>
> -  __tsan_func_exit();<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -void ScopedThread::Impl::send(Event *e) {<br>
> -  if (main) {<br>
> -    HandleEvent(e);<br>
> -  } else {<br>
> -    CHECK_EQ(atomic_load(&event, memory_order_relaxed), 0);<br>
> -    atomic_store(&event, (uintptr_t)e, memory_order_release);<br>
> -    while (atomic_load(&event, memory_order_acquire) != 0)<br>
> -      pthread_yield();<br>
> -  }<br>
> -}<br>
> -<br>
> -ScopedThread::ScopedThread(bool detached, bool main) {<br>
> -  impl_ = new Impl;<br>
> -  impl_->main = main;<br>
> -  impl_->detached = detached;<br>
> -  atomic_store(&impl_->event, 0, memory_order_relaxed);<br>
> -  if (!main) {<br>
> -    pthread_attr_t attr;<br>
> -    pthread_attr_init(&attr);<br>
> -    pthread_attr_setdetachstate(&attr, detached);<br>
> -    pthread_attr_setstacksize(&attr, 64*1024);<br>
> -    pthread_create(&impl_->thread, &attr,<br>
> -        ScopedThread::Impl::ScopedThreadCallback, impl_);<br>
> -  }<br>
> -}<br>
> -<br>
> -ScopedThread::~ScopedThread() {<br>
> -  if (!impl_->main) {<br>
> -    Event event(Event::SHUTDOWN);<br>
> -    impl_->send(&event);<br>
> -    if (!impl_->detached)<br>
> -      pthread_join(impl_->thread, 0);<br>
> -  }<br>
> -  delete impl_;<br>
> -}<br>
> -<br>
> -void ScopedThread::Detach() {<br>
> -  CHECK(!impl_->main);<br>
> -  CHECK(!impl_->detached);<br>
> -  impl_->detached = true;<br>
> -  pthread_detach(impl_->thread);<br>
> -}<br>
> -<br>
> -void ScopedThread::Access(void *addr, bool is_write,<br>
> -                          int size, bool expect_race) {<br>
> -  Event event(is_write ? Event::WRITE : Event::READ, addr, size);<br>
> -  if (expect_race)<br>
> -    event.ExpectReport(ReportTypeRace);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::VptrUpdate(const MemLoc &vptr,<br>
> -                              const MemLoc &new_val,<br>
> -                              bool expect_race) {<br>
> -  Event event(Event::VPTR_UPDATE, vptr.loc(), (uptr)new_val.loc());<br>
> -  if (expect_race)<br>
> -    event.ExpectReport(ReportTypeRace);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Call(void(*pc)()) {<br>
> -  Event event(Event::CALL, (void*)pc);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Return() {<br>
> -  Event event(Event::RETURN);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Create(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_CREATE, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Destroy(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_DESTROY, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Lock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_LOCK, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -bool ScopedThread::TryLock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_TRYLOCK, &m);<br>
> -  impl_->send(&event);<br>
> -  return event.res;<br>
> -}<br>
> -<br>
> -void ScopedThread::Unlock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_UNLOCK, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::ReadLock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_READLOCK, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -bool ScopedThread::TryReadLock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_TRYREADLOCK, &m);<br>
> -  impl_->send(&event);<br>
> -  return event.res;<br>
> -}<br>
> -<br>
> -void ScopedThread::ReadUnlock(const Mutex &m) {<br>
> -  Event event(Event::MUTEX_READUNLOCK, &m);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Memcpy(void *dst, const void *src, int size,<br>
> -                          bool expect_race) {<br>
> -  Event event(Event::MEMCPY, dst, (uptr)src, size);<br>
> -  if (expect_race)<br>
> -    event.ExpectReport(ReportTypeRace);<br>
> -  impl_->send(&event);<br>
> -}<br>
> -<br>
> -void ScopedThread::Memset(void *dst, int val, int size,<br>
> -                          bool expect_race) {<br>
> -  Event event(Event::MEMSET, dst, val, size);<br>
> -  if (expect_race)<br>
> -    event.ExpectReport(ReportTypeRace);<br>
> -  impl_->send(&event);<br>
> -}<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/rtl_tests/tsan_thread.cc (removed)<br>
> @@ -1,59 +0,0 @@<br>
> -//===-- tsan_thread.cc ----------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_test_util.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -TEST(ThreadSanitizer, ThreadSync) {<br>
> -  MainThread t0;<br>
> -  MemLoc l;<br>
> -  t0.Write1(l);<br>
> -  {<br>
> -    ScopedThread t1;<br>
> -    t1.Write1(l);<br>
> -  }<br>
> -  t0.Write1(l);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, ThreadDetach1) {<br>
> -  ScopedThread t1(true);<br>
> -  MemLoc l;<br>
> -  t1.Write1(l);<br>
> -}<br>
> -<br>
> -TEST(ThreadSanitizer, ThreadDetach2) {<br>
> -  ScopedThread t1;<br>
> -  MemLoc l;<br>
> -  t1.Write1(l);<br>
> -  t1.Detach();<br>
> -}<br>
> -<br>
> -static void *thread_alot_func(void *arg) {<br>
> -  (void)arg;<br>
> -  int usleep(unsigned);<br>
> -  usleep(50);<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(DISABLED_SLOW_ThreadSanitizer, ThreadALot) {<br>
> -  const int kThreads = 70000;<br>
> -  const int kAlive = 1000;<br>
> -  pthread_t threads[kAlive] = {};<br>
> -  for (int i = 0; i < kThreads; i++) {<br>
> -    if (threads[i % kAlive])<br>
> -      pthread_join(threads[i % kAlive], 0);<br>
> -    pthread_create(&threads[i % kAlive], 0, thread_alot_func, 0);<br>
> -  }<br>
> -  for (int i = 0; i < kAlive; i++) {<br>
> -    pthread_join(threads[i], 0);<br>
> -  }<br>
> -}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/CMakeLists.txt Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,24 @@<br>
> +include_directories(../rtl)<br>
> +<br>
> +add_custom_target(TsanUnitTests)<br>
> +set_target_properties(TsanUnitTests PROPERTIES<br>
> +  FOLDER "TSan unittests")<br>
> +function(add_tsan_unittest testname)<br>
> +  # Build unit tests only on 64-bit Linux.<br>
> +  if(UNIX AND NOT APPLE<br>
> +      AND CAN_TARGET_X86_64<br>
> +      AND CMAKE_SIZEOF_VOID_P EQUAL 8<br>
> +      AND NOT LLVM_BUILD_32_BITS)<br>
> +    add_unittest(TsanUnitTests ${testname} ${ARGN})<br>
> +    # Link with TSan runtime.<br>
> +    target_link_libraries(${testname} clang_rt.tsan-x86_64)<br>
> +    # Build tests with PIE and debug info.<br>
> +    set_property(TARGET ${testname} APPEND_STRING<br>
> +      PROPERTY COMPILE_FLAGS " -fPIE -g")<br>
> +    set_property(TARGET ${testname} APPEND_STRING<br>
> +      PROPERTY LINK_FLAGS " -pie")<br>
> +  endif()<br>
> +endfunction()<br>
> +<br>
> +add_subdirectory(rtl)<br>
> +add_subdirectory(unit)<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/CMakeLists.txt Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,15 @@<br>
> +set(TSAN_RTL_TESTS<br>
> +  tsan_bench.cc<br>
> +  tsan_mop.cc<br>
> +  tsan_mutex.cc<br>
> +  tsan_posix.cc<br>
> +  tsan_string.cc<br>
> +  tsan_test.cc<br>
> +  tsan_thread.cc<br>
> +  )<br>
> +<br>
> +if(UNIX AND NOT APPLE)<br>
> +  list(APPEND TSAN_RTL_TESTS tsan_test_util_linux.cc)<br>
> +endif()<br>
> +<br>
> +add_tsan_unittest(TsanRtlTest ${TSAN_RTL_TESTS})<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_bench.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,105 @@<br>
> +//===-- tsan_bench.cc -----------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_test_util.h"<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_defs.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <stdint.h><br>
> +<br>
> +const int kSize = 128;<br>
> +const int kRepeat = 2*1024*1024;<br>
> +<br>
> +void noinstr(void *p) {}<br>
> +<br>
> +template<typename T, void(*__tsan_mop)(void *p)><br>
> +static void Benchmark() {<br>
> +  volatile T data[kSize];<br>
> +  for (int i = 0; i < kRepeat; i++) {<br>
> +    for (int j = 0; j < kSize; j++) {<br>
> +      __tsan_mop((void*)&data[j]);<br>
> +      data[j]++;<br>
> +    }<br>
> +  }<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop1) {<br>
> +  Benchmark<uint8_t, noinstr>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop1Read) {<br>
> +  Benchmark<uint8_t, __tsan_read1>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop1Write) {<br>
> +  Benchmark<uint8_t, __tsan_write1>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop2) {<br>
> +  Benchmark<uint16_t, noinstr>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop2Read) {<br>
> +  Benchmark<uint16_t, __tsan_read2>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop2Write) {<br>
> +  Benchmark<uint16_t, __tsan_write2>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop4) {<br>
> +  Benchmark<uint32_t, noinstr>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop4Read) {<br>
> +  Benchmark<uint32_t, __tsan_read4>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop4Write) {<br>
> +  Benchmark<uint32_t, __tsan_write4>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop8) {<br>
> +  Benchmark<uint8_t, noinstr>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop8Read) {<br>
> +  Benchmark<uint64_t, __tsan_read8>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, Mop8Write) {<br>
> +  Benchmark<uint64_t, __tsan_write8>();<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, FuncCall) {<br>
> +  for (int i = 0; i < kRepeat; i++) {<br>
> +    for (int j = 0; j < kSize; j++)<br>
> +      __tsan_func_entry((void*)(uintptr_t)j);<br>
> +    for (int j = 0; j < kSize; j++)<br>
> +      __tsan_func_exit();<br>
> +  }<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH, MutexLocal) {<br>
> +  Mutex m;<br>
> +  ScopedThread().Create(m);<br>
> +  for (int i = 0; i < 50; i++) {<br>
> +    ScopedThread t;<br>
> +    t.Lock(m);<br>
> +    t.Unlock(m);<br>
> +  }<br>
> +  for (int i = 0; i < 16*1024*1024; i++) {<br>
> +    m.Lock();<br>
> +    m.Unlock();<br>
> +  }<br>
> +  ScopedThread().Destroy(m);<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mop.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,233 @@<br>
> +//===-- tsan_mop.cc -------------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <stddef.h><br>
> +#include <stdint.h><br>
> +<br>
> +TEST(ThreadSanitizer, SimpleWrite) {<br>
> +  ScopedThread t;<br>
> +  MemLoc l;<br>
> +  t.Write1(l);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, SimpleWriteWrite) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l1, l2;<br>
> +  t1.Write1(l1);<br>
> +  t2.Write1(l2);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, WriteWriteRace) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Write1(l);<br>
> +  t2.Write1(l, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, ReadWriteRace) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Read1(l);<br>
> +  t2.Write1(l, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, WriteReadRace) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Write1(l);<br>
> +  t2.Read1(l, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, ReadReadNoRace) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Read1(l);<br>
> +  t2.Read1(l);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, WriteThenRead) {<br>
> +  MemLoc l;<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Write1(l);<br>
> +  t1.Read1(l);<br>
> +  t2.Read1(l, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, WriteThenLockedRead) {<br>
> +  Mutex m(Mutex::RW);<br>
> +  MainThread t0;<br>
> +  t0.Create(m);<br>
> +  MemLoc l;<br>
> +  {<br>
> +    ScopedThread t1, t2;<br>
> +<br>
> +    t1.Write8(l);<br>
> +<br>
> +    t1.Lock(m);<br>
> +    t1.Read8(l);<br>
> +    t1.Unlock(m);<br>
> +<br>
> +    t2.Read8(l, true);<br>
> +  }<br>
> +  t0.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, LockedWriteThenRead) {<br>
> +  Mutex m(Mutex::RW);<br>
> +  MainThread t0;<br>
> +  t0.Create(m);<br>
> +  MemLoc l;<br>
> +  {<br>
> +    ScopedThread t1, t2;<br>
> +<br>
> +    t1.Lock(m);<br>
> +    t1.Write8(l);<br>
> +    t1.Unlock(m);<br>
> +<br>
> +    t1.Read8(l);<br>
> +<br>
> +    t2.Read8(l, true);<br>
> +  }<br>
> +  t0.Destroy(m);<br>
> +}<br>
> +<br>
> +<br>
> +TEST(ThreadSanitizer, RaceWithOffset) {<br>
> +  ScopedThread t1, t2;<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access(l.loc(), true, 8, false);<br>
> +    t2.Access((char*)l.loc() + 4, true, 4, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access(l.loc(), true, 8, false);<br>
> +    t2.Access((char*)l.loc() + 7, true, 1, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 4, true, 4, false);<br>
> +    t2.Access((char*)l.loc() + 4, true, 2, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 4, true, 4, false);<br>
> +    t2.Access((char*)l.loc() + 6, true, 2, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 3, true, 2, false);<br>
> +    t2.Access((char*)l.loc() + 4, true, 1, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 1, true, 8, false);<br>
> +    t2.Access((char*)l.loc() + 3, true, 1, true);<br>
> +  }<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, RaceWithOffset2) {<br>
> +  ScopedThread t1, t2;<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc(), true, 4, false);<br>
> +    t2.Access((char*)l.loc() + 2, true, 1, true);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 2, true, 1, false);<br>
> +    t2.Access((char*)l.loc(), true, 4, true);<br>
> +  }<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, NoRaceWithOffset) {<br>
> +  ScopedThread t1, t2;<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access(l.loc(), true, 4, false);<br>
> +    t2.Access((char*)l.loc() + 4, true, 4, false);<br>
> +  }<br>
> +  {<br>
> +    MemLoc l;<br>
> +    t1.Access((char*)l.loc() + 3, true, 2, false);<br>
> +    t2.Access((char*)l.loc() + 1, true, 2, false);<br>
> +    t2.Access((char*)l.loc() + 5, true, 2, false);<br>
> +  }<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, RaceWithDeadThread) {<br>
> +  MemLoc l;<br>
> +  ScopedThread t;<br>
> +  ScopedThread().Write1(l);<br>
> +  t.Write1(l, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, BenignRaceOnVptr) {<br>
> +  void *vptr_storage;<br>
> +  MemLoc vptr(&vptr_storage), val;<br>
> +  vptr_storage = val.loc();<br>
> +  ScopedThread t1, t2;<br>
> +  t1.VptrUpdate(vptr, val);<br>
> +  t2.Read8(vptr);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, HarmfulRaceOnVptr) {<br>
> +  void *vptr_storage;<br>
> +  MemLoc vptr(&vptr_storage), val1, val2;<br>
> +  vptr_storage = val1.loc();<br>
> +  ScopedThread t1, t2;<br>
> +  t1.VptrUpdate(vptr, val2);<br>
> +  t2.Read8(vptr, true);<br>
> +}<br>
> +<br>
> +static void foo() {<br>
> +  volatile int x = 42;<br>
> +  int x2 = x;<br>
> +  (void)x2;<br>
> +}<br>
> +<br>
> +static void bar() {<br>
> +  volatile int x = 43;<br>
> +  int x2 = x;<br>
> +  (void)x2;<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, ReportDeadThread) {<br>
> +  MemLoc l;<br>
> +  ScopedThread t1;<br>
> +  {<br>
> +    ScopedThread t2;<br>
> +    t2.Call(&foo);<br>
> +    t2.Call(&bar);<br>
> +    t2.Write1(l);<br>
> +  }<br>
> +  t1.Write1(l, true);<br>
> +}<br>
> +<br>
> +struct ClassWithStatic {<br>
> +  static int Data[4];<br>
> +};<br>
> +<br>
> +int ClassWithStatic::Data[4];<br>
> +<br>
> +static void foobarbaz() {}<br>
> +<br>
> +TEST(ThreadSanitizer, ReportRace) {<br>
> +  ScopedThread t1;<br>
> +  MainThread().Access(&ClassWithStatic::Data, true, 4, false);<br>
> +  t1.Call(&foobarbaz);<br>
> +  t1.Access(&ClassWithStatic::Data, true, 2, true);<br>
> +  t1.Return();<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_mutex.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,221 @@<br>
> +//===-- tsan_mutex.cc -----------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "sanitizer_common/sanitizer_atomic.h"<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_interface_ann.h"<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <stdint.h><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(ThreadSanitizer, BasicMutex) {<br>
> +  ScopedThread t;<br>
> +  Mutex m;<br>
> +  t.Create(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  t.Unlock(m);<br>
> +<br>
> +  CHECK(t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  CHECK(!t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, BasicSpinMutex) {<br>
> +  ScopedThread t;<br>
> +  Mutex m(Mutex::Spin);<br>
> +  t.Create(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  t.Unlock(m);<br>
> +<br>
> +  CHECK(t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  CHECK(!t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, BasicRwMutex) {<br>
> +  ScopedThread t;<br>
> +  Mutex m(Mutex::RW);<br>
> +  t.Create(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  t.Unlock(m);<br>
> +<br>
> +  CHECK(t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  CHECK(!t.TryLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.ReadLock(m);<br>
> +  t.ReadUnlock(m);<br>
> +<br>
> +  CHECK(t.TryReadLock(m));<br>
> +  t.ReadUnlock(m);<br>
> +<br>
> +  t.Lock(m);<br>
> +  CHECK(!t.TryReadLock(m));<br>
> +  t.Unlock(m);<br>
> +<br>
> +  t.ReadLock(m);<br>
> +  CHECK(!t.TryLock(m));<br>
> +  t.ReadUnlock(m);<br>
> +<br>
> +  t.ReadLock(m);<br>
> +  CHECK(t.TryReadLock(m));<br>
> +  t.ReadUnlock(m);<br>
> +  t.ReadUnlock(m);<br>
> +<br>
> +  t.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, Mutex) {<br>
> +  Mutex m;<br>
> +  MainThread t0;<br>
> +  t0.Create(m);<br>
> +<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Lock(m);<br>
> +  t1.Write1(l);<br>
> +  t1.Unlock(m);<br>
> +  t2.Lock(m);<br>
> +  t2.Write1(l);<br>
> +  t2.Unlock(m);<br>
> +  t2.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, SpinMutex) {<br>
> +  Mutex m(Mutex::Spin);<br>
> +  MainThread t0;<br>
> +  t0.Create(m);<br>
> +<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Lock(m);<br>
> +  t1.Write1(l);<br>
> +  t1.Unlock(m);<br>
> +  t2.Lock(m);<br>
> +  t2.Write1(l);<br>
> +  t2.Unlock(m);<br>
> +  t2.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, RwMutex) {<br>
> +  Mutex m(Mutex::RW);<br>
> +  MainThread t0;<br>
> +  t0.Create(m);<br>
> +<br>
> +  ScopedThread t1, t2, t3;<br>
> +  MemLoc l;<br>
> +  t1.Lock(m);<br>
> +  t1.Write1(l);<br>
> +  t1.Unlock(m);<br>
> +  t2.Lock(m);<br>
> +  t2.Write1(l);<br>
> +  t2.Unlock(m);<br>
> +  t1.ReadLock(m);<br>
> +  t3.ReadLock(m);<br>
> +  t1.Read1(l);<br>
> +  t3.Read1(l);<br>
> +  t1.ReadUnlock(m);<br>
> +  t3.ReadUnlock(m);<br>
> +  t2.Lock(m);<br>
> +  t2.Write1(l);<br>
> +  t2.Unlock(m);<br>
> +  t2.Destroy(m);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, StaticMutex) {<br>
> +  // Emulates statically initialized mutex.<br>
> +  Mutex m;<br>
> +  m.StaticInit();<br>
> +  {<br>
> +    ScopedThread t1, t2;<br>
> +    t1.Lock(m);<br>
> +    t1.Unlock(m);<br>
> +    t2.Lock(m);<br>
> +    t2.Unlock(m);<br>
> +  }<br>
> +  MainThread().Destroy(m);<br>
> +}<br>
> +<br>
> +static void *singleton_thread(void *param) {<br>
> +  atomic_uintptr_t *singleton = (atomic_uintptr_t *)param;<br>
> +  for (int i = 0; i < 4*1024*1024; i++) {<br>
> +    int *val = (int *)atomic_load(singleton, memory_order_acquire);<br>
> +    __tsan_acquire(singleton);<br>
> +    __tsan_read4(val);<br>
> +    CHECK_EQ(*val, 42);<br>
> +  }<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH_ThreadSanitizer, Singleton) {<br>
> +  const int kClockSize = 100;<br>
> +  const int kThreadCount = 8;<br>
> +<br>
> +  // Puff off thread's clock.<br>
> +  for (int i = 0; i < kClockSize; i++) {<br>
> +    ScopedThread t1;<br>
> +    (void)t1;<br>
> +  }<br>
> +  // Create the singleton.<br>
> +  int val = 42;<br>
> +  __tsan_write4(&val);<br>
> +  atomic_uintptr_t singleton;<br>
> +  __tsan_release(&singleton);<br>
> +  atomic_store(&singleton, (uintptr_t)&val, memory_order_release);<br>
> +  // Create reader threads.<br>
> +  pthread_t threads[kThreadCount];<br>
> +  for (int t = 0; t < kThreadCount; t++)<br>
> +    pthread_create(&threads[t], 0, singleton_thread, &singleton);<br>
> +  for (int t = 0; t < kThreadCount; t++)<br>
> +    pthread_join(threads[t], 0);<br>
> +}<br>
> +<br>
> +TEST(DISABLED_BENCH_ThreadSanitizer, StopFlag) {<br>
> +  const int kClockSize = 100;<br>
> +  const int kIters = 16*1024*1024;<br>
> +<br>
> +  // Puff off thread's clock.<br>
> +  for (int i = 0; i < kClockSize; i++) {<br>
> +    ScopedThread t1;<br>
> +    (void)t1;<br>
> +  }<br>
> +  // Create the stop flag.<br>
> +  atomic_uintptr_t flag;<br>
> +  __tsan_release(&flag);<br>
> +  atomic_store(&flag, 0, memory_order_release);<br>
> +  // Read it a lot.<br>
> +  for (int i = 0; i < kIters; i++) {<br>
> +    uptr v = atomic_load(&flag, memory_order_acquire);<br>
> +    __tsan_acquire(&flag);<br>
> +    CHECK_EQ(v, 0);<br>
> +  }<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_posix.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,146 @@<br>
> +//===-- tsan_posix.cc -----------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <pthread.h><br>
> +<br>
> +struct thread_key {<br>
> +  pthread_key_t key;<br>
> +  pthread_mutex_t *mtx;<br>
> +  int val;<br>
> +  int *cnt;<br>
> +  thread_key(pthread_key_t key, pthread_mutex_t *mtx, int val, int *cnt)<br>
> +    : key(key)<br>
> +    , mtx(mtx)<br>
> +    , val(val)<br>
> +    , cnt(cnt) {<br>
> +  }<br>
> +};<br>
> +<br>
> +static void thread_secific_dtor(void *v) {<br>
> +  thread_key *k = (thread_key *)v;<br>
> +  EXPECT_EQ(pthread_mutex_lock(k->mtx), 0);<br>
> +  (*k->cnt)++;<br>
> +  __tsan_write4(&k->cnt);<br>
> +  EXPECT_EQ(pthread_mutex_unlock(k->mtx), 0);<br>
> +  if (k->val == 42) {<br>
> +    delete k;<br>
> +  } else if (k->val == 43 || k->val == 44) {<br>
> +    k->val--;<br>
> +    EXPECT_EQ(pthread_setspecific(k->key, k), 0);<br>
> +  } else {<br>
> +    ASSERT_TRUE(false);<br>
> +  }<br>
> +}<br>
> +<br>
> +static void *dtors_thread(void *p) {<br>
> +  thread_key *k = (thread_key *)p;<br>
> +  EXPECT_EQ(pthread_setspecific(k->key, k), 0);<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(Posix, ThreadSpecificDtors) {<br>
> +  int cnt = 0;<br>
> +  pthread_key_t key;<br>
> +  EXPECT_EQ(pthread_key_create(&key, thread_secific_dtor), 0);<br>
> +  pthread_mutex_t mtx;<br>
> +  EXPECT_EQ(pthread_mutex_init(&mtx, 0), 0);<br>
> +  pthread_t th[3];<br>
> +  thread_key *k[3];<br>
> +  k[0] = new thread_key(key, &mtx, 42, &cnt);<br>
> +  k[1] = new thread_key(key, &mtx, 43, &cnt);<br>
> +  k[2] = new thread_key(key, &mtx, 44, &cnt);<br>
> +  EXPECT_EQ(pthread_create(&th[0], 0, dtors_thread, k[0]), 0);<br>
> +  EXPECT_EQ(pthread_create(&th[1], 0, dtors_thread, k[1]), 0);<br>
> +  EXPECT_EQ(pthread_join(th[0], 0), 0);<br>
> +  EXPECT_EQ(pthread_create(&th[2], 0, dtors_thread, k[2]), 0);<br>
> +  EXPECT_EQ(pthread_join(th[1], 0), 0);<br>
> +  EXPECT_EQ(pthread_join(th[2], 0), 0);<br>
> +  EXPECT_EQ(pthread_key_delete(key), 0);<br>
> +  EXPECT_EQ(6, cnt);<br>
> +}<br>
> +<br>
> +static __thread int local_var;<br>
> +<br>
> +static void *local_thread(void *p) {<br>
> +  __tsan_write1(&local_var);<br>
> +  __tsan_write1(&p);<br>
> +  if (p == 0)<br>
> +    return 0;<br>
> +  const int kThreads = 4;<br>
> +  pthread_t th[kThreads];<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    EXPECT_EQ(pthread_create(&th[i], 0, local_thread,<br>
> +              (void*)((long)p - 1)), 0);  // NOLINT<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    EXPECT_EQ(pthread_join(th[i], 0), 0);<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(Posix, ThreadLocalAccesses) {<br>
> +  local_thread((void*)2);<br>
> +}<br>
> +<br>
> +struct CondContext {<br>
> +  pthread_mutex_t m;<br>
> +  pthread_cond_t c;<br>
> +  int data;<br>
> +};<br>
> +<br>
> +static void *cond_thread(void *p) {<br>
> +  CondContext &ctx = *static_cast<CondContext*>(p);<br>
> +<br>
> +  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> +  EXPECT_EQ(ctx.data, 0);<br>
> +  ctx.data = 1;<br>
> +  EXPECT_EQ(pthread_cond_signal(&ctx.c), 0);<br>
> +  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> +<br>
> +  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> +  while (ctx.data != 2)<br>
> +    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> +  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> +<br>
> +  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> +  ctx.data = 3;<br>
> +  EXPECT_EQ(pthread_cond_broadcast(&ctx.c), 0);<br>
> +  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> +<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(Posix, CondBasic) {<br>
> +  CondContext ctx;<br>
> +  EXPECT_EQ(pthread_mutex_init(&ctx.m, 0), 0);<br>
> +  EXPECT_EQ(pthread_cond_init(&ctx.c, 0), 0);<br>
> +  ctx.data = 0;<br>
> +  pthread_t th;<br>
> +  EXPECT_EQ(pthread_create(&th, 0, cond_thread, &ctx), 0);<br>
> +<br>
> +  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> +  while (ctx.data != 1)<br>
> +    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> +  ctx.data = 2;<br>
> +  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> +  EXPECT_EQ(pthread_cond_broadcast(&ctx.c), 0);<br>
> +<br>
> +  EXPECT_EQ(pthread_mutex_lock(&ctx.m), 0);<br>
> +  while (ctx.data != 3)<br>
> +    EXPECT_EQ(pthread_cond_wait(&ctx.c, &ctx.m), 0);<br>
> +  EXPECT_EQ(pthread_mutex_unlock(&ctx.m), 0);<br>
> +<br>
> +  EXPECT_EQ(pthread_join(th, 0), 0);<br>
> +  EXPECT_EQ(pthread_cond_destroy(&ctx.c), 0);<br>
> +  EXPECT_EQ(pthread_mutex_destroy(&ctx.m), 0);<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_string.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,82 @@<br>
> +//===-- tsan_string.cc ----------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <string.h><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(ThreadSanitizer, Memcpy) {<br>
> +  char data0[7] = {1, 2, 3, 4, 5, 6, 7};<br>
> +  char data[7] = {42, 42, 42, 42, 42, 42, 42};<br>
> +  MainThread().Memcpy(data+1, data0+1, 5);<br>
> +  EXPECT_EQ(data[0], 42);<br>
> +  EXPECT_EQ(data[1], 2);<br>
> +  EXPECT_EQ(data[2], 3);<br>
> +  EXPECT_EQ(data[3], 4);<br>
> +  EXPECT_EQ(data[4], 5);<br>
> +  EXPECT_EQ(data[5], 6);<br>
> +  EXPECT_EQ(data[6], 42);<br>
> +  MainThread().Memset(data+1, 13, 5);<br>
> +  EXPECT_EQ(data[0], 42);<br>
> +  EXPECT_EQ(data[1], 13);<br>
> +  EXPECT_EQ(data[2], 13);<br>
> +  EXPECT_EQ(data[3], 13);<br>
> +  EXPECT_EQ(data[4], 13);<br>
> +  EXPECT_EQ(data[5], 13);<br>
> +  EXPECT_EQ(data[6], 42);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, MemcpyRace1) {<br>
> +  char *data = new char[10];<br>
> +  char *data1 = new char[10];<br>
> +  char *data2 = new char[10];<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Memcpy(data, data1, 10);<br>
> +  t2.Memcpy(data, data2, 10, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, MemcpyRace2) {<br>
> +  char *data = new char[10];<br>
> +  char *data1 = new char[10];<br>
> +  char *data2 = new char[10];<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Memcpy(data+5, data1, 1);<br>
> +  t2.Memcpy(data+3, data2, 4, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, MemcpyRace3) {<br>
> +  char *data = new char[10];<br>
> +  char *data1 = new char[10];<br>
> +  char *data2 = new char[10];<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Memcpy(data, data1, 10);<br>
> +  t2.Memcpy(data1, data2, 10, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, MemcpyStack) {<br>
> +  char *data = new char[10];<br>
> +  char *data1 = new char[10];<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Memcpy(data, data1, 10);<br>
> +  t2.Memcpy(data, data1, 10, true);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, MemsetRace1) {<br>
> +  char *data = new char[10];<br>
> +  ScopedThread t1, t2;<br>
> +  t1.Memset(data, 1, 10);<br>
> +  t2.Memset(data, 2, 10, true);<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,44 @@<br>
> +//===-- tsan_test.cc ------------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +static void foo() {}<br>
> +static void bar() {}<br>
> +<br>
> +TEST(ThreadSanitizer, FuncCall) {<br>
> +  ScopedThread t1, t2;<br>
> +  MemLoc l;<br>
> +  t1.Write1(l);<br>
> +  t2.Call(foo);<br>
> +  t2.Call(bar);<br>
> +  t2.Write1(l, true);<br>
> +  t2.Return();<br>
> +  t2.Return();<br>
> +}<br>
> +<br>
> +int main(int argc, char **argv) {<br>
> +  TestMutexBeforeInit();  // Mutexes must be usable before __tsan_init();<br>
> +  __tsan_init();<br>
> +  __tsan_func_entry(__builtin_return_address(0));<br>
> +  __tsan_func_entry((char*)&main + 1);<br>
<br>
This seems to break the CMake build:<br>
<br>
llvm/projects/compiler-rt/lib/tsan/tests/rtl/tsan_test.cc:35:21:<br>
error: cast between pointer-to-function and pointer-to-object is an<br>
extension [-Werror,-Wpedantic]<br>
  __tsan_func_entry((char*)&main + 1);<br>
                    ^~~~~~~~~~~~<br>
1 error generated.<br>
<br>
I'm not sure what, if anything, is the right fix for this.<br>
<br>
> +<br>
> +  testing::GTEST_FLAG(death_test_style) = "threadsafe";<br>
> +  testing::InitGoogleTest(&argc, argv);<br>
> +  int res = RUN_ALL_TESTS();<br>
> +<br>
> +  __tsan_func_exit();<br>
> +  __tsan_func_exit();<br>
> +  return res;<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util.h Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,122 @@<br>
> +//===-- tsan_test_util.h ----------------------------------------*- C++ -*-===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +// Test utils.<br>
> +//===----------------------------------------------------------------------===//<br>
> +#ifndef TSAN_TEST_UTIL_H<br>
> +#define TSAN_TEST_UTIL_H<br>
> +<br>
> +void TestMutexBeforeInit();<br>
> +<br>
> +// A location of memory on which a race may be detected.<br>
> +class MemLoc {<br>
> + public:<br>
> +  explicit MemLoc(int offset_from_aligned = 0);<br>
> +  explicit MemLoc(void *const real_addr) : loc_(real_addr) { }<br>
> +  ~MemLoc();<br>
> +  void *loc() const { return loc_; }<br>
> + private:<br>
> +  void *const loc_;<br>
> +  MemLoc(const MemLoc&);<br>
> +  void operator = (const MemLoc&);<br>
> +};<br>
> +<br>
> +class Mutex {<br>
> + public:<br>
> +  enum Type { Normal, Spin, RW };<br>
> +<br>
> +  explicit Mutex(Type type = Normal);<br>
> +  ~Mutex();<br>
> +<br>
> +  void Init();<br>
> +  void StaticInit();  // Emulates static initalization (tsan invisible).<br>
> +  void Destroy();<br>
> +  void Lock();<br>
> +  bool TryLock();<br>
> +  void Unlock();<br>
> +  void ReadLock();<br>
> +  bool TryReadLock();<br>
> +  void ReadUnlock();<br>
> +<br>
> + private:<br>
> +  // Placeholder for pthread_mutex_t, CRITICAL_SECTION or whatever.<br>
> +  void *mtx_[128];<br>
> +  bool alive_;<br>
> +  const Type type_;<br>
> +<br>
> +  Mutex(const Mutex&);<br>
> +  void operator = (const Mutex&);<br>
> +};<br>
> +<br>
> +// A thread is started in CTOR and joined in DTOR.<br>
> +class ScopedThread {<br>
> + public:<br>
> +  explicit ScopedThread(bool detached = false, bool main = false);<br>
> +  ~ScopedThread();<br>
> +  void Detach();<br>
> +<br>
> +  void Access(void *addr, bool is_write, int size, bool expect_race);<br>
> +  void Read(const MemLoc &ml, int size, bool expect_race = false) {<br>
> +    Access(ml.loc(), false, size, expect_race);<br>
> +  }<br>
> +  void Write(const MemLoc &ml, int size, bool expect_race = false) {<br>
> +    Access(ml.loc(), true, size, expect_race);<br>
> +  }<br>
> +  void Read1(const MemLoc &ml, bool expect_race = false) {<br>
> +    Read(ml, 1, expect_race); }<br>
> +  void Read2(const MemLoc &ml, bool expect_race = false) {<br>
> +    Read(ml, 2, expect_race); }<br>
> +  void Read4(const MemLoc &ml, bool expect_race = false) {<br>
> +    Read(ml, 4, expect_race); }<br>
> +  void Read8(const MemLoc &ml, bool expect_race = false) {<br>
> +    Read(ml, 8, expect_race); }<br>
> +  void Write1(const MemLoc &ml, bool expect_race = false) {<br>
> +    Write(ml, 1, expect_race); }<br>
> +  void Write2(const MemLoc &ml, bool expect_race = false) {<br>
> +    Write(ml, 2, expect_race); }<br>
> +  void Write4(const MemLoc &ml, bool expect_race = false) {<br>
> +    Write(ml, 4, expect_race); }<br>
> +  void Write8(const MemLoc &ml, bool expect_race = false) {<br>
> +    Write(ml, 8, expect_race); }<br>
> +<br>
> +  void VptrUpdate(const MemLoc &vptr, const MemLoc &new_val,<br>
> +                  bool expect_race = false);<br>
> +<br>
> +  void Call(void(*pc)());<br>
> +  void Return();<br>
> +<br>
> +  void Create(const Mutex &m);<br>
> +  void Destroy(const Mutex &m);<br>
> +  void Lock(const Mutex &m);<br>
> +  bool TryLock(const Mutex &m);<br>
> +  void Unlock(const Mutex &m);<br>
> +  void ReadLock(const Mutex &m);<br>
> +  bool TryReadLock(const Mutex &m);<br>
> +  void ReadUnlock(const Mutex &m);<br>
> +<br>
> +  void Memcpy(void *dst, const void *src, int size, bool expect_race = false);<br>
> +  void Memset(void *dst, int val, int size, bool expect_race = false);<br>
> +<br>
> + private:<br>
> +  struct Impl;<br>
> +  Impl *impl_;<br>
> +  ScopedThread(const ScopedThread&);  // Not implemented.<br>
> +  void operator = (const ScopedThread&);  // Not implemented.<br>
> +};<br>
> +<br>
> +class MainThread : public ScopedThread {<br>
> + public:<br>
> +  MainThread()<br>
> +    : ScopedThread(false, true) {<br>
> +  }<br>
> +};<br>
> +<br>
> +#endif  // #ifndef TSAN_TEST_UTIL_H<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_test_util_linux.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,465 @@<br>
> +<br>
> +//===-- tsan_test_util_linux.cc -------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +// Test utils, linux implementation.<br>
> +//===----------------------------------------------------------------------===//<br>
> +<br>
> +#include "sanitizer_common/sanitizer_atomic.h"<br>
> +#include "tsan_interface.h"<br>
> +#include "tsan_test_util.h"<br>
> +#include "tsan_report.h"<br>
> +<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +#include <assert.h><br>
> +#include <pthread.h><br>
> +#include <stdio.h><br>
> +#include <stdint.h><br>
> +#include <string.h><br>
> +#include <unistd.h><br>
> +#include <errno.h><br>
> +<br>
> +using namespace __tsan;  // NOLINT<br>
> +<br>
> +static __thread bool expect_report;<br>
> +static __thread bool expect_report_reported;<br>
> +static __thread ReportType expect_report_type;<br>
> +<br>
> +extern "C" void *__interceptor_memcpy(void*, const void*, uptr);<br>
> +extern "C" void *__interceptor_memset(void*, int, uptr);<br>
> +<br>
> +static void *BeforeInitThread(void *param) {<br>
> +  (void)param;<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +static void AtExit() {<br>
> +}<br>
> +<br>
> +void TestMutexBeforeInit() {<br>
> +  // Mutexes must be usable before __tsan_init();<br>
> +  pthread_mutex_t mtx = PTHREAD_MUTEX_INITIALIZER;<br>
> +  pthread_mutex_lock(&mtx);<br>
> +  pthread_mutex_unlock(&mtx);<br>
> +  pthread_mutex_destroy(&mtx);<br>
> +  pthread_t thr;<br>
> +  pthread_create(&thr, 0, BeforeInitThread, 0);<br>
> +  pthread_join(thr, 0);<br>
> +  atexit(AtExit);<br>
> +}<br>
> +<br>
> +namespace __tsan {<br>
> +bool OnReport(const ReportDesc *rep, bool suppressed) {<br>
> +  if (expect_report) {<br>
> +    if (rep->typ != expect_report_type) {<br>
> +      printf("Expected report of type %d, got type %d\n",<br>
> +             (int)expect_report_type, (int)rep->typ);<br>
> +      EXPECT_FALSE("Wrong report type");<br>
> +      return false;<br>
> +    }<br>
> +  } else {<br>
> +    EXPECT_FALSE("Unexpected report");<br>
> +    return false;<br>
> +  }<br>
> +  expect_report_reported = true;<br>
> +  return true;<br>
> +}<br>
> +}<br>
> +<br>
> +static void* allocate_addr(int size, int offset_from_aligned = 0) {<br>
> +  static uintptr_t foo;<br>
> +  static atomic_uintptr_t uniq = {(uintptr_t)&foo};  // Some real address.<br>
> +  const int kAlign = 16;<br>
> +  CHECK(offset_from_aligned < kAlign);<br>
> +  size = (size + 2 * kAlign) & ~(kAlign - 1);<br>
> +  uintptr_t addr = atomic_fetch_add(&uniq, size, memory_order_relaxed);<br>
> +  return (void*)(addr + offset_from_aligned);<br>
> +}<br>
> +<br>
> +MemLoc::MemLoc(int offset_from_aligned)<br>
> +  : loc_(allocate_addr(16, offset_from_aligned)) {<br>
> +}<br>
> +<br>
> +MemLoc::~MemLoc() {<br>
> +}<br>
> +<br>
> +Mutex::Mutex(Type type)<br>
> +  : alive_()<br>
> +  , type_(type) {<br>
> +}<br>
> +<br>
> +Mutex::~Mutex() {<br>
> +  CHECK(!alive_);<br>
> +}<br>
> +<br>
> +void Mutex::Init() {<br>
> +  CHECK(!alive_);<br>
> +  alive_ = true;<br>
> +  if (type_ == Normal)<br>
> +    CHECK_EQ(pthread_mutex_init((pthread_mutex_t*)mtx_, 0), 0);<br>
> +  else if (type_ == Spin)<br>
> +    CHECK_EQ(pthread_spin_init((pthread_spinlock_t*)mtx_, 0), 0);<br>
> +  else if (type_ == RW)<br>
> +    CHECK_EQ(pthread_rwlock_init((pthread_rwlock_t*)mtx_, 0), 0);<br>
> +  else<br>
> +    CHECK(0);<br>
> +}<br>
> +<br>
> +void Mutex::StaticInit() {<br>
> +  CHECK(!alive_);<br>
> +  CHECK(type_ == Normal);<br>
> +  alive_ = true;<br>
> +  pthread_mutex_t tmp = PTHREAD_MUTEX_INITIALIZER;<br>
> +  memcpy(mtx_, &tmp, sizeof(tmp));<br>
> +}<br>
> +<br>
> +void Mutex::Destroy() {<br>
> +  CHECK(alive_);<br>
> +  alive_ = false;<br>
> +  if (type_ == Normal)<br>
> +    CHECK_EQ(pthread_mutex_destroy((pthread_mutex_t*)mtx_), 0);<br>
> +  else if (type_ == Spin)<br>
> +    CHECK_EQ(pthread_spin_destroy((pthread_spinlock_t*)mtx_), 0);<br>
> +  else if (type_ == RW)<br>
> +    CHECK_EQ(pthread_rwlock_destroy((pthread_rwlock_t*)mtx_), 0);<br>
> +}<br>
> +<br>
> +void Mutex::Lock() {<br>
> +  CHECK(alive_);<br>
> +  if (type_ == Normal)<br>
> +    CHECK_EQ(pthread_mutex_lock((pthread_mutex_t*)mtx_), 0);<br>
> +  else if (type_ == Spin)<br>
> +    CHECK_EQ(pthread_spin_lock((pthread_spinlock_t*)mtx_), 0);<br>
> +  else if (type_ == RW)<br>
> +    CHECK_EQ(pthread_rwlock_wrlock((pthread_rwlock_t*)mtx_), 0);<br>
> +}<br>
> +<br>
> +bool Mutex::TryLock() {<br>
> +  CHECK(alive_);<br>
> +  if (type_ == Normal)<br>
> +    return pthread_mutex_trylock((pthread_mutex_t*)mtx_) == 0;<br>
> +  else if (type_ == Spin)<br>
> +    return pthread_spin_trylock((pthread_spinlock_t*)mtx_) == 0;<br>
> +  else if (type_ == RW)<br>
> +    return pthread_rwlock_trywrlock((pthread_rwlock_t*)mtx_) == 0;<br>
> +  return false;<br>
> +}<br>
> +<br>
> +void Mutex::Unlock() {<br>
> +  CHECK(alive_);<br>
> +  if (type_ == Normal)<br>
> +    CHECK_EQ(pthread_mutex_unlock((pthread_mutex_t*)mtx_), 0);<br>
> +  else if (type_ == Spin)<br>
> +    CHECK_EQ(pthread_spin_unlock((pthread_spinlock_t*)mtx_), 0);<br>
> +  else if (type_ == RW)<br>
> +    CHECK_EQ(pthread_rwlock_unlock((pthread_rwlock_t*)mtx_), 0);<br>
> +}<br>
> +<br>
> +void Mutex::ReadLock() {<br>
> +  CHECK(alive_);<br>
> +  CHECK(type_ == RW);<br>
> +  CHECK_EQ(pthread_rwlock_rdlock((pthread_rwlock_t*)mtx_), 0);<br>
> +}<br>
> +<br>
> +bool Mutex::TryReadLock() {<br>
> +  CHECK(alive_);<br>
> +  CHECK(type_ == RW);<br>
> +  return pthread_rwlock_tryrdlock((pthread_rwlock_t*)mtx_) ==  0;<br>
> +}<br>
> +<br>
> +void Mutex::ReadUnlock() {<br>
> +  CHECK(alive_);<br>
> +  CHECK(type_ == RW);<br>
> +  CHECK_EQ(pthread_rwlock_unlock((pthread_rwlock_t*)mtx_), 0);<br>
> +}<br>
> +<br>
> +struct Event {<br>
> +  enum Type {<br>
> +    SHUTDOWN,<br>
> +    READ,<br>
> +    WRITE,<br>
> +    VPTR_UPDATE,<br>
> +    CALL,<br>
> +    RETURN,<br>
> +    MUTEX_CREATE,<br>
> +    MUTEX_DESTROY,<br>
> +    MUTEX_LOCK,<br>
> +    MUTEX_TRYLOCK,<br>
> +    MUTEX_UNLOCK,<br>
> +    MUTEX_READLOCK,<br>
> +    MUTEX_TRYREADLOCK,<br>
> +    MUTEX_READUNLOCK,<br>
> +    MEMCPY,<br>
> +    MEMSET<br>
> +  };<br>
> +  Type type;<br>
> +  void *ptr;<br>
> +  uptr arg;<br>
> +  uptr arg2;<br>
> +  bool res;<br>
> +  bool expect_report;<br>
> +  ReportType report_type;<br>
> +<br>
> +  Event(Type type, const void *ptr = 0, uptr arg = 0, uptr arg2 = 0)<br>
> +    : type(type)<br>
> +    , ptr(const_cast<void*>(ptr))<br>
> +    , arg(arg)<br>
> +    , arg2(arg2)<br>
> +    , res()<br>
> +    , expect_report()<br>
> +    , report_type() {<br>
> +  }<br>
> +<br>
> +  void ExpectReport(ReportType type) {<br>
> +    expect_report = true;<br>
> +    report_type = type;<br>
> +  }<br>
> +};<br>
> +<br>
> +struct ScopedThread::Impl {<br>
> +  pthread_t thread;<br>
> +  bool main;<br>
> +  bool detached;<br>
> +  atomic_uintptr_t event;  // Event*<br>
> +<br>
> +  static void *ScopedThreadCallback(void *arg);<br>
> +  void send(Event *ev);<br>
> +  void HandleEvent(Event *ev);<br>
> +};<br>
> +<br>
> +void ScopedThread::Impl::HandleEvent(Event *ev) {<br>
> +  CHECK_EQ(expect_report, false);<br>
> +  expect_report = ev->expect_report;<br>
> +  expect_report_reported = false;<br>
> +  expect_report_type = ev->report_type;<br>
> +  switch (ev->type) {<br>
> +  case Event::READ:<br>
> +  case Event::WRITE: {<br>
> +    void (*tsan_mop)(void *addr) = 0;<br>
> +    if (ev->type == Event::READ) {<br>
> +      switch (ev->arg /*size*/) {<br>
> +        case 1: tsan_mop = __tsan_read1; break;<br>
> +        case 2: tsan_mop = __tsan_read2; break;<br>
> +        case 4: tsan_mop = __tsan_read4; break;<br>
> +        case 8: tsan_mop = __tsan_read8; break;<br>
> +        case 16: tsan_mop = __tsan_read16; break;<br>
> +      }<br>
> +    } else {<br>
> +      switch (ev->arg /*size*/) {<br>
> +        case 1: tsan_mop = __tsan_write1; break;<br>
> +        case 2: tsan_mop = __tsan_write2; break;<br>
> +        case 4: tsan_mop = __tsan_write4; break;<br>
> +        case 8: tsan_mop = __tsan_write8; break;<br>
> +        case 16: tsan_mop = __tsan_write16; break;<br>
> +      }<br>
> +    }<br>
> +    CHECK_NE(tsan_mop, 0);<br>
> +    errno = ECHRNG;<br>
> +    tsan_mop(ev->ptr);<br>
> +    CHECK_EQ(errno, ECHRNG);  // In no case must errno be changed.<br>
> +    break;<br>
> +  }<br>
> +  case Event::VPTR_UPDATE:<br>
> +    __tsan_vptr_update((void**)ev->ptr, (void*)ev->arg);<br>
> +    break;<br>
> +  case Event::CALL:<br>
> +    __tsan_func_entry((void*)((uptr)ev->ptr));<br>
> +    break;<br>
> +  case Event::RETURN:<br>
> +    __tsan_func_exit();<br>
> +    break;<br>
> +  case Event::MUTEX_CREATE:<br>
> +    static_cast<Mutex*>(ev->ptr)->Init();<br>
> +    break;<br>
> +  case Event::MUTEX_DESTROY:<br>
> +    static_cast<Mutex*>(ev->ptr)->Destroy();<br>
> +    break;<br>
> +  case Event::MUTEX_LOCK:<br>
> +    static_cast<Mutex*>(ev->ptr)->Lock();<br>
> +    break;<br>
> +  case Event::MUTEX_TRYLOCK:<br>
> +    ev->res = static_cast<Mutex*>(ev->ptr)->TryLock();<br>
> +    break;<br>
> +  case Event::MUTEX_UNLOCK:<br>
> +    static_cast<Mutex*>(ev->ptr)->Unlock();<br>
> +    break;<br>
> +  case Event::MUTEX_READLOCK:<br>
> +    static_cast<Mutex*>(ev->ptr)->ReadLock();<br>
> +    break;<br>
> +  case Event::MUTEX_TRYREADLOCK:<br>
> +    ev->res = static_cast<Mutex*>(ev->ptr)->TryReadLock();<br>
> +    break;<br>
> +  case Event::MUTEX_READUNLOCK:<br>
> +    static_cast<Mutex*>(ev->ptr)->ReadUnlock();<br>
> +    break;<br>
> +  case Event::MEMCPY:<br>
> +    __interceptor_memcpy(ev->ptr, (void*)ev->arg, ev->arg2);<br>
> +    break;<br>
> +  case Event::MEMSET:<br>
> +    __interceptor_memset(ev->ptr, ev->arg, ev->arg2);<br>
> +    break;<br>
> +  default: CHECK(0);<br>
> +  }<br>
> +  if (expect_report && !expect_report_reported) {<br>
> +    printf("Missed expected report of type %d\n", (int)ev->report_type);<br>
> +    EXPECT_FALSE("Missed expected race");<br>
> +  }<br>
> +  expect_report = false;<br>
> +}<br>
> +<br>
> +void *ScopedThread::Impl::ScopedThreadCallback(void *arg) {<br>
> +  __tsan_func_entry(__builtin_return_address(0));<br>
> +  Impl *impl = (Impl*)arg;<br>
> +  for (;;) {<br>
> +    Event* ev = (Event*)atomic_load(&impl->event, memory_order_acquire);<br>
> +    if (ev == 0) {<br>
> +      pthread_yield();<br>
> +      continue;<br>
> +    }<br>
> +    if (ev->type == Event::SHUTDOWN) {<br>
> +      atomic_store(&impl->event, 0, memory_order_release);<br>
> +      break;<br>
> +    }<br>
> +    impl->HandleEvent(ev);<br>
> +    atomic_store(&impl->event, 0, memory_order_release);<br>
> +  }<br>
> +  __tsan_func_exit();<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +void ScopedThread::Impl::send(Event *e) {<br>
> +  if (main) {<br>
> +    HandleEvent(e);<br>
> +  } else {<br>
> +    CHECK_EQ(atomic_load(&event, memory_order_relaxed), 0);<br>
> +    atomic_store(&event, (uintptr_t)e, memory_order_release);<br>
> +    while (atomic_load(&event, memory_order_acquire) != 0)<br>
> +      pthread_yield();<br>
> +  }<br>
> +}<br>
> +<br>
> +ScopedThread::ScopedThread(bool detached, bool main) {<br>
> +  impl_ = new Impl;<br>
> +  impl_->main = main;<br>
> +  impl_->detached = detached;<br>
> +  atomic_store(&impl_->event, 0, memory_order_relaxed);<br>
> +  if (!main) {<br>
> +    pthread_attr_t attr;<br>
> +    pthread_attr_init(&attr);<br>
> +    pthread_attr_setdetachstate(&attr, detached);<br>
> +    pthread_attr_setstacksize(&attr, 64*1024);<br>
> +    pthread_create(&impl_->thread, &attr,<br>
> +        ScopedThread::Impl::ScopedThreadCallback, impl_);<br>
> +  }<br>
> +}<br>
> +<br>
> +ScopedThread::~ScopedThread() {<br>
> +  if (!impl_->main) {<br>
> +    Event event(Event::SHUTDOWN);<br>
> +    impl_->send(&event);<br>
> +    if (!impl_->detached)<br>
> +      pthread_join(impl_->thread, 0);<br>
> +  }<br>
> +  delete impl_;<br>
> +}<br>
> +<br>
> +void ScopedThread::Detach() {<br>
> +  CHECK(!impl_->main);<br>
> +  CHECK(!impl_->detached);<br>
> +  impl_->detached = true;<br>
> +  pthread_detach(impl_->thread);<br>
> +}<br>
> +<br>
> +void ScopedThread::Access(void *addr, bool is_write,<br>
> +                          int size, bool expect_race) {<br>
> +  Event event(is_write ? Event::WRITE : Event::READ, addr, size);<br>
> +  if (expect_race)<br>
> +    event.ExpectReport(ReportTypeRace);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::VptrUpdate(const MemLoc &vptr,<br>
> +                              const MemLoc &new_val,<br>
> +                              bool expect_race) {<br>
> +  Event event(Event::VPTR_UPDATE, vptr.loc(), (uptr)new_val.loc());<br>
> +  if (expect_race)<br>
> +    event.ExpectReport(ReportTypeRace);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Call(void(*pc)()) {<br>
> +  Event event(Event::CALL, (void*)pc);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Return() {<br>
> +  Event event(Event::RETURN);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Create(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_CREATE, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Destroy(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_DESTROY, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Lock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_LOCK, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +bool ScopedThread::TryLock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_TRYLOCK, &m);<br>
> +  impl_->send(&event);<br>
> +  return event.res;<br>
> +}<br>
> +<br>
> +void ScopedThread::Unlock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_UNLOCK, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::ReadLock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_READLOCK, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +bool ScopedThread::TryReadLock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_TRYREADLOCK, &m);<br>
> +  impl_->send(&event);<br>
> +  return event.res;<br>
> +}<br>
> +<br>
> +void ScopedThread::ReadUnlock(const Mutex &m) {<br>
> +  Event event(Event::MUTEX_READUNLOCK, &m);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Memcpy(void *dst, const void *src, int size,<br>
> +                          bool expect_race) {<br>
> +  Event event(Event::MEMCPY, dst, (uptr)src, size);<br>
> +  if (expect_race)<br>
> +    event.ExpectReport(ReportTypeRace);<br>
> +  impl_->send(&event);<br>
> +}<br>
> +<br>
> +void ScopedThread::Memset(void *dst, int val, int size,<br>
> +                          bool expect_race) {<br>
> +  Event event(Event::MEMSET, dst, val, size);<br>
> +  if (expect_race)<br>
> +    event.ExpectReport(ReportTypeRace);<br>
> +  impl_->send(&event);<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/rtl/tsan_thread.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,59 @@<br>
> +//===-- tsan_thread.cc ----------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_test_util.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +TEST(ThreadSanitizer, ThreadSync) {<br>
> +  MainThread t0;<br>
> +  MemLoc l;<br>
> +  t0.Write1(l);<br>
> +  {<br>
> +    ScopedThread t1;<br>
> +    t1.Write1(l);<br>
> +  }<br>
> +  t0.Write1(l);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, ThreadDetach1) {<br>
> +  ScopedThread t1(true);<br>
> +  MemLoc l;<br>
> +  t1.Write1(l);<br>
> +}<br>
> +<br>
> +TEST(ThreadSanitizer, ThreadDetach2) {<br>
> +  ScopedThread t1;<br>
> +  MemLoc l;<br>
> +  t1.Write1(l);<br>
> +  t1.Detach();<br>
> +}<br>
> +<br>
> +static void *thread_alot_func(void *arg) {<br>
> +  (void)arg;<br>
> +  int usleep(unsigned);<br>
> +  usleep(50);<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(DISABLED_SLOW_ThreadSanitizer, ThreadALot) {<br>
> +  const int kThreads = 70000;<br>
> +  const int kAlive = 1000;<br>
> +  pthread_t threads[kAlive] = {};<br>
> +  for (int i = 0; i < kThreads; i++) {<br>
> +    if (threads[i % kAlive])<br>
> +      pthread_join(threads[i % kAlive], 0);<br>
> +    pthread_create(&threads[i % kAlive], 0, thread_alot_func, 0);<br>
> +  }<br>
> +  for (int i = 0; i < kAlive; i++) {<br>
> +    pthread_join(threads[i], 0);<br>
> +  }<br>
> +}<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/CMakeLists.txt Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,15 @@<br>
> +set(TSAN_UNIT_TESTS<br>
> +  tsan_clock_test.cc<br>
> +  tsan_flags_test.cc<br>
> +  tsan_mman_test.cc<br>
> +  tsan_mutex_test.cc<br>
> +  tsan_platform_test.cc<br>
> +  tsan_printf_test.cc<br>
> +  tsan_shadow_test.cc<br>
> +  tsan_stack_test.cc<br>
> +  tsan_suppressions_test.cc<br>
> +  tsan_sync_test.cc<br>
> +  tsan_vector_test.cc<br>
> +  )<br>
> +<br>
> +add_tsan_unittest(TsanUnitTest ${TSAN_UNIT_TESTS})<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_clock_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,123 @@<br>
> +//===-- tsan_clock_test.cc ------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_clock.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Clock, VectorBasic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadClock clk;<br>
> +  CHECK_EQ(clk.size(), 0);<br>
> +  clk.tick(0);<br>
> +  CHECK_EQ(clk.size(), 1);<br>
> +  CHECK_EQ(clk.get(0), 1);<br>
> +  clk.tick(3);<br>
> +  CHECK_EQ(clk.size(), 4);<br>
> +  CHECK_EQ(clk.get(0), 1);<br>
> +  CHECK_EQ(clk.get(1), 0);<br>
> +  CHECK_EQ(clk.get(2), 0);<br>
> +  CHECK_EQ(clk.get(3), 1);<br>
> +  clk.tick(3);<br>
> +  CHECK_EQ(clk.get(3), 2);<br>
> +}<br>
> +<br>
> +TEST(Clock, ChunkedBasic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadClock vector;<br>
> +  SyncClock chunked;<br>
> +  CHECK_EQ(vector.size(), 0);<br>
> +  CHECK_EQ(chunked.size(), 0);<br>
> +  vector.acquire(&chunked);<br>
> +  CHECK_EQ(vector.size(), 0);<br>
> +  CHECK_EQ(chunked.size(), 0);<br>
> +  vector.release(&chunked);<br>
> +  CHECK_EQ(vector.size(), 0);<br>
> +  CHECK_EQ(chunked.size(), 0);<br>
> +  vector.acq_rel(&chunked);<br>
> +  CHECK_EQ(vector.size(), 0);<br>
> +  CHECK_EQ(chunked.size(), 0);<br>
> +}<br>
> +<br>
> +TEST(Clock, AcquireRelease) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadClock vector1;<br>
> +  vector1.tick(100);<br>
> +  SyncClock chunked;<br>
> +  vector1.release(&chunked);<br>
> +  CHECK_EQ(chunked.size(), 101);<br>
> +  ThreadClock vector2;<br>
> +  vector2.acquire(&chunked);<br>
> +  CHECK_EQ(vector2.size(), 101);<br>
> +  CHECK_EQ(vector2.get(0), 0);<br>
> +  CHECK_EQ(vector2.get(1), 0);<br>
> +  CHECK_EQ(vector2.get(99), 0);<br>
> +  CHECK_EQ(vector2.get(100), 1);<br>
> +}<br>
> +<br>
> +TEST(Clock, ManyThreads) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  SyncClock chunked;<br>
> +  for (int i = 0; i < 100; i++) {<br>
> +    ThreadClock vector;<br>
> +    vector.tick(i);<br>
> +    vector.release(&chunked);<br>
> +    CHECK_EQ(chunked.size(), i + 1);<br>
> +    vector.acquire(&chunked);<br>
> +    CHECK_EQ(vector.size(), i + 1);<br>
> +  }<br>
> +  ThreadClock vector;<br>
> +  vector.acquire(&chunked);<br>
> +  CHECK_EQ(vector.size(), 100);<br>
> +  for (int i = 0; i < 100; i++)<br>
> +    CHECK_EQ(vector.get(i), 1);<br>
> +}<br>
> +<br>
> +TEST(Clock, DifferentSizes) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  {<br>
> +    ThreadClock vector1;<br>
> +    vector1.tick(10);<br>
> +    ThreadClock vector2;<br>
> +    vector2.tick(20);<br>
> +    {<br>
> +      SyncClock chunked;<br>
> +      vector1.release(&chunked);<br>
> +      CHECK_EQ(chunked.size(), 11);<br>
> +      vector2.release(&chunked);<br>
> +      CHECK_EQ(chunked.size(), 21);<br>
> +    }<br>
> +    {<br>
> +      SyncClock chunked;<br>
> +      vector2.release(&chunked);<br>
> +      CHECK_EQ(chunked.size(), 21);<br>
> +      vector1.release(&chunked);<br>
> +      CHECK_EQ(chunked.size(), 21);<br>
> +    }<br>
> +    {<br>
> +      SyncClock chunked;<br>
> +      vector1.release(&chunked);<br>
> +      vector2.acquire(&chunked);<br>
> +      CHECK_EQ(vector2.size(), 21);<br>
> +    }<br>
> +    {<br>
> +      SyncClock chunked;<br>
> +      vector2.release(&chunked);<br>
> +      vector1.acquire(&chunked);<br>
> +      CHECK_EQ(vector1.size(), 21);<br>
> +    }<br>
> +  }<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_flags_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,38 @@<br>
> +//===-- tsan_flags_test.cc ------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_flags.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Flags, Basic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  // At least should not crash.<br>
> +  Flags f = {};<br>
> +  InitializeFlags(&f, 0);<br>
> +  InitializeFlags(&f, "");<br>
> +}<br>
> +<br>
> +TEST(Flags, DefaultValues) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Flags f = {};<br>
> +<br>
> +  f.enable_annotations = false;<br>
> +  f.exitcode = -11;<br>
> +  InitializeFlags(&f, "");<br>
> +  EXPECT_EQ(66, f.exitcode);<br>
> +  EXPECT_EQ(true, f.enable_annotations);<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_mman_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,109 @@<br>
> +//===-- tsan_mman_test.cc -------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_mman.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Mman, Internal) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  char *p = (char*)internal_alloc(MBlockScopedBuf, 10);<br>
> +  EXPECT_NE(p, (char*)0);<br>
> +  char *p2 = (char*)internal_alloc(MBlockScopedBuf, 20);<br>
> +  EXPECT_NE(p2, (char*)0);<br>
> +  EXPECT_NE(p2, p);<br>
> +  for (int i = 0; i < 10; i++) {<br>
> +    p[i] = 42;<br>
> +  }<br>
> +  for (int i = 0; i < 20; i++) {<br>
> +    ((char*)p2)[i] = 42;<br>
> +  }<br>
> +  internal_free(p);<br>
> +  internal_free(p2);<br>
> +}<br>
> +<br>
> +TEST(Mman, User) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadState *thr = cur_thread();<br>
> +  uptr pc = 0;<br>
> +  char *p = (char*)user_alloc(thr, pc, 10);<br>
> +  EXPECT_NE(p, (char*)0);<br>
> +  char *p2 = (char*)user_alloc(thr, pc, 20);<br>
> +  EXPECT_NE(p2, (char*)0);<br>
> +  EXPECT_NE(p2, p);<br>
> +  MBlock *b = user_mblock(thr, p);<br>
> +  EXPECT_NE(b, (MBlock*)0);<br>
> +  EXPECT_EQ(b->size, (uptr)10);<br>
> +  MBlock *b2 = user_mblock(thr, p2);<br>
> +  EXPECT_NE(b2, (MBlock*)0);<br>
> +  EXPECT_EQ(b2->size, (uptr)20);<br>
> +  for (int i = 0; i < 10; i++) {<br>
> +    p[i] = 42;<br>
> +    EXPECT_EQ(b, user_mblock(thr, p + i));<br>
> +  }<br>
> +  for (int i = 0; i < 20; i++) {<br>
> +    ((char*)p2)[i] = 42;<br>
> +    EXPECT_EQ(b2, user_mblock(thr, p2 + i));<br>
> +  }<br>
> +  user_free(thr, pc, p);<br>
> +  user_free(thr, pc, p2);<br>
> +}<br>
> +<br>
> +TEST(Mman, UserRealloc) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadState *thr = cur_thread();<br>
> +  uptr pc = 0;<br>
> +  {<br>
> +    void *p = user_realloc(thr, pc, 0, 0);<br>
> +    // Strictly saying this is incorrect, realloc(NULL, N) is equivalent to<br>
> +    // malloc(N), thus must return non-NULL pointer.<br>
> +    EXPECT_EQ(p, (void*)0);<br>
> +  }<br>
> +  {<br>
> +    void *p = user_realloc(thr, pc, 0, 100);<br>
> +    EXPECT_NE(p, (void*)0);<br>
> +    memset(p, 0xde, 100);<br>
> +    user_free(thr, pc, p);<br>
> +  }<br>
> +  {<br>
> +    void *p = user_alloc(thr, pc, 100);<br>
> +    EXPECT_NE(p, (void*)0);<br>
> +    memset(p, 0xde, 100);<br>
> +    void *p2 = user_realloc(thr, pc, p, 0);<br>
> +    EXPECT_EQ(p2, (void*)0);<br>
> +  }<br>
> +  {<br>
> +    void *p = user_realloc(thr, pc, 0, 100);<br>
> +    EXPECT_NE(p, (void*)0);<br>
> +    memset(p, 0xde, 100);<br>
> +    void *p2 = user_realloc(thr, pc, p, 10000);<br>
> +    EXPECT_NE(p2, (void*)0);<br>
> +    for (int i = 0; i < 100; i++)<br>
> +      EXPECT_EQ(((char*)p2)[i], (char)0xde);<br>
> +    memset(p2, 0xde, 10000);<br>
> +    user_free(thr, pc, p2);<br>
> +  }<br>
> +  {<br>
> +    void *p = user_realloc(thr, pc, 0, 10000);<br>
> +    EXPECT_NE(p, (void*)0);<br>
> +    memset(p, 0xde, 10000);<br>
> +    void *p2 = user_realloc(thr, pc, p, 10);<br>
> +    EXPECT_NE(p2, (void*)0);<br>
> +    for (int i = 0; i < 10; i++)<br>
> +      EXPECT_EQ(((char*)p2)[i], (char)0xde);<br>
> +    user_free(thr, pc, p2);<br>
> +  }<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_mutex_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,126 @@<br>
> +//===-- tsan_mutex_test.cc ------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "sanitizer_common/sanitizer_internal_defs.h"<br>
> +#include "sanitizer_common/sanitizer_atomic.h"<br>
> +#include "sanitizer_common/sanitizer_common.h"<br>
> +#include "sanitizer_common/sanitizer_mutex.h"<br>
> +#include "tsan_mutex.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +template<typename MutexType><br>
> +class TestData {<br>
> + public:<br>
> +  explicit TestData(MutexType *mtx)<br>
> +    : mtx_(mtx) {<br>
> +    for (int i = 0; i < kSize; i++)<br>
> +      data_[i] = 0;<br>
> +  }<br>
> +<br>
> +  void Write() {<br>
> +    Lock l(mtx_);<br>
> +    T v0 = data_[0];<br>
> +    for (int i = 0; i < kSize; i++) {<br>
> +      CHECK_EQ(data_[i], v0);<br>
> +      data_[i]++;<br>
> +    }<br>
> +  }<br>
> +<br>
> +  void Read() {<br>
> +    ReadLock l(mtx_);<br>
> +    T v0 = data_[0];<br>
> +    for (int i = 0; i < kSize; i++) {<br>
> +      CHECK_EQ(data_[i], v0);<br>
> +    }<br>
> +  }<br>
> +<br>
> +  void Backoff() {<br>
> +    volatile T data[kSize] = {};<br>
> +    for (int i = 0; i < kSize; i++) {<br>
> +      data[i]++;<br>
> +      CHECK_EQ(data[i], 1);<br>
> +    }<br>
> +  }<br>
> +<br>
> + private:<br>
> +  typedef GenericScopedLock<MutexType> Lock;<br>
> +  static const int kSize = 64;<br>
> +  typedef u64 T;<br>
> +  MutexType *mtx_;<br>
> +  char pad_[kCacheLineSize];<br>
> +  T data_[kSize];<br>
> +};<br>
> +<br>
> +const int kThreads = 8;<br>
> +const int kWriteRate = 1024;<br>
> +#if TSAN_DEBUG<br>
> +const int kIters = 16*1024;<br>
> +#else<br>
> +const int kIters = 64*1024;<br>
> +#endif<br>
> +<br>
> +template<typename MutexType><br>
> +static void *write_mutex_thread(void *param) {<br>
> +  TestData<MutexType> *data = (TestData<MutexType>*)param;<br>
> +  for (int i = 0; i < kIters; i++) {<br>
> +    data->Write();<br>
> +    data->Backoff();<br>
> +  }<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +template<typename MutexType><br>
> +static void *read_mutex_thread(void *param) {<br>
> +  TestData<MutexType> *data = (TestData<MutexType>*)param;<br>
> +  for (int i = 0; i < kIters; i++) {<br>
> +    if ((i % kWriteRate) == 0)<br>
> +      data->Write();<br>
> +    else<br>
> +      data->Read();<br>
> +    data->Backoff();<br>
> +  }<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(Mutex, Write) {<br>
> +  Mutex mtx(MutexTypeAnnotations, StatMtxAnnotations);<br>
> +  TestData<Mutex> data(&mtx);<br>
> +  pthread_t threads[kThreads];<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_create(&threads[i], 0, write_mutex_thread<Mutex>, &data);<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_join(threads[i], 0);<br>
> +}<br>
> +<br>
> +TEST(Mutex, ReadWrite) {<br>
> +  Mutex mtx(MutexTypeAnnotations, StatMtxAnnotations);<br>
> +  TestData<Mutex> data(&mtx);<br>
> +  pthread_t threads[kThreads];<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_create(&threads[i], 0, read_mutex_thread<Mutex>, &data);<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_join(threads[i], 0);<br>
> +}<br>
> +<br>
> +TEST(Mutex, SpinWrite) {<br>
> +  SpinMutex mtx;<br>
> +  TestData<SpinMutex> data(&mtx);<br>
> +  pthread_t threads[kThreads];<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_create(&threads[i], 0, write_mutex_thread<SpinMutex>, &data);<br>
> +  for (int i = 0; i < kThreads; i++)<br>
> +    pthread_join(threads[i], 0);<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_platform_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,88 @@<br>
> +//===-- tsan_platform_test.cc ---------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "sanitizer_common/sanitizer_libc.h"<br>
> +#include "tsan_platform.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +static void TestThreadInfo(bool main) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  uptr stk_addr = 0;<br>
> +  uptr stk_size = 0;<br>
> +  uptr tls_addr = 0;<br>
> +  uptr tls_size = 0;<br>
> +  GetThreadStackAndTls(main, &stk_addr, &stk_size, &tls_addr, &tls_size);<br>
> +  // Printf("stk=%zx-%zx(%zu)\n", stk_addr, stk_addr + stk_size, stk_size);<br>
> +  // Printf("tls=%zx-%zx(%zu)\n", tls_addr, tls_addr + tls_size, tls_size);<br>
> +<br>
> +  int stack_var;<br>
> +  EXPECT_NE(stk_addr, (uptr)0);<br>
> +  EXPECT_NE(stk_size, (uptr)0);<br>
> +  EXPECT_GT((uptr)&stack_var, stk_addr);<br>
> +  EXPECT_LT((uptr)&stack_var, stk_addr + stk_size);<br>
> +<br>
> +  static __thread int thread_var;<br>
> +  EXPECT_NE(tls_addr, (uptr)0);<br>
> +  EXPECT_NE(tls_size, (uptr)0);<br>
> +  EXPECT_GT((uptr)&thread_var, tls_addr);<br>
> +  EXPECT_LT((uptr)&thread_var, tls_addr + tls_size);<br>
> +<br>
> +  // Ensure that tls and stack do not intersect.<br>
> +  uptr tls_end = tls_addr + tls_size;<br>
> +  EXPECT_TRUE(tls_addr < stk_addr || tls_addr >= stk_addr + stk_size);<br>
> +  EXPECT_TRUE(tls_end  < stk_addr || tls_end  >=  stk_addr + stk_size);<br>
> +  EXPECT_TRUE((tls_addr < stk_addr) == (tls_end  < stk_addr));<br>
> +}<br>
> +<br>
> +static void *WorkerThread(void *arg) {<br>
> +  TestThreadInfo(false);<br>
> +  return 0;<br>
> +}<br>
> +<br>
> +TEST(Platform, ThreadInfoMain) {<br>
> +  TestThreadInfo(true);<br>
> +}<br>
> +<br>
> +TEST(Platform, ThreadInfoWorker) {<br>
> +  pthread_t t;<br>
> +  pthread_create(&t, 0, WorkerThread, 0);<br>
> +  pthread_join(t, 0);<br>
> +}<br>
> +<br>
> +TEST(Platform, FileOps) {<br>
> +  const char *str1 = "qwerty";<br>
> +  uptr len1 = internal_strlen(str1);<br>
> +  const char *str2 = "zxcv";<br>
> +  uptr len2 = internal_strlen(str2);<br>
> +<br>
> +  fd_t fd = internal_open("./tsan_test.tmp", true);<br>
> +  EXPECT_NE(fd, kInvalidFd);<br>
> +  EXPECT_EQ(len1, internal_write(fd, str1, len1));<br>
> +  EXPECT_EQ(len2, internal_write(fd, str2, len2));<br>
> +  internal_close(fd);<br>
> +<br>
> +  fd = internal_open("./tsan_test.tmp", false);<br>
> +  EXPECT_NE(fd, kInvalidFd);<br>
> +  EXPECT_EQ(len1 + len2, internal_filesize(fd));<br>
> +  char buf[64] = {};<br>
> +  EXPECT_EQ(len1, internal_read(fd, buf, len1));<br>
> +  EXPECT_EQ(0, internal_memcmp(buf, str1, len1));<br>
> +  EXPECT_EQ((char)0, buf[len1 + 1]);<br>
> +  internal_memset(buf, 0, len1);<br>
> +  EXPECT_EQ(len2, internal_read(fd, buf, len2));<br>
> +  EXPECT_EQ(0, internal_memcmp(buf, str2, len2));<br>
> +  internal_close(fd);<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_printf_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,106 @@<br>
> +//===-- tsan_printf_test.cc -----------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +#include <string.h><br>
> +#include <limits.h><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Printf, Basic) {<br>
> +  char buf[1024];<br>
> +  uptr len = internal_snprintf(buf, sizeof(buf),<br>
> +      "a%db%zdc%ue%zuf%xh%zxq%pe%sr",<br>
> +      (int)-1, (long)-2, // NOLINT<br>
> +      (unsigned)-4, (unsigned long)5, // NOLINT<br>
> +      (unsigned)10, (unsigned long)11, // NOLINT<br>
> +      (void*)0x123, "_string_");<br>
> +  EXPECT_EQ(len, strlen(buf));<br>
> +  EXPECT_EQ(0, strcmp(buf, "a-1b-2c4294967292e5fahbq"<br>
> +                           "0x000000000123e_string_r"));<br>
> +}<br>
> +<br>
> +TEST(Printf, OverflowStr) {<br>
> +  char buf[] = "123456789";<br>
> +  uptr len = internal_snprintf(buf, 4, "%s", "abcdef");  // NOLINT<br>
> +  EXPECT_EQ(len, (uptr)6);<br>
> +  EXPECT_EQ(0, strcmp(buf, "abc"));<br>
> +  EXPECT_EQ(buf[3], 0);<br>
> +  EXPECT_EQ(buf[4], '5');<br>
> +  EXPECT_EQ(buf[5], '6');<br>
> +  EXPECT_EQ(buf[6], '7');<br>
> +  EXPECT_EQ(buf[7], '8');<br>
> +  EXPECT_EQ(buf[8], '9');<br>
> +  EXPECT_EQ(buf[9], 0);<br>
> +}<br>
> +<br>
> +TEST(Printf, OverflowInt) {<br>
> +  char buf[] = "123456789";<br>
> +  internal_snprintf(buf, 4, "%d", -123456789);  // NOLINT<br>
> +  EXPECT_EQ(0, strcmp(buf, "-12"));<br>
> +  EXPECT_EQ(buf[3], 0);<br>
> +  EXPECT_EQ(buf[4], '5');<br>
> +  EXPECT_EQ(buf[5], '6');<br>
> +  EXPECT_EQ(buf[6], '7');<br>
> +  EXPECT_EQ(buf[7], '8');<br>
> +  EXPECT_EQ(buf[8], '9');<br>
> +  EXPECT_EQ(buf[9], 0);<br>
> +}<br>
> +<br>
> +TEST(Printf, OverflowUint) {<br>
> +  char buf[] = "123456789";<br>
> +  internal_snprintf(buf, 4, "a%zx", (unsigned long)0x123456789);  // NOLINT<br>
> +  EXPECT_EQ(0, strcmp(buf, "a12"));<br>
> +  EXPECT_EQ(buf[3], 0);<br>
> +  EXPECT_EQ(buf[4], '5');<br>
> +  EXPECT_EQ(buf[5], '6');<br>
> +  EXPECT_EQ(buf[6], '7');<br>
> +  EXPECT_EQ(buf[7], '8');<br>
> +  EXPECT_EQ(buf[8], '9');<br>
> +  EXPECT_EQ(buf[9], 0);<br>
> +}<br>
> +<br>
> +TEST(Printf, OverflowPtr) {<br>
> +  char buf[] = "123456789";<br>
> +  internal_snprintf(buf, 4, "%p", (void*)0x123456789);  // NOLINT<br>
> +  EXPECT_EQ(0, strcmp(buf, "0x0"));<br>
> +  EXPECT_EQ(buf[3], 0);<br>
> +  EXPECT_EQ(buf[4], '5');<br>
> +  EXPECT_EQ(buf[5], '6');<br>
> +  EXPECT_EQ(buf[6], '7');<br>
> +  EXPECT_EQ(buf[7], '8');<br>
> +  EXPECT_EQ(buf[8], '9');<br>
> +  EXPECT_EQ(buf[9], 0);<br>
> +}<br>
> +<br>
> +template<typename T><br>
> +static void TestMinMax(const char *fmt, T min, T max) {<br>
> +  char buf[1024];<br>
> +  uptr len = internal_snprintf(buf, sizeof(buf), fmt, min, max);<br>
> +  char buf2[1024];<br>
> +  snprintf(buf2, sizeof(buf2), fmt, min, max);<br>
> +  EXPECT_EQ(len, strlen(buf));<br>
> +  EXPECT_EQ(0, strcmp(buf, buf2));<br>
> +}<br>
> +<br>
> +TEST(Printf, MinMax) {<br>
> +  TestMinMax<int>("%d-%d", INT_MIN, INT_MAX);  // NOLINT<br>
> +  TestMinMax<long>("%zd-%zd", LONG_MIN, LONG_MAX);  // NOLINT<br>
> +  TestMinMax<unsigned>("%u-%u", 0, UINT_MAX);  // NOLINT<br>
> +  TestMinMax<unsigned long>("%zu-%zu", 0, ULONG_MAX);  // NOLINT<br>
> +  TestMinMax<unsigned>("%x-%x", 0, UINT_MAX);  // NOLINT<br>
> +  TestMinMax<unsigned long>("%zx-%zx", 0, ULONG_MAX);  // NOLINT<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_shadow_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,47 @@<br>
> +//===-- tsan_shadow_test.cc -----------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_platform.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Shadow, Mapping) {<br>
> +  static int global;<br>
> +  int stack;<br>
> +  void *heap = malloc(0);<br>
> +  free(heap);<br>
> +<br>
> +  CHECK(IsAppMem((uptr)&global));<br>
> +  CHECK(IsAppMem((uptr)&stack));<br>
> +  CHECK(IsAppMem((uptr)heap));<br>
> +<br>
> +  CHECK(IsShadowMem(MemToShadow((uptr)&global)));<br>
> +  CHECK(IsShadowMem(MemToShadow((uptr)&stack)));<br>
> +  CHECK(IsShadowMem(MemToShadow((uptr)heap)));<br>
> +}<br>
> +<br>
> +TEST(Shadow, Celling) {<br>
> +  u64 aligned_data[4];<br>
> +  char *data = (char*)aligned_data;<br>
> +  CHECK_EQ((uptr)data % kShadowSize, 0);<br>
> +  uptr s0 = MemToShadow((uptr)&data[0]);<br>
> +  CHECK_EQ(s0 % kShadowSize, 0);<br>
> +  for (unsigned i = 1; i < kShadowCell; i++)<br>
> +    CHECK_EQ(s0, MemToShadow((uptr)&data[i]));<br>
> +  for (unsigned i = kShadowCell; i < 2*kShadowCell; i++)<br>
> +    CHECK_EQ(s0 + kShadowSize*kShadowCnt, MemToShadow((uptr)&data[i]));<br>
> +  for (unsigned i = 2*kShadowCell; i < 3*kShadowCell; i++)<br>
> +    CHECK_EQ(s0 + 2*kShadowSize*kShadowCnt, MemToShadow((uptr)&data[i]));<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_stack_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,80 @@<br>
> +//===-- tsan_stack_test.cc ------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_sync.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +#include <string.h><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +static void TestStackTrace(StackTrace *trace) {<br>
> +  ThreadState thr(0, 0, 0, 0, 0, 0, 0, 0);<br>
> +<br>
> +  trace->ObtainCurrent(&thr, 0);<br>
> +  EXPECT_EQ(trace->Size(), (uptr)0);<br>
> +<br>
> +  trace->ObtainCurrent(&thr, 42);<br>
> +  EXPECT_EQ(trace->Size(), (uptr)1);<br>
> +  EXPECT_EQ(trace->Get(0), (uptr)42);<br>
> +<br>
> +  *thr.shadow_stack_pos++ = 100;<br>
> +  *thr.shadow_stack_pos++ = 101;<br>
> +  trace->ObtainCurrent(&thr, 0);<br>
> +  EXPECT_EQ(trace->Size(), (uptr)2);<br>
> +  EXPECT_EQ(trace->Get(0), (uptr)100);<br>
> +  EXPECT_EQ(trace->Get(1), (uptr)101);<br>
> +<br>
> +  trace->ObtainCurrent(&thr, 42);<br>
> +  EXPECT_EQ(trace->Size(), (uptr)3);<br>
> +  EXPECT_EQ(trace->Get(0), (uptr)100);<br>
> +  EXPECT_EQ(trace->Get(1), (uptr)101);<br>
> +  EXPECT_EQ(trace->Get(2), (uptr)42);<br>
> +}<br>
> +<br>
> +TEST(StackTrace, Basic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  StackTrace trace;<br>
> +  TestStackTrace(&trace);<br>
> +}<br>
> +<br>
> +TEST(StackTrace, StaticBasic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  uptr buf[10];<br>
> +  StackTrace trace1(buf, 10);<br>
> +  TestStackTrace(&trace1);<br>
> +  StackTrace trace2(buf, 3);<br>
> +  TestStackTrace(&trace2);<br>
> +}<br>
> +<br>
> +TEST(StackTrace, StaticTrim) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  uptr buf[2];<br>
> +  StackTrace trace(buf, 2);<br>
> +  ThreadState thr(0, 0, 0, 0, 0, 0, 0, 0);<br>
> +<br>
> +  *thr.shadow_stack_pos++ = 100;<br>
> +  *thr.shadow_stack_pos++ = 101;<br>
> +  *thr.shadow_stack_pos++ = 102;<br>
> +  trace.ObtainCurrent(&thr, 0);<br>
> +  EXPECT_EQ(trace.Size(), (uptr)2);<br>
> +  EXPECT_EQ(trace.Get(0), (uptr)101);<br>
> +  EXPECT_EQ(trace.Get(1), (uptr)102);<br>
> +<br>
> +  trace.ObtainCurrent(&thr, 42);<br>
> +  EXPECT_EQ(trace.Size(), (uptr)2);<br>
> +  EXPECT_EQ(trace.Get(0), (uptr)102);<br>
> +  EXPECT_EQ(trace.Get(1), (uptr)42);<br>
> +}<br>
> +<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_suppressions_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,128 @@<br>
> +//===-- tsan_suppressions_test.cc -----------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_suppressions.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +#include <string.h><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Suppressions, Parse) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Suppression *supp0 = SuppressionParse(<br>
> +    "race:foo\n"<br>
> +    "  race:bar\n"  // NOLINT<br>
> +    "race:baz   \n"  // NOLINT<br>
> +    "# a comment\n"<br>
> +    "race:quz\n"<br>
> +  );  // NOLINT<br>
> +  Suppression *supp = supp0;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "quz"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "baz"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ((Suppression*)0, supp);<br>
> +}<br>
> +<br>
> +TEST(Suppressions, Parse2) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Suppression *supp0 = SuppressionParse(<br>
> +    "          # first line comment\n"  // NOLINT<br>
> +    "  race:bar        \n"  // NOLINT<br>
> +    "race:baz* *baz\n"<br>
> +    "# a comment\n"<br>
> +    "# last line comment\n"<br>
> +  );  // NOLINT<br>
> +  Suppression *supp = supp0;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "baz* *baz"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ((Suppression*)0, supp);<br>
> +}<br>
> +<br>
> +TEST(Suppressions, Parse3) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Suppression *supp0 = SuppressionParse(<br>
> +    "# last suppression w/o line-feed\n"<br>
> +    "race:foo\n"<br>
> +    "race:bar"<br>
> +  );  // NOLINT<br>
> +  Suppression *supp = supp0;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ((Suppression*)0, supp);<br>
> +}<br>
> +<br>
> +TEST(Suppressions, ParseType) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Suppression *supp0 = SuppressionParse(<br>
> +    "race:foo\n"<br>
> +    "thread:bar\n"<br>
> +    "mutex:baz\n"<br>
> +    "signal:quz\n"<br>
> +  );  // NOLINT<br>
> +  Suppression *supp = supp0;<br>
> +  EXPECT_EQ(supp->type, SuppressionSignal);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "quz"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionMutex);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "baz"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionThread);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ(supp->type, SuppressionRace);<br>
> +  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> +  supp = supp->next;<br>
> +  EXPECT_EQ((Suppression*)0, supp);<br>
> +}<br>
> +<br>
> +static bool MyMatch(const char *templ, const char *func) {<br>
> +  char tmp[1024];<br>
> +  strcpy(tmp, templ);  // NOLINT<br>
> +  return SuppressionMatch(tmp, func);<br>
> +}<br>
> +<br>
> +TEST(Suppressions, Match) {<br>
> +  EXPECT_TRUE(MyMatch("foobar", "foobar"));<br>
> +  EXPECT_TRUE(MyMatch("foobar", "prefix_foobar_postfix"));<br>
> +  EXPECT_TRUE(MyMatch("*foobar*", "prefix_foobar_postfix"));<br>
> +  EXPECT_TRUE(MyMatch("foo*bar", "foo_middle_bar"));<br>
> +  EXPECT_TRUE(MyMatch("foo*bar", "foobar"));<br>
> +  EXPECT_TRUE(MyMatch("foo*bar*baz", "foo_middle_bar_another_baz"));<br>
> +  EXPECT_TRUE(MyMatch("foo*bar*baz", "foo_middle_barbaz"));<br>
> +<br>
> +  EXPECT_FALSE(MyMatch("foo", "baz"));<br>
> +  EXPECT_FALSE(MyMatch("foobarbaz", "foobar"));<br>
> +  EXPECT_FALSE(MyMatch("foobarbaz", "barbaz"));<br>
> +  EXPECT_FALSE(MyMatch("foo*bar", "foobaz"));<br>
> +  EXPECT_FALSE(MyMatch("foo*bar", "foo_baz"));<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_sync_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,65 @@<br>
> +//===-- tsan_sync_test.cc -------------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_sync.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "tsan_mman.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +#include <stdlib.h><br>
> +#include <stdint.h><br>
> +#include <map><br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Sync, Table) {<br>
> +  const uintptr_t kIters = 512*1024;<br>
> +  const uintptr_t kRange = 10000;<br>
> +<br>
> +  ScopedInRtl in_rtl;<br>
> +  ThreadState *thr = cur_thread();<br>
> +  uptr pc = 0;<br>
> +<br>
> +  SyncTab tab;<br>
> +  SyncVar *golden[kRange] = {};<br>
> +  unsigned seed = 0;<br>
> +  for (uintptr_t i = 0; i < kIters; i++) {<br>
> +    uintptr_t addr = rand_r(&seed) % (kRange - 1) + 1;<br>
> +    if (rand_r(&seed) % 2) {<br>
> +      // Get or add.<br>
> +      SyncVar *v = tab.GetAndLock(thr, pc, addr, true);<br>
> +      EXPECT_TRUE(golden[addr] == 0 || golden[addr] == v);<br>
> +      EXPECT_EQ(v->addr, addr);<br>
> +      golden[addr] = v;<br>
> +      v->mtx.Unlock();<br>
> +    } else {<br>
> +      // Remove.<br>
> +      SyncVar *v = tab.GetAndRemove(thr, pc, addr);<br>
> +      EXPECT_EQ(golden[addr], v);<br>
> +      if (v) {<br>
> +        EXPECT_EQ(v->addr, addr);<br>
> +        golden[addr] = 0;<br>
> +        DestroyAndFree(v);<br>
> +      }<br>
> +    }<br>
> +  }<br>
> +  for (uintptr_t addr = 0; addr < kRange; addr++) {<br>
> +    if (golden[addr] == 0)<br>
> +      continue;<br>
> +    SyncVar *v = tab.GetAndRemove(thr, pc, addr);<br>
> +    EXPECT_EQ(v, golden[addr]);<br>
> +    EXPECT_EQ(v->addr, addr);<br>
> +    DestroyAndFree(v);<br>
> +  }<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Added: compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc?rev=164022&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc?rev=164022&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc (added)<br>
> +++ compiler-rt/trunk/lib/tsan/tests/unit/tsan_vector_test.cc Mon Sep 17 05:02:17 2012<br>
> @@ -0,0 +1,45 @@<br>
> +//===-- tsan_vector_test.cc -----------------------------------------------===//<br>
> +//<br>
> +//                     The LLVM Compiler Infrastructure<br>
> +//<br>
> +// This file is distributed under the University of Illinois Open Source<br>
> +// License. See LICENSE.TXT for details.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +//<br>
> +// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> +//<br>
> +//===----------------------------------------------------------------------===//<br>
> +#include "tsan_vector.h"<br>
> +#include "tsan_rtl.h"<br>
> +#include "gtest/gtest.h"<br>
> +<br>
> +namespace __tsan {<br>
> +<br>
> +TEST(Vector, Basic) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Vector<int> v(MBlockScopedBuf);<br>
> +  EXPECT_EQ(v.Size(), (uptr)0);<br>
> +  v.PushBack(42);<br>
> +  EXPECT_EQ(v.Size(), (uptr)1);<br>
> +  EXPECT_EQ(v[0], 42);<br>
> +  v.PushBack(43);<br>
> +  EXPECT_EQ(v.Size(), (uptr)2);<br>
> +  EXPECT_EQ(v[0], 42);<br>
> +  EXPECT_EQ(v[1], 43);<br>
> +}<br>
> +<br>
> +TEST(Vector, Stride) {<br>
> +  ScopedInRtl in_rtl;<br>
> +  Vector<int> v(MBlockScopedBuf);<br>
> +  for (int i = 0; i < 1000; i++) {<br>
> +    v.PushBack(i);<br>
> +    EXPECT_EQ(v.Size(), (uptr)(i + 1));<br>
> +    EXPECT_EQ(v[i], i);<br>
> +  }<br>
> +  for (int i = 0; i < 1000; i++) {<br>
> +    EXPECT_EQ(v[i], i);<br>
> +  }<br>
> +}<br>
> +<br>
> +}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/CMakeLists.txt (removed)<br>
> @@ -1,15 +0,0 @@<br>
> -set(TSAN_UNIT_TESTS<br>
> -  tsan_clock_test.cc<br>
> -  tsan_flags_test.cc<br>
> -  tsan_mman_test.cc<br>
> -  tsan_mutex_test.cc<br>
> -  tsan_platform_test.cc<br>
> -  tsan_printf_test.cc<br>
> -  tsan_shadow_test.cc<br>
> -  tsan_stack_test.cc<br>
> -  tsan_suppressions_test.cc<br>
> -  tsan_sync_test.cc<br>
> -  tsan_vector_test.cc<br>
> -  )<br>
> -<br>
> -add_tsan_unittest(TsanUnitTest ${TSAN_UNIT_TESTS})<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_clock_test.cc (removed)<br>
> @@ -1,123 +0,0 @@<br>
> -//===-- tsan_clock_test.cc ------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_clock.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Clock, VectorBasic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadClock clk;<br>
> -  CHECK_EQ(clk.size(), 0);<br>
> -  clk.tick(0);<br>
> -  CHECK_EQ(clk.size(), 1);<br>
> -  CHECK_EQ(clk.get(0), 1);<br>
> -  clk.tick(3);<br>
> -  CHECK_EQ(clk.size(), 4);<br>
> -  CHECK_EQ(clk.get(0), 1);<br>
> -  CHECK_EQ(clk.get(1), 0);<br>
> -  CHECK_EQ(clk.get(2), 0);<br>
> -  CHECK_EQ(clk.get(3), 1);<br>
> -  clk.tick(3);<br>
> -  CHECK_EQ(clk.get(3), 2);<br>
> -}<br>
> -<br>
> -TEST(Clock, ChunkedBasic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadClock vector;<br>
> -  SyncClock chunked;<br>
> -  CHECK_EQ(vector.size(), 0);<br>
> -  CHECK_EQ(chunked.size(), 0);<br>
> -  vector.acquire(&chunked);<br>
> -  CHECK_EQ(vector.size(), 0);<br>
> -  CHECK_EQ(chunked.size(), 0);<br>
> -  vector.release(&chunked);<br>
> -  CHECK_EQ(vector.size(), 0);<br>
> -  CHECK_EQ(chunked.size(), 0);<br>
> -  vector.acq_rel(&chunked);<br>
> -  CHECK_EQ(vector.size(), 0);<br>
> -  CHECK_EQ(chunked.size(), 0);<br>
> -}<br>
> -<br>
> -TEST(Clock, AcquireRelease) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadClock vector1;<br>
> -  vector1.tick(100);<br>
> -  SyncClock chunked;<br>
> -  vector1.release(&chunked);<br>
> -  CHECK_EQ(chunked.size(), 101);<br>
> -  ThreadClock vector2;<br>
> -  vector2.acquire(&chunked);<br>
> -  CHECK_EQ(vector2.size(), 101);<br>
> -  CHECK_EQ(vector2.get(0), 0);<br>
> -  CHECK_EQ(vector2.get(1), 0);<br>
> -  CHECK_EQ(vector2.get(99), 0);<br>
> -  CHECK_EQ(vector2.get(100), 1);<br>
> -}<br>
> -<br>
> -TEST(Clock, ManyThreads) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  SyncClock chunked;<br>
> -  for (int i = 0; i < 100; i++) {<br>
> -    ThreadClock vector;<br>
> -    vector.tick(i);<br>
> -    vector.release(&chunked);<br>
> -    CHECK_EQ(chunked.size(), i + 1);<br>
> -    vector.acquire(&chunked);<br>
> -    CHECK_EQ(vector.size(), i + 1);<br>
> -  }<br>
> -  ThreadClock vector;<br>
> -  vector.acquire(&chunked);<br>
> -  CHECK_EQ(vector.size(), 100);<br>
> -  for (int i = 0; i < 100; i++)<br>
> -    CHECK_EQ(vector.get(i), 1);<br>
> -}<br>
> -<br>
> -TEST(Clock, DifferentSizes) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  {<br>
> -    ThreadClock vector1;<br>
> -    vector1.tick(10);<br>
> -    ThreadClock vector2;<br>
> -    vector2.tick(20);<br>
> -    {<br>
> -      SyncClock chunked;<br>
> -      vector1.release(&chunked);<br>
> -      CHECK_EQ(chunked.size(), 11);<br>
> -      vector2.release(&chunked);<br>
> -      CHECK_EQ(chunked.size(), 21);<br>
> -    }<br>
> -    {<br>
> -      SyncClock chunked;<br>
> -      vector2.release(&chunked);<br>
> -      CHECK_EQ(chunked.size(), 21);<br>
> -      vector1.release(&chunked);<br>
> -      CHECK_EQ(chunked.size(), 21);<br>
> -    }<br>
> -    {<br>
> -      SyncClock chunked;<br>
> -      vector1.release(&chunked);<br>
> -      vector2.acquire(&chunked);<br>
> -      CHECK_EQ(vector2.size(), 21);<br>
> -    }<br>
> -    {<br>
> -      SyncClock chunked;<br>
> -      vector2.release(&chunked);<br>
> -      vector1.acquire(&chunked);<br>
> -      CHECK_EQ(vector1.size(), 21);<br>
> -    }<br>
> -  }<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_flags_test.cc (removed)<br>
> @@ -1,38 +0,0 @@<br>
> -//===-- tsan_flags_test.cc ------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_flags.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Flags, Basic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  // At least should not crash.<br>
> -  Flags f = {};<br>
> -  InitializeFlags(&f, 0);<br>
> -  InitializeFlags(&f, "");<br>
> -}<br>
> -<br>
> -TEST(Flags, DefaultValues) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Flags f = {};<br>
> -<br>
> -  f.enable_annotations = false;<br>
> -  f.exitcode = -11;<br>
> -  InitializeFlags(&f, "");<br>
> -  EXPECT_EQ(66, f.exitcode);<br>
> -  EXPECT_EQ(true, f.enable_annotations);<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_mman_test.cc (removed)<br>
> @@ -1,109 +0,0 @@<br>
> -//===-- tsan_mman_test.cc -------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_mman.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Mman, Internal) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  char *p = (char*)internal_alloc(MBlockScopedBuf, 10);<br>
> -  EXPECT_NE(p, (char*)0);<br>
> -  char *p2 = (char*)internal_alloc(MBlockScopedBuf, 20);<br>
> -  EXPECT_NE(p2, (char*)0);<br>
> -  EXPECT_NE(p2, p);<br>
> -  for (int i = 0; i < 10; i++) {<br>
> -    p[i] = 42;<br>
> -  }<br>
> -  for (int i = 0; i < 20; i++) {<br>
> -    ((char*)p2)[i] = 42;<br>
> -  }<br>
> -  internal_free(p);<br>
> -  internal_free(p2);<br>
> -}<br>
> -<br>
> -TEST(Mman, User) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadState *thr = cur_thread();<br>
> -  uptr pc = 0;<br>
> -  char *p = (char*)user_alloc(thr, pc, 10);<br>
> -  EXPECT_NE(p, (char*)0);<br>
> -  char *p2 = (char*)user_alloc(thr, pc, 20);<br>
> -  EXPECT_NE(p2, (char*)0);<br>
> -  EXPECT_NE(p2, p);<br>
> -  MBlock *b = user_mblock(thr, p);<br>
> -  EXPECT_NE(b, (MBlock*)0);<br>
> -  EXPECT_EQ(b->size, (uptr)10);<br>
> -  MBlock *b2 = user_mblock(thr, p2);<br>
> -  EXPECT_NE(b2, (MBlock*)0);<br>
> -  EXPECT_EQ(b2->size, (uptr)20);<br>
> -  for (int i = 0; i < 10; i++) {<br>
> -    p[i] = 42;<br>
> -    EXPECT_EQ(b, user_mblock(thr, p + i));<br>
> -  }<br>
> -  for (int i = 0; i < 20; i++) {<br>
> -    ((char*)p2)[i] = 42;<br>
> -    EXPECT_EQ(b2, user_mblock(thr, p2 + i));<br>
> -  }<br>
> -  user_free(thr, pc, p);<br>
> -  user_free(thr, pc, p2);<br>
> -}<br>
> -<br>
> -TEST(Mman, UserRealloc) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadState *thr = cur_thread();<br>
> -  uptr pc = 0;<br>
> -  {<br>
> -    void *p = user_realloc(thr, pc, 0, 0);<br>
> -    // Strictly saying this is incorrect, realloc(NULL, N) is equivalent to<br>
> -    // malloc(N), thus must return non-NULL pointer.<br>
> -    EXPECT_EQ(p, (void*)0);<br>
> -  }<br>
> -  {<br>
> -    void *p = user_realloc(thr, pc, 0, 100);<br>
> -    EXPECT_NE(p, (void*)0);<br>
> -    memset(p, 0xde, 100);<br>
> -    user_free(thr, pc, p);<br>
> -  }<br>
> -  {<br>
> -    void *p = user_alloc(thr, pc, 100);<br>
> -    EXPECT_NE(p, (void*)0);<br>
> -    memset(p, 0xde, 100);<br>
> -    void *p2 = user_realloc(thr, pc, p, 0);<br>
> -    EXPECT_EQ(p2, (void*)0);<br>
> -  }<br>
> -  {<br>
> -    void *p = user_realloc(thr, pc, 0, 100);<br>
> -    EXPECT_NE(p, (void*)0);<br>
> -    memset(p, 0xde, 100);<br>
> -    void *p2 = user_realloc(thr, pc, p, 10000);<br>
> -    EXPECT_NE(p2, (void*)0);<br>
> -    for (int i = 0; i < 100; i++)<br>
> -      EXPECT_EQ(((char*)p2)[i], (char)0xde);<br>
> -    memset(p2, 0xde, 10000);<br>
> -    user_free(thr, pc, p2);<br>
> -  }<br>
> -  {<br>
> -    void *p = user_realloc(thr, pc, 0, 10000);<br>
> -    EXPECT_NE(p, (void*)0);<br>
> -    memset(p, 0xde, 10000);<br>
> -    void *p2 = user_realloc(thr, pc, p, 10);<br>
> -    EXPECT_NE(p2, (void*)0);<br>
> -    for (int i = 0; i < 10; i++)<br>
> -      EXPECT_EQ(((char*)p2)[i], (char)0xde);<br>
> -    user_free(thr, pc, p2);<br>
> -  }<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_mutex_test.cc (removed)<br>
> @@ -1,126 +0,0 @@<br>
> -//===-- tsan_mutex_test.cc ------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "sanitizer_common/sanitizer_internal_defs.h"<br>
> -#include "sanitizer_common/sanitizer_atomic.h"<br>
> -#include "sanitizer_common/sanitizer_common.h"<br>
> -#include "sanitizer_common/sanitizer_mutex.h"<br>
> -#include "tsan_mutex.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -template<typename MutexType><br>
> -class TestData {<br>
> - public:<br>
> -  explicit TestData(MutexType *mtx)<br>
> -    : mtx_(mtx) {<br>
> -    for (int i = 0; i < kSize; i++)<br>
> -      data_[i] = 0;<br>
> -  }<br>
> -<br>
> -  void Write() {<br>
> -    Lock l(mtx_);<br>
> -    T v0 = data_[0];<br>
> -    for (int i = 0; i < kSize; i++) {<br>
> -      CHECK_EQ(data_[i], v0);<br>
> -      data_[i]++;<br>
> -    }<br>
> -  }<br>
> -<br>
> -  void Read() {<br>
> -    ReadLock l(mtx_);<br>
> -    T v0 = data_[0];<br>
> -    for (int i = 0; i < kSize; i++) {<br>
> -      CHECK_EQ(data_[i], v0);<br>
> -    }<br>
> -  }<br>
> -<br>
> -  void Backoff() {<br>
> -    volatile T data[kSize] = {};<br>
> -    for (int i = 0; i < kSize; i++) {<br>
> -      data[i]++;<br>
> -      CHECK_EQ(data[i], 1);<br>
> -    }<br>
> -  }<br>
> -<br>
> - private:<br>
> -  typedef GenericScopedLock<MutexType> Lock;<br>
> -  static const int kSize = 64;<br>
> -  typedef u64 T;<br>
> -  MutexType *mtx_;<br>
> -  char pad_[kCacheLineSize];<br>
> -  T data_[kSize];<br>
> -};<br>
> -<br>
> -const int kThreads = 8;<br>
> -const int kWriteRate = 1024;<br>
> -#if TSAN_DEBUG<br>
> -const int kIters = 16*1024;<br>
> -#else<br>
> -const int kIters = 64*1024;<br>
> -#endif<br>
> -<br>
> -template<typename MutexType><br>
> -static void *write_mutex_thread(void *param) {<br>
> -  TestData<MutexType> *data = (TestData<MutexType>*)param;<br>
> -  for (int i = 0; i < kIters; i++) {<br>
> -    data->Write();<br>
> -    data->Backoff();<br>
> -  }<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -template<typename MutexType><br>
> -static void *read_mutex_thread(void *param) {<br>
> -  TestData<MutexType> *data = (TestData<MutexType>*)param;<br>
> -  for (int i = 0; i < kIters; i++) {<br>
> -    if ((i % kWriteRate) == 0)<br>
> -      data->Write();<br>
> -    else<br>
> -      data->Read();<br>
> -    data->Backoff();<br>
> -  }<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(Mutex, Write) {<br>
> -  Mutex mtx(MutexTypeAnnotations, StatMtxAnnotations);<br>
> -  TestData<Mutex> data(&mtx);<br>
> -  pthread_t threads[kThreads];<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_create(&threads[i], 0, write_mutex_thread<Mutex>, &data);<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_join(threads[i], 0);<br>
> -}<br>
> -<br>
> -TEST(Mutex, ReadWrite) {<br>
> -  Mutex mtx(MutexTypeAnnotations, StatMtxAnnotations);<br>
> -  TestData<Mutex> data(&mtx);<br>
> -  pthread_t threads[kThreads];<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_create(&threads[i], 0, read_mutex_thread<Mutex>, &data);<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_join(threads[i], 0);<br>
> -}<br>
> -<br>
> -TEST(Mutex, SpinWrite) {<br>
> -  SpinMutex mtx;<br>
> -  TestData<SpinMutex> data(&mtx);<br>
> -  pthread_t threads[kThreads];<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_create(&threads[i], 0, write_mutex_thread<SpinMutex>, &data);<br>
> -  for (int i = 0; i < kThreads; i++)<br>
> -    pthread_join(threads[i], 0);<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_platform_test.cc (removed)<br>
> @@ -1,88 +0,0 @@<br>
> -//===-- tsan_platform_test.cc ---------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "sanitizer_common/sanitizer_libc.h"<br>
> -#include "tsan_platform.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -static void TestThreadInfo(bool main) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  uptr stk_addr = 0;<br>
> -  uptr stk_size = 0;<br>
> -  uptr tls_addr = 0;<br>
> -  uptr tls_size = 0;<br>
> -  GetThreadStackAndTls(main, &stk_addr, &stk_size, &tls_addr, &tls_size);<br>
> -  // Printf("stk=%zx-%zx(%zu)\n", stk_addr, stk_addr + stk_size, stk_size);<br>
> -  // Printf("tls=%zx-%zx(%zu)\n", tls_addr, tls_addr + tls_size, tls_size);<br>
> -<br>
> -  int stack_var;<br>
> -  EXPECT_NE(stk_addr, (uptr)0);<br>
> -  EXPECT_NE(stk_size, (uptr)0);<br>
> -  EXPECT_GT((uptr)&stack_var, stk_addr);<br>
> -  EXPECT_LT((uptr)&stack_var, stk_addr + stk_size);<br>
> -<br>
> -  static __thread int thread_var;<br>
> -  EXPECT_NE(tls_addr, (uptr)0);<br>
> -  EXPECT_NE(tls_size, (uptr)0);<br>
> -  EXPECT_GT((uptr)&thread_var, tls_addr);<br>
> -  EXPECT_LT((uptr)&thread_var, tls_addr + tls_size);<br>
> -<br>
> -  // Ensure that tls and stack do not intersect.<br>
> -  uptr tls_end = tls_addr + tls_size;<br>
> -  EXPECT_TRUE(tls_addr < stk_addr || tls_addr >= stk_addr + stk_size);<br>
> -  EXPECT_TRUE(tls_end  < stk_addr || tls_end  >=  stk_addr + stk_size);<br>
> -  EXPECT_TRUE((tls_addr < stk_addr) == (tls_end  < stk_addr));<br>
> -}<br>
> -<br>
> -static void *WorkerThread(void *arg) {<br>
> -  TestThreadInfo(false);<br>
> -  return 0;<br>
> -}<br>
> -<br>
> -TEST(Platform, ThreadInfoMain) {<br>
> -  TestThreadInfo(true);<br>
> -}<br>
> -<br>
> -TEST(Platform, ThreadInfoWorker) {<br>
> -  pthread_t t;<br>
> -  pthread_create(&t, 0, WorkerThread, 0);<br>
> -  pthread_join(t, 0);<br>
> -}<br>
> -<br>
> -TEST(Platform, FileOps) {<br>
> -  const char *str1 = "qwerty";<br>
> -  uptr len1 = internal_strlen(str1);<br>
> -  const char *str2 = "zxcv";<br>
> -  uptr len2 = internal_strlen(str2);<br>
> -<br>
> -  fd_t fd = internal_open("./tsan_test.tmp", true);<br>
> -  EXPECT_NE(fd, kInvalidFd);<br>
> -  EXPECT_EQ(len1, internal_write(fd, str1, len1));<br>
> -  EXPECT_EQ(len2, internal_write(fd, str2, len2));<br>
> -  internal_close(fd);<br>
> -<br>
> -  fd = internal_open("./tsan_test.tmp", false);<br>
> -  EXPECT_NE(fd, kInvalidFd);<br>
> -  EXPECT_EQ(len1 + len2, internal_filesize(fd));<br>
> -  char buf[64] = {};<br>
> -  EXPECT_EQ(len1, internal_read(fd, buf, len1));<br>
> -  EXPECT_EQ(0, internal_memcmp(buf, str1, len1));<br>
> -  EXPECT_EQ((char)0, buf[len1 + 1]);<br>
> -  internal_memset(buf, 0, len1);<br>
> -  EXPECT_EQ(len2, internal_read(fd, buf, len2));<br>
> -  EXPECT_EQ(0, internal_memcmp(buf, str2, len2));<br>
> -  internal_close(fd);<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_printf_test.cc (removed)<br>
> @@ -1,106 +0,0 @@<br>
> -//===-- tsan_printf_test.cc -----------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -#include <string.h><br>
> -#include <limits.h><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Printf, Basic) {<br>
> -  char buf[1024];<br>
> -  uptr len = internal_snprintf(buf, sizeof(buf),<br>
> -      "a%db%zdc%ue%zuf%xh%zxq%pe%sr",<br>
> -      (int)-1, (long)-2, // NOLINT<br>
> -      (unsigned)-4, (unsigned long)5, // NOLINT<br>
> -      (unsigned)10, (unsigned long)11, // NOLINT<br>
> -      (void*)0x123, "_string_");<br>
> -  EXPECT_EQ(len, strlen(buf));<br>
> -  EXPECT_EQ(0, strcmp(buf, "a-1b-2c4294967292e5fahbq"<br>
> -                           "0x000000000123e_string_r"));<br>
> -}<br>
> -<br>
> -TEST(Printf, OverflowStr) {<br>
> -  char buf[] = "123456789";<br>
> -  uptr len = internal_snprintf(buf, 4, "%s", "abcdef");  // NOLINT<br>
> -  EXPECT_EQ(len, (uptr)6);<br>
> -  EXPECT_EQ(0, strcmp(buf, "abc"));<br>
> -  EXPECT_EQ(buf[3], 0);<br>
> -  EXPECT_EQ(buf[4], '5');<br>
> -  EXPECT_EQ(buf[5], '6');<br>
> -  EXPECT_EQ(buf[6], '7');<br>
> -  EXPECT_EQ(buf[7], '8');<br>
> -  EXPECT_EQ(buf[8], '9');<br>
> -  EXPECT_EQ(buf[9], 0);<br>
> -}<br>
> -<br>
> -TEST(Printf, OverflowInt) {<br>
> -  char buf[] = "123456789";<br>
> -  internal_snprintf(buf, 4, "%d", -123456789);  // NOLINT<br>
> -  EXPECT_EQ(0, strcmp(buf, "-12"));<br>
> -  EXPECT_EQ(buf[3], 0);<br>
> -  EXPECT_EQ(buf[4], '5');<br>
> -  EXPECT_EQ(buf[5], '6');<br>
> -  EXPECT_EQ(buf[6], '7');<br>
> -  EXPECT_EQ(buf[7], '8');<br>
> -  EXPECT_EQ(buf[8], '9');<br>
> -  EXPECT_EQ(buf[9], 0);<br>
> -}<br>
> -<br>
> -TEST(Printf, OverflowUint) {<br>
> -  char buf[] = "123456789";<br>
> -  internal_snprintf(buf, 4, "a%zx", (unsigned long)0x123456789);  // NOLINT<br>
> -  EXPECT_EQ(0, strcmp(buf, "a12"));<br>
> -  EXPECT_EQ(buf[3], 0);<br>
> -  EXPECT_EQ(buf[4], '5');<br>
> -  EXPECT_EQ(buf[5], '6');<br>
> -  EXPECT_EQ(buf[6], '7');<br>
> -  EXPECT_EQ(buf[7], '8');<br>
> -  EXPECT_EQ(buf[8], '9');<br>
> -  EXPECT_EQ(buf[9], 0);<br>
> -}<br>
> -<br>
> -TEST(Printf, OverflowPtr) {<br>
> -  char buf[] = "123456789";<br>
> -  internal_snprintf(buf, 4, "%p", (void*)0x123456789);  // NOLINT<br>
> -  EXPECT_EQ(0, strcmp(buf, "0x0"));<br>
> -  EXPECT_EQ(buf[3], 0);<br>
> -  EXPECT_EQ(buf[4], '5');<br>
> -  EXPECT_EQ(buf[5], '6');<br>
> -  EXPECT_EQ(buf[6], '7');<br>
> -  EXPECT_EQ(buf[7], '8');<br>
> -  EXPECT_EQ(buf[8], '9');<br>
> -  EXPECT_EQ(buf[9], 0);<br>
> -}<br>
> -<br>
> -template<typename T><br>
> -static void TestMinMax(const char *fmt, T min, T max) {<br>
> -  char buf[1024];<br>
> -  uptr len = internal_snprintf(buf, sizeof(buf), fmt, min, max);<br>
> -  char buf2[1024];<br>
> -  snprintf(buf2, sizeof(buf2), fmt, min, max);<br>
> -  EXPECT_EQ(len, strlen(buf));<br>
> -  EXPECT_EQ(0, strcmp(buf, buf2));<br>
> -}<br>
> -<br>
> -TEST(Printf, MinMax) {<br>
> -  TestMinMax<int>("%d-%d", INT_MIN, INT_MAX);  // NOLINT<br>
> -  TestMinMax<long>("%zd-%zd", LONG_MIN, LONG_MAX);  // NOLINT<br>
> -  TestMinMax<unsigned>("%u-%u", 0, UINT_MAX);  // NOLINT<br>
> -  TestMinMax<unsigned long>("%zu-%zu", 0, ULONG_MAX);  // NOLINT<br>
> -  TestMinMax<unsigned>("%x-%x", 0, UINT_MAX);  // NOLINT<br>
> -  TestMinMax<unsigned long>("%zx-%zx", 0, ULONG_MAX);  // NOLINT<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_shadow_test.cc (removed)<br>
> @@ -1,47 +0,0 @@<br>
> -//===-- tsan_shadow_test.cc -----------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_platform.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Shadow, Mapping) {<br>
> -  static int global;<br>
> -  int stack;<br>
> -  void *heap = malloc(0);<br>
> -  free(heap);<br>
> -<br>
> -  CHECK(IsAppMem((uptr)&global));<br>
> -  CHECK(IsAppMem((uptr)&stack));<br>
> -  CHECK(IsAppMem((uptr)heap));<br>
> -<br>
> -  CHECK(IsShadowMem(MemToShadow((uptr)&global)));<br>
> -  CHECK(IsShadowMem(MemToShadow((uptr)&stack)));<br>
> -  CHECK(IsShadowMem(MemToShadow((uptr)heap)));<br>
> -}<br>
> -<br>
> -TEST(Shadow, Celling) {<br>
> -  u64 aligned_data[4];<br>
> -  char *data = (char*)aligned_data;<br>
> -  CHECK_EQ((uptr)data % kShadowSize, 0);<br>
> -  uptr s0 = MemToShadow((uptr)&data[0]);<br>
> -  CHECK_EQ(s0 % kShadowSize, 0);<br>
> -  for (unsigned i = 1; i < kShadowCell; i++)<br>
> -    CHECK_EQ(s0, MemToShadow((uptr)&data[i]));<br>
> -  for (unsigned i = kShadowCell; i < 2*kShadowCell; i++)<br>
> -    CHECK_EQ(s0 + kShadowSize*kShadowCnt, MemToShadow((uptr)&data[i]));<br>
> -  for (unsigned i = 2*kShadowCell; i < 3*kShadowCell; i++)<br>
> -    CHECK_EQ(s0 + 2*kShadowSize*kShadowCnt, MemToShadow((uptr)&data[i]));<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_stack_test.cc (removed)<br>
> @@ -1,80 +0,0 @@<br>
> -//===-- tsan_stack_test.cc ------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_sync.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -#include <string.h><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -static void TestStackTrace(StackTrace *trace) {<br>
> -  ThreadState thr(0, 0, 0, 0, 0, 0, 0, 0);<br>
> -<br>
> -  trace->ObtainCurrent(&thr, 0);<br>
> -  EXPECT_EQ(trace->Size(), (uptr)0);<br>
> -<br>
> -  trace->ObtainCurrent(&thr, 42);<br>
> -  EXPECT_EQ(trace->Size(), (uptr)1);<br>
> -  EXPECT_EQ(trace->Get(0), (uptr)42);<br>
> -<br>
> -  *thr.shadow_stack_pos++ = 100;<br>
> -  *thr.shadow_stack_pos++ = 101;<br>
> -  trace->ObtainCurrent(&thr, 0);<br>
> -  EXPECT_EQ(trace->Size(), (uptr)2);<br>
> -  EXPECT_EQ(trace->Get(0), (uptr)100);<br>
> -  EXPECT_EQ(trace->Get(1), (uptr)101);<br>
> -<br>
> -  trace->ObtainCurrent(&thr, 42);<br>
> -  EXPECT_EQ(trace->Size(), (uptr)3);<br>
> -  EXPECT_EQ(trace->Get(0), (uptr)100);<br>
> -  EXPECT_EQ(trace->Get(1), (uptr)101);<br>
> -  EXPECT_EQ(trace->Get(2), (uptr)42);<br>
> -}<br>
> -<br>
> -TEST(StackTrace, Basic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  StackTrace trace;<br>
> -  TestStackTrace(&trace);<br>
> -}<br>
> -<br>
> -TEST(StackTrace, StaticBasic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  uptr buf[10];<br>
> -  StackTrace trace1(buf, 10);<br>
> -  TestStackTrace(&trace1);<br>
> -  StackTrace trace2(buf, 3);<br>
> -  TestStackTrace(&trace2);<br>
> -}<br>
> -<br>
> -TEST(StackTrace, StaticTrim) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  uptr buf[2];<br>
> -  StackTrace trace(buf, 2);<br>
> -  ThreadState thr(0, 0, 0, 0, 0, 0, 0, 0);<br>
> -<br>
> -  *thr.shadow_stack_pos++ = 100;<br>
> -  *thr.shadow_stack_pos++ = 101;<br>
> -  *thr.shadow_stack_pos++ = 102;<br>
> -  trace.ObtainCurrent(&thr, 0);<br>
> -  EXPECT_EQ(trace.Size(), (uptr)2);<br>
> -  EXPECT_EQ(trace.Get(0), (uptr)101);<br>
> -  EXPECT_EQ(trace.Get(1), (uptr)102);<br>
> -<br>
> -  trace.ObtainCurrent(&thr, 42);<br>
> -  EXPECT_EQ(trace.Size(), (uptr)2);<br>
> -  EXPECT_EQ(trace.Get(0), (uptr)102);<br>
> -  EXPECT_EQ(trace.Get(1), (uptr)42);<br>
> -}<br>
> -<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_suppressions_test.cc (removed)<br>
> @@ -1,128 +0,0 @@<br>
> -//===-- tsan_suppressions_test.cc -----------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_suppressions.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -#include <string.h><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Suppressions, Parse) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Suppression *supp0 = SuppressionParse(<br>
> -    "race:foo\n"<br>
> -    "  race:bar\n"  // NOLINT<br>
> -    "race:baz   \n"  // NOLINT<br>
> -    "# a comment\n"<br>
> -    "race:quz\n"<br>
> -  );  // NOLINT<br>
> -  Suppression *supp = supp0;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "quz"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "baz"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ((Suppression*)0, supp);<br>
> -}<br>
> -<br>
> -TEST(Suppressions, Parse2) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Suppression *supp0 = SuppressionParse(<br>
> -    "          # first line comment\n"  // NOLINT<br>
> -    "  race:bar        \n"  // NOLINT<br>
> -    "race:baz* *baz\n"<br>
> -    "# a comment\n"<br>
> -    "# last line comment\n"<br>
> -  );  // NOLINT<br>
> -  Suppression *supp = supp0;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "baz* *baz"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ((Suppression*)0, supp);<br>
> -}<br>
> -<br>
> -TEST(Suppressions, Parse3) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Suppression *supp0 = SuppressionParse(<br>
> -    "# last suppression w/o line-feed\n"<br>
> -    "race:foo\n"<br>
> -    "race:bar"<br>
> -  );  // NOLINT<br>
> -  Suppression *supp = supp0;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ((Suppression*)0, supp);<br>
> -}<br>
> -<br>
> -TEST(Suppressions, ParseType) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Suppression *supp0 = SuppressionParse(<br>
> -    "race:foo\n"<br>
> -    "thread:bar\n"<br>
> -    "mutex:baz\n"<br>
> -    "signal:quz\n"<br>
> -  );  // NOLINT<br>
> -  Suppression *supp = supp0;<br>
> -  EXPECT_EQ(supp->type, SuppressionSignal);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "quz"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionMutex);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "baz"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionThread);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "bar"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ(supp->type, SuppressionRace);<br>
> -  EXPECT_EQ(0, strcmp(supp->templ, "foo"));<br>
> -  supp = supp->next;<br>
> -  EXPECT_EQ((Suppression*)0, supp);<br>
> -}<br>
> -<br>
> -static bool MyMatch(const char *templ, const char *func) {<br>
> -  char tmp[1024];<br>
> -  strcpy(tmp, templ);  // NOLINT<br>
> -  return SuppressionMatch(tmp, func);<br>
> -}<br>
> -<br>
> -TEST(Suppressions, Match) {<br>
> -  EXPECT_TRUE(MyMatch("foobar", "foobar"));<br>
> -  EXPECT_TRUE(MyMatch("foobar", "prefix_foobar_postfix"));<br>
> -  EXPECT_TRUE(MyMatch("*foobar*", "prefix_foobar_postfix"));<br>
> -  EXPECT_TRUE(MyMatch("foo*bar", "foo_middle_bar"));<br>
> -  EXPECT_TRUE(MyMatch("foo*bar", "foobar"));<br>
> -  EXPECT_TRUE(MyMatch("foo*bar*baz", "foo_middle_bar_another_baz"));<br>
> -  EXPECT_TRUE(MyMatch("foo*bar*baz", "foo_middle_barbaz"));<br>
> -<br>
> -  EXPECT_FALSE(MyMatch("foo", "baz"));<br>
> -  EXPECT_FALSE(MyMatch("foobarbaz", "foobar"));<br>
> -  EXPECT_FALSE(MyMatch("foobarbaz", "barbaz"));<br>
> -  EXPECT_FALSE(MyMatch("foo*bar", "foobaz"));<br>
> -  EXPECT_FALSE(MyMatch("foo*bar", "foo_baz"));<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_sync_test.cc (removed)<br>
> @@ -1,65 +0,0 @@<br>
> -//===-- tsan_sync_test.cc -------------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_sync.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "tsan_mman.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -#include <stdlib.h><br>
> -#include <stdint.h><br>
> -#include <map><br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Sync, Table) {<br>
> -  const uintptr_t kIters = 512*1024;<br>
> -  const uintptr_t kRange = 10000;<br>
> -<br>
> -  ScopedInRtl in_rtl;<br>
> -  ThreadState *thr = cur_thread();<br>
> -  uptr pc = 0;<br>
> -<br>
> -  SyncTab tab;<br>
> -  SyncVar *golden[kRange] = {};<br>
> -  unsigned seed = 0;<br>
> -  for (uintptr_t i = 0; i < kIters; i++) {<br>
> -    uintptr_t addr = rand_r(&seed) % (kRange - 1) + 1;<br>
> -    if (rand_r(&seed) % 2) {<br>
> -      // Get or add.<br>
> -      SyncVar *v = tab.GetAndLock(thr, pc, addr, true);<br>
> -      EXPECT_TRUE(golden[addr] == 0 || golden[addr] == v);<br>
> -      EXPECT_EQ(v->addr, addr);<br>
> -      golden[addr] = v;<br>
> -      v->mtx.Unlock();<br>
> -    } else {<br>
> -      // Remove.<br>
> -      SyncVar *v = tab.GetAndRemove(thr, pc, addr);<br>
> -      EXPECT_EQ(golden[addr], v);<br>
> -      if (v) {<br>
> -        EXPECT_EQ(v->addr, addr);<br>
> -        golden[addr] = 0;<br>
> -        DestroyAndFree(v);<br>
> -      }<br>
> -    }<br>
> -  }<br>
> -  for (uintptr_t addr = 0; addr < kRange; addr++) {<br>
> -    if (golden[addr] == 0)<br>
> -      continue;<br>
> -    SyncVar *v = tab.GetAndRemove(thr, pc, addr);<br>
> -    EXPECT_EQ(v, golden[addr]);<br>
> -    EXPECT_EQ(v->addr, addr);<br>
> -    DestroyAndFree(v);<br>
> -  }<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
> Removed: compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc<br>
> URL: <a href="http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc?rev=164021&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc?rev=164021&view=auto</a><br>

> ==============================================================================<br>
> --- compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc (original)<br>
> +++ compiler-rt/trunk/lib/tsan/unit_tests/tsan_vector_test.cc (removed)<br>
> @@ -1,45 +0,0 @@<br>
> -//===-- tsan_vector_test.cc -----------------------------------------------===//<br>
> -//<br>
> -//                     The LLVM Compiler Infrastructure<br>
> -//<br>
> -// This file is distributed under the University of Illinois Open Source<br>
> -// License. See LICENSE.TXT for details.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -//<br>
> -// This file is a part of ThreadSanitizer (TSan), a race detector.<br>
> -//<br>
> -//===----------------------------------------------------------------------===//<br>
> -#include "tsan_vector.h"<br>
> -#include "tsan_rtl.h"<br>
> -#include "gtest/gtest.h"<br>
> -<br>
> -namespace __tsan {<br>
> -<br>
> -TEST(Vector, Basic) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Vector<int> v(MBlockScopedBuf);<br>
> -  EXPECT_EQ(v.Size(), (uptr)0);<br>
> -  v.PushBack(42);<br>
> -  EXPECT_EQ(v.Size(), (uptr)1);<br>
> -  EXPECT_EQ(v[0], 42);<br>
> -  v.PushBack(43);<br>
> -  EXPECT_EQ(v.Size(), (uptr)2);<br>
> -  EXPECT_EQ(v[0], 42);<br>
> -  EXPECT_EQ(v[1], 43);<br>
> -}<br>
> -<br>
> -TEST(Vector, Stride) {<br>
> -  ScopedInRtl in_rtl;<br>
> -  Vector<int> v(MBlockScopedBuf);<br>
> -  for (int i = 0; i < 1000; i++) {<br>
> -    v.PushBack(i);<br>
> -    EXPECT_EQ(v.Size(), (uptr)(i + 1));<br>
> -    EXPECT_EQ(v[i], i);<br>
> -  }<br>
> -  for (int i = 0; i < 1000; i++) {<br>
> -    EXPECT_EQ(v[i], i);<br>
> -  }<br>
> -}<br>
> -<br>
> -}  // namespace __tsan<br>
><br>
><br>
> _______________________________________________<br>
> llvm-commits mailing list<br>
> <a href="mailto:llvm-commits@cs.uiuc.edu">llvm-commits@cs.uiuc.edu</a><br>
> <a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits" target="_blank">http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br><br clear="all"><div><br></div>-- <br><div>Alexey Samsonov, MSK</div><br>
</div>