1 // Copyright 2012 The Chromium Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef BASE_THREADING_THREAD_H_ 6 #define BASE_THREADING_THREAD_H_ 7 8 #include <stddef.h> 9 10 #include <memory> 11 #include <string> 12 13 #include "base/base_export.h" 14 #include "base/check.h" 15 #include "base/compiler_specific.h" 16 #include "base/functional/callback.h" 17 #include "base/memory/raw_ptr.h" 18 #include "base/message_loop/message_pump_type.h" 19 #include "base/sequence_checker.h" 20 #include "base/synchronization/atomic_flag.h" 21 #include "base/synchronization/lock.h" 22 #include "base/synchronization/waitable_event.h" 23 #include "base/task/single_thread_task_runner.h" 24 #include "base/threading/platform_thread.h" 25 #include "build/build_config.h" 26 27 namespace base { 28 29 class MessagePump; 30 class RunLoop; 31 32 // IMPORTANT: Instead of creating a base::Thread, consider using 33 // base::ThreadPool::Create(Sequenced|SingleThread)TaskRunner(). 34 // 35 // A simple thread abstraction that establishes a MessageLoop on a new thread. 36 // The consumer uses the MessageLoop of the thread to cause code to execute on 37 // the thread. When this object is destroyed the thread is terminated. All 38 // pending tasks queued on the thread's message loop will run to completion 39 // before the thread is terminated. 40 // 41 // WARNING! SUBCLASSES MUST CALL Stop() IN THEIR DESTRUCTORS! See ~Thread(). 42 // 43 // After the thread is stopped, the destruction sequence is: 44 // 45 // (1) Thread::CleanUp() 46 // (2) MessageLoop::~MessageLoop 47 // (3.b) CurrentThread::DestructionObserver::WillDestroyCurrentMessageLoop 48 // 49 // This API is not thread-safe: unless indicated otherwise its methods are only 50 // valid from the owning sequence (which is the one from which Start() is 51 // invoked -- should it differ from the one on which it was constructed). 52 // 53 // Sometimes it's useful to kick things off on the initial sequence (e.g. 54 // construction, Start(), task_runner()), but to then hand the Thread over to a 55 // pool of users for the last one of them to destroy it when done. For that use 56 // case, Thread::DetachFromSequence() allows the owning sequence to give up 57 // ownership. The caller is then responsible to ensure a happens-after 58 // relationship between the DetachFromSequence() call and the next use of that 59 // Thread object (including ~Thread()). 60 class BASE_EXPORT Thread : PlatformThread::Delegate { 61 public: 62 class BASE_EXPORT Delegate { 63 public: 64 virtual ~Delegate() = default; 65 66 virtual scoped_refptr<SingleThreadTaskRunner> GetDefaultTaskRunner() = 0; 67 68 // Binds a RunLoop::Delegate and task runner CurrentDefaultHandle to the 69 // thread. 70 virtual void BindToCurrentThread() = 0; 71 }; 72 73 struct BASE_EXPORT Options { 74 using MessagePumpFactory = 75 RepeatingCallback<std::unique_ptr<MessagePump>()>; 76 77 Options(); 78 Options(MessagePumpType type, size_t size); 79 explicit Options(ThreadType thread_type); 80 Options(Options&& other); 81 Options& operator=(Options&& other); 82 ~Options(); 83 84 // Specifies the type of message pump that will be allocated on the thread. 85 // This is ignored if message_pump_factory.is_null() is false. 86 MessagePumpType message_pump_type = MessagePumpType::DEFAULT; 87 88 // An unbound Delegate that will be bound to the thread. Ownership 89 // of |delegate| will be transferred to the thread. 90 std::unique_ptr<Delegate> delegate = nullptr; 91 92 // Used to create the MessagePump for the MessageLoop. The callback is Run() 93 // on the thread. If message_pump_factory.is_null(), then a MessagePump 94 // appropriate for |message_pump_type| is created. Setting this forces the 95 // MessagePumpType to TYPE_CUSTOM. This is not compatible with a non-null 96 // |delegate|. 97 MessagePumpFactory message_pump_factory; 98 99 // Specifies the maximum stack size that the thread is allowed to use. 100 // This does not necessarily correspond to the thread's initial stack size. 101 // A value of 0 indicates that the default maximum should be used. 102 size_t stack_size = 0; 103 104 // Specifies the initial thread type. 105 ThreadType thread_type = ThreadType::kDefault; 106 107 // If false, the thread will not be joined on destruction. This is intended 108 // for threads that want TaskShutdownBehavior::CONTINUE_ON_SHUTDOWN 109 // semantics. Non-joinable threads can't be joined (must be leaked and 110 // can't be destroyed or Stop()'ed). 111 // TODO(gab): allow non-joinable instances to be deleted without causing 112 // user-after-frees (proposal @ https://crbug.com/629139#c14) 113 bool joinable = true; 114 IsValidOptions115 bool IsValid() const { return !moved_from; } 116 117 private: 118 // Set to true when the object is moved into another. Use to prevent reuse 119 // of a moved-from object. 120 bool moved_from = false; 121 }; 122 123 // Constructor. 124 // name is a display string to identify the thread. 125 explicit Thread(const std::string& name); 126 127 Thread(const Thread&) = delete; 128 Thread& operator=(const Thread&) = delete; 129 130 // Destroys the thread, stopping it if necessary. 131 // 132 // NOTE: ALL SUBCLASSES OF Thread MUST CALL Stop() IN THEIR DESTRUCTORS (or 133 // guarantee Stop() is explicitly called before the subclass is destroyed). 134 // This is required to avoid a data race between the destructor modifying the 135 // vtable, and the thread's ThreadMain calling the virtual method Run(). It 136 // also ensures that the CleanUp() virtual method is called on the subclass 137 // before it is destructed. 138 ~Thread() override; 139 140 #if BUILDFLAG(IS_WIN) 141 // Causes the thread to initialize COM. This must be called before calling 142 // Start() or StartWithOptions(). If |use_mta| is false, the thread is also 143 // started with a TYPE_UI message loop. It is an error to call 144 // init_com_with_mta(false) and then StartWithOptions() with any message loop 145 // type other than TYPE_UI. init_com_with_mta(bool use_mta)146 void init_com_with_mta(bool use_mta) { 147 DCHECK(!delegate_); 148 com_status_ = use_mta ? MTA : STA; 149 } 150 #endif 151 152 // Starts the thread. Returns true if the thread was successfully started; 153 // otherwise, returns false. Upon successful return, the message_loop() 154 // getter will return non-null. 155 // 156 // Note: This function can't be called on Windows with the loader lock held; 157 // i.e. during a DllMain, global object construction or destruction, atexit() 158 // callback. 159 bool Start(); 160 161 // Starts the thread. Behaves exactly like Start in addition to allow to 162 // override the default options. 163 // 164 // Note: This function can't be called on Windows with the loader lock held; 165 // i.e. during a DllMain, global object construction or destruction, atexit() 166 // callback. 167 bool StartWithOptions(Options options); 168 169 // Starts the thread and wait for the thread to start and run initialization 170 // before returning. It's same as calling Start() and then 171 // WaitUntilThreadStarted(). 172 // Note that using this (instead of Start() or StartWithOptions() causes 173 // jank on the calling thread, should be used only in testing code. 174 bool StartAndWaitForTesting(); 175 176 // Blocks until the thread starts running. Called within StartAndWait(). 177 // Note that calling this causes jank on the calling thread, must be used 178 // carefully for production code. 179 bool WaitUntilThreadStarted() const; 180 181 // Blocks until all tasks previously posted to this thread have been executed. 182 void FlushForTesting(); 183 184 // Signals the thread to exit and returns once the thread has exited. The 185 // Thread object is completely reset and may be used as if it were newly 186 // constructed (i.e., Start may be called again). Can only be called if 187 // |joinable_|. 188 // 189 // Stop may be called multiple times and is simply ignored if the thread is 190 // already stopped or currently stopping. 191 // 192 // Start/Stop are not thread-safe and callers that desire to invoke them from 193 // different threads must ensure mutual exclusion. 194 // 195 // NOTE: If you are a consumer of Thread, it is not necessary to call this 196 // before deleting your Thread objects, as the destructor will do it. 197 // IF YOU ARE A SUBCLASS OF Thread, YOU MUST CALL THIS IN YOUR DESTRUCTOR. 198 void Stop(); 199 200 // Signals the thread to exit in the near future. 201 // 202 // WARNING: This function is not meant to be commonly used. Use at your own 203 // risk. Calling this function will cause message_loop() to become invalid in 204 // the near future. This function was created to workaround a specific 205 // deadlock on Windows with printer worker thread. In any other case, Stop() 206 // should be used. 207 // 208 // Call Stop() to reset the thread object once it is known that the thread has 209 // quit. 210 void StopSoon(); 211 212 // Detaches the owning sequence, indicating that the next call to this API 213 // (including ~Thread()) can happen from a different sequence (to which it 214 // will be rebound). This call itself must happen on the current owning 215 // sequence and the caller must ensure the next API call has a happens-after 216 // relationship with this one. 217 void DetachFromSequence(); 218 219 // Returns a TaskRunner for this thread. Use the TaskRunner's PostTask 220 // methods to execute code on the thread. Returns nullptr if the thread is not 221 // running (e.g. before Start or after Stop have been called). Callers can 222 // hold on to this even after the thread is gone; in this situation, attempts 223 // to PostTask() will fail. 224 // 225 // In addition to this Thread's owning sequence, this can also safely be 226 // called from the underlying thread itself. task_runner()227 scoped_refptr<SingleThreadTaskRunner> task_runner() const { 228 // This class doesn't provide synchronization around |message_loop_base_| 229 // and as such only the owner should access it (and the underlying thread 230 // which never sees it before it's set). In practice, many callers are 231 // coming from unrelated threads but provide their own implicit (e.g. memory 232 // barriers from task posting) or explicit (e.g. locks) synchronization 233 // making the access of |message_loop_base_| safe... Changing all of those 234 // callers is unfeasible; instead verify that they can reliably see 235 // |message_loop_base_ != nullptr| without synchronization as a proof that 236 // their external synchronization catches the unsynchronized effects of 237 // Start(). 238 DCHECK(owning_sequence_checker_.CalledOnValidSequence() || 239 (id_event_.IsSignaled() && id_ == PlatformThread::CurrentId()) || 240 delegate_); 241 return delegate_ ? delegate_->GetDefaultTaskRunner() : nullptr; 242 } 243 244 // Returns the name of this thread (for display in debugger too). thread_name()245 const std::string& thread_name() const LIFETIME_BOUND { return name_; } 246 247 // Returns the thread ID. Should not be called before the first Start*() 248 // call. Keeps on returning the same ID even after a Stop() call. The next 249 // Start*() call renews the ID. 250 // 251 // WARNING: This function will block if the thread hasn't started yet. 252 // 253 // This method is thread-safe. 254 PlatformThreadId GetThreadId() const; 255 256 // Returns true if the thread has been started, and not yet stopped. 257 bool IsRunning() const; 258 259 protected: 260 // Called just prior to starting the message loop Init()261 virtual void Init() {} 262 263 // Called to start the run loop. Inhibit tail calls to this function so that 264 // the caller will be on the stack for profiling and crash analysis. 265 NOT_TAIL_CALLED virtual void Run(RunLoop* run_loop); 266 267 // Called just after the message loop ends CleanUp()268 virtual void CleanUp() {} 269 270 static void SetThreadWasQuitProperly(bool flag); 271 static bool GetThreadWasQuitProperly(); 272 273 private: 274 // Friends for message_loop() access: 275 friend class MessageLoopTaskRunnerTest; 276 friend class ScheduleWorkTest; 277 278 #if BUILDFLAG(IS_WIN) 279 enum ComStatus { 280 NONE, 281 STA, 282 MTA, 283 }; 284 #endif 285 286 // PlatformThread::Delegate methods: 287 void ThreadMain() override; 288 289 void ThreadQuitHelper(); 290 291 #if BUILDFLAG(IS_WIN) 292 // Whether this thread needs to initialize COM, and if so, in what mode. 293 ComStatus com_status_ = NONE; 294 #endif 295 296 // Mirrors the Options::joinable field used to start this thread. Verified 297 // on Stop() -- non-joinable threads can't be joined (must be leaked). 298 bool joinable_ = true; 299 300 // If true, we're in the middle of stopping, and shouldn't access 301 // |message_loop_|. It may non-nullptr and invalid. 302 // Should be written on the thread that created this thread. Also read data 303 // could be wrong on other threads. 304 bool stopping_ = false; 305 306 // True while inside of Run(). 307 bool running_ = false; 308 mutable base::Lock running_lock_; // Protects |running_|. 309 310 // The thread's handle. 311 PlatformThreadHandle thread_; 312 mutable base::Lock thread_lock_; // Protects |thread_|. 313 314 // The thread's id once it has started. 315 PlatformThreadId id_ = kInvalidThreadId; 316 // Protects |id_| which must only be read while it's signaled. 317 mutable WaitableEvent id_event_; 318 319 // The thread's Delegate and RunLoop are valid only while the thread is 320 // alive. Set by the created thread. 321 std::unique_ptr<Delegate> delegate_; 322 323 raw_ptr<RunLoop> run_loop_ = nullptr; 324 325 // The name of the thread. Used for debugging purposes. 326 const std::string name_; 327 328 // Signaled when the created thread gets ready to use the message loop. 329 mutable WaitableEvent start_event_; 330 331 // This class is not thread-safe, use this to verify access from the owning 332 // sequence of the Thread. 333 SequenceChecker owning_sequence_checker_; 334 }; 335 336 } // namespace base 337 338 #endif // BASE_THREADING_THREAD_H_ 339