thread_pool.h 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250
  1. // Copyright 2019 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef BASE_TASK_THREAD_POOL_H_
  5. #define BASE_TASK_THREAD_POOL_H_
  6. #include <memory>
  7. #include <utility>
  8. namespace base {
  9. // TODO(gab): thread_pool.h should include task_traits.h but it can't during the
  10. // migration because task_traits.h has to include thread_pool.h to get the old
  11. // base::ThreadPool() trait constructor and that would create a circular
  12. // dependency. Some of the includes below result in an extended version of this
  13. // circular dependency. These forward-declarations are temporarily required for
  14. // the duration of the migration.
  15. enum class TaskPriority : uint8_t;
  16. enum class TaskShutdownBehavior : uint8_t;
  17. enum class ThreadPolicy : uint8_t;
  18. struct MayBlock;
  19. struct WithBaseSyncPrimitives;
  20. class TaskTraits;
  21. // UpdateableSequencedTaskRunner is part of this dance too because
  22. // updateable_sequenced_task_runner.h includes task_traits.h
  23. class UpdateableSequencedTaskRunner;
  24. } // namespace base
  25. #include "base/base_export.h"
  26. #include "base/bind.h"
  27. #include "base/callback.h"
  28. #include "base/callback_helpers.h"
  29. #include "base/location.h"
  30. #include "base/memory/scoped_refptr.h"
  31. #include "base/post_task_and_reply_with_result_internal.h"
  32. #include "base/sequenced_task_runner.h"
  33. #include "base/single_thread_task_runner.h"
  34. #include "base/task/single_thread_task_runner_thread_mode.h"
  35. #include "base/task_runner.h"
  36. #include "base/time/time.h"
  37. #include "build/build_config.h"
  38. namespace base {
  39. // This is the interface to post tasks to base's thread pool.
  40. //
  41. // To post a simple one-off task with default traits:
  42. // base::ThreadPool::PostTask(FROM_HERE, base::BindOnce(...));
  43. //
  44. // To post a high priority one-off task to respond to a user interaction:
  45. // base::ThreadPool::PostTask(
  46. // FROM_HERE,
  47. // {base::TaskPriority::USER_BLOCKING},
  48. // base::BindOnce(...));
  49. //
  50. // To post tasks that must run in sequence with default traits:
  51. // scoped_refptr<SequencedTaskRunner> task_runner =
  52. // base::ThreadPool::CreateSequencedTaskRunner();
  53. // task_runner->PostTask(FROM_HERE, base::BindOnce(...));
  54. // task_runner->PostTask(FROM_HERE, base::BindOnce(...));
  55. //
  56. // To post tasks that may block, must run in sequence and can be skipped on
  57. // shutdown:
  58. // scoped_refptr<SequencedTaskRunner> task_runner =
  59. // base::ThreadPool::CreateSequencedTaskRunner(
  60. // {MayBlock(), TaskShutdownBehavior::SKIP_ON_SHUTDOWN});
  61. // task_runner->PostTask(FROM_HERE, base::BindOnce(...));
  62. // task_runner->PostTask(FROM_HERE, base::BindOnce(...));
  63. //
  64. // The default traits apply to tasks that:
  65. // (1) don't block (ref. MayBlock() and WithBaseSyncPrimitives()),
  66. // (2) prefer inheriting the current priority to specifying their own, and
  67. // (3) can either block shutdown or be skipped on shutdown
  68. // (implementation is free to choose a fitting default).
  69. // Explicit traits must be specified for tasks for which these loose
  70. // requirements are not sufficient.
  71. //
  72. // Prerequisite: A ThreadPoolInstance must have been registered for the current
  73. // process via ThreadPoolInstance::Set() before the API below can be invoked.
  74. // This is typically done during the initialization phase in each process. If
  75. // your code is not running in that phase, you most likely don't have to worry
  76. // about this. You will encounter DCHECKs or nullptr dereferences if this is
  77. // violated. For tests, use base::test::TaskEnvironment.
  78. class BASE_EXPORT ThreadPool {
  79. public:
  80. // base::ThreadPool is meant to be a static API. Do not use this constructor
  81. // in new code! It is a temporary hack to support the old base::ThreadPool()
  82. // trait during the migration to static base::ThreadPool:: APIs.
  83. // Tasks and task runners with this trait will run in the thread pool,
  84. // concurrently with tasks on other task runners. If you need mutual exclusion
  85. // between tasks, see base::ThreadPool::CreateSequencedTaskRunner.
  86. ThreadPool() = default;
  87. // Equivalent to calling PostTask with default TaskTraits.
  88. static bool PostTask(const Location& from_here, OnceClosure task);
  89. inline static bool PostTask(OnceClosure task,
  90. const Location& from_here = Location::Current()) {
  91. return PostTask(from_here, std::move(task));
  92. }
  93. // Equivalent to calling PostDelayedTask with default TaskTraits.
  94. //
  95. // Use PostDelayedTask to specify a BEST_EFFORT priority if the task doesn't
  96. // have to run as soon as |delay| expires.
  97. static bool PostDelayedTask(const Location& from_here,
  98. OnceClosure task,
  99. TimeDelta delay);
  100. // Equivalent to calling PostTaskAndReply with default TaskTraits.
  101. static bool PostTaskAndReply(const Location& from_here,
  102. OnceClosure task,
  103. OnceClosure reply);
  104. // Equivalent to calling PostTaskAndReplyWithResult with default TaskTraits.
  105. //
  106. // Though RepeatingCallback is convertible to OnceCallback, we need a
  107. // CallbackType template since we can not use template deduction and object
  108. // conversion at once on the overload resolution.
  109. // TODO(crbug.com/714018): Update all callers of the RepeatingCallback version
  110. // to use OnceCallback and remove the CallbackType template.
  111. template <template <typename> class CallbackType,
  112. typename TaskReturnType,
  113. typename ReplyArgType,
  114. typename = EnableIfIsBaseCallback<CallbackType>>
  115. static bool PostTaskAndReplyWithResult(
  116. const Location& from_here,
  117. CallbackType<TaskReturnType()> task,
  118. CallbackType<void(ReplyArgType)> reply) {
  119. return ThreadPool::PostTaskAndReplyWithResult(
  120. from_here, {}, std::move(task), std::move(reply));
  121. }
  122. // Posts |task| with specific |traits|. Returns false if the task definitely
  123. // won't run because of current shutdown state.
  124. static bool PostTask(const Location& from_here,
  125. const TaskTraits& traits,
  126. OnceClosure task);
  127. // Posts |task| with specific |traits|. |task| will not run before |delay|
  128. // expires. Returns false if the task definitely won't run because of current
  129. // shutdown state.
  130. //
  131. // Specify a BEST_EFFORT priority via |traits| if the task doesn't have to run
  132. // as soon as |delay| expires.
  133. static bool PostDelayedTask(const Location& from_here,
  134. const TaskTraits& traits,
  135. OnceClosure task,
  136. TimeDelta delay);
  137. // Posts |task| with specific |traits| and posts |reply| on the caller's
  138. // execution context (i.e. same sequence or thread and same TaskTraits if
  139. // applicable) when |task| completes. Returns false if the task definitely
  140. // won't run because of current shutdown state. Can only be called when
  141. // SequencedTaskRunnerHandle::IsSet().
  142. static bool PostTaskAndReply(const Location& from_here,
  143. const TaskTraits& traits,
  144. OnceClosure task,
  145. OnceClosure reply);
  146. // Posts |task| with specific |traits| and posts |reply| with the return value
  147. // of |task| as argument on the caller's execution context (i.e. same sequence
  148. // or thread and same TaskTraits if applicable) when |task| completes. Returns
  149. // false if the task definitely won't run because of current shutdown state.
  150. // Can only be called when SequencedTaskRunnerHandle::IsSet().
  151. //
  152. // Though RepeatingCallback is convertible to OnceCallback, we need a
  153. // CallbackType template since we can not use template deduction and object
  154. // conversion at once on the overload resolution.
  155. // TODO(crbug.com/714018): Update all callers of the RepeatingCallback version
  156. // to use OnceCallback and remove the CallbackType template.
  157. template <template <typename> class CallbackType,
  158. typename TaskReturnType,
  159. typename ReplyArgType,
  160. typename = EnableIfIsBaseCallback<CallbackType>>
  161. static bool PostTaskAndReplyWithResult(
  162. const Location& from_here,
  163. const TaskTraits& traits,
  164. CallbackType<TaskReturnType()> task,
  165. CallbackType<void(ReplyArgType)> reply) {
  166. auto* result = new std::unique_ptr<TaskReturnType>();
  167. return PostTaskAndReply(
  168. from_here, traits,
  169. BindOnce(&internal::ReturnAsParamAdapter<TaskReturnType>,
  170. std::move(task), result),
  171. BindOnce(&internal::ReplyAdapter<TaskReturnType, ReplyArgType>,
  172. std::move(reply), Owned(result)));
  173. }
  174. // Returns a TaskRunner whose PostTask invocations result in scheduling tasks
  175. // using |traits|. Tasks may run in any order and in parallel.
  176. static scoped_refptr<TaskRunner> CreateTaskRunner(const TaskTraits& traits);
  177. // Returns a SequencedTaskRunner whose PostTask invocations result in
  178. // scheduling tasks using |traits|. Tasks run one at a time in posting order.
  179. static scoped_refptr<SequencedTaskRunner> CreateSequencedTaskRunner(
  180. const TaskTraits& traits);
  181. // Returns a task runner whose PostTask invocations result in scheduling tasks
  182. // using |traits|. The priority in |traits| can be updated at any time via
  183. // UpdateableSequencedTaskRunner::UpdatePriority(). An update affects all
  184. // tasks posted to the task runner that aren't running yet. Tasks run one at a
  185. // time in posting order.
  186. //
  187. // |traits| requirements:
  188. // - base::ThreadPolicy must be specified if the priority of the task runner
  189. // will ever be increased from BEST_EFFORT.
  190. static scoped_refptr<UpdateableSequencedTaskRunner>
  191. CreateUpdateableSequencedTaskRunner(const TaskTraits& traits);
  192. // Returns a SingleThreadTaskRunner whose PostTask invocations result in
  193. // scheduling tasks using |traits| on a thread determined by |thread_mode|.
  194. // See base/task/single_thread_task_runner_thread_mode.h for |thread_mode|
  195. // details. If |traits| identifies an existing thread,
  196. // SingleThreadTaskRunnerThreadMode::SHARED must be used. Tasks run on a
  197. // single thread in posting order.
  198. //
  199. // If all you need is to make sure that tasks don't run concurrently (e.g.
  200. // because they access a data structure which is not thread-safe), use
  201. // CreateSequencedTaskRunner(). Only use this if you rely on a thread-affine
  202. // API (it might be safer to assume thread-affinity when dealing with
  203. // under-documented third-party APIs, e.g. other OS') or share data across
  204. // tasks using thread-local storage.
  205. static scoped_refptr<SingleThreadTaskRunner> CreateSingleThreadTaskRunner(
  206. const TaskTraits& traits,
  207. SingleThreadTaskRunnerThreadMode thread_mode =
  208. SingleThreadTaskRunnerThreadMode::SHARED);
  209. #if defined(OS_WIN)
  210. // Returns a SingleThreadTaskRunner whose PostTask invocations result in
  211. // scheduling tasks using |traits| in a COM Single-Threaded Apartment on a
  212. // thread determined by |thread_mode|. See
  213. // base/task/single_thread_task_runner_thread_mode.h for |thread_mode|
  214. // details. If |traits| identifies an existing thread,
  215. // SingleThreadTaskRunnerThreadMode::SHARED must be used. Tasks run in the
  216. // same Single-Threaded Apartment in posting order for the returned
  217. // SingleThreadTaskRunner. There is not necessarily a one-to-one
  218. // correspondence between SingleThreadTaskRunners and Single-Threaded
  219. // Apartments. The implementation is free to share apartments or create new
  220. // apartments as necessary. In either case, care should be taken to make sure
  221. // COM pointers are not smuggled across apartments.
  222. static scoped_refptr<SingleThreadTaskRunner> CreateCOMSTATaskRunner(
  223. const TaskTraits& traits,
  224. SingleThreadTaskRunnerThreadMode thread_mode =
  225. SingleThreadTaskRunnerThreadMode::SHARED);
  226. #endif // defined(OS_WIN)
  227. };
  228. } // namespace base
  229. #endif // BASE_TASK_THREAD_POOL_H_