1 //===-- tsan_mutexset.h -----------------------------------------*- C++ -*-===// 2 // 3 // This file is distributed under the University of Illinois Open Source 4 // License. See LICENSE.TXT for details. 5 // 6 //===----------------------------------------------------------------------===// 7 // 8 // This file is a part of ThreadSanitizer (TSan), a race detector. 9 // 10 // MutexSet holds the set of mutexes currently held by a thread. 11 //===----------------------------------------------------------------------===// 12 #ifndef TSAN_MUTEXSET_H 13 #define TSAN_MUTEXSET_H 14 15 #include "tsan_defs.h" 16 17 namespace __tsan { 18 19 class MutexSet { 20 public: 21 // Holds limited number of mutexes. 22 // The oldest mutexes are discarded on overflow. 23 static const uptr kMaxSize = 16; 24 struct Desc { 25 u64 id; 26 u64 epoch; 27 int count; 28 bool write; 29 }; 30 31 MutexSet(); 32 // The 'id' is obtained from SyncVar::GetId(). 33 void Add(u64 id, bool write, u64 epoch); 34 void Del(u64 id, bool write); 35 void Remove(u64 id); // Removes the mutex completely (if it's destroyed). 36 uptr Size() const; 37 Desc Get(uptr i) const; 38 39 void operator=(const MutexSet &other) { 40 internal_memcpy(this, &other, sizeof(*this)); 41 } 42 43 private: 44 #if !SANITIZER_GO 45 uptr size_; 46 Desc descs_[kMaxSize]; 47 #endif 48 49 void RemovePos(uptr i); 50 MutexSet(const MutexSet&); 51 }; 52 53 // Go does not have mutexes, so do not spend memory and time. 54 // (Go sync.Mutex is actually a semaphore -- can be unlocked 55 // in different goroutine). 56 #if SANITIZER_GO 57 MutexSet::MutexSet() {} 58 void MutexSet::Add(u64 id, bool write, u64 epoch) {} 59 void MutexSet::Del(u64 id, bool write) {} 60 void MutexSet::Remove(u64 id) {} 61 void MutexSet::RemovePos(uptr i) {} 62 uptr MutexSet::Size() const { return 0; } 63 MutexSet::Desc MutexSet::Get(uptr i) const { return Desc(); } 64 #endif 65 66 } // namespace __tsan 67 68 #endif // TSAN_MUTEXSET_H 69