1 /* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ART_RUNTIME_THREAD_LIST_H_ 18 #define ART_RUNTIME_THREAD_LIST_H_ 19 20 #include "base/mutex.h" 21 #include "jni.h" 22 #include "object_callbacks.h" 23 24 #include <bitset> 25 #include <list> 26 27 namespace art { 28 class Closure; 29 class Thread; 30 class TimingLogger; 31 32 class ThreadList { 33 public: 34 static const uint32_t kMaxThreadId = 0xFFFF; 35 static const uint32_t kInvalidThreadId = 0; 36 static const uint32_t kMainThreadId = 1; 37 38 explicit ThreadList(); 39 ~ThreadList(); 40 41 void DumpForSigQuit(std::ostream& os) 42 LOCKS_EXCLUDED(Locks::thread_list_lock_) 43 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 44 void DumpLocked(std::ostream& os) // For thread suspend timeout dumps. 45 EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_lock_) 46 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 47 pid_t GetLockOwner(); // For SignalCatcher. 48 49 // Thread suspension support. 50 void ResumeAll() 51 UNLOCK_FUNCTION(Locks::mutator_lock_) 52 LOCKS_EXCLUDED(Locks::thread_list_lock_, 53 Locks::thread_suspend_count_lock_); 54 void Resume(Thread* thread, bool for_debugger = false) 55 LOCKS_EXCLUDED(Locks::thread_suspend_count_lock_); 56 57 // Suspends all threads and gets exclusive access to the mutator_lock_. 58 void SuspendAll() 59 EXCLUSIVE_LOCK_FUNCTION(Locks::mutator_lock_) 60 LOCKS_EXCLUDED(Locks::thread_list_lock_, 61 Locks::thread_suspend_count_lock_); 62 63 64 // Suspend a thread using a peer, typically used by the debugger. Returns the thread on success, 65 // else NULL. The peer is used to identify the thread to avoid races with the thread terminating. 66 // If the thread should be suspended then value of request_suspension should be true otherwise 67 // the routine will wait for a previous suspend request. If the suspension times out then *timeout 68 // is set to true. 69 Thread* SuspendThreadByPeer(jobject peer, bool request_suspension, bool debug_suspension, 70 bool* timed_out) 71 EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_suspend_thread_lock_) 72 LOCKS_EXCLUDED(Locks::mutator_lock_, 73 Locks::thread_list_lock_, 74 Locks::thread_suspend_count_lock_); 75 76 // Suspend a thread using its thread id, typically used by lock/monitor inflation. Returns the 77 // thread on success else NULL. The thread id is used to identify the thread to avoid races with 78 // the thread terminating. Note that as thread ids are recycled this may not suspend the expected 79 // thread, that may be terminating. If the suspension times out then *timeout is set to true. 80 Thread* SuspendThreadByThreadId(uint32_t thread_id, bool debug_suspension, bool* timed_out) 81 EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_suspend_thread_lock_) 82 LOCKS_EXCLUDED(Locks::mutator_lock_, 83 Locks::thread_list_lock_, 84 Locks::thread_suspend_count_lock_); 85 86 // Find an already suspended thread (or self) by its id. 87 Thread* FindThreadByThreadId(uint32_t thin_lock_id); 88 89 // Run a checkpoint on threads, running threads are not suspended but run the checkpoint inside 90 // of the suspend check. Returns how many checkpoints we should expect to run. 91 size_t RunCheckpoint(Closure* checkpoint_function) 92 LOCKS_EXCLUDED(Locks::thread_list_lock_, 93 Locks::thread_suspend_count_lock_); 94 95 size_t RunCheckpointOnRunnableThreads(Closure* checkpoint_function) 96 LOCKS_EXCLUDED(Locks::thread_list_lock_, Locks::thread_suspend_count_lock_); 97 98 // Suspends all threads 99 void SuspendAllForDebugger() 100 LOCKS_EXCLUDED(Locks::mutator_lock_, 101 Locks::thread_list_lock_, 102 Locks::thread_suspend_count_lock_); 103 104 void SuspendSelfForDebugger() 105 LOCKS_EXCLUDED(Locks::thread_suspend_count_lock_); 106 107 void UndoDebuggerSuspensions() 108 LOCKS_EXCLUDED(Locks::thread_list_lock_, 109 Locks::thread_suspend_count_lock_); 110 111 // Iterates over all the threads. 112 void ForEach(void (*callback)(Thread*, void*), void* context) 113 EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_lock_); 114 115 // Add/remove current thread from list. 116 void Register(Thread* self) 117 EXCLUSIVE_LOCKS_REQUIRED(Locks::runtime_shutdown_lock_) 118 LOCKS_EXCLUDED(Locks::mutator_lock_, Locks::thread_list_lock_); 119 void Unregister(Thread* self) LOCKS_EXCLUDED(Locks::mutator_lock_, Locks::thread_list_lock_); 120 121 void VisitRoots(RootCallback* callback, void* arg) const 122 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 123 124 void VerifyRoots(VerifyRootCallback* callback, void* arg) const 125 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 126 127 // Return a copy of the thread list. GetList()128 std::list<Thread*> GetList() EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_lock_) { 129 return list_; 130 } 131 132 void DumpNativeStacks(std::ostream& os) 133 LOCKS_EXCLUDED(Locks::thread_list_lock_); 134 135 private: 136 uint32_t AllocThreadId(Thread* self); 137 void ReleaseThreadId(Thread* self, uint32_t id) LOCKS_EXCLUDED(Locks::allocated_thread_ids_lock_); 138 139 bool Contains(Thread* thread) EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_lock_); 140 bool Contains(pid_t tid) EXCLUSIVE_LOCKS_REQUIRED(Locks::thread_list_lock_); 141 142 void DumpUnattachedThreads(std::ostream& os) 143 LOCKS_EXCLUDED(Locks::thread_list_lock_); 144 145 void SuspendAllDaemonThreads() 146 LOCKS_EXCLUDED(Locks::thread_list_lock_, 147 Locks::thread_suspend_count_lock_); 148 void WaitForOtherNonDaemonThreadsToExit() 149 LOCKS_EXCLUDED(Locks::thread_list_lock_, 150 Locks::thread_suspend_count_lock_); 151 152 void AssertThreadsAreSuspended(Thread* self, Thread* ignore1, Thread* ignore2 = NULL) 153 LOCKS_EXCLUDED(Locks::thread_list_lock_, 154 Locks::thread_suspend_count_lock_); 155 156 std::bitset<kMaxThreadId> allocated_ids_ GUARDED_BY(Locks::allocated_thread_ids_lock_); 157 158 // The actual list of all threads. 159 std::list<Thread*> list_ GUARDED_BY(Locks::thread_list_lock_); 160 161 // Ongoing suspend all requests, used to ensure threads added to list_ respect SuspendAll. 162 int suspend_all_count_ GUARDED_BY(Locks::thread_suspend_count_lock_); 163 int debug_suspend_all_count_ GUARDED_BY(Locks::thread_suspend_count_lock_); 164 165 // Signaled when threads terminate. Used to determine when all non-daemons have terminated. 166 ConditionVariable thread_exit_cond_ GUARDED_BY(Locks::thread_list_lock_); 167 168 friend class Thread; 169 170 DISALLOW_COPY_AND_ASSIGN(ThreadList); 171 }; 172 173 } // namespace art 174 175 #endif // ART_RUNTIME_THREAD_LIST_H_ 176