blob: 45251f02ef7035bd155239ea8b416cef9a8d9865 [file] [log] [blame]
Kostya Serebryany4ad375f2012-05-10 13:48:04 +00001//===-- 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 "tsan_atomic.h"
17#include "tsan_clock.h"
18#include "tsan_defs.h"
19#include "tsan_mutex.h"
20
21namespace __tsan {
22
23class SlabCache;
24
25class StackTrace {
26 public:
27 StackTrace();
28 ~StackTrace();
29 void Reset();
30
31 void Init(const uptr *pcs, uptr cnt);
32 void ObtainCurrent(ThreadState *thr, uptr toppc);
33 bool IsEmpty() const;
34 uptr Size() const;
35 uptr Get(uptr i) const;
36 const uptr *Begin() const;
37 void CopyFrom(const StackTrace& other);
38
39 private:
40 uptr n_;
41 uptr *s_;
42
43 StackTrace(const StackTrace&);
44 void operator = (const StackTrace&);
45};
46
47struct SyncVar {
48 explicit SyncVar(uptr addr);
49
50 static const int kInvalidTid = -1;
51
52 Mutex mtx;
53 const uptr addr;
54 SyncClock clock;
55 StackTrace creation_stack;
56 SyncClock read_clock; // Used for rw mutexes only.
57 int owner_tid; // Set only by exclusive owners.
58 int recursion;
59 bool is_rw;
60 bool is_recursive;
61 bool is_broken;
62 SyncVar *next; // In SyncTab hashtable.
63};
64
65class SyncTab {
66 public:
67 SyncTab();
68 ~SyncTab();
69
70 // If the SyncVar does not exist yet, it is created.
71 SyncVar* GetAndLock(ThreadState *thr, uptr pc,
72 uptr addr, bool write_lock);
73
74 // If the SyncVar does not exist, returns 0.
75 SyncVar* GetAndRemove(ThreadState *thr, uptr pc, uptr addr);
76
77 private:
78 struct Part {
79 Mutex mtx;
80 SyncVar *val;
81 char pad[kCacheLineSize - sizeof(Mutex) - sizeof(SyncVar*)]; // NOLINT
82 Part();
83 };
84
85 // FIXME: Implement something more sane.
86 static const int kPartCount = 1009;
87 Part tab_[kPartCount];
88
89 int PartIdx(uptr addr);
90
91 SyncTab(const SyncTab&); // Not implemented.
92 void operator = (const SyncTab&); // Not implemented.
93};
94
95} // namespace __tsan
96
97#endif // TSAN_SYNC_H