1//===-- asan_thread.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 AddressSanitizer, an address sanity checker. 11// 12// ASan-private header for asan_thread.cc. 13//===----------------------------------------------------------------------===// 14#ifndef ASAN_THREAD_H 15#define ASAN_THREAD_H 16 17#include "asan_allocator.h" 18#include "asan_internal.h" 19#include "asan_stack.h" 20#include "asan_stats.h" 21#include "sanitizer_common/sanitizer_libc.h" 22 23namespace __asan { 24 25const u32 kInvalidTid = 0xffffff; // Must fit into 24 bits. 26 27class AsanThread; 28 29// These objects are created for every thread and are never deleted, 30// so we can find them by tid even if the thread is long dead. 31class AsanThreadSummary { 32 public: 33 explicit AsanThreadSummary(LinkerInitialized) { } // for T0. 34 void Init(u32 parent_tid, StackTrace *stack) { 35 parent_tid_ = parent_tid; 36 announced_ = false; 37 tid_ = kInvalidTid; 38 if (stack) { 39 internal_memcpy(&stack_, stack, sizeof(*stack)); 40 } 41 thread_ = 0; 42 } 43 u32 tid() { return tid_; } 44 void set_tid(u32 tid) { tid_ = tid; } 45 u32 parent_tid() { return parent_tid_; } 46 bool announced() { return announced_; } 47 void set_announced(bool announced) { announced_ = announced; } 48 StackTrace *stack() { return &stack_; } 49 AsanThread *thread() { return thread_; } 50 void set_thread(AsanThread *thread) { thread_ = thread; } 51 static void TSDDtor(void *tsd); 52 53 private: 54 u32 tid_; 55 u32 parent_tid_; 56 bool announced_; 57 StackTrace stack_; 58 AsanThread *thread_; 59}; 60 61// AsanThread are stored in TSD and destroyed when the thread dies. 62class AsanThread { 63 public: 64 explicit AsanThread(LinkerInitialized); // for T0. 65 static AsanThread *Create(u32 parent_tid, thread_callback_t start_routine, 66 void *arg, StackTrace *stack); 67 void Destroy(); 68 69 void Init(); // Should be called from the thread itself. 70 thread_return_t ThreadStart(); 71 72 uptr stack_top() { return stack_top_; } 73 uptr stack_bottom() { return stack_bottom_; } 74 uptr stack_size() { return stack_top_ - stack_bottom_; } 75 u32 tid() { return summary_->tid(); } 76 AsanThreadSummary *summary() { return summary_; } 77 void set_summary(AsanThreadSummary *summary) { summary_ = summary; } 78 79 const char *GetFrameNameByAddr(uptr addr, uptr *offset); 80 81 bool AddrIsInStack(uptr addr) { 82 return addr >= stack_bottom_ && addr < stack_top_; 83 } 84 85 FakeStack &fake_stack() { return fake_stack_; } 86 AsanThreadLocalMallocStorage &malloc_storage() { return malloc_storage_; } 87 AsanStats &stats() { return stats_; } 88 89 private: 90 void SetThreadStackTopAndBottom(); 91 void ClearShadowForThreadStack(); 92 AsanThreadSummary *summary_; 93 thread_callback_t start_routine_; 94 void *arg_; 95 uptr stack_top_; 96 uptr stack_bottom_; 97 98 FakeStack fake_stack_; 99 AsanThreadLocalMallocStorage malloc_storage_; 100 AsanStats stats_; 101}; 102 103} // namespace __asan 104 105#endif // ASAN_THREAD_H 106