Home | History | Annotate | Download | only in rtl
      1 //===-- tsan_sync.h ---------------------------------------------*- C++ -*-===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 // This file is a part of ThreadSanitizer (TSan), a race detector.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 #ifndef TSAN_SYNC_H
     14 #define TSAN_SYNC_H
     15 
     16 #include "sanitizer_common/sanitizer_atomic.h"
     17 #include "sanitizer_common/sanitizer_common.h"
     18 #include "tsan_clock.h"
     19 #include "tsan_defs.h"
     20 #include "tsan_mutex.h"
     21 
     22 namespace __tsan {
     23 
     24 class SlabCache;
     25 
     26 class StackTrace {
     27  public:
     28   StackTrace();
     29   // Initialized the object in "static mode",
     30   // in this mode it never calls malloc/free but uses the provided buffer.
     31   StackTrace(uptr *buf, uptr cnt);
     32   ~StackTrace();
     33   void Reset();
     34 
     35   void Init(const uptr *pcs, uptr cnt);
     36   void ObtainCurrent(ThreadState *thr, uptr toppc);
     37   bool IsEmpty() const;
     38   uptr Size() const;
     39   uptr Get(uptr i) const;
     40   const uptr *Begin() const;
     41   void CopyFrom(const StackTrace& other);
     42 
     43  private:
     44   uptr n_;
     45   uptr *s_;
     46   const uptr c_;
     47 
     48   StackTrace(const StackTrace&);
     49   void operator = (const StackTrace&);
     50 };
     51 
     52 struct SyncVar {
     53   explicit SyncVar(uptr addr);
     54 
     55   static const int kInvalidTid = -1;
     56 
     57   Mutex mtx;
     58   const uptr addr;
     59   SyncClock clock;
     60   SyncClock read_clock;  // Used for rw mutexes only.
     61   StackTrace creation_stack;
     62   int owner_tid;  // Set only by exclusive owners.
     63   u64 last_lock;
     64   int recursion;
     65   bool is_rw;
     66   bool is_recursive;
     67   bool is_broken;
     68   bool is_linker_init;
     69   SyncVar *next;  // In SyncTab hashtable.
     70 
     71   uptr GetMemoryConsumption();
     72 };
     73 
     74 class SyncTab {
     75  public:
     76   SyncTab();
     77   ~SyncTab();
     78 
     79   // If the SyncVar does not exist yet, it is created.
     80   SyncVar* GetAndLock(ThreadState *thr, uptr pc,
     81                       uptr addr, bool write_lock);
     82 
     83   // If the SyncVar does not exist, returns 0.
     84   SyncVar* GetAndRemove(ThreadState *thr, uptr pc, uptr addr);
     85 
     86   uptr GetMemoryConsumption(uptr *nsync);
     87 
     88  private:
     89   struct Part {
     90     Mutex mtx;
     91     SyncVar *val;
     92     char pad[kCacheLineSize - sizeof(Mutex) - sizeof(SyncVar*)];  // NOLINT
     93     Part();
     94   };
     95 
     96   // FIXME: Implement something more sane.
     97   static const int kPartCount = 1009;
     98   Part tab_[kPartCount];
     99 
    100   int PartIdx(uptr addr);
    101 
    102   SyncTab(const SyncTab&);  // Not implemented.
    103   void operator = (const SyncTab&);  // Not implemented.
    104 };
    105 
    106 }  // namespace __tsan
    107 
    108 #endif  // TSAN_SYNC_H
    109