[PATCH] [Sanitizer] Introduce atomic_ptr<T> type and use it in Symbolizer.

Alexey Samsonov samsonov at google.com
Mon Oct 28 15:54:01 PDT 2013


Hi dvyukov,

It is more convenient than using type-unsafe atomic_uintptr_t.

http://llvm-reviews.chandlerc.com/D2042

Files:
  lib/sanitizer_common/sanitizer_atomic.h
  lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc
  lib/sanitizer_common/tests/sanitizer_atomic_test.cc
  lib/sanitizer_common/sanitizer_symbolizer.cc
  lib/sanitizer_common/sanitizer_symbolizer.h

Index: lib/sanitizer_common/sanitizer_atomic.h
===================================================================
--- lib/sanitizer_common/sanitizer_atomic.h
+++ lib/sanitizer_common/sanitizer_atomic.h
@@ -52,6 +52,12 @@
   volatile Type val_dont_use;
 };
 
+template<typename T>
+struct atomic_ptr {
+  typedef T* Type;
+  volatile Type val_dont_use;
+};
+
 }  // namespace __sanitizer
 
 #if defined(__GNUC__)
Index: lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc
===================================================================
--- lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc
+++ lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc
@@ -22,8 +22,7 @@
   Symbolizer *platform_symbolizer = PlatformInit(path_to_external);
   if (!platform_symbolizer)
     return Disable();
-  atomic_store(&symbolizer_, reinterpret_cast<uptr>(platform_symbolizer),
-               memory_order_release);
+  atomic_store(&symbolizer_, platform_symbolizer, memory_order_release);
   return platform_symbolizer;
 }
 
@@ -34,15 +33,13 @@
 
 Symbolizer *Symbolizer::GetOrInit() {
   static StaticSpinMutex init_mu;
-
-  uptr sym = atomic_load(&symbolizer_, memory_order_acquire);
+  Symbolizer *sym = atomic_load(&symbolizer_, memory_order_acquire);
   if (!sym) {
     SpinMutexLock l(&init_mu);
     sym = atomic_load(&symbolizer_, memory_order_relaxed);
     if (!sym) return CreateAndStore(0);
   }
-
-  return reinterpret_cast<Symbolizer *>(sym);
+  return sym;
 }
 
 }  // namespace __sanitizer
Index: lib/sanitizer_common/tests/sanitizer_atomic_test.cc
===================================================================
--- lib/sanitizer_common/tests/sanitizer_atomic_test.cc
+++ lib/sanitizer_common/tests/sanitizer_atomic_test.cc
@@ -18,22 +18,23 @@
 // Clang crashes while compiling this test for Android:
 // http://llvm.org/bugs/show_bug.cgi?id=15587
 #if !SANITIZER_ANDROID
-template<typename T>
-void CheckAtomicCompareExchange() {
+template <typename T>
+void CheckAtomicCompareExchange(typename T::Type old_v,
+                                typename T::Type new_v) {
   typedef typename T::Type Type;
   {
-    Type old_val = 42;
-    Type new_val = 24;
+    Type old_val = old_v;
+    Type new_val = new_v;
     Type var = old_val;
     EXPECT_TRUE(atomic_compare_exchange_strong((T*)&var, &old_val, new_val,
                                                memory_order_relaxed));
     EXPECT_FALSE(atomic_compare_exchange_strong((T*)&var, &old_val, new_val,
                                                 memory_order_relaxed));
     EXPECT_EQ(new_val, old_val);
   }
   {
-    Type old_val = 42;
-    Type new_val = 24;
+    Type old_val = old_v;
+    Type new_val = new_v;
     Type var = old_val;
     EXPECT_TRUE(atomic_compare_exchange_weak((T*)&var, &old_val, new_val,
                                              memory_order_relaxed));
@@ -44,11 +45,13 @@
 }
 
 TEST(SanitizerCommon, AtomicCompareExchangeTest) {
-  CheckAtomicCompareExchange<atomic_uint8_t>();
-  CheckAtomicCompareExchange<atomic_uint16_t>();
-  CheckAtomicCompareExchange<atomic_uint32_t>();
-  CheckAtomicCompareExchange<atomic_uint64_t>();
-  CheckAtomicCompareExchange<atomic_uintptr_t>();
+  CheckAtomicCompareExchange<atomic_uint8_t>(42, 24);
+  CheckAtomicCompareExchange<atomic_uint16_t>(42, 24);
+  CheckAtomicCompareExchange<atomic_uint32_t>(500000, 600000);
+  CheckAtomicCompareExchange<atomic_uint64_t>(1ULL << 62, 1ULL << 63);
+  CheckAtomicCompareExchange<atomic_uintptr_t>(10, 20);
+  int a, b;
+  CheckAtomicCompareExchange<atomic_ptr<int> >(&a, &b);
 }
 #endif  //!SANITIZER_ANDROID
 
Index: lib/sanitizer_common/sanitizer_symbolizer.cc
===================================================================
--- lib/sanitizer_common/sanitizer_symbolizer.cc
+++ lib/sanitizer_common/sanitizer_symbolizer.cc
@@ -18,12 +18,11 @@
 
 namespace __sanitizer {
 
-atomic_uintptr_t Symbolizer::symbolizer_;
+atomic_ptr<Symbolizer> Symbolizer::symbolizer_;
 LowLevelAllocator Symbolizer::symbolizer_allocator_;
 
 Symbolizer *Symbolizer::GetOrNull() {
-  return reinterpret_cast<Symbolizer *>(
-      atomic_load(&symbolizer_, memory_order_acquire));
+  return atomic_load(&symbolizer_, memory_order_acquire);
 }
 
 Symbolizer *Symbolizer::Get() {
@@ -35,8 +34,7 @@
 Symbolizer *Symbolizer::Disable() {
   CHECK_EQ(0, atomic_load(&symbolizer_, memory_order_acquire));
   Symbolizer *dummy_sym = new(symbolizer_allocator_) Symbolizer;
-  atomic_store(&symbolizer_, reinterpret_cast<uptr>(dummy_sym),
-               memory_order_release);
+  atomic_store(&symbolizer_, dummy_sym, memory_order_release);
   return dummy_sym;
 }
 
Index: lib/sanitizer_common/sanitizer_symbolizer.h
===================================================================
--- lib/sanitizer_common/sanitizer_symbolizer.h
+++ lib/sanitizer_common/sanitizer_symbolizer.h
@@ -118,7 +118,7 @@
   /// already exists.  Not thread safe.
   static Symbolizer *CreateAndStore(const char *path_to_external);
 
-  static atomic_uintptr_t symbolizer_;
+  static atomic_ptr<Symbolizer> symbolizer_;
 
  protected:
   static LowLevelAllocator symbolizer_allocator_;
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D2042.1.patch
Type: text/x-patch
Size: 5131 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20131028/adb2f7ec/attachment.bin>


More information about the llvm-commits mailing list