OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "base/task_scheduler/task_scheduler_impl.h" | 5 #include "base/task_scheduler/task_scheduler_impl.h" |
6 | 6 |
7 #include <utility> | 7 #include <utility> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
11 #include "base/memory/ptr_util.h" | 11 #include "base/memory/ptr_util.h" |
12 #include "base/task_scheduler/delayed_task_manager.h" | 12 #include "base/task_scheduler/delayed_task_manager.h" |
13 #include "base/task_scheduler/scheduler_single_thread_task_runner_manager.h" | |
14 #include "base/task_scheduler/scheduler_worker_pool_params.h" | 13 #include "base/task_scheduler/scheduler_worker_pool_params.h" |
15 #include "base/task_scheduler/sequence_sort_key.h" | 14 #include "base/task_scheduler/sequence_sort_key.h" |
16 #include "base/task_scheduler/task.h" | 15 #include "base/task_scheduler/task.h" |
17 #include "base/task_scheduler/task_tracker.h" | 16 #include "base/task_scheduler/task_tracker.h" |
18 | 17 |
19 namespace base { | 18 namespace base { |
20 namespace internal { | 19 namespace internal { |
21 | 20 |
22 namespace { | 21 namespace { |
23 | 22 |
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
92 return GetWorkerPoolForTraits(traits)->CreateSequencedTaskRunnerWithTraits( | 91 return GetWorkerPoolForTraits(traits)->CreateSequencedTaskRunnerWithTraits( |
93 traits); | 92 traits); |
94 } | 93 } |
95 | 94 |
96 scoped_refptr<SingleThreadTaskRunner> | 95 scoped_refptr<SingleThreadTaskRunner> |
97 TaskSchedulerImpl::CreateSingleThreadTaskRunnerWithTraits( | 96 TaskSchedulerImpl::CreateSingleThreadTaskRunnerWithTraits( |
98 const TaskTraits& traits) { | 97 const TaskTraits& traits) { |
99 const auto& environment_params = | 98 const auto& environment_params = |
100 kEnvironmentParams[GetEnvironmentIndexForTraits(traits)]; | 99 kEnvironmentParams[GetEnvironmentIndexForTraits(traits)]; |
101 return single_thread_task_runner_manager_ | 100 return single_thread_task_runner_manager_ |
102 ->CreateSingleThreadTaskRunnerWithTraits( | 101 .CreateSingleThreadTaskRunnerWithTraits( |
103 name_ + environment_params.name_suffix, | 102 name_ + environment_params.name_suffix, |
104 environment_params.priority_hint, traits); | 103 environment_params.priority_hint, traits); |
105 } | 104 } |
106 | 105 |
107 #if defined(OS_WIN) | 106 #if defined(OS_WIN) |
108 scoped_refptr<SingleThreadTaskRunner> | 107 scoped_refptr<SingleThreadTaskRunner> |
109 TaskSchedulerImpl::CreateCOMSTATaskRunnerWithTraits(const TaskTraits& traits) { | 108 TaskSchedulerImpl::CreateCOMSTATaskRunnerWithTraits(const TaskTraits& traits) { |
110 const auto& environment_params = | 109 const auto& environment_params = |
111 kEnvironmentParams[GetEnvironmentIndexForTraits(traits)]; | 110 kEnvironmentParams[GetEnvironmentIndexForTraits(traits)]; |
112 return single_thread_task_runner_manager_->CreateCOMSTATaskRunnerWithTraits( | 111 return single_thread_task_runner_manager_.CreateCOMSTATaskRunnerWithTraits( |
113 environment_params.name_suffix, environment_params.priority_hint, traits); | 112 environment_params.name_suffix, environment_params.priority_hint, traits); |
114 } | 113 } |
115 #endif // defined(OS_WIN) | 114 #endif // defined(OS_WIN) |
116 | 115 |
117 std::vector<const HistogramBase*> TaskSchedulerImpl::GetHistograms() const { | 116 std::vector<const HistogramBase*> TaskSchedulerImpl::GetHistograms() const { |
118 std::vector<const HistogramBase*> histograms; | 117 std::vector<const HistogramBase*> histograms; |
119 for (const auto& worker_pool : worker_pools_) | 118 for (const auto& worker_pool : worker_pools_) |
120 worker_pool->GetHistograms(&histograms); | 119 worker_pool->GetHistograms(&histograms); |
121 | 120 |
122 return histograms; | 121 return histograms; |
(...skipping 10 matching lines...) Expand all Loading... |
133 } | 132 } |
134 | 133 |
135 void TaskSchedulerImpl::FlushForTesting() { | 134 void TaskSchedulerImpl::FlushForTesting() { |
136 task_tracker_.Flush(); | 135 task_tracker_.Flush(); |
137 } | 136 } |
138 | 137 |
139 void TaskSchedulerImpl::JoinForTesting() { | 138 void TaskSchedulerImpl::JoinForTesting() { |
140 #if DCHECK_IS_ON() | 139 #if DCHECK_IS_ON() |
141 DCHECK(!join_for_testing_returned_.IsSet()); | 140 DCHECK(!join_for_testing_returned_.IsSet()); |
142 #endif | 141 #endif |
143 single_thread_task_runner_manager_->JoinForTesting(); | 142 single_thread_task_runner_manager_.JoinForTesting(); |
144 for (const auto& worker_pool : worker_pools_) | 143 for (const auto& worker_pool : worker_pools_) |
145 worker_pool->DisallowWorkerDetachmentForTesting(); | 144 worker_pool->DisallowWorkerDetachmentForTesting(); |
146 for (const auto& worker_pool : worker_pools_) | 145 for (const auto& worker_pool : worker_pools_) |
147 worker_pool->JoinForTesting(); | 146 worker_pool->JoinForTesting(); |
148 service_thread_.Stop(); | 147 service_thread_.Stop(); |
149 #if DCHECK_IS_ON() | 148 #if DCHECK_IS_ON() |
150 join_for_testing_returned_.Set(); | 149 join_for_testing_returned_.Set(); |
151 #endif | 150 #endif |
152 } | 151 } |
153 | 152 |
154 TaskSchedulerImpl::TaskSchedulerImpl(StringPiece name) | 153 TaskSchedulerImpl::TaskSchedulerImpl(StringPiece name) |
155 : name_(name), service_thread_("TaskSchedulerServiceThread") {} | 154 : name_(name), |
| 155 service_thread_("TaskSchedulerServiceThread"), |
| 156 single_thread_task_runner_manager_(&task_tracker_, |
| 157 &delayed_task_manager_) {} |
156 | 158 |
157 void TaskSchedulerImpl::Initialize( | 159 void TaskSchedulerImpl::Initialize( |
158 const TaskScheduler::InitParams& init_params) { | 160 const TaskScheduler::InitParams& init_params) { |
159 // Start the service thread. On platforms that support it (POSIX except NaCL | 161 // Start the service thread. On platforms that support it (POSIX except NaCL |
160 // SFI), the service thread runs a MessageLoopForIO which is used to support | 162 // SFI), the service thread runs a MessageLoopForIO which is used to support |
161 // FileDescriptorWatcher in the scope in which tasks run. | 163 // FileDescriptorWatcher in the scope in which tasks run. |
162 Thread::Options service_thread_options; | 164 Thread::Options service_thread_options; |
163 service_thread_options.message_loop_type = | 165 service_thread_options.message_loop_type = |
164 #if defined(OS_POSIX) && !defined(OS_NACL_SFI) | 166 #if defined(OS_POSIX) && !defined(OS_NACL_SFI) |
165 MessageLoop::TYPE_IO; | 167 MessageLoop::TYPE_IO; |
166 #else | 168 #else |
167 MessageLoop::TYPE_DEFAULT; | 169 MessageLoop::TYPE_DEFAULT; |
168 #endif | 170 #endif |
169 service_thread_options.timer_slack = TIMER_SLACK_MAXIMUM; | 171 service_thread_options.timer_slack = TIMER_SLACK_MAXIMUM; |
170 CHECK(service_thread_.StartWithOptions(service_thread_options)); | 172 CHECK(service_thread_.StartWithOptions(service_thread_options)); |
171 | 173 |
172 #if defined(OS_POSIX) && !defined(OS_NACL_SFI) | 174 #if defined(OS_POSIX) && !defined(OS_NACL_SFI) |
173 // Needs to happen after starting the service thread to get its | 175 // Needs to happen after starting the service thread to get its |
174 // message_loop(). | 176 // message_loop(). |
175 task_tracker_.set_watch_file_descriptor_message_loop( | 177 task_tracker_.set_watch_file_descriptor_message_loop( |
176 static_cast<MessageLoopForIO*>(service_thread_.message_loop())); | 178 static_cast<MessageLoopForIO*>(service_thread_.message_loop())); |
177 #endif | 179 #endif |
178 | 180 |
179 // Needs to happen after starting the service thread to get its task_runner(). | 181 // Needs to happen after starting the service thread to get its task_runner(). |
180 delayed_task_manager_ = | 182 delayed_task_manager_.Start(service_thread_.task_runner()); |
181 base::MakeUnique<DelayedTaskManager>(service_thread_.task_runner()); | |
182 | 183 |
183 single_thread_task_runner_manager_ = | 184 single_thread_task_runner_manager_.Start(); |
184 MakeUnique<SchedulerSingleThreadTaskRunnerManager>( | |
185 &task_tracker_, delayed_task_manager_.get()); | |
186 single_thread_task_runner_manager_->Start(); | |
187 | 185 |
188 // Callback invoked by workers to re-enqueue a sequence in the appropriate | 186 // Callback invoked by workers to re-enqueue a sequence in the appropriate |
189 // PriorityQueue. | 187 // PriorityQueue. |
190 const SchedulerWorkerPoolImpl::ReEnqueueSequenceCallback | 188 const SchedulerWorkerPoolImpl::ReEnqueueSequenceCallback |
191 re_enqueue_sequence_callback = | 189 re_enqueue_sequence_callback = |
192 Bind(&TaskSchedulerImpl::ReEnqueueSequenceCallback, Unretained(this)); | 190 Bind(&TaskSchedulerImpl::ReEnqueueSequenceCallback, Unretained(this)); |
193 | 191 |
194 // Order must match the EnvironmentType enum. | 192 // Order must match the EnvironmentType enum. |
195 const SchedulerWorkerPoolParams* worker_pool_params[] = { | 193 const SchedulerWorkerPoolParams* worker_pool_params[] = { |
196 &init_params.background_worker_pool_params, | 194 &init_params.background_worker_pool_params, |
(...skipping 12 matching lines...) Expand all Loading... |
209 | 207 |
210 // Start worker pools. | 208 // Start worker pools. |
211 for (int environment_type = 0; environment_type < ENVIRONMENT_COUNT; | 209 for (int environment_type = 0; environment_type < ENVIRONMENT_COUNT; |
212 ++environment_type) { | 210 ++environment_type) { |
213 // Passing pointers to objects owned by |this| to the constructor of | 211 // Passing pointers to objects owned by |this| to the constructor of |
214 // SchedulerWorkerPoolImpl is safe because a TaskSchedulerImpl can't be | 212 // SchedulerWorkerPoolImpl is safe because a TaskSchedulerImpl can't be |
215 // deleted before all its worker pools have been joined. | 213 // deleted before all its worker pools have been joined. |
216 worker_pools_[environment_type] = MakeUnique<SchedulerWorkerPoolImpl>( | 214 worker_pools_[environment_type] = MakeUnique<SchedulerWorkerPoolImpl>( |
217 name_ + kEnvironmentParams[environment_type].name_suffix, | 215 name_ + kEnvironmentParams[environment_type].name_suffix, |
218 kEnvironmentParams[environment_type].priority_hint, | 216 kEnvironmentParams[environment_type].priority_hint, |
219 re_enqueue_sequence_callback, &task_tracker_, | 217 re_enqueue_sequence_callback, &task_tracker_, &delayed_task_manager_); |
220 delayed_task_manager_.get()); | |
221 worker_pools_[environment_type]->Start( | 218 worker_pools_[environment_type]->Start( |
222 *worker_pool_params[environment_type]); | 219 *worker_pool_params[environment_type]); |
223 } | 220 } |
224 } | 221 } |
225 | 222 |
226 SchedulerWorkerPoolImpl* TaskSchedulerImpl::GetWorkerPoolForTraits( | 223 SchedulerWorkerPoolImpl* TaskSchedulerImpl::GetWorkerPoolForTraits( |
227 const TaskTraits& traits) const { | 224 const TaskTraits& traits) const { |
228 return worker_pools_[GetEnvironmentIndexForTraits(traits)].get(); | 225 return worker_pools_[GetEnvironmentIndexForTraits(traits)].get(); |
229 } | 226 } |
230 | 227 |
231 void TaskSchedulerImpl::ReEnqueueSequenceCallback( | 228 void TaskSchedulerImpl::ReEnqueueSequenceCallback( |
232 scoped_refptr<Sequence> sequence) { | 229 scoped_refptr<Sequence> sequence) { |
233 DCHECK(sequence); | 230 DCHECK(sequence); |
234 | 231 |
235 const SequenceSortKey sort_key = sequence->GetSortKey(); | 232 const SequenceSortKey sort_key = sequence->GetSortKey(); |
236 | 233 |
237 // The next task in |sequence| should run in a worker pool suited for its | 234 // The next task in |sequence| should run in a worker pool suited for its |
238 // traits, except for the priority which is adjusted to the highest priority | 235 // traits, except for the priority which is adjusted to the highest priority |
239 // in |sequence|. | 236 // in |sequence|. |
240 const TaskTraits traits = | 237 const TaskTraits traits = |
241 sequence->PeekTaskTraits().WithPriority(sort_key.priority()); | 238 sequence->PeekTaskTraits().WithPriority(sort_key.priority()); |
242 | 239 |
243 GetWorkerPoolForTraits(traits)->ReEnqueueSequence(std::move(sequence), | 240 GetWorkerPoolForTraits(traits)->ReEnqueueSequence(std::move(sequence), |
244 sort_key); | 241 sort_key); |
245 } | 242 } |
246 | 243 |
247 } // namespace internal | 244 } // namespace internal |
248 } // namespace base | 245 } // namespace base |
OLD | NEW |