1 //===-- tsan_rtl.h ----------------------------------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file is a part of ThreadSanitizer (TSan), a race detector. 10 // 11 // Main internal TSan header file. 12 // 13 // Ground rules: 14 // - C++ run-time should not be used (static CTORs, RTTI, exceptions, static 15 // function-scope locals) 16 // - All functions/classes/etc reside in namespace __tsan, except for those 17 // declared in tsan_interface.h. 18 // - Platform-specific files should be used instead of ifdefs (*). 19 // - No system headers included in header files (*). 20 // - Platform specific headres included only into platform-specific files (*). 21 // 22 // (*) Except when inlining is critical for performance. 23 //===----------------------------------------------------------------------===// 24 25 #ifndef TSAN_RTL_H 26 #define TSAN_RTL_H 27 28 #include "sanitizer_common/sanitizer_allocator.h" 29 #include "sanitizer_common/sanitizer_allocator_internal.h" 30 #include "sanitizer_common/sanitizer_asm.h" 31 #include "sanitizer_common/sanitizer_common.h" 32 #include "sanitizer_common/sanitizer_deadlock_detector_interface.h" 33 #include "sanitizer_common/sanitizer_libignore.h" 34 #include "sanitizer_common/sanitizer_suppressions.h" 35 #include "sanitizer_common/sanitizer_thread_registry.h" 36 #include "sanitizer_common/sanitizer_vector.h" 37 #include "tsan_clock.h" 38 #include "tsan_defs.h" 39 #include "tsan_flags.h" 40 #include "tsan_mman.h" 41 #include "tsan_sync.h" 42 #include "tsan_trace.h" 43 #include "tsan_report.h" 44 #include "tsan_platform.h" 45 #include "tsan_mutexset.h" 46 #include "tsan_ignoreset.h" 47 #include "tsan_stack_trace.h" 48 49 #if SANITIZER_WORDSIZE != 64 50 # error "ThreadSanitizer is supported only on 64-bit platforms" 51 #endif 52 53 namespace __tsan { 54 55 #if !SANITIZER_GO 56 struct MapUnmapCallback; 57 #if defined(__mips64) || defined(__aarch64__) || defined(__powerpc__) 58 59 struct AP32 { 60 static const uptr kSpaceBeg = 0; 61 static const u64 kSpaceSize = SANITIZER_MMAP_RANGE_SIZE; 62 static const uptr kMetadataSize = 0; 63 typedef __sanitizer::CompactSizeClassMap SizeClassMap; 64 static const uptr kRegionSizeLog = 20; 65 using AddressSpaceView = LocalAddressSpaceView; 66 typedef __tsan::MapUnmapCallback MapUnmapCallback; 67 static const uptr kFlags = 0; 68 }; 69 typedef SizeClassAllocator32<AP32> PrimaryAllocator; 70 #else 71 struct AP64 { // Allocator64 parameters. Deliberately using a short name. 72 static const uptr kSpaceBeg = Mapping::kHeapMemBeg; 73 static const uptr kSpaceSize = Mapping::kHeapMemEnd - Mapping::kHeapMemBeg; 74 static const uptr kMetadataSize = 0; 75 typedef DefaultSizeClassMap SizeClassMap; 76 typedef __tsan::MapUnmapCallback MapUnmapCallback; 77 static const uptr kFlags = 0; 78 using AddressSpaceView = LocalAddressSpaceView; 79 }; 80 typedef SizeClassAllocator64<AP64> PrimaryAllocator; 81 #endif 82 typedef CombinedAllocator<PrimaryAllocator> Allocator; 83 typedef Allocator::AllocatorCache AllocatorCache; 84 Allocator *allocator(); 85 #endif 86 87 const u64 kShadowRodata = (u64)-1; // .rodata shadow marker 88 89 // FastState (from most significant bit): 90 // ignore : 1 91 // tid : kTidBits 92 // unused : - 93 // history_size : 3 94 // epoch : kClkBits 95 class FastState { 96 public: 97 FastState(u64 tid, u64 epoch) { 98 x_ = tid << kTidShift; 99 x_ |= epoch; 100 DCHECK_EQ(tid, this->tid()); 101 DCHECK_EQ(epoch, this->epoch()); 102 DCHECK_EQ(GetIgnoreBit(), false); 103 } 104 105 explicit FastState(u64 x) 106 : x_(x) { 107 } 108 109 u64 raw() const { 110 return x_; 111 } 112 113 u64 tid() const { 114 u64 res = (x_ & ~kIgnoreBit) >> kTidShift; 115 return res; 116 } 117 118 u64 TidWithIgnore() const { 119 u64 res = x_ >> kTidShift; 120 return res; 121 } 122 123 u64 epoch() const { 124 u64 res = x_ & ((1ull << kClkBits) - 1); 125 return res; 126 } 127 128 void IncrementEpoch() { 129 u64 old_epoch = epoch(); 130 x_ += 1; 131 DCHECK_EQ(old_epoch + 1, epoch()); 132 (void)old_epoch; 133 } 134 135 void SetIgnoreBit() { x_ |= kIgnoreBit; } 136 void ClearIgnoreBit() { x_ &= ~kIgnoreBit; } 137 bool GetIgnoreBit() const { return (s64)x_ < 0; } 138 139 void SetHistorySize(int hs) { 140 CHECK_GE(hs, 0); 141 CHECK_LE(hs, 7); 142 x_ = (x_ & ~(kHistoryMask << kHistoryShift)) | (u64(hs) << kHistoryShift); 143 } 144 145 ALWAYS_INLINE 146 int GetHistorySize() const { 147 return (int)((x_ >> kHistoryShift) & kHistoryMask); 148 } 149 150 void ClearHistorySize() { 151 SetHistorySize(0); 152 } 153 154 ALWAYS_INLINE 155 u64 GetTracePos() const { 156 const int hs = GetHistorySize(); 157 // When hs == 0, the trace consists of 2 parts. 158 const u64 mask = (1ull << (kTracePartSizeBits + hs + 1)) - 1; 159 return epoch() & mask; 160 } 161 162 private: 163 friend class Shadow; 164 static const int kTidShift = 64 - kTidBits - 1; 165 static const u64 kIgnoreBit = 1ull << 63; 166 static const u64 kFreedBit = 1ull << 63; 167 static const u64 kHistoryShift = kClkBits; 168 static const u64 kHistoryMask = 7; 169 u64 x_; 170 }; 171 172 // Shadow (from most significant bit): 173 // freed : 1 174 // tid : kTidBits 175 // is_atomic : 1 176 // is_read : 1 177 // size_log : 2 178 // addr0 : 3 179 // epoch : kClkBits 180 class Shadow : public FastState { 181 public: 182 explicit Shadow(u64 x) 183 : FastState(x) { 184 } 185 186 explicit Shadow(const FastState &s) 187 : FastState(s.x_) { 188 ClearHistorySize(); 189 } 190 191 void SetAddr0AndSizeLog(u64 addr0, unsigned kAccessSizeLog) { 192 DCHECK_EQ((x_ >> kClkBits) & 31, 0); 193 DCHECK_LE(addr0, 7); 194 DCHECK_LE(kAccessSizeLog, 3); 195 x_ |= ((kAccessSizeLog << 3) | addr0) << kClkBits; 196 DCHECK_EQ(kAccessSizeLog, size_log()); 197 DCHECK_EQ(addr0, this->addr0()); 198 } 199 200 void SetWrite(unsigned kAccessIsWrite) { 201 DCHECK_EQ(x_ & kReadBit, 0); 202 if (!kAccessIsWrite) 203 x_ |= kReadBit; 204 DCHECK_EQ(kAccessIsWrite, IsWrite()); 205 } 206 207 void SetAtomic(bool kIsAtomic) { 208 DCHECK(!IsAtomic()); 209 if (kIsAtomic) 210 x_ |= kAtomicBit; 211 DCHECK_EQ(IsAtomic(), kIsAtomic); 212 } 213 214 bool IsAtomic() const { 215 return x_ & kAtomicBit; 216 } 217 218 bool IsZero() const { 219 return x_ == 0; 220 } 221 222 static inline bool TidsAreEqual(const Shadow s1, const Shadow s2) { 223 u64 shifted_xor = (s1.x_ ^ s2.x_) >> kTidShift; 224 DCHECK_EQ(shifted_xor == 0, s1.TidWithIgnore() == s2.TidWithIgnore()); 225 return shifted_xor == 0; 226 } 227 228 static ALWAYS_INLINE 229 bool Addr0AndSizeAreEqual(const Shadow s1, const Shadow s2) { 230 u64 masked_xor = ((s1.x_ ^ s2.x_) >> kClkBits) & 31; 231 return masked_xor == 0; 232 } 233 234 static ALWAYS_INLINE bool TwoRangesIntersect(Shadow s1, Shadow s2, 235 unsigned kS2AccessSize) { 236 bool res = false; 237 u64 diff = s1.addr0() - s2.addr0(); 238 if ((s64)diff < 0) { // s1.addr0 < s2.addr0 239 // if (s1.addr0() + size1) > s2.addr0()) return true; 240 if (s1.size() > -diff) 241 res = true; 242 } else { 243 // if (s2.addr0() + kS2AccessSize > s1.addr0()) return true; 244 if (kS2AccessSize > diff) 245 res = true; 246 } 247 DCHECK_EQ(res, TwoRangesIntersectSlow(s1, s2)); 248 DCHECK_EQ(res, TwoRangesIntersectSlow(s2, s1)); 249 return res; 250 } 251 252 u64 ALWAYS_INLINE addr0() const { return (x_ >> kClkBits) & 7; } 253 u64 ALWAYS_INLINE size() const { return 1ull << size_log(); } 254 bool ALWAYS_INLINE IsWrite() const { return !IsRead(); } 255 bool ALWAYS_INLINE IsRead() const { return x_ & kReadBit; } 256 257 // The idea behind the freed bit is as follows. 258 // When the memory is freed (or otherwise unaccessible) we write to the shadow 259 // values with tid/epoch related to the free and the freed bit set. 260 // During memory accesses processing the freed bit is considered 261 // as msb of tid. So any access races with shadow with freed bit set 262 // (it is as if write from a thread with which we never synchronized before). 263 // This allows us to detect accesses to freed memory w/o additional 264 // overheads in memory access processing and at the same time restore 265 // tid/epoch of free. 266 void MarkAsFreed() { 267 x_ |= kFreedBit; 268 } 269 270 bool IsFreed() const { 271 return x_ & kFreedBit; 272 } 273 274 bool GetFreedAndReset() { 275 bool res = x_ & kFreedBit; 276 x_ &= ~kFreedBit; 277 return res; 278 } 279 280 bool ALWAYS_INLINE IsBothReadsOrAtomic(bool kIsWrite, bool kIsAtomic) const { 281 bool v = x_ & ((u64(kIsWrite ^ 1) << kReadShift) 282 | (u64(kIsAtomic) << kAtomicShift)); 283 DCHECK_EQ(v, (!IsWrite() && !kIsWrite) || (IsAtomic() && kIsAtomic)); 284 return v; 285 } 286 287 bool ALWAYS_INLINE IsRWNotWeaker(bool kIsWrite, bool kIsAtomic) const { 288 bool v = ((x_ >> kReadShift) & 3) 289 <= u64((kIsWrite ^ 1) | (kIsAtomic << 1)); 290 DCHECK_EQ(v, (IsAtomic() < kIsAtomic) || 291 (IsAtomic() == kIsAtomic && !IsWrite() <= !kIsWrite)); 292 return v; 293 } 294 295 bool ALWAYS_INLINE IsRWWeakerOrEqual(bool kIsWrite, bool kIsAtomic) const { 296 bool v = ((x_ >> kReadShift) & 3) 297 >= u64((kIsWrite ^ 1) | (kIsAtomic << 1)); 298 DCHECK_EQ(v, (IsAtomic() > kIsAtomic) || 299 (IsAtomic() == kIsAtomic && !IsWrite() >= !kIsWrite)); 300 return v; 301 } 302 303 private: 304 static const u64 kReadShift = 5 + kClkBits; 305 static const u64 kReadBit = 1ull << kReadShift; 306 static const u64 kAtomicShift = 6 + kClkBits; 307 static const u64 kAtomicBit = 1ull << kAtomicShift; 308 309 u64 size_log() const { return (x_ >> (3 + kClkBits)) & 3; } 310 311 static bool TwoRangesIntersectSlow(const Shadow s1, const Shadow s2) { 312 if (s1.addr0() == s2.addr0()) return true; 313 if (s1.addr0() < s2.addr0() && s1.addr0() + s1.size() > s2.addr0()) 314 return true; 315 if (s2.addr0() < s1.addr0() && s2.addr0() + s2.size() > s1.addr0()) 316 return true; 317 return false; 318 } 319 }; 320 321 struct ThreadSignalContext; 322 323 struct JmpBuf { 324 uptr sp; 325 int int_signal_send; 326 bool in_blocking_func; 327 uptr in_signal_handler; 328 uptr *shadow_stack_pos; 329 }; 330 331 // A Processor represents a physical thread, or a P for Go. 332 // It is used to store internal resources like allocate cache, and does not 333 // participate in race-detection logic (invisible to end user). 334 // In C++ it is tied to an OS thread just like ThreadState, however ideally 335 // it should be tied to a CPU (this way we will have fewer allocator caches). 336 // In Go it is tied to a P, so there are significantly fewer Processor's than 337 // ThreadState's (which are tied to Gs). 338 // A ThreadState must be wired with a Processor to handle events. 339 struct Processor { 340 ThreadState *thr; // currently wired thread, or nullptr 341 #if !SANITIZER_GO 342 AllocatorCache alloc_cache; 343 InternalAllocatorCache internal_alloc_cache; 344 #endif 345 DenseSlabAllocCache block_cache; 346 DenseSlabAllocCache sync_cache; 347 DenseSlabAllocCache clock_cache; 348 DDPhysicalThread *dd_pt; 349 }; 350 351 #if !SANITIZER_GO 352 // ScopedGlobalProcessor temporary setups a global processor for the current 353 // thread, if it does not have one. Intended for interceptors that can run 354 // at the very thread end, when we already destroyed the thread processor. 355 struct ScopedGlobalProcessor { 356 ScopedGlobalProcessor(); 357 ~ScopedGlobalProcessor(); 358 }; 359 #endif 360 361 // This struct is stored in TLS. 362 struct ThreadState { 363 FastState fast_state; 364 // Synch epoch represents the threads's epoch before the last synchronization 365 // action. It allows to reduce number of shadow state updates. 366 // For example, fast_synch_epoch=100, last write to addr X was at epoch=150, 367 // if we are processing write to X from the same thread at epoch=200, 368 // we do nothing, because both writes happen in the same 'synch epoch'. 369 // That is, if another memory access does not race with the former write, 370 // it does not race with the latter as well. 371 // QUESTION: can we can squeeze this into ThreadState::Fast? 372 // E.g. ThreadState::Fast is a 44-bit, 32 are taken by synch_epoch and 12 are 373 // taken by epoch between synchs. 374 // This way we can save one load from tls. 375 u64 fast_synch_epoch; 376 // Technically `current` should be a separate THREADLOCAL variable; 377 // but it is placed here in order to share cache line with previous fields. 378 ThreadState* current; 379 // This is a slow path flag. On fast path, fast_state.GetIgnoreBit() is read. 380 // We do not distinguish beteween ignoring reads and writes 381 // for better performance. 382 int ignore_reads_and_writes; 383 int ignore_sync; 384 int suppress_reports; 385 // Go does not support ignores. 386 #if !SANITIZER_GO 387 IgnoreSet mop_ignore_set; 388 IgnoreSet sync_ignore_set; 389 #endif 390 // C/C++ uses fixed size shadow stack embed into Trace. 391 // Go uses malloc-allocated shadow stack with dynamic size. 392 uptr *shadow_stack; 393 uptr *shadow_stack_end; 394 uptr *shadow_stack_pos; 395 u64 *racy_shadow_addr; 396 u64 racy_state[2]; 397 MutexSet mset; 398 ThreadClock clock; 399 #if !SANITIZER_GO 400 Vector<JmpBuf> jmp_bufs; 401 int ignore_interceptors; 402 #endif 403 const u32 tid; 404 const int unique_id; 405 bool in_symbolizer; 406 bool in_ignored_lib; 407 bool is_inited; 408 bool is_dead; 409 bool is_freeing; 410 bool is_vptr_access; 411 const uptr stk_addr; 412 const uptr stk_size; 413 const uptr tls_addr; 414 const uptr tls_size; 415 ThreadContext *tctx; 416 417 DDLogicalThread *dd_lt; 418 419 // Current wired Processor, or nullptr. Required to handle any events. 420 Processor *proc1; 421 #if !SANITIZER_GO 422 Processor *proc() { return proc1; } 423 #else 424 Processor *proc(); 425 #endif 426 427 atomic_uintptr_t in_signal_handler; 428 ThreadSignalContext *signal_ctx; 429 430 #if !SANITIZER_GO 431 u32 last_sleep_stack_id; 432 ThreadClock last_sleep_clock; 433 #endif 434 435 // Set in regions of runtime that must be signal-safe and fork-safe. 436 // If set, malloc must not be called. 437 int nomalloc; 438 439 const ReportDesc *current_report; 440 441 explicit ThreadState(Context *ctx, u32 tid, int unique_id, u64 epoch, 442 unsigned reuse_count, uptr stk_addr, uptr stk_size, 443 uptr tls_addr, uptr tls_size); 444 }; 445 446 #if !SANITIZER_GO 447 #if SANITIZER_MAC || SANITIZER_ANDROID 448 ThreadState *cur_thread(); 449 void set_cur_thread(ThreadState *thr); 450 void cur_thread_finalize(); 451 inline void cur_thread_init() { } 452 #else 453 __attribute__((tls_model("initial-exec"))) 454 extern THREADLOCAL char cur_thread_placeholder[]; 455 inline ThreadState *cur_thread() { 456 return reinterpret_cast<ThreadState *>(cur_thread_placeholder)->current; 457 } 458 inline void cur_thread_init() { 459 ThreadState *thr = reinterpret_cast<ThreadState *>(cur_thread_placeholder); 460 if (UNLIKELY(!thr->current)) 461 thr->current = thr; 462 } 463 inline void set_cur_thread(ThreadState *thr) { 464 reinterpret_cast<ThreadState *>(cur_thread_placeholder)->current = thr; 465 } 466 inline void cur_thread_finalize() { } 467 #endif // SANITIZER_MAC || SANITIZER_ANDROID 468 #endif // SANITIZER_GO 469 470 class ThreadContext final : public ThreadContextBase { 471 public: 472 explicit ThreadContext(int tid); 473 ~ThreadContext(); 474 ThreadState *thr; 475 u32 creation_stack_id; 476 SyncClock sync; 477 // Epoch at which the thread had started. 478 // If we see an event from the thread stamped by an older epoch, 479 // the event is from a dead thread that shared tid with this thread. 480 u64 epoch0; 481 u64 epoch1; 482 483 // Override superclass callbacks. 484 void OnDead() override; 485 void OnJoined(void *arg) override; 486 void OnFinished() override; 487 void OnStarted(void *arg) override; 488 void OnCreated(void *arg) override; 489 void OnReset() override; 490 void OnDetached(void *arg) override; 491 }; 492 493 struct RacyStacks { 494 MD5Hash hash[2]; 495 bool operator==(const RacyStacks &other) const { 496 if (hash[0] == other.hash[0] && hash[1] == other.hash[1]) 497 return true; 498 if (hash[0] == other.hash[1] && hash[1] == other.hash[0]) 499 return true; 500 return false; 501 } 502 }; 503 504 struct RacyAddress { 505 uptr addr_min; 506 uptr addr_max; 507 }; 508 509 struct FiredSuppression { 510 ReportType type; 511 uptr pc_or_addr; 512 Suppression *supp; 513 }; 514 515 struct Context { 516 Context(); 517 518 bool initialized; 519 #if !SANITIZER_GO 520 bool after_multithreaded_fork; 521 #endif 522 523 MetaMap metamap; 524 525 Mutex report_mtx; 526 int nreported; 527 int nmissed_expected; 528 atomic_uint64_t last_symbolize_time_ns; 529 530 void *background_thread; 531 atomic_uint32_t stop_background_thread; 532 533 ThreadRegistry *thread_registry; 534 535 Mutex racy_mtx; 536 Vector<RacyStacks> racy_stacks; 537 Vector<RacyAddress> racy_addresses; 538 // Number of fired suppressions may be large enough. 539 Mutex fired_suppressions_mtx; 540 InternalMmapVector<FiredSuppression> fired_suppressions; 541 DDetector *dd; 542 543 ClockAlloc clock_alloc; 544 545 Flags flags; 546 547 u64 int_alloc_cnt[MBlockTypeCount]; 548 u64 int_alloc_siz[MBlockTypeCount]; 549 }; 550 551 extern Context *ctx; // The one and the only global runtime context. 552 553 ALWAYS_INLINE Flags *flags() { 554 return &ctx->flags; 555 } 556 557 struct ScopedIgnoreInterceptors { 558 ScopedIgnoreInterceptors() { 559 #if !SANITIZER_GO 560 cur_thread()->ignore_interceptors++; 561 #endif 562 } 563 564 ~ScopedIgnoreInterceptors() { 565 #if !SANITIZER_GO 566 cur_thread()->ignore_interceptors--; 567 #endif 568 } 569 }; 570 571 const char *GetObjectTypeFromTag(uptr tag); 572 const char *GetReportHeaderFromTag(uptr tag); 573 uptr TagFromShadowStackFrame(uptr pc); 574 575 class ScopedReportBase { 576 public: 577 void AddMemoryAccess(uptr addr, uptr external_tag, Shadow s, StackTrace stack, 578 const MutexSet *mset); 579 void AddStack(StackTrace stack, bool suppressable = false); 580 void AddThread(const ThreadContext *tctx, bool suppressable = false); 581 void AddThread(int unique_tid, bool suppressable = false); 582 void AddUniqueTid(int unique_tid); 583 void AddMutex(const SyncVar *s); 584 u64 AddMutex(u64 id); 585 void AddLocation(uptr addr, uptr size); 586 void AddSleep(u32 stack_id); 587 void SetCount(int count); 588 589 const ReportDesc *GetReport() const; 590 591 protected: 592 ScopedReportBase(ReportType typ, uptr tag); 593 ~ScopedReportBase(); 594 595 private: 596 ReportDesc *rep_; 597 // Symbolizer makes lots of intercepted calls. If we try to process them, 598 // at best it will cause deadlocks on internal mutexes. 599 ScopedIgnoreInterceptors ignore_interceptors_; 600 601 void AddDeadMutex(u64 id); 602 603 ScopedReportBase(const ScopedReportBase &) = delete; 604 void operator=(const ScopedReportBase &) = delete; 605 }; 606 607 class ScopedReport : public ScopedReportBase { 608 public: 609 explicit ScopedReport(ReportType typ, uptr tag = kExternalTagNone); 610 ~ScopedReport(); 611 612 private: 613 ScopedErrorReportLock lock_; 614 }; 615 616 bool ShouldReport(ThreadState *thr, ReportType typ); 617 ThreadContext *IsThreadStackOrTls(uptr addr, bool *is_stack); 618 void RestoreStack(int tid, const u64 epoch, VarSizeStackTrace *stk, 619 MutexSet *mset, uptr *tag = nullptr); 620 621 // The stack could look like: 622 // <start> | <main> | <foo> | tag | <bar> 623 // This will extract the tag and keep: 624 // <start> | <main> | <foo> | <bar> 625 template<typename StackTraceTy> 626 void ExtractTagFromStack(StackTraceTy *stack, uptr *tag = nullptr) { 627 if (stack->size < 2) return; 628 uptr possible_tag_pc = stack->trace[stack->size - 2]; 629 uptr possible_tag = TagFromShadowStackFrame(possible_tag_pc); 630 if (possible_tag == kExternalTagNone) return; 631 stack->trace_buffer[stack->size - 2] = stack->trace_buffer[stack->size - 1]; 632 stack->size -= 1; 633 if (tag) *tag = possible_tag; 634 } 635 636 template<typename StackTraceTy> 637 void ObtainCurrentStack(ThreadState *thr, uptr toppc, StackTraceTy *stack, 638 uptr *tag = nullptr) { 639 uptr size = thr->shadow_stack_pos - thr->shadow_stack; 640 uptr start = 0; 641 if (size + !!toppc > kStackTraceMax) { 642 start = size + !!toppc - kStackTraceMax; 643 size = kStackTraceMax - !!toppc; 644 } 645 stack->Init(&thr->shadow_stack[start], size, toppc); 646 ExtractTagFromStack(stack, tag); 647 } 648 649 #define GET_STACK_TRACE_FATAL(thr, pc) \ 650 VarSizeStackTrace stack; \ 651 ObtainCurrentStack(thr, pc, &stack); \ 652 stack.ReverseOrder(); 653 654 void MapShadow(uptr addr, uptr size); 655 void MapThreadTrace(uptr addr, uptr size, const char *name); 656 void DontNeedShadowFor(uptr addr, uptr size); 657 void UnmapShadow(ThreadState *thr, uptr addr, uptr size); 658 void InitializeShadowMemory(); 659 void InitializeInterceptors(); 660 void InitializeLibIgnore(); 661 void InitializeDynamicAnnotations(); 662 663 void ForkBefore(ThreadState *thr, uptr pc); 664 void ForkParentAfter(ThreadState *thr, uptr pc); 665 void ForkChildAfter(ThreadState *thr, uptr pc); 666 667 void ReportRace(ThreadState *thr); 668 bool OutputReport(ThreadState *thr, const ScopedReport &srep); 669 bool IsFiredSuppression(Context *ctx, ReportType type, StackTrace trace); 670 bool IsExpectedReport(uptr addr, uptr size); 671 void PrintMatchedBenignRaces(); 672 673 #if defined(TSAN_DEBUG_OUTPUT) && TSAN_DEBUG_OUTPUT >= 1 674 # define DPrintf Printf 675 #else 676 # define DPrintf(...) 677 #endif 678 679 #if defined(TSAN_DEBUG_OUTPUT) && TSAN_DEBUG_OUTPUT >= 2 680 # define DPrintf2 Printf 681 #else 682 # define DPrintf2(...) 683 #endif 684 685 u32 CurrentStackId(ThreadState *thr, uptr pc); 686 ReportStack *SymbolizeStackId(u32 stack_id); 687 void PrintCurrentStack(ThreadState *thr, uptr pc); 688 void PrintCurrentStackSlow(uptr pc); // uses libunwind 689 690 void Initialize(ThreadState *thr); 691 void MaybeSpawnBackgroundThread(); 692 int Finalize(ThreadState *thr); 693 694 void OnUserAlloc(ThreadState *thr, uptr pc, uptr p, uptr sz, bool write); 695 void OnUserFree(ThreadState *thr, uptr pc, uptr p, bool write); 696 697 void MemoryAccess(ThreadState *thr, uptr pc, uptr addr, 698 int kAccessSizeLog, bool kAccessIsWrite, bool kIsAtomic); 699 void MemoryAccessImpl(ThreadState *thr, uptr addr, 700 int kAccessSizeLog, bool kAccessIsWrite, bool kIsAtomic, 701 u64 *shadow_mem, Shadow cur); 702 void MemoryAccessRange(ThreadState *thr, uptr pc, uptr addr, 703 uptr size, bool is_write); 704 void MemoryAccessRangeStep(ThreadState *thr, uptr pc, uptr addr, 705 uptr size, uptr step, bool is_write); 706 void UnalignedMemoryAccess(ThreadState *thr, uptr pc, uptr addr, 707 int size, bool kAccessIsWrite, bool kIsAtomic); 708 709 const int kSizeLog1 = 0; 710 const int kSizeLog2 = 1; 711 const int kSizeLog4 = 2; 712 const int kSizeLog8 = 3; 713 714 void ALWAYS_INLINE MemoryRead(ThreadState *thr, uptr pc, 715 uptr addr, int kAccessSizeLog) { 716 MemoryAccess(thr, pc, addr, kAccessSizeLog, false, false); 717 } 718 719 void ALWAYS_INLINE MemoryWrite(ThreadState *thr, uptr pc, 720 uptr addr, int kAccessSizeLog) { 721 MemoryAccess(thr, pc, addr, kAccessSizeLog, true, false); 722 } 723 724 void ALWAYS_INLINE MemoryReadAtomic(ThreadState *thr, uptr pc, 725 uptr addr, int kAccessSizeLog) { 726 MemoryAccess(thr, pc, addr, kAccessSizeLog, false, true); 727 } 728 729 void ALWAYS_INLINE MemoryWriteAtomic(ThreadState *thr, uptr pc, 730 uptr addr, int kAccessSizeLog) { 731 MemoryAccess(thr, pc, addr, kAccessSizeLog, true, true); 732 } 733 734 void MemoryResetRange(ThreadState *thr, uptr pc, uptr addr, uptr size); 735 void MemoryRangeFreed(ThreadState *thr, uptr pc, uptr addr, uptr size); 736 void MemoryRangeImitateWrite(ThreadState *thr, uptr pc, uptr addr, uptr size); 737 void MemoryRangeImitateWriteOrResetRange(ThreadState *thr, uptr pc, uptr addr, 738 uptr size); 739 740 void ThreadIgnoreBegin(ThreadState *thr, uptr pc, bool save_stack = true); 741 void ThreadIgnoreEnd(ThreadState *thr, uptr pc); 742 void ThreadIgnoreSyncBegin(ThreadState *thr, uptr pc, bool save_stack = true); 743 void ThreadIgnoreSyncEnd(ThreadState *thr, uptr pc); 744 745 void FuncEntry(ThreadState *thr, uptr pc); 746 void FuncExit(ThreadState *thr); 747 748 int ThreadCreate(ThreadState *thr, uptr pc, uptr uid, bool detached); 749 void ThreadStart(ThreadState *thr, int tid, tid_t os_id, 750 ThreadType thread_type); 751 void ThreadFinish(ThreadState *thr); 752 int ThreadConsumeTid(ThreadState *thr, uptr pc, uptr uid); 753 void ThreadJoin(ThreadState *thr, uptr pc, int tid); 754 void ThreadDetach(ThreadState *thr, uptr pc, int tid); 755 void ThreadFinalize(ThreadState *thr); 756 void ThreadSetName(ThreadState *thr, const char *name); 757 int ThreadCount(ThreadState *thr); 758 void ProcessPendingSignals(ThreadState *thr); 759 void ThreadNotJoined(ThreadState *thr, uptr pc, int tid, uptr uid); 760 761 Processor *ProcCreate(); 762 void ProcDestroy(Processor *proc); 763 void ProcWire(Processor *proc, ThreadState *thr); 764 void ProcUnwire(Processor *proc, ThreadState *thr); 765 766 // Note: the parameter is called flagz, because flags is already taken 767 // by the global function that returns flags. 768 void MutexCreate(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 769 void MutexDestroy(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 770 void MutexPreLock(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 771 void MutexPostLock(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0, 772 int rec = 1); 773 int MutexUnlock(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 774 void MutexPreReadLock(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 775 void MutexPostReadLock(ThreadState *thr, uptr pc, uptr addr, u32 flagz = 0); 776 void MutexReadUnlock(ThreadState *thr, uptr pc, uptr addr); 777 void MutexReadOrWriteUnlock(ThreadState *thr, uptr pc, uptr addr); 778 void MutexRepair(ThreadState *thr, uptr pc, uptr addr); // call on EOWNERDEAD 779 void MutexInvalidAccess(ThreadState *thr, uptr pc, uptr addr); 780 781 void Acquire(ThreadState *thr, uptr pc, uptr addr); 782 // AcquireGlobal synchronizes the current thread with all other threads. 783 // In terms of happens-before relation, it draws a HB edge from all threads 784 // (where they happen to execute right now) to the current thread. We use it to 785 // handle Go finalizers. Namely, finalizer goroutine executes AcquireGlobal 786 // right before executing finalizers. This provides a coarse, but simple 787 // approximation of the actual required synchronization. 788 void AcquireGlobal(ThreadState *thr, uptr pc); 789 void Release(ThreadState *thr, uptr pc, uptr addr); 790 void ReleaseStoreAcquire(ThreadState *thr, uptr pc, uptr addr); 791 void ReleaseStore(ThreadState *thr, uptr pc, uptr addr); 792 void AfterSleep(ThreadState *thr, uptr pc); 793 void AcquireImpl(ThreadState *thr, uptr pc, SyncClock *c); 794 void ReleaseImpl(ThreadState *thr, uptr pc, SyncClock *c); 795 void ReleaseStoreAcquireImpl(ThreadState *thr, uptr pc, SyncClock *c); 796 void ReleaseStoreImpl(ThreadState *thr, uptr pc, SyncClock *c); 797 void AcquireReleaseImpl(ThreadState *thr, uptr pc, SyncClock *c); 798 799 // The hacky call uses custom calling convention and an assembly thunk. 800 // It is considerably faster that a normal call for the caller 801 // if it is not executed (it is intended for slow paths from hot functions). 802 // The trick is that the call preserves all registers and the compiler 803 // does not treat it as a call. 804 // If it does not work for you, use normal call. 805 #if !SANITIZER_DEBUG && defined(__x86_64__) && !SANITIZER_MAC 806 // The caller may not create the stack frame for itself at all, 807 // so we create a reserve stack frame for it (1024b must be enough). 808 #define HACKY_CALL(f) \ 809 __asm__ __volatile__("sub $1024, %%rsp;" \ 810 CFI_INL_ADJUST_CFA_OFFSET(1024) \ 811 ".hidden " #f "_thunk;" \ 812 "call " #f "_thunk;" \ 813 "add $1024, %%rsp;" \ 814 CFI_INL_ADJUST_CFA_OFFSET(-1024) \ 815 ::: "memory", "cc"); 816 #else 817 #define HACKY_CALL(f) f() 818 #endif 819 820 void TraceSwitch(ThreadState *thr); 821 uptr TraceTopPC(ThreadState *thr); 822 uptr TraceSize(); 823 uptr TraceParts(); 824 Trace *ThreadTrace(int tid); 825 826 extern "C" void __tsan_trace_switch(); 827 void ALWAYS_INLINE TraceAddEvent(ThreadState *thr, FastState fs, 828 EventType typ, u64 addr) { 829 if (!kCollectHistory) 830 return; 831 DCHECK_GE((int)typ, 0); 832 DCHECK_LE((int)typ, 7); 833 DCHECK_EQ(GetLsb(addr, kEventPCBits), addr); 834 u64 pos = fs.GetTracePos(); 835 if (UNLIKELY((pos % kTracePartSize) == 0)) { 836 #if !SANITIZER_GO 837 HACKY_CALL(__tsan_trace_switch); 838 #else 839 TraceSwitch(thr); 840 #endif 841 } 842 Event *trace = (Event*)GetThreadTrace(fs.tid()); 843 Event *evp = &trace[pos]; 844 Event ev = (u64)addr | ((u64)typ << kEventPCBits); 845 *evp = ev; 846 } 847 848 #if !SANITIZER_GO 849 uptr ALWAYS_INLINE HeapEnd() { 850 return HeapMemEnd() + PrimaryAllocator::AdditionalSize(); 851 } 852 #endif 853 854 ThreadState *FiberCreate(ThreadState *thr, uptr pc, unsigned flags); 855 void FiberDestroy(ThreadState *thr, uptr pc, ThreadState *fiber); 856 void FiberSwitch(ThreadState *thr, uptr pc, ThreadState *fiber, unsigned flags); 857 858 // These need to match __tsan_switch_to_fiber_* flags defined in 859 // tsan_interface.h. See documentation there as well. 860 enum FiberSwitchFlags { 861 FiberSwitchFlagNoSync = 1 << 0, // __tsan_switch_to_fiber_no_sync 862 }; 863 864 } // namespace __tsan 865 866 #endif // TSAN_RTL_H 867