1 // Copyright 2018 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 #include "base/task/sequence_manager/sequence_manager_impl.h"
6
7 #include <stddef.h>
8
9 #include <memory>
10 #include <string>
11 #include <string_view>
12 #include <tuple>
13 #include <utility>
14 #include <vector>
15
16 #include "base/auto_reset.h"
17 #include "base/cancelable_callback.h"
18 #include "base/debug/stack_trace.h"
19 #include "base/functional/bind.h"
20 #include "base/functional/callback.h"
21 #include "base/functional/callback_forward.h"
22 #include "base/functional/callback_helpers.h"
23 #include "base/location.h"
24 #include "base/memory/raw_ptr.h"
25 #include "base/memory/ref_counted_memory.h"
26 #include "base/memory/scoped_refptr.h"
27 #include "base/message_loop/message_pump_default.h"
28 #include "base/message_loop/message_pump_type.h"
29 #include "base/rand_util.h"
30 #include "base/run_loop.h"
31 #include "base/sequence_checker_impl.h"
32 #include "base/strings/strcat.h"
33 #include "base/strings/string_number_conversions.h"
34 #include "base/strings/string_split.h"
35 #include "base/strings/stringprintf.h"
36 #include "base/synchronization/waitable_event.h"
37 #include "base/task/current_thread.h"
38 #include "base/task/sequence_manager/sequence_manager.h"
39 #include "base/task/sequence_manager/task_queue.h"
40 #include "base/task/sequence_manager/task_queue_impl.h"
41 #include "base/task/sequence_manager/task_queue_selector.h"
42 #include "base/task/sequence_manager/tasks.h"
43 #include "base/task/sequence_manager/test/mock_time_domain.h"
44 #include "base/task/sequence_manager/test/mock_time_message_pump.h"
45 #include "base/task/sequence_manager/test/sequence_manager_for_test.h"
46 #include "base/task/sequence_manager/test/test_task_time_observer.h"
47 #include "base/task/sequence_manager/thread_controller_with_message_pump_impl.h"
48 #include "base/task/sequence_manager/work_queue.h"
49 #include "base/task/sequence_manager/work_queue_sets.h"
50 #include "base/task/sequenced_task_runner.h"
51 #include "base/task/single_thread_task_runner.h"
52 #include "base/task/task_features.h"
53 #include "base/task/thread_pool.h"
54 #include "base/task/thread_pool/thread_pool_instance.h"
55 #include "base/test/bind.h"
56 #include "base/test/mock_callback.h"
57 #include "base/test/null_task_runner.h"
58 #include "base/test/scoped_feature_list.h"
59 #include "base/test/simple_test_tick_clock.h"
60 #include "base/test/task_environment.h"
61 #include "base/test/test_mock_time_task_runner.h"
62 #include "base/test/test_simple_task_runner.h"
63 #include "base/test/test_timeouts.h"
64 #include "base/threading/platform_thread.h"
65 #include "base/threading/sequence_local_storage_slot.h"
66 #include "base/threading/thread.h"
67 #include "base/time/time.h"
68 #include "base/trace_event/base_tracing.h"
69 #include "base/tracing_buildflags.h"
70 #include "build/build_config.h"
71 #include "testing/gmock/include/gmock/gmock.h"
72
73 #if BUILDFLAG(ENABLE_BASE_TRACING)
74 #include <optional>
75
76 #include "base/test/trace_event_analyzer.h"
77 #endif // BUILDFLAG(ENABLE_BASE_TRACING)
78
79 using base::sequence_manager::EnqueueOrder;
80 using testing::_;
81 using testing::AnyNumber;
82 using testing::Contains;
83 using testing::ElementsAre;
84 using testing::ElementsAreArray;
85 using testing::HasSubstr;
86 using testing::Mock;
87 using testing::Not;
88 using testing::Return;
89 using testing::StrictMock;
90 using testing::UnorderedElementsAre;
91
92 namespace base {
93 namespace sequence_manager {
94 namespace internal {
95
96 namespace {
97
98 enum class RunnerType {
99 kMockTaskRunner,
100 kMessagePump,
101 };
102
103 enum class WakeUpType {
104 kDefault,
105 kAlign,
106 };
107
108 // Expresses whether metrics subsampling in ThreadController should always or
109 // never sample which affects the count of calls to Now().
110 enum class MetricsSampling {
111 kMetricsOn,
112 kMetricsOff,
113 };
114
115 enum class TestQueuePriority : TaskQueue::QueuePriority {
116 kControlPriority = 0,
117 kHighestPriority = 1,
118 kVeryHighPriority = 2,
119 kHighPriority = 3,
120
121 kNormalPriority = 4,
122 kDefaultPriority = kNormalPriority,
123
124 kLowPriority = 5,
125 kBestEffortPriority = 6,
126 kQueuePriorityCount = 7,
127 kFirstQueuePriority = kControlPriority,
128 };
129
ToString(RunnerType type)130 std::string ToString(RunnerType type) {
131 switch (type) {
132 case RunnerType::kMockTaskRunner:
133 return "kMockTaskRunner";
134 case RunnerType::kMessagePump:
135 return "kMessagePump";
136 }
137 }
138
ToString(WakeUpType type)139 std::string ToString(WakeUpType type) {
140 switch (type) {
141 case WakeUpType::kDefault:
142 return "";
143 case WakeUpType::kAlign:
144 return "AlignedWakeUps";
145 }
146 }
147
ToString(MetricsSampling sampling)148 std::string ToString(MetricsSampling sampling) {
149 switch (sampling) {
150 case MetricsSampling::kMetricsOn:
151 return "MetricsOn";
152 case MetricsSampling::kMetricsOff:
153 return "MetricsOff";
154 }
155 }
156
GetTestNameSuffix(const testing::TestParamInfo<std::tuple<RunnerType,WakeUpType,MetricsSampling>> & info)157 std::string GetTestNameSuffix(
158 const testing::TestParamInfo<
159 std::tuple<RunnerType, WakeUpType, MetricsSampling>>& info) {
160 return StrCat({"With", ToString(std::get<0>(info.param)).substr(1),
161 ToString(std::get<1>(info.param)),
162 ToString(std::get<2>(info.param))});
163 }
164
GetTaskQueueImpl(TaskQueue * task_queue)165 TaskQueueImpl* GetTaskQueueImpl(TaskQueue* task_queue) {
166 return static_cast<TaskQueueImpl*>(task_queue);
167 }
168
169 constexpr TimeDelta kLeeway = kDefaultLeeway;
170
171 using MockTask = MockCallback<base::RepeatingCallback<void()>>;
172
173 // This class abstracts the details of how the SequenceManager runs tasks.
174 // Subclasses will use a MockTaskRunner, a MessageLoop or a MockMessagePump. We
175 // can then have common tests for all the scenarios by just using this
176 // interface.
177 class Fixture {
178 public:
179 virtual ~Fixture() = default;
180 virtual void AdvanceMockTickClock(TimeDelta delta) = 0;
181 virtual const TickClock* mock_tick_clock() const = 0;
182 virtual TimeTicks NextPendingTaskTime() const = 0;
183 // Keeps advancing time as needed to run tasks up to the specified limit.
184 virtual void FastForwardBy(TimeDelta delta) = 0;
185 // Keeps advancing time as needed to run tasks until no more tasks are
186 // available.
187 virtual void FastForwardUntilNoTasksRemain() = 0;
188 virtual void RunDoWorkOnce() = 0;
189 virtual SequenceManagerForTest* sequence_manager() const = 0;
190 virtual void DestroySequenceManager() = 0;
191 virtual int GetNowTicksCallCount() = 0;
192 virtual TimeTicks FromStartAligned(TimeDelta delta) const = 0;
193 };
194
195 class CallCountingTickClock : public TickClock {
196 public:
CallCountingTickClock(RepeatingCallback<TimeTicks ()> now_callback)197 explicit CallCountingTickClock(RepeatingCallback<TimeTicks()> now_callback)
198 : now_callback_(std::move(now_callback)) {}
CallCountingTickClock(TickClock * clock)199 explicit CallCountingTickClock(TickClock* clock)
200 : CallCountingTickClock(
201 BindLambdaForTesting([clock]() { return clock->NowTicks(); })) {}
202
203 ~CallCountingTickClock() override = default;
204
NowTicks() const205 TimeTicks NowTicks() const override {
206 ++now_call_count_;
207 return now_callback_.Run();
208 }
209
Reset()210 void Reset() { now_call_count_.store(0); }
211
now_call_count() const212 int now_call_count() const { return now_call_count_; }
213
214 private:
215 const RepeatingCallback<TimeTicks()> now_callback_;
216 mutable std::atomic<int> now_call_count_{0};
217 };
218
219 class FixtureWithMockTaskRunner final : public Fixture {
220 public:
FixtureWithMockTaskRunner()221 FixtureWithMockTaskRunner()
222 : test_task_runner_(MakeRefCounted<TestMockTimeTaskRunner>(
223 TestMockTimeTaskRunner::Type::kBoundToThread)),
224 call_counting_clock_(BindRepeating(&TestMockTimeTaskRunner::NowTicks,
225 test_task_runner_)),
226 sequence_manager_(SequenceManagerForTest::Create(
227 nullptr,
228 SingleThreadTaskRunner::GetCurrentDefault(),
229 mock_tick_clock(),
230 SequenceManager::Settings::Builder()
231 .SetMessagePumpType(MessagePumpType::DEFAULT)
232 .SetRandomisedSamplingEnabled(false)
233 .SetTickClock(mock_tick_clock())
234 .SetPrioritySettings(SequenceManager::PrioritySettings(
235 TestQueuePriority::kQueuePriorityCount,
236 TestQueuePriority::kDefaultPriority))
237 .Build())) {
238 // A null clock triggers some assertions.
239 AdvanceMockTickClock(Milliseconds(1));
240 start_time_ = test_task_runner_->NowTicks();
241
242 // The SequenceManager constructor calls Now() once for setting up
243 // housekeeping.
244 EXPECT_EQ(1, GetNowTicksCallCount());
245 call_counting_clock_.Reset();
246 }
247
AdvanceMockTickClock(TimeDelta delta)248 void AdvanceMockTickClock(TimeDelta delta) override {
249 test_task_runner_->AdvanceMockTickClock(delta);
250 }
251
mock_tick_clock() const252 const TickClock* mock_tick_clock() const override {
253 return &call_counting_clock_;
254 }
255
NextPendingTaskTime() const256 TimeTicks NextPendingTaskTime() const override {
257 return test_task_runner_->NowTicks() +
258 test_task_runner_->NextPendingTaskDelay();
259 }
260
FastForwardBy(TimeDelta delta)261 void FastForwardBy(TimeDelta delta) override {
262 test_task_runner_->FastForwardBy(delta);
263 }
264
FastForwardUntilNoTasksRemain()265 void FastForwardUntilNoTasksRemain() override {
266 test_task_runner_->FastForwardUntilNoTasksRemain();
267 }
268
RunDoWorkOnce()269 void RunDoWorkOnce() override {
270 EXPECT_EQ(test_task_runner_->GetPendingTaskCount(), 1u);
271 // We should only run tasks already posted by that moment.
272 RunLoop run_loop;
273 test_task_runner_->PostTask(FROM_HERE, run_loop.QuitClosure());
274 // TestMockTimeTaskRunner will fast-forward mock clock if necessary.
275 run_loop.Run();
276 }
277
test_task_runner() const278 scoped_refptr<TestMockTimeTaskRunner> test_task_runner() const {
279 return test_task_runner_;
280 }
281
sequence_manager() const282 SequenceManagerForTest* sequence_manager() const override {
283 return sequence_manager_.get();
284 }
285
DestroySequenceManager()286 void DestroySequenceManager() override { sequence_manager_.reset(); }
287
GetNowTicksCallCount()288 int GetNowTicksCallCount() override {
289 return call_counting_clock_.now_call_count();
290 }
291
FromStartAligned(TimeDelta delta) const292 TimeTicks FromStartAligned(TimeDelta delta) const override {
293 return start_time_ + delta;
294 }
295
296 private:
297 scoped_refptr<TestMockTimeTaskRunner> test_task_runner_;
298 CallCountingTickClock call_counting_clock_;
299 std::unique_ptr<SequenceManagerForTest> sequence_manager_;
300 TimeTicks start_time_;
301 };
302
303 class FixtureWithMockMessagePump : public Fixture {
304 public:
FixtureWithMockMessagePump(WakeUpType wake_up_type)305 explicit FixtureWithMockMessagePump(WakeUpType wake_up_type)
306 : call_counting_clock_(&mock_clock_), wake_up_type_(wake_up_type) {
307 if (wake_up_type_ == WakeUpType::kAlign) {
308 feature_list_.InitWithFeatures(
309 {kAlignWakeUps, kExplicitHighResolutionTimerWin}, {});
310 } else {
311 feature_list_.InitWithFeatures(
312 {}, {kAlignWakeUps, kExplicitHighResolutionTimerWin});
313 }
314 // A null clock triggers some assertions.
315 mock_clock_.Advance(Milliseconds(1));
316
317 auto pump = std::make_unique<MockTimeMessagePump>(&mock_clock_);
318 pump_ = pump.get();
319 auto settings = SequenceManager::Settings::Builder()
320 .SetMessagePumpType(MessagePumpType::DEFAULT)
321 .SetRandomisedSamplingEnabled(false)
322 .SetTickClock(mock_tick_clock())
323 .SetPrioritySettings(SequenceManager::PrioritySettings(
324 TestQueuePriority::kQueuePriorityCount,
325 TestQueuePriority::kDefaultPriority))
326 .Build();
327 auto thread_controller =
328 std::make_unique<ThreadControllerWithMessagePumpImpl>(std::move(pump),
329 settings);
330 MessagePump::InitializeFeatures();
331 ThreadControllerWithMessagePumpImpl::InitializeFeatures();
332 sequence_manager_ = SequenceManagerForTest::Create(
333 std::move(thread_controller), std::move(settings));
334 sequence_manager_->SetDefaultTaskRunner(MakeRefCounted<NullTaskRunner>());
335 start_time_ = mock_clock_.NowTicks();
336
337 // The SequenceManager constructor calls Now() once for setting up
338 // housekeeping.
339 EXPECT_EQ(1, GetNowTicksCallCount());
340 call_counting_clock_.Reset();
341 }
~FixtureWithMockMessagePump()342 ~FixtureWithMockMessagePump() override {
343 ThreadControllerWithMessagePumpImpl::ResetFeatures();
344 }
345
AdvanceMockTickClock(TimeDelta delta)346 void AdvanceMockTickClock(TimeDelta delta) override {
347 mock_clock_.Advance(delta);
348 }
349
mock_tick_clock() const350 const TickClock* mock_tick_clock() const override {
351 return &call_counting_clock_;
352 }
353
NextPendingTaskTime() const354 TimeTicks NextPendingTaskTime() const override {
355 return pump_->next_wake_up_time();
356 }
357
FastForwardBy(TimeDelta delta)358 void FastForwardBy(TimeDelta delta) override {
359 pump_->SetAllowTimeToAutoAdvanceUntil(mock_tick_clock()->NowTicks() +
360 delta);
361 pump_->SetStopWhenMessagePumpIsIdle(true);
362 RunLoop().Run();
363 pump_->SetStopWhenMessagePumpIsIdle(false);
364 }
365
FastForwardUntilNoTasksRemain()366 void FastForwardUntilNoTasksRemain() override {
367 pump_->SetAllowTimeToAutoAdvanceUntil(TimeTicks::Max());
368 pump_->SetStopWhenMessagePumpIsIdle(true);
369 RunLoop().Run();
370 pump_->SetStopWhenMessagePumpIsIdle(false);
371 pump_->SetAllowTimeToAutoAdvanceUntil(mock_tick_clock()->NowTicks());
372 }
373
RunDoWorkOnce()374 void RunDoWorkOnce() override {
375 pump_->SetQuitAfterDoWork(true);
376 RunLoop().Run();
377 pump_->SetQuitAfterDoWork(false);
378 }
379
sequence_manager() const380 SequenceManagerForTest* sequence_manager() const override {
381 return sequence_manager_.get();
382 }
383
DestroySequenceManager()384 void DestroySequenceManager() override {
385 pump_ = nullptr;
386 sequence_manager_.reset();
387 }
388
GetNowTicksCallCount()389 int GetNowTicksCallCount() override {
390 return call_counting_clock_.now_call_count();
391 }
392
FromStartAligned(TimeDelta delta) const393 TimeTicks FromStartAligned(TimeDelta delta) const override {
394 if (wake_up_type_ == WakeUpType::kAlign) {
395 return (start_time_ + delta).SnappedToNextTick(TimeTicks(), kLeeway);
396 }
397 return start_time_ + delta;
398 }
399
400 private:
401 base::test::ScopedFeatureList feature_list_;
402 SimpleTestTickClock mock_clock_;
403 CallCountingTickClock call_counting_clock_;
404
405 // Must outlive `pump_`.
406 std::unique_ptr<SequenceManagerForTest> sequence_manager_;
407
408 raw_ptr<MockTimeMessagePump> pump_ = nullptr;
409 WakeUpType wake_up_type_;
410 TimeTicks start_time_;
411 };
412
413 // Convenience wrapper around the fixtures so that we can use parametrized tests
414 // instead of templated ones. The latter would be more verbose as all method
415 // calls to the fixture would need to be like this->method()
416 class SequenceManagerTest
417 : public testing::TestWithParam<
418 std::tuple<RunnerType, WakeUpType, MetricsSampling>>,
419 public Fixture {
420 public:
SequenceManagerTest()421 SequenceManagerTest() {
422 switch (GetUnderlyingRunnerType()) {
423 case RunnerType::kMockTaskRunner:
424 fixture_ = std::make_unique<FixtureWithMockTaskRunner>();
425 break;
426 case RunnerType::kMessagePump:
427 fixture_ =
428 std::make_unique<FixtureWithMockMessagePump>(GetWakeUpType());
429 break;
430 }
431
432 if (GetSampling() == MetricsSampling::kMetricsOn) {
433 always_sample_scoper_.emplace();
434 } else {
435 never_sample_scoper_.emplace();
436 }
437 }
438
439 // Accounts for the extra calls to Now() that come when sampling is enabled.
GetExtraNowSampleCount()440 int GetExtraNowSampleCount() {
441 // When no extra metrics are sampled there are no extra Now() calls.
442 if (GetSampling() == MetricsSampling::kMetricsOff) {
443 return 0;
444 }
445
446 // In both cases when sampling metrics there is a new call to Now() when
447 // ThreadController goes idle and the LazyNow instance used
448 // has no value. There is an equivalent use of LazyNow upon becoming active.
449 // In the case of RunnerType::kMessagePump the LazyNow has no value but it
450 // does when using RunnerType::kMockTaskRunner since it was already
451 // populated on entering OnWorkStarted().
452 switch (GetUnderlyingRunnerType()) {
453 case RunnerType::kMockTaskRunner:
454 return 1;
455 case RunnerType::kMessagePump:
456 return 2;
457 }
458 }
459
CreateTaskQueue(TaskQueue::Spec spec=TaskQueue::Spec (QueueName::TEST_TQ))460 TaskQueue::Handle CreateTaskQueue(
461 TaskQueue::Spec spec = TaskQueue::Spec(QueueName::TEST_TQ)) {
462 return sequence_manager()->CreateTaskQueue(spec);
463 }
464
CreateTaskQueues(size_t num_queues)465 std::vector<TaskQueue::Handle> CreateTaskQueues(size_t num_queues) {
466 std::vector<TaskQueue::Handle> queues;
467 for (size_t i = 0; i < num_queues; i++)
468 queues.push_back(CreateTaskQueue());
469 return queues;
470 }
471
RunUntilManagerIsIdle(RepeatingClosure per_run_time_callback)472 void RunUntilManagerIsIdle(RepeatingClosure per_run_time_callback) {
473 for (;;) {
474 // Advance time if we've run out of immediate work to do.
475 if (!sequence_manager()->HasImmediateWork()) {
476 LazyNow lazy_now(mock_tick_clock());
477 auto wake_up = sequence_manager()->GetNextDelayedWakeUp();
478 if (wake_up.has_value()) {
479 AdvanceMockTickClock(wake_up->time - lazy_now.Now());
480 per_run_time_callback.Run();
481 } else {
482 break;
483 }
484 }
485 RunLoop().RunUntilIdle();
486 }
487 }
488
dummy_key()489 debug::CrashKeyString* dummy_key() { return &dummy_key_; }
490
AdvanceMockTickClock(TimeDelta delta)491 void AdvanceMockTickClock(TimeDelta delta) override {
492 fixture_->AdvanceMockTickClock(delta);
493 }
494
mock_tick_clock() const495 const TickClock* mock_tick_clock() const override {
496 return fixture_->mock_tick_clock();
497 }
498
NextPendingTaskTime() const499 TimeTicks NextPendingTaskTime() const override {
500 return fixture_->NextPendingTaskTime();
501 }
502
FastForwardBy(TimeDelta delta)503 void FastForwardBy(TimeDelta delta) override {
504 fixture_->FastForwardBy(delta);
505 }
506
FastForwardUntilNoTasksRemain()507 void FastForwardUntilNoTasksRemain() override {
508 fixture_->FastForwardUntilNoTasksRemain();
509 }
510
RunDoWorkOnce()511 void RunDoWorkOnce() override { fixture_->RunDoWorkOnce(); }
512
sequence_manager() const513 SequenceManagerForTest* sequence_manager() const override {
514 return fixture_->sequence_manager();
515 }
516
DestroySequenceManager()517 void DestroySequenceManager() override { fixture_->DestroySequenceManager(); }
518
GetNowTicksCallCount()519 int GetNowTicksCallCount() override {
520 return fixture_->GetNowTicksCallCount();
521 }
522
GetUnderlyingRunnerType()523 RunnerType GetUnderlyingRunnerType() { return std::get<0>(GetParam()); }
GetWakeUpType()524 WakeUpType GetWakeUpType() { return std::get<1>(GetParam()); }
GetSampling()525 MetricsSampling GetSampling() { return std::get<2>(GetParam()); }
526
FromStartAligned(TimeDelta delta) const527 TimeTicks FromStartAligned(TimeDelta delta) const override {
528 return fixture_->FromStartAligned(delta);
529 }
530
531 private:
532 std::optional<base::MetricsSubSampler::ScopedAlwaysSampleForTesting>
533 always_sample_scoper_;
534 std::optional<base::MetricsSubSampler::ScopedNeverSampleForTesting>
535 never_sample_scoper_;
536 debug::CrashKeyString dummy_key_{"dummy", debug::CrashKeySize::Size64};
537 std::unique_ptr<Fixture> fixture_;
538 };
539
GetTestTypes()540 auto GetTestTypes() {
541 return testing::Values(
542 std::make_tuple(RunnerType::kMessagePump, WakeUpType::kDefault,
543 MetricsSampling::kMetricsOn),
544 std::make_tuple(RunnerType::kMessagePump, WakeUpType::kDefault,
545 MetricsSampling::kMetricsOff),
546 #if !BUILDFLAG(IS_WIN)
547 std::make_tuple(RunnerType::kMessagePump, WakeUpType::kAlign,
548 MetricsSampling::kMetricsOn),
549 std::make_tuple(RunnerType::kMessagePump, WakeUpType::kAlign,
550 MetricsSampling::kMetricsOff),
551 #endif
552 std::make_tuple(RunnerType::kMockTaskRunner, WakeUpType::kDefault,
553 MetricsSampling::kMetricsOn),
554 std::make_tuple(RunnerType::kMockTaskRunner, WakeUpType::kDefault,
555 MetricsSampling::kMetricsOff));
556 }
557
558 INSTANTIATE_TEST_SUITE_P(All,
559 SequenceManagerTest,
560 GetTestTypes(),
561 GetTestNameSuffix);
562
PostFromNestedRunloop(scoped_refptr<SingleThreadTaskRunner> runner,std::vector<std::pair<OnceClosure,bool>> * tasks)563 void PostFromNestedRunloop(scoped_refptr<SingleThreadTaskRunner> runner,
564 std::vector<std::pair<OnceClosure, bool>>* tasks) {
565 for (std::pair<OnceClosure, bool>& pair : *tasks) {
566 if (pair.second) {
567 runner->PostTask(FROM_HERE, std::move(pair.first));
568 } else {
569 runner->PostNonNestableTask(FROM_HERE, std::move(pair.first));
570 }
571 }
572 RunLoop(RunLoop::Type::kNestableTasksAllowed).RunUntilIdle();
573 }
574
NopTask()575 void NopTask() {}
576
577 class TestCountUsesTimeSource : public TickClock {
578 public:
579 TestCountUsesTimeSource() = default;
580 TestCountUsesTimeSource(const TestCountUsesTimeSource&) = delete;
581 TestCountUsesTimeSource& operator=(const TestCountUsesTimeSource&) = delete;
582 ~TestCountUsesTimeSource() override = default;
583
NowTicks() const584 TimeTicks NowTicks() const override {
585 now_calls_count_++;
586 // Don't return 0, as it triggers some assertions.
587 return TimeTicks() + Seconds(1);
588 }
589
now_calls_count() const590 int now_calls_count() const { return now_calls_count_; }
591
592 private:
593 mutable int now_calls_count_ = 0;
594 };
595
596 class QueueTimeTaskObserver : public TaskObserver {
597 public:
WillProcessTask(const PendingTask & pending_task,bool was_blocked_or_low_priority)598 void WillProcessTask(const PendingTask& pending_task,
599 bool was_blocked_or_low_priority) override {
600 queue_times_.push_back(pending_task.queue_time);
601 }
DidProcessTask(const PendingTask & pending_task)602 void DidProcessTask(const PendingTask& pending_task) override {}
queue_times() const603 std::vector<TimeTicks> queue_times() const { return queue_times_; }
604
605 private:
606 std::vector<TimeTicks> queue_times_;
607 };
608
609 } // namespace
610
TEST_P(SequenceManagerTest,GetCorrectTaskRunnerForCurrentTask)611 TEST_P(SequenceManagerTest, GetCorrectTaskRunnerForCurrentTask) {
612 auto queue = CreateTaskQueue();
613
614 queue->task_runner()->PostTask(
615 FROM_HERE, BindLambdaForTesting([&]() {
616 EXPECT_EQ(queue->task_runner(),
617 sequence_manager()->GetTaskRunnerForCurrentTask());
618 }));
619
620 RunLoop().RunUntilIdle();
621 }
622
TEST_P(SequenceManagerTest,NowNotCalledIfUnneeded)623 TEST_P(SequenceManagerTest, NowNotCalledIfUnneeded) {
624 sequence_manager()->SetWorkBatchSize(6);
625
626 auto queues = CreateTaskQueues(3u);
627
628 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
629 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
630 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
631 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
632 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
633 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
634
635 RunLoop().RunUntilIdle();
636
637 // In the absence of calls to Now() for TimeObserver the only calls will
638 // come from metrics. There will be one call when the ThreadController
639 // becomes active and one when it becomes idle.
640 int extra_call_count = 0;
641 if (GetSampling() == MetricsSampling::kMetricsOn) {
642 extra_call_count = 2;
643 }
644 EXPECT_EQ(0 + extra_call_count, GetNowTicksCallCount());
645 }
646
TEST_P(SequenceManagerTest,NowCalledMinimumNumberOfTimesToComputeTaskDurations)647 TEST_P(SequenceManagerTest,
648 NowCalledMinimumNumberOfTimesToComputeTaskDurations) {
649 TestTaskTimeObserver time_observer;
650 sequence_manager()->SetWorkBatchSize(6);
651 sequence_manager()->AddTaskTimeObserver(&time_observer);
652
653 auto queues = CreateTaskQueues(3u);
654
655 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
656 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
657 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
658 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
659 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
660 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
661
662 RunLoop().RunUntilIdle();
663 // Now is called when we start work and then for each task when it's
664 // completed. 1 + 6 = 7 calls.
665 EXPECT_EQ(7 + GetExtraNowSampleCount(), GetNowTicksCallCount());
666 }
667
TEST_P(SequenceManagerTest,NowCalledMinimumNumberOfTimesToComputeTaskDurationsDelayedFenceAllowed)668 TEST_P(SequenceManagerTest,
669 NowCalledMinimumNumberOfTimesToComputeTaskDurationsDelayedFenceAllowed) {
670 TestTaskTimeObserver time_observer;
671 sequence_manager()->SetWorkBatchSize(6);
672 sequence_manager()->AddTaskTimeObserver(&time_observer);
673
674 std::vector<TaskQueue::Handle> queues;
675 for (size_t i = 0; i < 3; i++) {
676 queues.push_back(CreateTaskQueue(
677 TaskQueue::Spec(QueueName::TEST_TQ).SetDelayedFencesAllowed(true)));
678 }
679
680 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
681 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
682 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
683 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
684 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
685 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
686
687 RunLoop().RunUntilIdle();
688 // Now is called each time a task is queued, when first task is started
689 // running, and when a task is completed. 1 + 6 * 2 = 13 calls.
690 EXPECT_EQ(13 + GetExtraNowSampleCount(), GetNowTicksCallCount());
691 }
692
NullTask()693 void NullTask() {}
694
TestTask(uint64_t value,std::vector<EnqueueOrder> * out_result)695 void TestTask(uint64_t value, std::vector<EnqueueOrder>* out_result) {
696 out_result->push_back(EnqueueOrder::FromIntForTesting(value));
697 }
698
DisableQueueTestTask(uint64_t value,std::vector<EnqueueOrder> * out_result,TaskQueue::QueueEnabledVoter * voter)699 void DisableQueueTestTask(uint64_t value,
700 std::vector<EnqueueOrder>* out_result,
701 TaskQueue::QueueEnabledVoter* voter) {
702 out_result->push_back(EnqueueOrder::FromIntForTesting(value));
703 voter->SetVoteToEnable(false);
704 }
705
TEST_P(SequenceManagerTest,SingleQueuePosting)706 TEST_P(SequenceManagerTest, SingleQueuePosting) {
707 auto queue = CreateTaskQueue();
708
709 std::vector<EnqueueOrder> run_order;
710 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
711 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
712 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
713
714 RunLoop().RunUntilIdle();
715 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
716 }
717
TEST_P(SequenceManagerTest,MultiQueuePosting)718 TEST_P(SequenceManagerTest, MultiQueuePosting) {
719 auto queues = CreateTaskQueues(3u);
720
721 std::vector<EnqueueOrder> run_order;
722 queues[0]->task_runner()->PostTask(FROM_HERE,
723 BindOnce(&TestTask, 1, &run_order));
724 queues[0]->task_runner()->PostTask(FROM_HERE,
725 BindOnce(&TestTask, 2, &run_order));
726 queues[1]->task_runner()->PostTask(FROM_HERE,
727 BindOnce(&TestTask, 3, &run_order));
728 queues[1]->task_runner()->PostTask(FROM_HERE,
729 BindOnce(&TestTask, 4, &run_order));
730 queues[2]->task_runner()->PostTask(FROM_HERE,
731 BindOnce(&TestTask, 5, &run_order));
732 queues[2]->task_runner()->PostTask(FROM_HERE,
733 BindOnce(&TestTask, 6, &run_order));
734
735 RunLoop().RunUntilIdle();
736 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u, 6u));
737 }
738
TEST_P(SequenceManagerTest,NonNestableTaskPosting)739 TEST_P(SequenceManagerTest, NonNestableTaskPosting) {
740 auto queue = CreateTaskQueue();
741
742 std::vector<EnqueueOrder> run_order;
743 queue->task_runner()->PostNonNestableTask(FROM_HERE,
744 BindOnce(&TestTask, 1, &run_order));
745
746 RunLoop().RunUntilIdle();
747 EXPECT_THAT(run_order, ElementsAre(1u));
748 }
749
TEST_P(SequenceManagerTest,NonNestableTaskExecutesInExpectedOrder)750 TEST_P(SequenceManagerTest, NonNestableTaskExecutesInExpectedOrder) {
751 auto queue = CreateTaskQueue();
752
753 std::vector<EnqueueOrder> run_order;
754 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
755 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
756 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
757 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order));
758 queue->task_runner()->PostNonNestableTask(FROM_HERE,
759 BindOnce(&TestTask, 5, &run_order));
760
761 RunLoop().RunUntilIdle();
762 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u));
763 }
764
TEST_P(SequenceManagerTest,NonNestableTasksDoesntExecuteInNestedLoop)765 TEST_P(SequenceManagerTest, NonNestableTasksDoesntExecuteInNestedLoop) {
766 // TestMockTimeTaskRunner doesn't support nested loops.
767 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
768 return;
769 auto queue = CreateTaskQueue();
770
771 std::vector<EnqueueOrder> run_order;
772 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
773 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
774
775 std::vector<std::pair<OnceClosure, bool>> tasks_to_post_from_nested_loop;
776 tasks_to_post_from_nested_loop.push_back(
777 std::make_pair(BindOnce(&TestTask, 3, &run_order), false));
778 tasks_to_post_from_nested_loop.push_back(
779 std::make_pair(BindOnce(&TestTask, 4, &run_order), false));
780 tasks_to_post_from_nested_loop.push_back(
781 std::make_pair(BindOnce(&TestTask, 5, &run_order), true));
782 tasks_to_post_from_nested_loop.push_back(
783 std::make_pair(BindOnce(&TestTask, 6, &run_order), true));
784
785 queue->task_runner()->PostTask(
786 FROM_HERE, BindOnce(&PostFromNestedRunloop, queue->task_runner(),
787 Unretained(&tasks_to_post_from_nested_loop)));
788
789 RunLoop().RunUntilIdle();
790 // Note we expect tasks 3 & 4 to run last because they're non-nestable.
791 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 5u, 6u, 3u, 4u));
792 }
793
TEST_P(SequenceManagerTest,NonNestableTasksShutdownQueue)794 TEST_P(SequenceManagerTest, NonNestableTasksShutdownQueue) {
795 // TestMockTimeTaskRunner doesn't support nested loops.
796 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner) {
797 return;
798 }
799 auto queue = CreateTaskQueue();
800
801 std::vector<EnqueueOrder> run_order;
802
803 std::vector<std::pair<OnceClosure, bool>> tasks_to_post_from_nested_loop;
804 tasks_to_post_from_nested_loop.emplace_back(
805 BindOnce(&TestTask, 1, &run_order), false);
806 tasks_to_post_from_nested_loop.emplace_back(
807 BindOnce(&TestTask, 2, &run_order), true);
808 tasks_to_post_from_nested_loop.emplace_back(
809 BindLambdaForTesting([&queue]() { queue.reset(); }), true);
810
811 queue->task_runner()->PostTask(
812 FROM_HERE, BindOnce(&PostFromNestedRunloop, queue->task_runner(),
813 Unretained(&tasks_to_post_from_nested_loop)));
814
815 RunLoop().RunUntilIdle();
816 // We don't expect task 1 to run because the queue was shutdown.
817 EXPECT_THAT(run_order, ElementsAre(2u));
818 }
819
TEST_P(SequenceManagerTest,NonNestableTaskQueueTimeShiftsToEndOfNestedLoop)820 TEST_P(SequenceManagerTest, NonNestableTaskQueueTimeShiftsToEndOfNestedLoop) {
821 // TestMockTimeTaskRunner doesn't support nested loops.
822 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
823 return;
824
825 auto queue = CreateTaskQueue();
826
827 QueueTimeTaskObserver observer;
828 sequence_manager()->AddTaskObserver(&observer);
829 sequence_manager()->SetAddQueueTimeToTasks(true);
830
831 RunLoop nested_run_loop(RunLoop::Type::kNestableTasksAllowed);
832
833 const TimeTicks start_time = mock_tick_clock()->NowTicks();
834
835 constexpr auto kTimeSpentInNestedLoop = Seconds(1);
836 constexpr auto kTimeInTaskAfterNestedLoop = Seconds(3);
837
838 // 1) Run task 1
839 // 2) Enter a nested loop
840 // 3) Run task 3
841 // 4) Advance time by 1 second
842 // 5) Run task 5
843 // 6) Exit nested loop
844 // 7) Run task 7 (non-nestable)
845 // 8) Advance time by 3 seconds (non-nestable)
846 // 9) Run task 9 (non-nestable)
847 // Steps 7-9 are expected to run last and have had their queue time adjusted
848 // to 6 (task 8 shouldn't affect task 9's queue time).
849 std::vector<EnqueueOrder> run_order;
850 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
851 queue->task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
852 TestTask(2, &run_order);
853 nested_run_loop.Run();
854 }));
855 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
856 queue->task_runner()->PostNonNestableTask(FROM_HERE,
857 BindOnce(&TestTask, 7, &run_order));
858 queue->task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
859 TestTask(4, &run_order);
860 AdvanceMockTickClock(kTimeSpentInNestedLoop);
861 }));
862 queue->task_runner()->PostNonNestableTask(
863 FROM_HERE, BindLambdaForTesting([&]() {
864 TestTask(8, &run_order);
865 AdvanceMockTickClock(kTimeInTaskAfterNestedLoop);
866 }));
867 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 5, &run_order));
868 queue->task_runner()->PostNonNestableTask(FROM_HERE,
869 BindOnce(&TestTask, 9, &run_order));
870 queue->task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
871 TestTask(6, &run_order);
872 nested_run_loop.Quit();
873 }));
874
875 RunLoop().RunUntilIdle();
876
877 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u, 6u, 7u, 8u, 9u));
878
879 const TimeTicks expected_adjusted_queueing_time =
880 start_time + kTimeSpentInNestedLoop;
881 EXPECT_THAT(
882 observer.queue_times(),
883 ElementsAre(start_time, start_time, start_time, start_time, start_time,
884 start_time, expected_adjusted_queueing_time,
885 expected_adjusted_queueing_time,
886 expected_adjusted_queueing_time));
887
888 sequence_manager()->RemoveTaskObserver(&observer);
889 }
890
891 namespace {
892
InsertFenceAndPostTestTask(int id,std::vector<EnqueueOrder> * run_order,TaskQueue * task_queue,SequenceManagerForTest * manager)893 void InsertFenceAndPostTestTask(int id,
894 std::vector<EnqueueOrder>* run_order,
895 TaskQueue* task_queue,
896 SequenceManagerForTest* manager) {
897 run_order->push_back(EnqueueOrder::FromIntForTesting(id));
898 task_queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
899 task_queue->task_runner()->PostTask(FROM_HERE,
900 BindOnce(&TestTask, id + 1, run_order));
901
902 // Force reload of immediate work queue. In real life the same effect can be
903 // achieved with cross-thread posting.
904 manager->ReloadEmptyWorkQueues();
905 }
906
907 } // namespace
908
TEST_P(SequenceManagerTest,TaskQueueDisabledFromNestedLoop)909 TEST_P(SequenceManagerTest, TaskQueueDisabledFromNestedLoop) {
910 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
911 return;
912 auto queue = CreateTaskQueue();
913 std::vector<EnqueueOrder> run_order;
914
915 std::vector<std::pair<OnceClosure, bool>> tasks_to_post_from_nested_loop;
916
917 tasks_to_post_from_nested_loop.push_back(
918 std::make_pair(BindOnce(&TestTask, 1, &run_order), false));
919 tasks_to_post_from_nested_loop.push_back(
920 std::make_pair(BindOnce(&InsertFenceAndPostTestTask, 2, &run_order,
921 queue.get(), sequence_manager()),
922 true));
923
924 queue->task_runner()->PostTask(
925 FROM_HERE, BindOnce(&PostFromNestedRunloop, queue->task_runner(),
926 Unretained(&tasks_to_post_from_nested_loop)));
927 RunLoop().RunUntilIdle();
928
929 // Task 1 shouldn't run first due to it being non-nestable and queue gets
930 // blocked after task 2. Task 1 runs after existing nested message loop
931 // due to being posted before inserting a fence.
932 // This test checks that breaks when nestable task is pushed into a redo
933 // queue.
934 EXPECT_THAT(run_order, ElementsAre(2u, 1u));
935
936 queue->RemoveFence();
937 RunLoop().RunUntilIdle();
938 EXPECT_THAT(run_order, ElementsAre(2u, 1u, 3u));
939 }
940
TEST_P(SequenceManagerTest,HasTaskToRunImmediatelyOrReadyDelayedTask_ImmediateTask)941 TEST_P(SequenceManagerTest,
942 HasTaskToRunImmediatelyOrReadyDelayedTask_ImmediateTask) {
943 auto queue = CreateTaskQueue();
944
945 std::vector<EnqueueOrder> run_order;
946 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
947 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
948 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
949
950 // Move the task into the |immediate_work_queue|.
951 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->immediate_work_queue()->Empty());
952 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
953 queue->CreateQueueEnabledVoter();
954 voter->SetVoteToEnable(false);
955 RunLoop().RunUntilIdle();
956 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->immediate_work_queue()->Empty());
957 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
958
959 // Run the task, making the queue empty.
960 voter->SetVoteToEnable(true);
961 RunLoop().RunUntilIdle();
962 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
963 }
964
TEST_P(SequenceManagerTest,HasTaskToRunImmediatelyOrReadyDelayedTask_DelayedTask)965 TEST_P(SequenceManagerTest,
966 HasTaskToRunImmediatelyOrReadyDelayedTask_DelayedTask) {
967 auto queue = CreateTaskQueue();
968
969 std::vector<EnqueueOrder> run_order;
970 TimeDelta delay(Milliseconds(10));
971 queue->task_runner()->PostDelayedTask(
972 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
973 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
974 AdvanceMockTickClock(delay);
975 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
976
977 // Move the task into the |delayed_work_queue|.
978 LazyNow lazy_now(mock_tick_clock());
979 sequence_manager()->MoveReadyDelayedTasksToWorkQueues(&lazy_now);
980 sequence_manager()->ScheduleWork();
981 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->delayed_work_queue()->Empty());
982 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
983
984 // Run the task, making the queue empty.
985 RunLoop().RunUntilIdle();
986 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->delayed_work_queue()->Empty());
987 }
988
TEST_P(SequenceManagerTest,DelayedTaskPosting)989 TEST_P(SequenceManagerTest, DelayedTaskPosting) {
990 auto queue = CreateTaskQueue();
991
992 std::vector<EnqueueOrder> run_order;
993 TimeDelta delay(Milliseconds(10));
994 queue->task_runner()->PostDelayedTask(
995 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
996 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
997 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
998 EXPECT_TRUE(run_order.empty());
999
1000 // The task doesn't run before the delay has completed.
1001 FastForwardBy(Milliseconds(9));
1002 EXPECT_TRUE(run_order.empty());
1003
1004 // After the delay has completed, the task runs normally.
1005 FastForwardBy(Milliseconds(1));
1006 EXPECT_THAT(run_order, ElementsAre(1u));
1007 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1008 }
1009
TEST_P(SequenceManagerTest,DelayedTaskAtPosting)1010 TEST_P(SequenceManagerTest, DelayedTaskAtPosting) {
1011 auto queue = CreateTaskQueue();
1012
1013 std::vector<EnqueueOrder> run_order;
1014 constexpr TimeDelta kDelay(Milliseconds(10));
1015 auto handle = queue->task_runner()->PostCancelableDelayedTaskAt(
1016 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1017 BindOnce(&TestTask, 1, &run_order),
1018 sequence_manager()->NowTicks() + kDelay,
1019 subtle::DelayPolicy::kFlexibleNoSooner);
1020 EXPECT_EQ(FromStartAligned(kDelay), NextPendingTaskTime());
1021 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1022 EXPECT_TRUE(run_order.empty());
1023
1024 // The task doesn't run before the delay has completed.
1025 FastForwardBy(kDelay - Milliseconds(1));
1026 EXPECT_TRUE(run_order.empty());
1027
1028 // After the delay has completed, the task runs normally.
1029 FastForwardBy(Milliseconds(1));
1030 EXPECT_THAT(run_order, ElementsAre(1u));
1031 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1032 }
1033
TEST_P(SequenceManagerTest,DelayedTaskAtPosting_FlexiblePreferEarly)1034 TEST_P(SequenceManagerTest, DelayedTaskAtPosting_FlexiblePreferEarly) {
1035 auto queue = CreateTaskQueue();
1036
1037 TimeTicks start_time = sequence_manager()->NowTicks();
1038 std::vector<EnqueueOrder> run_order;
1039 constexpr TimeDelta kDelay(Milliseconds(20));
1040 auto handle = queue->task_runner()->PostCancelableDelayedTaskAt(
1041 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1042 BindOnce(&TestTask, 1, &run_order),
1043 sequence_manager()->NowTicks() + kDelay,
1044 subtle::DelayPolicy::kFlexiblePreferEarly);
1045 TimeTicks expected_run_time = start_time + kDelay;
1046 if (GetWakeUpType() == WakeUpType::kAlign) {
1047 expected_run_time =
1048 (start_time + kDelay - kLeeway).SnappedToNextTick(TimeTicks(), kLeeway);
1049 }
1050 EXPECT_EQ(expected_run_time, NextPendingTaskTime());
1051 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1052 EXPECT_TRUE(run_order.empty());
1053 LazyNow lazy_now(mock_tick_clock());
1054 EXPECT_EQ((WakeUp{start_time + kDelay, kLeeway, WakeUpResolution::kLow,
1055 subtle::DelayPolicy::kFlexiblePreferEarly}),
1056 sequence_manager()->GetPendingWakeUp(&lazy_now));
1057
1058 // The task doesn't run before the delay has completed.
1059 FastForwardBy(kDelay - kLeeway - Milliseconds(1));
1060 EXPECT_TRUE(run_order.empty());
1061
1062 // After the delay has completed, the task runs normally.
1063 FastForwardBy(kLeeway + Milliseconds(1));
1064 EXPECT_THAT(run_order, ElementsAre(1u));
1065 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1066 }
1067
TEST_P(SequenceManagerTest,DelayedTaskAtPosting_MixedDelayPolicy)1068 TEST_P(SequenceManagerTest, DelayedTaskAtPosting_MixedDelayPolicy) {
1069 auto queue = CreateTaskQueue();
1070
1071 TimeTicks start_time = sequence_manager()->NowTicks();
1072 std::vector<EnqueueOrder> run_order;
1073 auto handle1 = queue->task_runner()->PostCancelableDelayedTaskAt(
1074 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1075 BindOnce(&TestTask, 2, &run_order),
1076 sequence_manager()->NowTicks() + Milliseconds(8),
1077 subtle::DelayPolicy::kFlexibleNoSooner);
1078 auto handle2 = queue->task_runner()->PostCancelableDelayedTaskAt(
1079 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1080 BindOnce(&TestTask, 1, &run_order),
1081 sequence_manager()->NowTicks() + Milliseconds(10),
1082 subtle::DelayPolicy::kPrecise);
1083 EXPECT_EQ(start_time + Milliseconds(10), NextPendingTaskTime());
1084 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1085 EXPECT_TRUE(run_order.empty());
1086 LazyNow lazy_now(mock_tick_clock());
1087 EXPECT_EQ((WakeUp{start_time + Milliseconds(10), kLeeway,
1088 WakeUpResolution::kLow, subtle::DelayPolicy::kPrecise}),
1089 sequence_manager()->GetPendingWakeUp(&lazy_now));
1090
1091 // The task doesn't run before the delay has completed.
1092 FastForwardBy(Milliseconds(10) - Milliseconds(1));
1093 EXPECT_TRUE(run_order.empty());
1094
1095 // After the delay has completed, the task runs normally.
1096 FastForwardBy(Milliseconds(1));
1097 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1098 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1099 }
1100
TEST_P(SequenceManagerTest,DelayedTaskAtPosting_Immediate)1101 TEST_P(SequenceManagerTest, DelayedTaskAtPosting_Immediate) {
1102 auto queue = CreateTaskQueue();
1103
1104 std::vector<EnqueueOrder> run_order;
1105 auto handle = queue->task_runner()->PostCancelableDelayedTaskAt(
1106 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1107 BindOnce(&TestTask, 1, &run_order), TimeTicks(),
1108 subtle::DelayPolicy::kFlexibleNoSooner);
1109 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->HasTaskToRunImmediately());
1110 EXPECT_TRUE(run_order.empty());
1111
1112 // The task runs immediately.
1113 RunLoop().RunUntilIdle();
1114 EXPECT_THAT(run_order, ElementsAre(1u));
1115 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1116 }
1117
TEST(SequenceManagerTestWithMockTaskRunner,DelayedTaskExecutedInOneMessageLoopTask)1118 TEST(SequenceManagerTestWithMockTaskRunner,
1119 DelayedTaskExecutedInOneMessageLoopTask) {
1120 FixtureWithMockTaskRunner fixture;
1121 auto queue = fixture.sequence_manager()->CreateTaskQueue(
1122 TaskQueue::Spec(QueueName::TEST_TQ));
1123
1124 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
1125 Milliseconds(10));
1126 RunLoop().RunUntilIdle();
1127 EXPECT_EQ(1u, fixture.test_task_runner()->GetPendingTaskCount());
1128 fixture.FastForwardUntilNoTasksRemain();
1129 EXPECT_EQ(0u, fixture.test_task_runner()->GetPendingTaskCount());
1130 }
1131
TEST_P(SequenceManagerTest,DelayedTaskPosting_MultipleTasks_DecendingOrder)1132 TEST_P(SequenceManagerTest, DelayedTaskPosting_MultipleTasks_DecendingOrder) {
1133 auto queue = CreateTaskQueue();
1134
1135 std::vector<EnqueueOrder> run_order;
1136 queue->task_runner()->PostDelayedTask(
1137 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(10));
1138
1139 queue->task_runner()->PostDelayedTask(
1140 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(8));
1141
1142 queue->task_runner()->PostDelayedTask(
1143 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(5));
1144
1145 EXPECT_EQ(FromStartAligned(Milliseconds(5)), NextPendingTaskTime());
1146
1147 FastForwardBy(Milliseconds(5));
1148 EXPECT_THAT(run_order, ElementsAre(3u));
1149 EXPECT_EQ(FromStartAligned(Milliseconds(8)), NextPendingTaskTime());
1150
1151 FastForwardBy(Milliseconds(3));
1152 EXPECT_THAT(run_order, ElementsAre(3u, 2u));
1153 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
1154
1155 FastForwardBy(Milliseconds(2));
1156 EXPECT_THAT(run_order, ElementsAre(3u, 2u, 1u));
1157 }
1158
TEST_P(SequenceManagerTest,DelayedTaskAtPosting_MultipleTasks_DescendingOrder)1159 TEST_P(SequenceManagerTest,
1160 DelayedTaskAtPosting_MultipleTasks_DescendingOrder) {
1161 auto queue = CreateTaskQueue();
1162
1163 std::vector<EnqueueOrder> run_order;
1164 auto handle1 = queue->task_runner()->PostCancelableDelayedTaskAt(
1165 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1166 BindOnce(&TestTask, 1, &run_order),
1167 sequence_manager()->NowTicks() + Milliseconds(10),
1168 subtle::DelayPolicy::kFlexibleNoSooner);
1169
1170 queue->task_runner()->PostDelayedTask(
1171 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(8));
1172
1173 auto handle2 = queue->task_runner()->PostCancelableDelayedTaskAt(
1174 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1175 BindOnce(&TestTask, 3, &run_order),
1176 sequence_manager()->NowTicks() + Milliseconds(5),
1177 subtle::DelayPolicy::kFlexibleNoSooner);
1178
1179 EXPECT_EQ(FromStartAligned(Milliseconds(5)), NextPendingTaskTime());
1180
1181 FastForwardBy(Milliseconds(5));
1182 EXPECT_THAT(run_order, ElementsAre(3u));
1183 EXPECT_EQ(FromStartAligned(Milliseconds(8)), NextPendingTaskTime());
1184
1185 FastForwardBy(Milliseconds(3));
1186 EXPECT_THAT(run_order, ElementsAre(3u, 2u));
1187 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
1188
1189 FastForwardBy(Milliseconds(2));
1190 EXPECT_THAT(run_order, ElementsAre(3u, 2u, 1u));
1191 }
1192
TEST_P(SequenceManagerTest,DelayedTaskPosting_MultipleTasks_AscendingOrder)1193 TEST_P(SequenceManagerTest, DelayedTaskPosting_MultipleTasks_AscendingOrder) {
1194 auto queue = CreateTaskQueue();
1195
1196 std::vector<EnqueueOrder> run_order;
1197 queue->task_runner()->PostDelayedTask(
1198 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(1));
1199
1200 queue->task_runner()->PostDelayedTask(
1201 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(5));
1202
1203 queue->task_runner()->PostDelayedTask(
1204 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(10));
1205
1206 EXPECT_EQ(FromStartAligned(Milliseconds(1)), NextPendingTaskTime());
1207
1208 FastForwardBy(Milliseconds(1));
1209 EXPECT_THAT(run_order, ElementsAre(1u));
1210 EXPECT_EQ(FromStartAligned(Milliseconds(5)), NextPendingTaskTime());
1211
1212 FastForwardBy(Milliseconds(4));
1213 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1214 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
1215
1216 FastForwardBy(Milliseconds(5));
1217 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
1218 }
1219
TEST_P(SequenceManagerTest,DelayedTaskAtPosting_MultipleTasks_AscendingOrder)1220 TEST_P(SequenceManagerTest, DelayedTaskAtPosting_MultipleTasks_AscendingOrder) {
1221 auto queue = CreateTaskQueue();
1222
1223 std::vector<EnqueueOrder> run_order;
1224 auto handle1 = queue->task_runner()->PostCancelableDelayedTaskAt(
1225 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1226 BindOnce(&TestTask, 1, &run_order),
1227 sequence_manager()->NowTicks() + Milliseconds(1),
1228 subtle::DelayPolicy::kFlexibleNoSooner);
1229
1230 queue->task_runner()->PostDelayedTask(
1231 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(5));
1232
1233 auto handle2 = queue->task_runner()->PostCancelableDelayedTaskAt(
1234 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
1235 BindOnce(&TestTask, 3, &run_order),
1236 sequence_manager()->NowTicks() + Milliseconds(10),
1237 subtle::DelayPolicy::kFlexibleNoSooner);
1238
1239 EXPECT_EQ(FromStartAligned(Milliseconds(1)), NextPendingTaskTime());
1240
1241 FastForwardBy(Milliseconds(1));
1242 EXPECT_THAT(run_order, ElementsAre(1u));
1243 EXPECT_EQ(FromStartAligned(Milliseconds(5)), NextPendingTaskTime());
1244
1245 FastForwardBy(Milliseconds(4));
1246 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1247 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
1248
1249 FastForwardBy(Milliseconds(5));
1250 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
1251 }
1252
TEST(SequenceManagerTestWithMockTaskRunner,PostDelayedTask_SharesUnderlyingDelayedTasks)1253 TEST(SequenceManagerTestWithMockTaskRunner,
1254 PostDelayedTask_SharesUnderlyingDelayedTasks) {
1255 FixtureWithMockTaskRunner fixture;
1256 auto queue = fixture.sequence_manager()->CreateTaskQueue(
1257 TaskQueue::Spec(QueueName::TEST_TQ));
1258
1259 std::vector<EnqueueOrder> run_order;
1260 TimeDelta delay(Milliseconds(10));
1261 queue->task_runner()->PostDelayedTask(
1262 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
1263 queue->task_runner()->PostDelayedTask(
1264 FROM_HERE, BindOnce(&TestTask, 2, &run_order), delay);
1265 queue->task_runner()->PostDelayedTask(
1266 FROM_HERE, BindOnce(&TestTask, 3, &run_order), delay);
1267
1268 EXPECT_EQ(1u, fixture.test_task_runner()->GetPendingTaskCount());
1269 }
1270
TEST(SequenceManagerTestWithMockTaskRunner,CrossThreadTaskPostingToDisabledQueueDoesntScheduleWork)1271 TEST(SequenceManagerTestWithMockTaskRunner,
1272 CrossThreadTaskPostingToDisabledQueueDoesntScheduleWork) {
1273 FixtureWithMockTaskRunner fixture;
1274 auto queue = fixture.sequence_manager()->CreateTaskQueue(
1275 TaskQueue::Spec(QueueName::TEST_TQ));
1276 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1277 queue->CreateQueueEnabledVoter();
1278 voter->SetVoteToEnable(false);
1279
1280 WaitableEvent done_event;
1281 Thread thread("TestThread");
1282 thread.Start();
1283 thread.task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
1284 // Should not schedule a DoWork.
1285 queue->task_runner()->PostTask(
1286 FROM_HERE, BindOnce(&NopTask));
1287 done_event.Signal();
1288 }));
1289 done_event.Wait();
1290 thread.Stop();
1291
1292 EXPECT_EQ(0u, fixture.test_task_runner()->GetPendingTaskCount());
1293
1294 // But if the queue becomes re-enabled it does schedule work.
1295 voter->SetVoteToEnable(true);
1296 EXPECT_EQ(1u, fixture.test_task_runner()->GetPendingTaskCount());
1297 }
1298
TEST(SequenceManagerTestWithMockTaskRunner,CrossThreadTaskPostingToBlockedQueueDoesntScheduleWork)1299 TEST(SequenceManagerTestWithMockTaskRunner,
1300 CrossThreadTaskPostingToBlockedQueueDoesntScheduleWork) {
1301 FixtureWithMockTaskRunner fixture;
1302 auto queue = fixture.sequence_manager()->CreateTaskQueue(
1303 TaskQueue::Spec(QueueName::TEST_TQ));
1304 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1305
1306 WaitableEvent done_event;
1307 Thread thread("TestThread");
1308 thread.Start();
1309 thread.task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
1310 // Should not schedule a DoWork.
1311 queue->task_runner()->PostTask(
1312 FROM_HERE, BindOnce(&NopTask));
1313 done_event.Signal();
1314 }));
1315 done_event.Wait();
1316 thread.Stop();
1317
1318 EXPECT_EQ(0u, fixture.test_task_runner()->GetPendingTaskCount());
1319
1320 // But if the queue becomes unblocked it does schedule work.
1321 queue->RemoveFence();
1322 EXPECT_EQ(1u, fixture.test_task_runner()->GetPendingTaskCount());
1323 }
1324
1325 namespace {
1326
1327 class TestObject {
1328 public:
~TestObject()1329 ~TestObject() { destructor_count__++; }
1330
Run()1331 void Run() { FAIL() << "TestObject::Run should not be called"; }
1332
1333 static int destructor_count__;
1334 };
1335
1336 int TestObject::destructor_count__ = 0;
1337
1338 } // namespace
1339
TEST_P(SequenceManagerTest,PendingDelayedTasksRemovedOnShutdown)1340 TEST_P(SequenceManagerTest, PendingDelayedTasksRemovedOnShutdown) {
1341 auto queue = CreateTaskQueue();
1342
1343 TestObject::destructor_count__ = 0;
1344
1345 TimeDelta delay(Milliseconds(10));
1346 queue->task_runner()->PostDelayedTask(
1347 FROM_HERE, BindOnce(&TestObject::Run, Owned(new TestObject())), delay);
1348 queue->task_runner()->PostTask(
1349 FROM_HERE, BindOnce(&TestObject::Run, Owned(new TestObject())));
1350
1351 DestroySequenceManager();
1352
1353 EXPECT_EQ(2, TestObject::destructor_count__);
1354 }
1355
TEST_P(SequenceManagerTest,InsertAndRemoveFence)1356 TEST_P(SequenceManagerTest, InsertAndRemoveFence) {
1357 auto queue = CreateTaskQueue();
1358 StrictMock<MockTask> task;
1359
1360 // Posting a task when pumping is disabled doesn't result in work getting
1361 // posted.
1362 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1363 queue->task_runner()->PostTask(FROM_HERE, task.Get());
1364 EXPECT_CALL(task, Run).Times(0);
1365 RunLoop().RunUntilIdle();
1366
1367 // However polling still works.
1368 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
1369
1370 // After removing the fence the task runs normally.
1371 queue->RemoveFence();
1372 EXPECT_CALL(task, Run);
1373 RunLoop().RunUntilIdle();
1374 }
1375
TEST_P(SequenceManagerTest,RemovingFenceForDisabledQueueDoesNotPostDoWork)1376 TEST_P(SequenceManagerTest, RemovingFenceForDisabledQueueDoesNotPostDoWork) {
1377 auto queue = CreateTaskQueue();
1378 StrictMock<MockTask> task;
1379
1380 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1381 queue->CreateQueueEnabledVoter();
1382 voter->SetVoteToEnable(false);
1383 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1384 queue->task_runner()->PostTask(FROM_HERE, task.Get());
1385
1386 queue->RemoveFence();
1387 EXPECT_CALL(task, Run).Times(0);
1388 RunLoop().RunUntilIdle();
1389 }
1390
TEST_P(SequenceManagerTest,EnablingFencedQueueDoesNotPostDoWork)1391 TEST_P(SequenceManagerTest, EnablingFencedQueueDoesNotPostDoWork) {
1392 auto queue = CreateTaskQueue();
1393 StrictMock<MockTask> task;
1394
1395 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1396 queue->CreateQueueEnabledVoter();
1397 voter->SetVoteToEnable(false);
1398 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1399 queue->task_runner()->PostTask(FROM_HERE, task.Get());
1400 voter->SetVoteToEnable(true);
1401
1402 EXPECT_CALL(task, Run).Times(0);
1403 RunLoop().RunUntilIdle();
1404 }
1405
TEST_P(SequenceManagerTest,DenyRunning_BeforePosting)1406 TEST_P(SequenceManagerTest, DenyRunning_BeforePosting) {
1407 auto queue = CreateTaskQueue();
1408 StrictMock<MockTask> task;
1409
1410 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1411 queue->CreateQueueEnabledVoter();
1412 voter->SetVoteToEnable(false);
1413 queue->task_runner()->PostTask(FROM_HERE, task.Get());
1414
1415 EXPECT_CALL(task, Run).Times(0);
1416 RunLoop().RunUntilIdle();
1417
1418 voter->SetVoteToEnable(true);
1419 EXPECT_CALL(task, Run);
1420 RunLoop().RunUntilIdle();
1421 }
1422
TEST_P(SequenceManagerTest,DenyRunning_AfterPosting)1423 TEST_P(SequenceManagerTest, DenyRunning_AfterPosting) {
1424 auto queue = CreateTaskQueue();
1425 StrictMock<MockTask> task;
1426
1427 queue->task_runner()->PostTask(FROM_HERE, task.Get());
1428 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1429 queue->CreateQueueEnabledVoter();
1430 voter->SetVoteToEnable(false);
1431
1432 EXPECT_CALL(task, Run).Times(0);
1433 RunLoop().RunUntilIdle();
1434
1435 voter->SetVoteToEnable(true);
1436 EXPECT_CALL(task, Run);
1437 RunLoop().RunUntilIdle();
1438 }
1439
TEST_P(SequenceManagerTest,DenyRunning_AfterRemovingFence)1440 TEST_P(SequenceManagerTest, DenyRunning_AfterRemovingFence) {
1441 auto queue = CreateTaskQueue();
1442
1443 std::vector<EnqueueOrder> run_order;
1444 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1445 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
1446 queue->CreateQueueEnabledVoter();
1447 voter->SetVoteToEnable(false);
1448 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1449
1450 RunLoop().RunUntilIdle();
1451 EXPECT_TRUE(run_order.empty());
1452
1453 queue->RemoveFence();
1454 voter->SetVoteToEnable(true);
1455 RunLoop().RunUntilIdle();
1456 EXPECT_THAT(run_order, ElementsAre(1u));
1457 }
1458
TEST_P(SequenceManagerTest,RemovingFenceWithDelayedTask)1459 TEST_P(SequenceManagerTest, RemovingFenceWithDelayedTask) {
1460 TimeDelta kDelay = Milliseconds(10);
1461 auto queue = CreateTaskQueue();
1462 StrictMock<MockTask> task;
1463
1464 // Posting a delayed task when fenced will apply the delay, but won't cause
1465 // work to executed afterwards.
1466 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1467
1468 queue->task_runner()->PostDelayedTask(FROM_HERE, task.Get(), kDelay);
1469
1470 // The task does not run even though it's delay is up.
1471 EXPECT_CALL(task, Run).Times(0);
1472 FastForwardBy(kDelay);
1473
1474 // Removing the fence causes the task to run.
1475 queue->RemoveFence();
1476 EXPECT_CALL(task, Run);
1477 RunLoop().RunUntilIdle();
1478 }
1479
TEST_P(SequenceManagerTest,RemovingFenceWithMultipleDelayedTasks)1480 TEST_P(SequenceManagerTest, RemovingFenceWithMultipleDelayedTasks) {
1481 auto queue = CreateTaskQueue();
1482 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1483
1484 std::vector<EnqueueOrder> run_order;
1485 // Posting a delayed task when fenced will apply the delay, but won't cause
1486 // work to executed afterwards.
1487 TimeDelta delay1(Milliseconds(1));
1488 TimeDelta delay2(Milliseconds(10));
1489 TimeDelta delay3(Milliseconds(20));
1490 queue->task_runner()->PostDelayedTask(
1491 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay1);
1492 queue->task_runner()->PostDelayedTask(
1493 FROM_HERE, BindOnce(&TestTask, 2, &run_order), delay2);
1494 queue->task_runner()->PostDelayedTask(
1495 FROM_HERE, BindOnce(&TestTask, 3, &run_order), delay3);
1496
1497 AdvanceMockTickClock(Milliseconds(15));
1498 RunLoop().RunUntilIdle();
1499 EXPECT_TRUE(run_order.empty());
1500
1501 // Removing the fence causes the ready tasks to run.
1502 queue->RemoveFence();
1503 RunLoop().RunUntilIdle();
1504 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1505 }
1506
TEST_P(SequenceManagerTest,InsertFencePreventsDelayedTasksFromRunning)1507 TEST_P(SequenceManagerTest, InsertFencePreventsDelayedTasksFromRunning) {
1508 auto queue = CreateTaskQueue();
1509 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1510
1511 std::vector<EnqueueOrder> run_order;
1512 TimeDelta delay(Milliseconds(10));
1513 queue->task_runner()->PostDelayedTask(
1514 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
1515
1516 FastForwardBy(Milliseconds(10));
1517 EXPECT_TRUE(run_order.empty());
1518 }
1519
TEST_P(SequenceManagerTest,MultipleFences)1520 TEST_P(SequenceManagerTest, MultipleFences) {
1521 auto queue = CreateTaskQueue();
1522
1523 std::vector<EnqueueOrder> run_order;
1524 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1525 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1526 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1527
1528 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
1529 RunLoop().RunUntilIdle();
1530 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1531
1532 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1533 // Subsequent tasks should be blocked.
1534 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order));
1535 RunLoop().RunUntilIdle();
1536 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
1537 }
1538
TEST_P(SequenceManagerTest,InsertFenceThenImmediatlyRemoveDoesNotBlock)1539 TEST_P(SequenceManagerTest, InsertFenceThenImmediatlyRemoveDoesNotBlock) {
1540 auto queue = CreateTaskQueue();
1541 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1542 queue->RemoveFence();
1543
1544 std::vector<EnqueueOrder> run_order;
1545 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1546 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1547
1548 RunLoop().RunUntilIdle();
1549 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1550 }
1551
TEST_P(SequenceManagerTest,InsertFencePostThenRemoveDoesNotBlock)1552 TEST_P(SequenceManagerTest, InsertFencePostThenRemoveDoesNotBlock) {
1553 auto queue = CreateTaskQueue();
1554 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1555
1556 std::vector<EnqueueOrder> run_order;
1557 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1558 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1559 queue->RemoveFence();
1560
1561 RunLoop().RunUntilIdle();
1562 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
1563 }
1564
TEST_P(SequenceManagerTest,MultipleFencesWithInitiallyEmptyQueue)1565 TEST_P(SequenceManagerTest, MultipleFencesWithInitiallyEmptyQueue) {
1566 auto queue = CreateTaskQueue();
1567 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1568
1569 std::vector<EnqueueOrder> run_order;
1570 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1571 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1572 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1573
1574 RunLoop().RunUntilIdle();
1575 EXPECT_THAT(run_order, ElementsAre(1u));
1576 }
1577
TEST_P(SequenceManagerTest,BlockedByFence)1578 TEST_P(SequenceManagerTest, BlockedByFence) {
1579 auto queue = CreateTaskQueue();
1580 EXPECT_FALSE(queue->BlockedByFence());
1581
1582 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1583 EXPECT_TRUE(queue->BlockedByFence());
1584
1585 queue->RemoveFence();
1586 EXPECT_FALSE(queue->BlockedByFence());
1587
1588 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
1589 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1590 EXPECT_FALSE(queue->BlockedByFence());
1591
1592 RunLoop().RunUntilIdle();
1593 EXPECT_TRUE(queue->BlockedByFence());
1594
1595 queue->RemoveFence();
1596 EXPECT_FALSE(queue->BlockedByFence());
1597 }
1598
TEST_P(SequenceManagerTest,BlockedByFence_BothTypesOfFence)1599 TEST_P(SequenceManagerTest, BlockedByFence_BothTypesOfFence) {
1600 auto queue = CreateTaskQueue();
1601
1602 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
1603
1604 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
1605 EXPECT_FALSE(queue->BlockedByFence());
1606
1607 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
1608 EXPECT_TRUE(queue->BlockedByFence());
1609 }
1610
1611 namespace {
1612
RecordTimeTask(std::vector<TimeTicks> * run_times,const TickClock * clock)1613 void RecordTimeTask(std::vector<TimeTicks>* run_times, const TickClock* clock) {
1614 run_times->push_back(clock->NowTicks());
1615 }
1616
RecordTimeAndQueueTask(std::vector<std::pair<TaskQueue *,TimeTicks>> * run_times,TaskQueue * task_queue,const TickClock * clock)1617 void RecordTimeAndQueueTask(
1618 std::vector<std::pair<TaskQueue*, TimeTicks>>* run_times,
1619 TaskQueue* task_queue,
1620 const TickClock* clock) {
1621 run_times->emplace_back(task_queue, clock->NowTicks());
1622 }
1623
1624 } // namespace
1625
TEST_P(SequenceManagerTest,DelayedFence_DelayedTasks)1626 TEST_P(SequenceManagerTest, DelayedFence_DelayedTasks) {
1627 TaskQueue::Handle queue = CreateTaskQueue(
1628 TaskQueue::Spec(QueueName::TEST_TQ).SetDelayedFencesAllowed(true));
1629
1630 std::vector<TimeTicks> run_times;
1631 queue->task_runner()->PostDelayedTask(
1632 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
1633 Milliseconds(100));
1634 queue->task_runner()->PostDelayedTask(
1635 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
1636 Milliseconds(200));
1637 queue->task_runner()->PostDelayedTask(
1638 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
1639 Milliseconds(300));
1640
1641 queue->InsertFenceAt(mock_tick_clock()->NowTicks() + Milliseconds(250));
1642 EXPECT_FALSE(queue->HasActiveFence());
1643
1644 FastForwardUntilNoTasksRemain();
1645
1646 EXPECT_TRUE(queue->HasActiveFence());
1647 EXPECT_THAT(run_times, ElementsAre(FromStartAligned(Milliseconds(100)),
1648 FromStartAligned(Milliseconds(200))));
1649 run_times.clear();
1650
1651 queue->RemoveFence();
1652
1653 FastForwardUntilNoTasksRemain();
1654
1655 EXPECT_FALSE(queue->HasActiveFence());
1656 EXPECT_THAT(run_times, ElementsAre(FromStartAligned(Milliseconds(300))));
1657 }
1658
TEST_P(SequenceManagerTest,DelayedFence_ImmediateTasks)1659 TEST_P(SequenceManagerTest, DelayedFence_ImmediateTasks) {
1660 const auto kStartTime = mock_tick_clock()->NowTicks();
1661 TaskQueue::Handle queue = CreateTaskQueue(
1662 TaskQueue::Spec(QueueName::TEST_TQ).SetDelayedFencesAllowed(true));
1663
1664 std::vector<TimeTicks> run_times;
1665 queue->InsertFenceAt(mock_tick_clock()->NowTicks() + Milliseconds(250));
1666
1667 for (int i = 0; i < 5; ++i) {
1668 queue->task_runner()->PostTask(
1669 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()));
1670 FastForwardBy(Milliseconds(100));
1671 if (i < 2) {
1672 EXPECT_FALSE(queue->HasActiveFence());
1673 } else {
1674 EXPECT_TRUE(queue->HasActiveFence());
1675 }
1676 }
1677
1678 EXPECT_THAT(run_times, ElementsAre(kStartTime, kStartTime + Milliseconds(100),
1679 kStartTime + Milliseconds(200)));
1680 run_times.clear();
1681
1682 queue->RemoveFence();
1683 FastForwardUntilNoTasksRemain();
1684
1685 EXPECT_THAT(run_times, ElementsAre(kStartTime + Milliseconds(500),
1686 kStartTime + Milliseconds(500)));
1687 }
1688
TEST_P(SequenceManagerTest,DelayedFence_RemovedFenceDoesNotActivate)1689 TEST_P(SequenceManagerTest, DelayedFence_RemovedFenceDoesNotActivate) {
1690 const auto kStartTime = mock_tick_clock()->NowTicks();
1691 TaskQueue::Handle queue = CreateTaskQueue(
1692 TaskQueue::Spec(QueueName::TEST_TQ).SetDelayedFencesAllowed(true));
1693
1694 std::vector<TimeTicks> run_times;
1695 queue->InsertFenceAt(mock_tick_clock()->NowTicks() + Milliseconds(250));
1696
1697 for (int i = 0; i < 3; ++i) {
1698 queue->task_runner()->PostTask(
1699 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()));
1700 EXPECT_FALSE(queue->HasActiveFence());
1701 FastForwardBy(Milliseconds(100));
1702 }
1703
1704 EXPECT_TRUE(queue->HasActiveFence());
1705 queue->RemoveFence();
1706
1707 for (int i = 0; i < 2; ++i) {
1708 queue->task_runner()->PostTask(
1709 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()));
1710 FastForwardBy(Milliseconds(100));
1711 EXPECT_FALSE(queue->HasActiveFence());
1712 }
1713
1714 EXPECT_THAT(run_times, ElementsAre(kStartTime, kStartTime + Milliseconds(100),
1715 kStartTime + Milliseconds(200),
1716 kStartTime + Milliseconds(300),
1717 kStartTime + Milliseconds(400)));
1718 }
1719
TEST_P(SequenceManagerTest,DelayedFence_TakeIncomingImmediateQueue)1720 TEST_P(SequenceManagerTest, DelayedFence_TakeIncomingImmediateQueue) {
1721 // This test checks that everything works correctly when a work queue
1722 // is swapped with an immediate incoming queue and a delayed fence
1723 // is activated, forcing a different queue to become active.
1724 const auto kStartTime = mock_tick_clock()->NowTicks();
1725 TaskQueue::Handle queue1 = CreateTaskQueue(
1726 TaskQueue::Spec(QueueName::TEST_TQ).SetDelayedFencesAllowed(true));
1727 TaskQueue::Handle queue2 = CreateTaskQueue(
1728 TaskQueue::Spec(QueueName::TEST2_TQ).SetDelayedFencesAllowed(true));
1729
1730 std::vector<std::pair<TaskQueue*, TimeTicks>> run_times;
1731
1732 // Fence ensures that the task posted after advancing time is blocked.
1733 queue1->InsertFenceAt(mock_tick_clock()->NowTicks() + Milliseconds(250));
1734
1735 // This task should not be blocked and should run immediately after
1736 // advancing time at 301ms.
1737 queue1->task_runner()->PostTask(
1738 FROM_HERE, BindOnce(&RecordTimeAndQueueTask, &run_times,
1739 Unretained(queue1.get()), mock_tick_clock()));
1740 // Force reload of immediate work queue. In real life the same effect can be
1741 // achieved with cross-thread posting.
1742 sequence_manager()->ReloadEmptyWorkQueues();
1743
1744 AdvanceMockTickClock(Milliseconds(300));
1745
1746 // This task should be blocked.
1747 queue1->task_runner()->PostTask(
1748 FROM_HERE, BindOnce(&RecordTimeAndQueueTask, &run_times,
1749 Unretained(queue1.get()), mock_tick_clock()));
1750 // This task on a different runner should run as expected.
1751 queue2->task_runner()->PostTask(
1752 FROM_HERE, BindOnce(&RecordTimeAndQueueTask, &run_times,
1753 Unretained(queue2.get()), mock_tick_clock()));
1754
1755 FastForwardUntilNoTasksRemain();
1756
1757 EXPECT_THAT(
1758 run_times,
1759 ElementsAre(
1760 std::make_pair(queue1.get(), kStartTime + Milliseconds(300)),
1761 std::make_pair(queue2.get(), kStartTime + Milliseconds(300))));
1762 }
1763
1764 namespace {
1765
ReentrantTestTask(TaskQueue * runner,int countdown,std::vector<EnqueueOrder> * out_result)1766 void ReentrantTestTask(TaskQueue* runner,
1767 int countdown,
1768 std::vector<EnqueueOrder>* out_result) {
1769 out_result->push_back(EnqueueOrder::FromIntForTesting(countdown));
1770 if (--countdown) {
1771 runner->task_runner()->PostTask(
1772 FROM_HERE, BindOnce(&ReentrantTestTask, Unretained(runner), countdown,
1773 out_result));
1774 }
1775 }
1776
1777 } // namespace
1778
TEST_P(SequenceManagerTest,ReentrantPosting)1779 TEST_P(SequenceManagerTest, ReentrantPosting) {
1780 auto queue = CreateTaskQueue();
1781
1782 std::vector<EnqueueOrder> run_order;
1783 queue->task_runner()->PostTask(
1784 FROM_HERE,
1785 BindOnce(&ReentrantTestTask, Unretained(queue.get()), 3, &run_order));
1786
1787 RunLoop().RunUntilIdle();
1788 EXPECT_THAT(run_order, ElementsAre(3u, 2u, 1u));
1789 }
1790
1791 namespace {
1792
1793 class RefCountedCallbackFactory {
1794 public:
WrapCallback(OnceCallback<void ()> cb)1795 OnceCallback<void()> WrapCallback(OnceCallback<void()> cb) {
1796 return BindOnce(
1797 [](OnceCallback<void()> cb, WeakPtr<bool>) { std::move(cb).Run(); },
1798 std::move(cb), task_references_.GetWeakPtr());
1799 }
1800
HasReferences() const1801 bool HasReferences() const { return task_references_.HasWeakPtrs(); }
1802
1803 private:
1804 bool dummy_;
1805 WeakPtrFactory<bool> task_references_{&dummy_};
1806 };
1807
1808 } // namespace
1809
TEST_P(SequenceManagerTest,NoTasksAfterShutdown)1810 TEST_P(SequenceManagerTest, NoTasksAfterShutdown) {
1811 auto queue = CreateTaskQueue();
1812 StrictMock<MockTask> task;
1813 RefCountedCallbackFactory counter;
1814
1815 EXPECT_CALL(task, Run).Times(0);
1816 queue->task_runner()->PostTask(FROM_HERE, counter.WrapCallback(task.Get()));
1817 DestroySequenceManager();
1818 queue->task_runner()->PostTask(FROM_HERE, counter.WrapCallback(task.Get()));
1819
1820 if (GetUnderlyingRunnerType() != RunnerType::kMessagePump) {
1821 RunLoop().RunUntilIdle();
1822 }
1823
1824 EXPECT_FALSE(counter.HasReferences());
1825 }
1826
PostTaskToRunner(TaskQueue * runner,std::vector<EnqueueOrder> * run_order)1827 void PostTaskToRunner(TaskQueue* runner, std::vector<EnqueueOrder>* run_order) {
1828 runner->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, run_order));
1829 }
1830
TEST_P(SequenceManagerTest,PostFromThread)1831 TEST_P(SequenceManagerTest, PostFromThread) {
1832 auto queue = CreateTaskQueue();
1833
1834 std::vector<EnqueueOrder> run_order;
1835 Thread thread("TestThread");
1836 thread.Start();
1837 thread.task_runner()->PostTask(
1838 FROM_HERE,
1839 BindOnce(&PostTaskToRunner, Unretained(queue.get()), &run_order));
1840 thread.Stop();
1841
1842 RunLoop().RunUntilIdle();
1843 EXPECT_THAT(run_order, ElementsAre(1u));
1844 }
1845
RePostingTestTask(TaskQueue * runner,int * run_count)1846 void RePostingTestTask(TaskQueue* runner, int* run_count) {
1847 (*run_count)++;
1848 runner->task_runner()->PostTask(
1849 FROM_HERE, BindOnce(&RePostingTestTask, Unretained(runner), run_count));
1850 }
1851
TEST_P(SequenceManagerTest,DoWorkCantPostItselfMultipleTimes)1852 TEST_P(SequenceManagerTest, DoWorkCantPostItselfMultipleTimes) {
1853 auto queue = CreateTaskQueue();
1854
1855 int run_count = 0;
1856 queue->task_runner()->PostTask(
1857 FROM_HERE,
1858 BindOnce(&RePostingTestTask, Unretained(queue.get()), &run_count));
1859
1860 RunDoWorkOnce();
1861 EXPECT_EQ(1u, sequence_manager()->GetPendingTaskCountForTesting());
1862 EXPECT_EQ(1, run_count);
1863 }
1864
TEST_P(SequenceManagerTest,PostFromNestedRunloop)1865 TEST_P(SequenceManagerTest, PostFromNestedRunloop) {
1866 auto queue = CreateTaskQueue();
1867
1868 std::vector<EnqueueOrder> run_order;
1869 std::vector<std::pair<OnceClosure, bool>> tasks_to_post_from_nested_loop;
1870 tasks_to_post_from_nested_loop.push_back(
1871 std::make_pair(BindOnce(&TestTask, 1, &run_order), true));
1872
1873 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 0, &run_order));
1874 queue->task_runner()->PostTask(
1875 FROM_HERE, BindOnce(&PostFromNestedRunloop, queue->task_runner(),
1876 Unretained(&tasks_to_post_from_nested_loop)));
1877 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1878
1879 RunLoop().RunUntilIdle();
1880
1881 EXPECT_THAT(run_order, ElementsAre(0u, 2u, 1u));
1882 }
1883
TEST_P(SequenceManagerTest,WorkBatching)1884 TEST_P(SequenceManagerTest, WorkBatching) {
1885 auto queue = CreateTaskQueue();
1886 sequence_manager()->SetWorkBatchSize(2);
1887
1888 std::vector<EnqueueOrder> run_order;
1889 for (int i = 0; i < 4; ++i) {
1890 queue->task_runner()->PostTask(FROM_HERE,
1891 BindOnce(&TestTask, i, &run_order));
1892 }
1893
1894 // Running one task in the host message loop should cause two posted tasks
1895 // to get executed.
1896 RunDoWorkOnce();
1897 EXPECT_THAT(run_order, ElementsAre(0u, 1u));
1898
1899 // The second task runs the remaining two posted tasks.
1900 RunDoWorkOnce();
1901 EXPECT_THAT(run_order, ElementsAre(0u, 1u, 2u, 3u));
1902 }
1903
1904 namespace {
1905
1906 class MockTaskObserver : public TaskObserver {
1907 public:
1908 MOCK_METHOD1(DidProcessTask, void(const PendingTask& task));
1909 MOCK_METHOD2(WillProcessTask,
1910 void(const PendingTask& task, bool was_blocked_or_low_priority));
1911 };
1912
1913 } // namespace
1914
TEST_P(SequenceManagerTest,TaskObserverAdding)1915 TEST_P(SequenceManagerTest, TaskObserverAdding) {
1916 auto queue = CreateTaskQueue();
1917 MockTaskObserver observer;
1918
1919 sequence_manager()->SetWorkBatchSize(2);
1920 sequence_manager()->AddTaskObserver(&observer);
1921
1922 std::vector<EnqueueOrder> run_order;
1923 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1924 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
1925
1926 EXPECT_CALL(observer,
1927 WillProcessTask(_, /*was_blocked_or_low_priority=*/false))
1928 .Times(2);
1929 EXPECT_CALL(observer, DidProcessTask(_)).Times(2);
1930 RunLoop().RunUntilIdle();
1931 }
1932
TEST_P(SequenceManagerTest,TaskObserverRemoving)1933 TEST_P(SequenceManagerTest, TaskObserverRemoving) {
1934 auto queue = CreateTaskQueue();
1935 MockTaskObserver observer;
1936 sequence_manager()->SetWorkBatchSize(2);
1937 sequence_manager()->AddTaskObserver(&observer);
1938 sequence_manager()->RemoveTaskObserver(&observer);
1939
1940 std::vector<EnqueueOrder> run_order;
1941 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1942
1943 EXPECT_CALL(observer, WillProcessTask(_, _)).Times(0);
1944 EXPECT_CALL(observer, DidProcessTask(_)).Times(0);
1945 RunLoop().RunUntilIdle();
1946 }
1947
RemoveObserverTask(SequenceManagerImpl * manager,TaskObserver * observer)1948 void RemoveObserverTask(SequenceManagerImpl* manager, TaskObserver* observer) {
1949 manager->RemoveTaskObserver(observer);
1950 }
1951
TEST_P(SequenceManagerTest,TaskObserverRemovingInsideTask)1952 TEST_P(SequenceManagerTest, TaskObserverRemovingInsideTask) {
1953 auto queue = CreateTaskQueue();
1954 MockTaskObserver observer;
1955 sequence_manager()->SetWorkBatchSize(3);
1956 sequence_manager()->AddTaskObserver(&observer);
1957
1958 queue->task_runner()->PostTask(
1959 FROM_HERE, BindOnce(&RemoveObserverTask, sequence_manager(), &observer));
1960
1961 EXPECT_CALL(observer,
1962 WillProcessTask(_, /*was_blocked_or_low_priority=*/false))
1963 .Times(1);
1964 EXPECT_CALL(observer, DidProcessTask(_)).Times(0);
1965 RunLoop().RunUntilIdle();
1966 }
1967
TEST_P(SequenceManagerTest,QueueTaskObserverAdding)1968 TEST_P(SequenceManagerTest, QueueTaskObserverAdding) {
1969 auto queues = CreateTaskQueues(2);
1970 MockTaskObserver observer;
1971
1972 sequence_manager()->SetWorkBatchSize(2);
1973 queues[0]->AddTaskObserver(&observer);
1974
1975 std::vector<EnqueueOrder> run_order;
1976 queues[0]->task_runner()->PostTask(FROM_HERE,
1977 BindOnce(&TestTask, 1, &run_order));
1978 queues[1]->task_runner()->PostTask(FROM_HERE,
1979 BindOnce(&TestTask, 2, &run_order));
1980
1981 EXPECT_CALL(observer,
1982 WillProcessTask(_, /*was_blocked_or_low_priority=*/false))
1983 .Times(1);
1984 EXPECT_CALL(observer, DidProcessTask(_)).Times(1);
1985 RunLoop().RunUntilIdle();
1986 }
1987
TEST_P(SequenceManagerTest,QueueTaskObserverRemoving)1988 TEST_P(SequenceManagerTest, QueueTaskObserverRemoving) {
1989 auto queue = CreateTaskQueue();
1990 MockTaskObserver observer;
1991 sequence_manager()->SetWorkBatchSize(2);
1992 queue->AddTaskObserver(&observer);
1993 queue->RemoveTaskObserver(&observer);
1994
1995 std::vector<EnqueueOrder> run_order;
1996 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
1997
1998 EXPECT_CALL(observer,
1999 WillProcessTask(_, /*was_blocked_or_low_priority=*/false))
2000 .Times(0);
2001 EXPECT_CALL(observer, DidProcessTask(_)).Times(0);
2002
2003 RunLoop().RunUntilIdle();
2004 }
2005
RemoveQueueObserverTask(TaskQueue * queue,TaskObserver * observer)2006 void RemoveQueueObserverTask(TaskQueue* queue, TaskObserver* observer) {
2007 queue->RemoveTaskObserver(observer);
2008 }
2009
TEST_P(SequenceManagerTest,QueueTaskObserverRemovingInsideTask)2010 TEST_P(SequenceManagerTest, QueueTaskObserverRemovingInsideTask) {
2011 auto queue = CreateTaskQueue();
2012 MockTaskObserver observer;
2013 queue->AddTaskObserver(&observer);
2014
2015 queue->task_runner()->PostTask(
2016 FROM_HERE,
2017 BindOnce(&RemoveQueueObserverTask, Unretained(queue.get()), &observer));
2018
2019 EXPECT_CALL(observer,
2020 WillProcessTask(_, /*was_blocked_or_low_priority=*/false))
2021 .Times(1);
2022 EXPECT_CALL(observer, DidProcessTask(_)).Times(0);
2023 RunLoop().RunUntilIdle();
2024 }
2025
TEST_P(SequenceManagerTest,CancelHandleInsideTaskObserver)2026 TEST_P(SequenceManagerTest, CancelHandleInsideTaskObserver) {
2027 class CancelingTaskObserver : public TaskObserver {
2028 public:
2029 DelayedTaskHandle handle;
2030 bool will_run_task_called = false;
2031 bool did_process_task_called = false;
2032 explicit CancelingTaskObserver(DelayedTaskHandle handle_in)
2033 : handle(std::move(handle_in)) {
2034 EXPECT_TRUE(handle.IsValid());
2035 }
2036
2037 ~CancelingTaskObserver() override {
2038 EXPECT_FALSE(handle.IsValid());
2039 EXPECT_TRUE(will_run_task_called);
2040 EXPECT_TRUE(did_process_task_called);
2041 }
2042
2043 void DidProcessTask(const PendingTask& task) override {
2044 did_process_task_called = true;
2045 }
2046 void WillProcessTask(const PendingTask& task,
2047 bool was_blocked_or_low_priority) override {
2048 handle.CancelTask();
2049 will_run_task_called = true;
2050 }
2051 };
2052
2053 auto queue = CreateTaskQueue();
2054
2055 auto handle = queue->task_runner()->PostCancelableDelayedTask(
2056 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE,
2057 BindLambdaForTesting([]() { FAIL(); }), base::TimeDelta());
2058
2059 CancelingTaskObserver observer(std::move(handle));
2060 queue->AddTaskObserver(&observer);
2061
2062 RunLoop().RunUntilIdle();
2063 }
2064
TEST_P(SequenceManagerTest,ThreadCheckAfterTermination)2065 TEST_P(SequenceManagerTest, ThreadCheckAfterTermination) {
2066 auto queue = CreateTaskQueue();
2067 EXPECT_TRUE(queue->task_runner()->RunsTasksInCurrentSequence());
2068 DestroySequenceManager();
2069 EXPECT_TRUE(queue->task_runner()->RunsTasksInCurrentSequence());
2070 }
2071
TEST_P(SequenceManagerTest,GetNextDelayedWakeUp)2072 TEST_P(SequenceManagerTest, GetNextDelayedWakeUp) {
2073 auto queues = CreateTaskQueues(2u);
2074 AdvanceMockTickClock(Microseconds(10000));
2075 LazyNow lazy_now_1(mock_tick_clock());
2076
2077 // With no delayed tasks.
2078 EXPECT_FALSE(sequence_manager()->GetNextDelayedWakeUp());
2079
2080 // With a non-delayed task.
2081 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2082 EXPECT_FALSE(sequence_manager()->GetNextDelayedWakeUp());
2083
2084 // With a delayed task.
2085 TimeDelta expected_delay = Milliseconds(50);
2086 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2087 expected_delay);
2088 EXPECT_EQ(lazy_now_1.Now() + expected_delay,
2089 sequence_manager()->GetNextDelayedWakeUp()->time);
2090
2091 // With another delayed task in the same queue with a longer delay.
2092 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2093 Milliseconds(100));
2094 EXPECT_EQ(lazy_now_1.Now() + expected_delay,
2095 sequence_manager()->GetNextDelayedWakeUp()->time);
2096
2097 // With another delayed task in the same queue with a shorter delay.
2098 expected_delay = Milliseconds(20);
2099 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2100 expected_delay);
2101 EXPECT_EQ(lazy_now_1.Now() + expected_delay,
2102 sequence_manager()->GetNextDelayedWakeUp()->time);
2103
2104 // With another delayed task in a different queue with a shorter delay.
2105 expected_delay = Milliseconds(10);
2106 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2107 expected_delay);
2108 EXPECT_EQ(lazy_now_1.Now() + expected_delay,
2109 sequence_manager()->GetNextDelayedWakeUp()->time);
2110 }
2111
TEST_P(SequenceManagerTest,GetNextDelayedWakeUp_MultipleQueues)2112 TEST_P(SequenceManagerTest, GetNextDelayedWakeUp_MultipleQueues) {
2113 auto queues = CreateTaskQueues(3u);
2114
2115 TimeDelta delay1 = Milliseconds(50);
2116 TimeDelta delay2 = Milliseconds(5);
2117 TimeDelta delay3 = Milliseconds(10);
2118 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2119 delay1);
2120 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2121 delay2);
2122 queues[2]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2123 delay3);
2124 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2125
2126 LazyNow lazy_now(mock_tick_clock());
2127 EXPECT_EQ(lazy_now.Now() + delay2,
2128 sequence_manager()->GetNextDelayedWakeUp()->time);
2129 }
2130
TEST(SequenceManagerWithTaskRunnerTest,DeleteSequenceManagerInsideATask)2131 TEST(SequenceManagerWithTaskRunnerTest, DeleteSequenceManagerInsideATask) {
2132 FixtureWithMockTaskRunner fixture;
2133 auto queue = fixture.sequence_manager()->CreateTaskQueue(
2134 TaskQueue::Spec(QueueName::TEST_TQ));
2135
2136 queue->task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
2137 fixture.DestroySequenceManager();
2138 }));
2139
2140 // This should not crash, assuming DoWork detects the SequenceManager has
2141 // been deleted.
2142 RunLoop().RunUntilIdle();
2143 }
2144
TEST_P(SequenceManagerTest,GetAndClearSystemIsQuiescentBit)2145 TEST_P(SequenceManagerTest, GetAndClearSystemIsQuiescentBit) {
2146 auto queues = CreateTaskQueues(3u);
2147
2148 TaskQueue::Handle queue0 = CreateTaskQueue(
2149 TaskQueue::Spec(QueueName::TEST_TQ).SetShouldMonitorQuiescence(true));
2150 TaskQueue::Handle queue1 = CreateTaskQueue(
2151 TaskQueue::Spec(QueueName::TEST2_TQ).SetShouldMonitorQuiescence(true));
2152 TaskQueue::Handle queue2 = CreateTaskQueue();
2153
2154 EXPECT_TRUE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2155
2156 queue0->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2157 RunLoop().RunUntilIdle();
2158 EXPECT_FALSE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2159 EXPECT_TRUE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2160
2161 queue1->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2162 RunLoop().RunUntilIdle();
2163 EXPECT_FALSE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2164 EXPECT_TRUE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2165
2166 queue2->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2167 RunLoop().RunUntilIdle();
2168 EXPECT_TRUE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2169
2170 queue0->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2171 queue1->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2172 RunLoop().RunUntilIdle();
2173 EXPECT_FALSE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2174 EXPECT_TRUE(sequence_manager()->GetAndClearSystemIsQuiescentBit());
2175 }
2176
TEST_P(SequenceManagerTest,HasTaskToRunImmediatelyOrReadyDelayedTask)2177 TEST_P(SequenceManagerTest, HasTaskToRunImmediatelyOrReadyDelayedTask) {
2178 auto queue = CreateTaskQueue();
2179
2180 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2181 queue->task_runner()->PostTask(FROM_HERE, BindOnce(NullTask));
2182 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2183
2184 RunLoop().RunUntilIdle();
2185 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2186 }
2187
TEST_P(SequenceManagerTest,HasTaskToRunImmediatelyOrReadyDelayedTask_DelayedTasks)2188 TEST_P(SequenceManagerTest,
2189 HasTaskToRunImmediatelyOrReadyDelayedTask_DelayedTasks) {
2190 auto queue = CreateTaskQueue();
2191
2192 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2193 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(NullTask),
2194 Milliseconds(12));
2195 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2196
2197 // Move time forwards until just before the delayed task should run.
2198 AdvanceMockTickClock(Milliseconds(10));
2199 LazyNow lazy_now_1(mock_tick_clock());
2200 sequence_manager()->MoveReadyDelayedTasksToWorkQueues(&lazy_now_1);
2201 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2202
2203 // Force the delayed task onto the work queue.
2204 AdvanceMockTickClock(Milliseconds(2));
2205 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2206
2207 LazyNow lazy_now_2(mock_tick_clock());
2208 sequence_manager()->MoveReadyDelayedTasksToWorkQueues(&lazy_now_2);
2209 EXPECT_TRUE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2210
2211 sequence_manager()->ScheduleWork();
2212 RunLoop().RunUntilIdle();
2213 EXPECT_FALSE(queue->HasTaskToRunImmediatelyOrReadyDelayedTask());
2214 }
2215
TEST_P(SequenceManagerTest,ImmediateTasksAreNotStarvedByDelayedTasks)2216 TEST_P(SequenceManagerTest, ImmediateTasksAreNotStarvedByDelayedTasks) {
2217 auto queue = CreateTaskQueue();
2218 std::vector<EnqueueOrder> run_order;
2219 constexpr auto kDelay = Milliseconds(10);
2220
2221 // By posting the immediate tasks from a delayed one we make sure that the
2222 // delayed tasks we post afterwards have a lower enqueue_order than the
2223 // immediate ones. Thus all the delayed ones would run before the immediate
2224 // ones if it weren't for the anti-starvation feature we are testing here.
2225 queue->task_runner()->PostDelayedTask(
2226 FROM_HERE, BindLambdaForTesting([&]() {
2227 for (int i = 0; i < 9; i++) {
2228 queue->task_runner()->PostTask(FROM_HERE,
2229 BindOnce(&TestTask, i, &run_order));
2230 }
2231 }),
2232 kDelay);
2233
2234 for (int i = 10; i < 19; i++) {
2235 queue->task_runner()->PostDelayedTask(
2236 FROM_HERE, BindOnce(&TestTask, i, &run_order), kDelay);
2237 }
2238
2239 FastForwardBy(Milliseconds(10));
2240
2241 // Delayed tasks are not allowed to starve out immediate work which is why
2242 // some of the immediate tasks run out of order.
2243 uint64_t expected_run_order[] = {10, 11, 12, 0, 13, 14, 15, 1, 16,
2244 17, 18, 2, 3, 4, 5, 6, 7, 8};
2245 EXPECT_THAT(run_order, ElementsAreArray(expected_run_order));
2246 }
2247
TEST_P(SequenceManagerTest,DelayedTaskDoesNotSkipAHeadOfNonDelayedTask_SameQueue)2248 TEST_P(SequenceManagerTest,
2249 DelayedTaskDoesNotSkipAHeadOfNonDelayedTask_SameQueue) {
2250 auto queue = CreateTaskQueue();
2251
2252 std::vector<EnqueueOrder> run_order;
2253 TimeDelta delay = Milliseconds(10);
2254 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
2255 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
2256 queue->task_runner()->PostDelayedTask(
2257 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
2258
2259 AdvanceMockTickClock(delay * 2);
2260 RunLoop().RunUntilIdle();
2261
2262 EXPECT_THAT(run_order, ElementsAre(2u, 3u, 1u));
2263 }
2264
TEST_P(SequenceManagerTest,DelayedTaskDoesNotSkipAHeadOfNonDelayedTask_DifferentQueues)2265 TEST_P(SequenceManagerTest,
2266 DelayedTaskDoesNotSkipAHeadOfNonDelayedTask_DifferentQueues) {
2267 auto queues = CreateTaskQueues(2u);
2268
2269 std::vector<EnqueueOrder> run_order;
2270 TimeDelta delay = Milliseconds(10);
2271 queues[1]->task_runner()->PostTask(FROM_HERE,
2272 BindOnce(&TestTask, 2, &run_order));
2273 queues[1]->task_runner()->PostTask(FROM_HERE,
2274 BindOnce(&TestTask, 3, &run_order));
2275 queues[0]->task_runner()->PostDelayedTask(
2276 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay);
2277
2278 AdvanceMockTickClock(delay * 2);
2279 RunLoop().RunUntilIdle();
2280
2281 EXPECT_THAT(run_order, ElementsAre(2u, 3u, 1u));
2282 }
2283
TEST_P(SequenceManagerTest,DelayedTaskDoesNotSkipAHeadOfShorterDelayedTask)2284 TEST_P(SequenceManagerTest, DelayedTaskDoesNotSkipAHeadOfShorterDelayedTask) {
2285 auto queues = CreateTaskQueues(2u);
2286
2287 std::vector<EnqueueOrder> run_order;
2288 TimeDelta delay1 = Milliseconds(10);
2289 TimeDelta delay2 = Milliseconds(5);
2290 queues[0]->task_runner()->PostDelayedTask(
2291 FROM_HERE, BindOnce(&TestTask, 1, &run_order), delay1);
2292 queues[1]->task_runner()->PostDelayedTask(
2293 FROM_HERE, BindOnce(&TestTask, 2, &run_order), delay2);
2294
2295 AdvanceMockTickClock(delay1 * 2);
2296 RunLoop().RunUntilIdle();
2297
2298 EXPECT_THAT(run_order, ElementsAre(2u, 1u));
2299 }
2300
2301 namespace {
2302
CheckIsNested(bool * is_nested)2303 void CheckIsNested(bool* is_nested) {
2304 *is_nested = RunLoop::IsNestedOnCurrentThread();
2305 }
2306
PostAndQuitFromNestedRunloop(RunLoop * run_loop,TaskQueue * runner,bool * was_nested)2307 void PostAndQuitFromNestedRunloop(RunLoop* run_loop,
2308 TaskQueue* runner,
2309 bool* was_nested) {
2310 runner->task_runner()->PostTask(FROM_HERE, run_loop->QuitClosure());
2311 runner->task_runner()->PostTask(FROM_HERE,
2312 BindOnce(&CheckIsNested, was_nested));
2313 run_loop->Run();
2314 }
2315
2316 } // namespace
2317
TEST_P(SequenceManagerTest,QuitWhileNested)2318 TEST_P(SequenceManagerTest, QuitWhileNested) {
2319 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
2320 return;
2321 // This test makes sure we don't continue running a work batch after a nested
2322 // run loop has been exited in the middle of the batch.
2323 auto queue = CreateTaskQueue();
2324 sequence_manager()->SetWorkBatchSize(2);
2325
2326 bool was_nested = true;
2327 RunLoop run_loop(RunLoop::Type::kNestableTasksAllowed);
2328 queue->task_runner()->PostTask(
2329 FROM_HERE, BindOnce(&PostAndQuitFromNestedRunloop, Unretained(&run_loop),
2330 queue.get(), Unretained(&was_nested)));
2331
2332 RunLoop().RunUntilIdle();
2333 EXPECT_FALSE(was_nested);
2334 }
2335
2336 namespace {
2337
2338 class SequenceNumberCapturingTaskObserver : public TaskObserver {
2339 public:
2340 // TaskObserver overrides.
WillProcessTask(const PendingTask & pending_task,bool was_blocked_or_low_priority)2341 void WillProcessTask(const PendingTask& pending_task,
2342 bool was_blocked_or_low_priority) override {}
DidProcessTask(const PendingTask & pending_task)2343 void DidProcessTask(const PendingTask& pending_task) override {
2344 sequence_numbers_.push_back(pending_task.sequence_num);
2345 }
2346
sequence_numbers() const2347 const std::vector<int>& sequence_numbers() const { return sequence_numbers_; }
2348
2349 private:
2350 std::vector<int> sequence_numbers_;
2351 };
2352
2353 } // namespace
2354
TEST_P(SequenceManagerTest,SequenceNumSetWhenTaskIsPosted)2355 TEST_P(SequenceManagerTest, SequenceNumSetWhenTaskIsPosted) {
2356 auto queue = CreateTaskQueue();
2357
2358 SequenceNumberCapturingTaskObserver observer;
2359 sequence_manager()->AddTaskObserver(&observer);
2360
2361 // Register four tasks that will run in reverse order.
2362 std::vector<EnqueueOrder> run_order;
2363 queue->task_runner()->PostDelayedTask(
2364 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(30));
2365 queue->task_runner()->PostDelayedTask(
2366 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(20));
2367 queue->task_runner()->PostDelayedTask(
2368 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(10));
2369 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order));
2370
2371 FastForwardBy(Milliseconds(40));
2372 ASSERT_THAT(run_order, ElementsAre(4u, 3u, 2u, 1u));
2373
2374 // The sequence numbers are a one-based monotonically incrememting counter
2375 // which should be set when the task is posted rather than when it's enqueued
2376 // onto the Incoming queue. This counter starts with 2.
2377 EXPECT_THAT(observer.sequence_numbers(), ElementsAre(5, 4, 3, 2));
2378
2379 sequence_manager()->RemoveTaskObserver(&observer);
2380 }
2381
TEST_P(SequenceManagerTest,NewTaskQueues)2382 TEST_P(SequenceManagerTest, NewTaskQueues) {
2383 auto queue = CreateTaskQueue();
2384
2385 TaskQueue::Handle queue1 = CreateTaskQueue();
2386 TaskQueue::Handle queue2 = CreateTaskQueue();
2387 TaskQueue::Handle queue3 = CreateTaskQueue();
2388
2389 ASSERT_NE(queue1.get(), queue2.get());
2390 ASSERT_NE(queue1.get(), queue3.get());
2391 ASSERT_NE(queue2.get(), queue3.get());
2392
2393 std::vector<EnqueueOrder> run_order;
2394 queue1->task_runner()->PostTask(FROM_HERE,
2395 BindOnce(&TestTask, 1, &run_order));
2396 queue2->task_runner()->PostTask(FROM_HERE,
2397 BindOnce(&TestTask, 2, &run_order));
2398 queue3->task_runner()->PostTask(FROM_HERE,
2399 BindOnce(&TestTask, 3, &run_order));
2400 RunLoop().RunUntilIdle();
2401
2402 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
2403 }
2404
TEST_P(SequenceManagerTest,ShutdownTaskQueue_TaskRunnersDetaching)2405 TEST_P(SequenceManagerTest, ShutdownTaskQueue_TaskRunnersDetaching) {
2406 TaskQueue::Handle queue = CreateTaskQueue();
2407
2408 scoped_refptr<SingleThreadTaskRunner> runner1 = queue->task_runner();
2409 scoped_refptr<SingleThreadTaskRunner> runner2 = queue->CreateTaskRunner(1);
2410
2411 std::vector<EnqueueOrder> run_order;
2412 EXPECT_TRUE(runner1->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order)));
2413 EXPECT_TRUE(runner2->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order)));
2414 queue.reset();
2415 EXPECT_FALSE(
2416 runner1->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order)));
2417 EXPECT_FALSE(
2418 runner2->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order)));
2419
2420 RunLoop().RunUntilIdle();
2421 EXPECT_THAT(run_order, ElementsAre());
2422 }
2423
TEST_P(SequenceManagerTest,ShutdownTaskQueue)2424 TEST_P(SequenceManagerTest, ShutdownTaskQueue) {
2425 auto queue = CreateTaskQueue();
2426
2427 TaskQueue::Handle queue1 = CreateTaskQueue();
2428 TaskQueue::Handle queue2 = CreateTaskQueue();
2429 TaskQueue::Handle queue3 = CreateTaskQueue();
2430
2431 ASSERT_NE(queue1.get(), queue2.get());
2432 ASSERT_NE(queue1.get(), queue3.get());
2433 ASSERT_NE(queue2.get(), queue3.get());
2434
2435 std::vector<EnqueueOrder> run_order;
2436 queue1->task_runner()->PostTask(FROM_HERE,
2437 BindOnce(&TestTask, 1, &run_order));
2438 queue2->task_runner()->PostTask(FROM_HERE,
2439 BindOnce(&TestTask, 2, &run_order));
2440 queue3->task_runner()->PostTask(FROM_HERE,
2441 BindOnce(&TestTask, 3, &run_order));
2442 queue2.reset();
2443 RunLoop().RunUntilIdle();
2444
2445 EXPECT_THAT(run_order, ElementsAre(1u, 3u));
2446 }
2447
TEST_P(SequenceManagerTest,ShutdownTaskQueue_WithDelayedTasks)2448 TEST_P(SequenceManagerTest, ShutdownTaskQueue_WithDelayedTasks) {
2449 auto queues = CreateTaskQueues(2u);
2450
2451 // Register three delayed tasks
2452 std::vector<EnqueueOrder> run_order;
2453 queues[0]->task_runner()->PostDelayedTask(
2454 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(10));
2455 queues[1]->task_runner()->PostDelayedTask(
2456 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(20));
2457 queues[0]->task_runner()->PostDelayedTask(
2458 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(30));
2459
2460 queues[1].reset();
2461 RunLoop().RunUntilIdle();
2462
2463 FastForwardBy(Milliseconds(40));
2464 ASSERT_THAT(run_order, ElementsAre(1u, 3u));
2465 }
2466
2467 namespace {
ShutdownQueue(TaskQueue::Handle queue)2468 void ShutdownQueue(TaskQueue::Handle queue) {}
2469 } // namespace
2470
TEST_P(SequenceManagerTest,ShutdownTaskQueue_InTasks)2471 TEST_P(SequenceManagerTest, ShutdownTaskQueue_InTasks) {
2472 auto queues = CreateTaskQueues(3u);
2473 auto runner1 = queues[1]->task_runner();
2474 auto runner2 = queues[2]->task_runner();
2475
2476 std::vector<EnqueueOrder> run_order;
2477 queues[0]->task_runner()->PostTask(FROM_HERE,
2478 BindOnce(&TestTask, 1, &run_order));
2479 queues[0]->task_runner()->PostTask(
2480 FROM_HERE, BindOnce(&ShutdownQueue, std::move(queues[1])));
2481 queues[0]->task_runner()->PostTask(
2482 FROM_HERE, BindOnce(&ShutdownQueue, std::move(queues[2])));
2483 runner1->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
2484 runner2->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
2485
2486 RunLoop().RunUntilIdle();
2487 ASSERT_THAT(run_order, ElementsAre(1u));
2488 }
2489
2490 namespace {
2491
2492 class MockObserver : public SequenceManager::Observer {
2493 public:
2494 MOCK_METHOD0(OnTriedToExecuteBlockedTask, void());
2495 MOCK_METHOD0(OnBeginNestedRunLoop, void());
2496 MOCK_METHOD0(OnExitNestedRunLoop, void());
2497 };
2498
2499 } // namespace
2500
TEST_P(SequenceManagerTest,ShutdownTaskQueueInNestedLoop)2501 TEST_P(SequenceManagerTest, ShutdownTaskQueueInNestedLoop) {
2502 auto queue = CreateTaskQueue();
2503
2504 // We retain a reference to the task queue even when the manager has deleted
2505 // its reference.
2506 TaskQueue::Handle queue_to_delete = CreateTaskQueue();
2507
2508 std::vector<bool> log;
2509 std::vector<std::pair<OnceClosure, bool>> tasks_to_post_from_nested_loop;
2510
2511 // Inside a nested run loop, delete `queue_to_delete`, bookended by Nop tasks.
2512 tasks_to_post_from_nested_loop.push_back(
2513 std::make_pair(BindOnce(&NopTask), true));
2514 tasks_to_post_from_nested_loop.push_back(std::make_pair(
2515 BindLambdaForTesting([&] { queue_to_delete.reset(); }), true));
2516 tasks_to_post_from_nested_loop.push_back(
2517 std::make_pair(BindOnce(&NopTask), true));
2518 queue->task_runner()->PostTask(
2519 FROM_HERE, BindOnce(&PostFromNestedRunloop, queue->task_runner(),
2520 Unretained(&tasks_to_post_from_nested_loop)));
2521 RunLoop().RunUntilIdle();
2522
2523 // Just make sure that we don't crash.
2524 }
2525
TEST_P(SequenceManagerTest,TimeDomainMigrationWithIncomingImmediateTasks)2526 TEST_P(SequenceManagerTest, TimeDomainMigrationWithIncomingImmediateTasks) {
2527 auto queue = CreateTaskQueue();
2528
2529 TimeTicks start_time_ticks = sequence_manager()->NowTicks();
2530 std::unique_ptr<MockTimeDomain> domain_a =
2531 std::make_unique<MockTimeDomain>(start_time_ticks);
2532 std::unique_ptr<MockTimeDomain> domain_b =
2533 std::make_unique<MockTimeDomain>(start_time_ticks);
2534
2535 sequence_manager()->SetTimeDomain(domain_a.get());
2536 std::vector<EnqueueOrder> run_order;
2537 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
2538 sequence_manager()->ResetTimeDomain();
2539 sequence_manager()->SetTimeDomain(domain_b.get());
2540
2541 RunLoop().RunUntilIdle();
2542 EXPECT_THAT(run_order, ElementsAre(1u));
2543
2544 sequence_manager()->ResetTimeDomain();
2545 }
2546
2547 // Test that no wake up is scheduled for a delayed task in the future when a
2548 // time domain is present.
TEST_P(SequenceManagerTest,TimeDomainDoesNotCauseWakeUp)2549 TEST_P(SequenceManagerTest, TimeDomainDoesNotCauseWakeUp) {
2550 auto queue = CreateTaskQueue();
2551
2552 std::unique_ptr<MockTimeDomain> domain =
2553 std::make_unique<MockTimeDomain>(sequence_manager()->NowTicks());
2554 sequence_manager()->SetTimeDomain(domain.get());
2555
2556 std::vector<EnqueueOrder> run_order;
2557 queue->task_runner()->PostDelayedTask(
2558 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(10));
2559 LazyNow lazy_now1(domain.get());
2560 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now1));
2561 EXPECT_EQ(TimeTicks::Max(), NextPendingTaskTime());
2562
2563 domain->SetNowTicks(sequence_manager()->NowTicks() + Milliseconds(10));
2564 LazyNow lazy_now2(domain.get());
2565 EXPECT_EQ(WakeUp{}, sequence_manager()->GetPendingWakeUp(&lazy_now2));
2566
2567 sequence_manager()->ResetTimeDomain();
2568 }
2569
TEST_P(SequenceManagerTest,PostDelayedTasksReverseOrderAlternatingTimeDomains)2570 TEST_P(SequenceManagerTest,
2571 PostDelayedTasksReverseOrderAlternatingTimeDomains) {
2572 auto queue = CreateTaskQueue();
2573
2574 std::vector<EnqueueOrder> run_order;
2575
2576 std::unique_ptr<sequence_manager::MockTimeDomain> domain =
2577 std::make_unique<sequence_manager::MockTimeDomain>(
2578 mock_tick_clock()->NowTicks());
2579
2580 sequence_manager()->SetTimeDomain(domain.get());
2581 queue->task_runner()->PostDelayedTask(
2582 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(400));
2583
2584 sequence_manager()->ResetTimeDomain();
2585 queue->task_runner()->PostDelayedTask(
2586 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(300));
2587
2588 sequence_manager()->SetTimeDomain(domain.get());
2589 queue->task_runner()->PostDelayedTask(
2590 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(200));
2591
2592 sequence_manager()->ResetTimeDomain();
2593 queue->task_runner()->PostDelayedTask(
2594 FROM_HERE, BindOnce(&TestTask, 4, &run_order), Milliseconds(100));
2595
2596 FastForwardBy(Milliseconds(400));
2597 EXPECT_THAT(run_order, ElementsAre(4u, 3u, 2u, 1u));
2598
2599 sequence_manager()->ResetTimeDomain();
2600 }
2601
2602 namespace {
2603
2604 class MockTaskQueueThrottler : public TaskQueue::Throttler {
2605 public:
2606 MockTaskQueueThrottler() = default;
2607 ~MockTaskQueueThrottler() = default;
2608
2609 MOCK_METHOD1(OnWakeUp, void(LazyNow*));
2610 MOCK_METHOD0(OnHasImmediateTask, void());
2611 MOCK_METHOD1(GetNextAllowedWakeUp_DesiredWakeUpTime, void(TimeTicks));
2612
GetNextAllowedWakeUp(LazyNow * lazy_now,std::optional<WakeUp> next_desired_wake_up,bool has_immediate_work)2613 std::optional<WakeUp> GetNextAllowedWakeUp(
2614 LazyNow* lazy_now,
2615 std::optional<WakeUp> next_desired_wake_up,
2616 bool has_immediate_work) override {
2617 if (next_desired_wake_up)
2618 GetNextAllowedWakeUp_DesiredWakeUpTime(next_desired_wake_up->time);
2619 if (next_allowed_wake_up_)
2620 return next_allowed_wake_up_;
2621 return next_desired_wake_up;
2622 }
2623
SetNextAllowedWakeUp(std::optional<WakeUp> next_allowed_wake_up)2624 void SetNextAllowedWakeUp(std::optional<WakeUp> next_allowed_wake_up) {
2625 next_allowed_wake_up_ = next_allowed_wake_up;
2626 }
2627
2628 private:
2629 std::optional<WakeUp> next_allowed_wake_up_;
2630 };
2631
2632 } // namespace
2633
TEST_P(SequenceManagerTest,TaskQueueThrottler_ImmediateTask)2634 TEST_P(SequenceManagerTest, TaskQueueThrottler_ImmediateTask) {
2635 StrictMock<MockTaskQueueThrottler> throttler;
2636 auto queue = CreateTaskQueue();
2637 queue->SetThrottler(&throttler);
2638
2639 // OnHasImmediateTask should be called when a task is posted on an empty
2640 // queue.
2641 EXPECT_CALL(throttler, OnHasImmediateTask());
2642 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2643 sequence_manager()->ReloadEmptyWorkQueues();
2644 Mock::VerifyAndClearExpectations(&throttler);
2645
2646 // But not subsequently.
2647 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2648 sequence_manager()->ReloadEmptyWorkQueues();
2649 Mock::VerifyAndClearExpectations(&throttler);
2650
2651 // Unless the immediate work queue is emptied.
2652 LazyNow lazy_now(mock_tick_clock());
2653 sequence_manager()->SelectNextTask(lazy_now);
2654 sequence_manager()->DidRunTask(lazy_now);
2655 sequence_manager()->SelectNextTask(lazy_now);
2656 sequence_manager()->DidRunTask(lazy_now);
2657 EXPECT_CALL(throttler, OnHasImmediateTask());
2658 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
2659 sequence_manager()->ReloadEmptyWorkQueues();
2660 Mock::VerifyAndClearExpectations(&throttler);
2661 }
2662
TEST_P(SequenceManagerTest,TaskQueueThrottler_DelayedTask)2663 TEST_P(SequenceManagerTest, TaskQueueThrottler_DelayedTask) {
2664 StrictMock<MockTaskQueueThrottler> throttler;
2665 auto queue = CreateTaskQueue();
2666 queue->SetThrottler(&throttler);
2667
2668 TimeTicks start_time = sequence_manager()->NowTicks();
2669 TimeDelta delay10s(Seconds(10));
2670 TimeDelta delay100s(Seconds(100));
2671 TimeDelta delay1s(Seconds(1));
2672
2673 // GetNextAllowedWakeUp should be called when a delayed task is posted on an
2674 // empty queue.
2675 EXPECT_CALL(throttler,
2676 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay10s));
2677 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2678 delay10s);
2679 Mock::VerifyAndClearExpectations(&throttler);
2680
2681 // GetNextAllowedWakeUp should be given the same delay when a longer delay
2682 // task is posted.
2683 EXPECT_CALL(throttler,
2684 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay10s));
2685 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2686 delay100s);
2687 Mock::VerifyAndClearExpectations(&throttler);
2688
2689 // GetNextAllowedWakeUp should be given the new delay when a task is posted
2690 // with a shorter delay.
2691 EXPECT_CALL(throttler,
2692 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1s));
2693 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay1s);
2694 Mock::VerifyAndClearExpectations(&throttler);
2695
2696 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
2697 queue->CreateQueueEnabledVoter();
2698 voter->SetVoteToEnable(false);
2699 Mock::VerifyAndClearExpectations(&throttler);
2700
2701 // When a queue has been enabled, we may get a notification if the
2702 // TimeDomain's next scheduled wake-up has changed.
2703 EXPECT_CALL(throttler,
2704 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1s));
2705 voter->SetVoteToEnable(true);
2706 Mock::VerifyAndClearExpectations(&throttler);
2707 }
2708
TEST_P(SequenceManagerTest,TaskQueueThrottler_OnWakeUp)2709 TEST_P(SequenceManagerTest, TaskQueueThrottler_OnWakeUp) {
2710 StrictMock<MockTaskQueueThrottler> throttler;
2711 auto queue = CreateTaskQueue();
2712 queue->SetThrottler(&throttler);
2713
2714 TimeTicks start_time = sequence_manager()->NowTicks();
2715 TimeDelta delay(Seconds(1));
2716
2717 EXPECT_CALL(throttler,
2718 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay));
2719 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay);
2720 Mock::VerifyAndClearExpectations(&throttler);
2721
2722 AdvanceMockTickClock(delay);
2723
2724 // OnWakeUp should be called when the queue has a scheduler wake up.
2725 EXPECT_CALL(throttler, OnWakeUp(_));
2726 // Move the task into the |delayed_work_queue|.
2727 LazyNow lazy_now(mock_tick_clock());
2728 sequence_manager()->MoveReadyDelayedTasksToWorkQueues(&lazy_now);
2729 Mock::VerifyAndClearExpectations(&throttler);
2730 }
2731
TEST_P(SequenceManagerTest,TaskQueueThrottler_ResetThrottler)2732 TEST_P(SequenceManagerTest, TaskQueueThrottler_ResetThrottler) {
2733 StrictMock<MockTaskQueueThrottler> throttler;
2734 auto queue = CreateTaskQueue();
2735 queue->SetThrottler(&throttler);
2736
2737 TimeTicks start_time = sequence_manager()->NowTicks();
2738 TimeDelta delay10s(Seconds(10));
2739 TimeDelta delay1s(Seconds(1));
2740
2741 EXPECT_FALSE(queue->GetNextDesiredWakeUp());
2742
2743 // GetNextAllowedWakeUp should be called when a delayed task is posted on an
2744 // empty queue.
2745 throttler.SetNextAllowedWakeUp(
2746 base::sequence_manager::WakeUp{start_time + delay10s});
2747 EXPECT_CALL(throttler,
2748 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1s));
2749 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay1s);
2750 Mock::VerifyAndClearExpectations(&throttler);
2751 // Expect throttled wake up.
2752 LazyNow lazy_now(mock_tick_clock());
2753 WakeUp expected_wake_up{start_time + delay10s};
2754 EXPECT_EQ(expected_wake_up, sequence_manager()->GetPendingWakeUp(&lazy_now));
2755
2756 queue->ResetThrottler();
2757 // Next wake up should be back to normal.
2758 EXPECT_EQ((WakeUp{start_time + delay1s, kLeeway}),
2759 sequence_manager()->GetPendingWakeUp(&lazy_now));
2760 }
2761
TEST_P(SequenceManagerTest,TaskQueueThrottler_DelayedTaskMultipleQueues)2762 TEST_P(SequenceManagerTest, TaskQueueThrottler_DelayedTaskMultipleQueues) {
2763 StrictMock<MockTaskQueueThrottler> throttler0;
2764 StrictMock<MockTaskQueueThrottler> throttler1;
2765 auto queues = CreateTaskQueues(2u);
2766 queues[0]->SetThrottler(&throttler0);
2767 queues[1]->SetThrottler(&throttler1);
2768
2769 TimeTicks start_time = sequence_manager()->NowTicks();
2770 TimeDelta delay1s(Seconds(1));
2771 TimeDelta delay10s(Seconds(10));
2772
2773 EXPECT_CALL(throttler0,
2774 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1s))
2775 .Times(1);
2776 EXPECT_CALL(throttler1,
2777 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay10s))
2778 .Times(1);
2779 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2780 delay1s);
2781 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
2782 delay10s);
2783 testing::Mock::VerifyAndClearExpectations(&throttler0);
2784 testing::Mock::VerifyAndClearExpectations(&throttler1);
2785
2786 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter0 =
2787 queues[0]->CreateQueueEnabledVoter();
2788 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter1 =
2789 queues[1]->CreateQueueEnabledVoter();
2790
2791 // Disabling a queue should not trigger a notification.
2792 voter0->SetVoteToEnable(false);
2793 Mock::VerifyAndClearExpectations(&throttler0);
2794
2795 // But re-enabling it should should trigger an GetNextAllowedWakeUp
2796 // notification.
2797 EXPECT_CALL(throttler0,
2798 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1s));
2799 voter0->SetVoteToEnable(true);
2800 Mock::VerifyAndClearExpectations(&throttler0);
2801
2802 // Disabling a queue should not trigger a notification.
2803 voter1->SetVoteToEnable(false);
2804 Mock::VerifyAndClearExpectations(&throttler0);
2805
2806 // But re-enabling it should should trigger a notification.
2807 EXPECT_CALL(throttler1,
2808 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay10s));
2809 voter1->SetVoteToEnable(true);
2810 Mock::VerifyAndClearExpectations(&throttler1);
2811 }
2812
TEST_P(SequenceManagerTest,TaskQueueThrottler_DelayedWorkWhichCanRunNow)2813 TEST_P(SequenceManagerTest, TaskQueueThrottler_DelayedWorkWhichCanRunNow) {
2814 // This test checks that when delayed work becomes available the notification
2815 // still fires. This usually happens when time advances and task becomes
2816 // available in the middle of the scheduling code. For this test we force
2817 // notification dispatching by calling UpdateWakeUp() explicitly.
2818
2819 StrictMock<MockTaskQueueThrottler> throttler;
2820 auto queue = CreateTaskQueue();
2821 queue->SetThrottler(&throttler);
2822
2823 TimeDelta delay1s(Seconds(1));
2824
2825 // GetNextAllowedWakeUp should be called when a delayed task is posted on an
2826 // empty queue.
2827 EXPECT_CALL(throttler, GetNextAllowedWakeUp_DesiredWakeUpTime(_));
2828 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay1s);
2829 Mock::VerifyAndClearExpectations(&throttler);
2830
2831 AdvanceMockTickClock(Seconds(10));
2832
2833 EXPECT_CALL(throttler, GetNextAllowedWakeUp_DesiredWakeUpTime(_));
2834 LazyNow lazy_now(mock_tick_clock());
2835 queue->UpdateWakeUp(&lazy_now);
2836 Mock::VerifyAndClearExpectations(&throttler);
2837 }
2838
2839 namespace {
2840
2841 class CancelableTask {
2842 public:
CancelableTask(const TickClock * clock)2843 explicit CancelableTask(const TickClock* clock) : clock_(clock) {}
2844
RecordTimeTask(std::vector<TimeTicks> * run_times)2845 void RecordTimeTask(std::vector<TimeTicks>* run_times) {
2846 run_times->push_back(clock_->NowTicks());
2847 }
2848
2849 template <typename... Args>
FailTask(Args...)2850 void FailTask(Args...) {
2851 FAIL();
2852 }
2853
2854 raw_ptr<const TickClock> clock_;
2855 WeakPtrFactory<CancelableTask> weak_factory_{this};
2856 };
2857
2858 class DestructionCallback {
2859 public:
DestructionCallback(OnceCallback<void ()> on_destroy)2860 explicit DestructionCallback(OnceCallback<void()> on_destroy)
2861 : on_destroy_(std::move(on_destroy)) {}
~DestructionCallback()2862 ~DestructionCallback() {
2863 if (on_destroy_)
2864 std::move(on_destroy_).Run();
2865 }
2866 DestructionCallback(const DestructionCallback&) = delete;
2867 DestructionCallback& operator=(const DestructionCallback&) = delete;
2868 DestructionCallback(DestructionCallback&&) = default;
2869
2870 private:
2871 OnceCallback<void()> on_destroy_;
2872 };
2873
2874 } // namespace
2875
TEST_P(SequenceManagerTest,TaskQueueThrottler_SweepCanceledDelayedTasks)2876 TEST_P(SequenceManagerTest, TaskQueueThrottler_SweepCanceledDelayedTasks) {
2877 StrictMock<MockTaskQueueThrottler> throttler;
2878 auto queue = CreateTaskQueue();
2879 queue->SetThrottler(&throttler);
2880
2881 TimeTicks start_time = sequence_manager()->NowTicks();
2882 TimeDelta delay1(Seconds(5));
2883 TimeDelta delay2(Seconds(10));
2884
2885 EXPECT_CALL(throttler,
2886 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay1))
2887 .Times(2);
2888
2889 CancelableTask task1(mock_tick_clock());
2890 CancelableTask task2(mock_tick_clock());
2891 std::vector<TimeTicks> run_times;
2892 queue->task_runner()->PostDelayedTask(
2893 FROM_HERE,
2894 BindOnce(&CancelableTask::RecordTimeTask,
2895 task1.weak_factory_.GetWeakPtr(), &run_times),
2896 delay1);
2897 queue->task_runner()->PostDelayedTask(
2898 FROM_HERE,
2899 BindOnce(&CancelableTask::RecordTimeTask,
2900 task2.weak_factory_.GetWeakPtr(), &run_times),
2901 delay2);
2902
2903 task1.weak_factory_.InvalidateWeakPtrs();
2904
2905 // Sweeping away canceled delayed tasks should trigger a notification.
2906 EXPECT_CALL(throttler,
2907 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay2))
2908 .Times(1);
2909 sequence_manager()->ReclaimMemory();
2910 }
2911
TEST_P(SequenceManagerTest,SweepLastTaskInQueue)2912 TEST_P(SequenceManagerTest, SweepLastTaskInQueue) {
2913 auto queue = CreateTaskQueue();
2914 CancelableTask task(mock_tick_clock());
2915 queue->task_runner()->PostDelayedTask(
2916 FROM_HERE,
2917 BindOnce(&CancelableTask::FailTask<>, task.weak_factory_.GetWeakPtr()),
2918 base::Seconds(1));
2919
2920 // Make sure sweeping away the last task in the queue doesn't end up accessing
2921 // invalid iterators.
2922 task.weak_factory_.InvalidateWeakPtrs();
2923 sequence_manager()->ReclaimMemory();
2924 }
2925
TEST_P(SequenceManagerTest,CancelledTaskPostAnother_ReclaimMemory)2926 TEST_P(SequenceManagerTest, CancelledTaskPostAnother_ReclaimMemory) {
2927 // This check ensures that a task whose destruction causes another task to be
2928 // posted as a side-effect doesn't cause us to access invalid iterators while
2929 // sweeping away cancelled tasks.
2930 auto queue = CreateTaskQueue();
2931 bool did_destroy = false;
2932 auto on_destroy = BindLambdaForTesting([&] {
2933 queue->task_runner()->PostDelayedTask(
2934 FROM_HERE, BindLambdaForTesting([] {}), base::Seconds(1));
2935 did_destroy = true;
2936 });
2937
2938 DestructionCallback destruction_observer(std::move(on_destroy));
2939 CancelableTask task(mock_tick_clock());
2940 queue->task_runner()->PostDelayedTask(
2941 FROM_HERE,
2942 BindOnce(&CancelableTask::FailTask<DestructionCallback>,
2943 task.weak_factory_.GetWeakPtr(),
2944 std::move(destruction_observer)),
2945 base::Seconds(1));
2946
2947 task.weak_factory_.InvalidateWeakPtrs();
2948 EXPECT_FALSE(did_destroy);
2949 sequence_manager()->ReclaimMemory();
2950 EXPECT_TRUE(did_destroy);
2951 }
2952
2953 // Regression test to ensure that posting a new task from the destructor of a
2954 // canceled task doesn't crash.
TEST_P(SequenceManagerTest,CancelledTaskPostAnother_MoveReadyDelayedTasksToWorkQueues)2955 TEST_P(SequenceManagerTest,
2956 CancelledTaskPostAnother_MoveReadyDelayedTasksToWorkQueues) {
2957 // This check ensures that a task whose destruction causes another task to be
2958 // posted as a side-effect doesn't cause us to access invalid iterators while
2959 // sweeping away cancelled tasks.
2960 auto queue = CreateTaskQueue();
2961 bool did_destroy = false;
2962 auto on_destroy = BindLambdaForTesting([&] {
2963 queue->task_runner()->PostDelayedTask(
2964 FROM_HERE, BindLambdaForTesting([] {}), base::Seconds(1));
2965 did_destroy = true;
2966 });
2967
2968 DestructionCallback destruction_observer(std::move(on_destroy));
2969 CancelableTask task(mock_tick_clock());
2970 queue->task_runner()->PostDelayedTask(
2971 FROM_HERE,
2972 BindOnce(&CancelableTask::FailTask<DestructionCallback>,
2973 task.weak_factory_.GetWeakPtr(),
2974 std::move(destruction_observer)),
2975 base::Seconds(1));
2976
2977 AdvanceMockTickClock(base::Seconds(1));
2978
2979 task.weak_factory_.InvalidateWeakPtrs();
2980 EXPECT_FALSE(did_destroy);
2981 LazyNow lazy_now(mock_tick_clock());
2982 sequence_manager()->MoveReadyDelayedTasksToWorkQueues(&lazy_now);
2983 EXPECT_TRUE(did_destroy);
2984 }
2985
TEST_P(SequenceManagerTest,CancelledTaskPostAnother_RemoveAllCanceledDelayedTasksFromFront)2986 TEST_P(SequenceManagerTest,
2987 CancelledTaskPostAnother_RemoveAllCanceledDelayedTasksFromFront) {
2988 // This check ensures that a task whose destruction causes another task to be
2989 // posted as a side-effect doesn't cause us to access invalid iterators while
2990 // removing canceled tasks from the front of the queues.
2991 auto queue = CreateTaskQueue();
2992 bool did_destroy = false;
2993 auto on_destroy = BindLambdaForTesting([&] {
2994 queue->task_runner()->PostDelayedTask(
2995 FROM_HERE, BindLambdaForTesting([] {}), base::Seconds(1));
2996 did_destroy = true;
2997 });
2998
2999 DestructionCallback destruction_observer(std::move(on_destroy));
3000 CancelableTask task(mock_tick_clock());
3001 queue->task_runner()->PostDelayedTask(
3002 FROM_HERE,
3003 BindOnce(&CancelableTask::FailTask<DestructionCallback>,
3004 task.weak_factory_.GetWeakPtr(),
3005 std::move(destruction_observer)),
3006 base::Seconds(1));
3007
3008 task.weak_factory_.InvalidateWeakPtrs();
3009 EXPECT_FALSE(did_destroy);
3010 LazyNow lazy_now(mock_tick_clock());
3011 // This removes canceled delayed tasks from the front of the queue.
3012 sequence_manager()->GetPendingWakeUp(&lazy_now);
3013 EXPECT_TRUE(did_destroy);
3014 }
3015
TEST_P(SequenceManagerTest,CancelledImmediateTaskShutsDownQueue)3016 TEST_P(SequenceManagerTest, CancelledImmediateTaskShutsDownQueue) {
3017 // This check ensures that an immediate task whose destruction causes the
3018 // owning task queue to be shut down doesn't cause us to access freed memory.
3019 auto queue = CreateTaskQueue();
3020 bool did_shutdown = false;
3021 auto on_destroy = BindLambdaForTesting([&] {
3022 queue.reset();
3023 did_shutdown = true;
3024 });
3025
3026 DestructionCallback destruction_observer(std::move(on_destroy));
3027 CancelableTask task(mock_tick_clock());
3028 queue->task_runner()->PostTask(
3029 FROM_HERE, BindOnce(&CancelableTask::FailTask<DestructionCallback>,
3030 task.weak_factory_.GetWeakPtr(),
3031 std::move(destruction_observer)));
3032
3033 task.weak_factory_.InvalidateWeakPtrs();
3034 EXPECT_FALSE(did_shutdown);
3035 RunLoop().RunUntilIdle();
3036 EXPECT_TRUE(did_shutdown);
3037 }
3038
TEST_P(SequenceManagerTest,CancelledDelayedTaskShutsDownQueue)3039 TEST_P(SequenceManagerTest, CancelledDelayedTaskShutsDownQueue) {
3040 // This check ensures that a delayed task whose destruction causes the owning
3041 // task queue to be shut down doesn't cause us to access freed memory.
3042 auto queue = CreateTaskQueue();
3043 bool did_shutdown = false;
3044 auto on_destroy = BindLambdaForTesting([&] {
3045 queue.reset();
3046 did_shutdown = true;
3047 });
3048
3049 DestructionCallback destruction_observer(std::move(on_destroy));
3050 CancelableTask task(mock_tick_clock());
3051 queue->task_runner()->PostDelayedTask(
3052 FROM_HERE,
3053 BindOnce(&CancelableTask::FailTask<DestructionCallback>,
3054 task.weak_factory_.GetWeakPtr(),
3055 std::move(destruction_observer)),
3056 base::Seconds(1));
3057
3058 task.weak_factory_.InvalidateWeakPtrs();
3059 EXPECT_FALSE(did_shutdown);
3060 sequence_manager()->ReclaimMemory();
3061 EXPECT_TRUE(did_shutdown);
3062 }
3063
3064 namespace {
3065
ChromiumRunloopInspectionTask(scoped_refptr<TestMockTimeTaskRunner> test_task_runner)3066 void ChromiumRunloopInspectionTask(
3067 scoped_refptr<TestMockTimeTaskRunner> test_task_runner) {
3068 // We don't expect more than 1 pending task at any time.
3069 EXPECT_GE(1u, test_task_runner->GetPendingTaskCount());
3070 }
3071
3072 } // namespace
3073
TEST(SequenceManagerTestWithMockTaskRunner,NumberOfPendingTasksOnChromiumRunLoop)3074 TEST(SequenceManagerTestWithMockTaskRunner,
3075 NumberOfPendingTasksOnChromiumRunLoop) {
3076 FixtureWithMockTaskRunner fixture;
3077 auto queue = fixture.sequence_manager()->CreateTaskQueue(
3078 TaskQueue::Spec(QueueName::TEST_TQ));
3079
3080 // NOTE because tasks posted to the chromiumrun loop are not cancellable, we
3081 // will end up with a lot more tasks posted if the delayed tasks were posted
3082 // in the reverse order.
3083 // TODO(alexclarke): Consider talking to the message pump directly.
3084 for (int i = 1; i < 100; i++) {
3085 queue->task_runner()->PostDelayedTask(
3086 FROM_HERE,
3087 BindOnce(&ChromiumRunloopInspectionTask, fixture.test_task_runner()),
3088 Milliseconds(i));
3089 }
3090 fixture.FastForwardUntilNoTasksRemain();
3091 }
3092
3093 namespace {
3094
3095 class QuadraticTask {
3096 public:
QuadraticTask(scoped_refptr<TaskRunner> task_runner,TimeDelta delay,Fixture * fixture)3097 QuadraticTask(scoped_refptr<TaskRunner> task_runner,
3098 TimeDelta delay,
3099 Fixture* fixture)
3100 : count_(0),
3101 task_runner_(task_runner),
3102 delay_(delay),
3103 fixture_(fixture) {}
3104
SetShouldExit(RepeatingCallback<bool ()> should_exit)3105 void SetShouldExit(RepeatingCallback<bool()> should_exit) {
3106 should_exit_ = should_exit;
3107 }
3108
Run()3109 void Run() {
3110 if (should_exit_.Run())
3111 return;
3112 count_++;
3113 task_runner_->PostDelayedTask(
3114 FROM_HERE, BindOnce(&QuadraticTask::Run, Unretained(this)), delay_);
3115 task_runner_->PostDelayedTask(
3116 FROM_HERE, BindOnce(&QuadraticTask::Run, Unretained(this)), delay_);
3117 fixture_->AdvanceMockTickClock(Milliseconds(5));
3118 }
3119
Count() const3120 int Count() const { return count_; }
3121
3122 private:
3123 int count_;
3124 scoped_refptr<TaskRunner> task_runner_;
3125 TimeDelta delay_;
3126 raw_ptr<Fixture> fixture_;
3127 RepeatingCallback<bool()> should_exit_;
3128 };
3129
3130 class LinearTask {
3131 public:
LinearTask(scoped_refptr<TaskRunner> task_runner,TimeDelta delay,Fixture * fixture)3132 LinearTask(scoped_refptr<TaskRunner> task_runner,
3133 TimeDelta delay,
3134 Fixture* fixture)
3135 : count_(0),
3136 task_runner_(task_runner),
3137 delay_(delay),
3138 fixture_(fixture) {}
3139
SetShouldExit(RepeatingCallback<bool ()> should_exit)3140 void SetShouldExit(RepeatingCallback<bool()> should_exit) {
3141 should_exit_ = should_exit;
3142 }
3143
Run()3144 void Run() {
3145 if (should_exit_.Run())
3146 return;
3147 count_++;
3148 task_runner_->PostDelayedTask(
3149 FROM_HERE, BindOnce(&LinearTask::Run, Unretained(this)), delay_);
3150 fixture_->AdvanceMockTickClock(Milliseconds(5));
3151 }
3152
Count() const3153 int Count() const { return count_; }
3154
3155 private:
3156 int count_;
3157 scoped_refptr<TaskRunner> task_runner_;
3158 TimeDelta delay_;
3159 raw_ptr<Fixture> fixture_;
3160 RepeatingCallback<bool()> should_exit_;
3161 };
3162
ShouldExit(QuadraticTask * quadratic_task,LinearTask * linear_task)3163 bool ShouldExit(QuadraticTask* quadratic_task, LinearTask* linear_task) {
3164 return quadratic_task->Count() == 1000 || linear_task->Count() == 1000;
3165 }
3166
3167 } // namespace
3168
TEST_P(SequenceManagerTest,DelayedTasksDontBadlyStarveNonDelayedWork_SameQueue)3169 TEST_P(SequenceManagerTest,
3170 DelayedTasksDontBadlyStarveNonDelayedWork_SameQueue) {
3171 auto queue = CreateTaskQueue();
3172
3173 QuadraticTask quadratic_delayed_task(queue->task_runner(), Milliseconds(10),
3174 this);
3175 LinearTask linear_immediate_task(queue->task_runner(), TimeDelta(), this);
3176 RepeatingCallback<bool()> should_exit = BindRepeating(
3177 ShouldExit, &quadratic_delayed_task, &linear_immediate_task);
3178 quadratic_delayed_task.SetShouldExit(should_exit);
3179 linear_immediate_task.SetShouldExit(should_exit);
3180
3181 quadratic_delayed_task.Run();
3182 linear_immediate_task.Run();
3183
3184 FastForwardUntilNoTasksRemain();
3185
3186 double ratio = static_cast<double>(linear_immediate_task.Count()) /
3187 static_cast<double>(quadratic_delayed_task.Count());
3188
3189 EXPECT_GT(ratio, 0.333);
3190 EXPECT_LT(ratio, 1.1);
3191 }
3192
TEST_P(SequenceManagerTest,ImmediateWorkCanStarveDelayedTasks_SameQueue)3193 TEST_P(SequenceManagerTest, ImmediateWorkCanStarveDelayedTasks_SameQueue) {
3194 auto queue = CreateTaskQueue();
3195
3196 QuadraticTask quadratic_immediate_task(queue->task_runner(), TimeDelta(),
3197 this);
3198 LinearTask linear_delayed_task(queue->task_runner(), Milliseconds(10), this);
3199 RepeatingCallback<bool()> should_exit = BindRepeating(
3200 &ShouldExit, &quadratic_immediate_task, &linear_delayed_task);
3201
3202 quadratic_immediate_task.SetShouldExit(should_exit);
3203 linear_delayed_task.SetShouldExit(should_exit);
3204
3205 quadratic_immediate_task.Run();
3206 linear_delayed_task.Run();
3207
3208 FastForwardUntilNoTasksRemain();
3209
3210 double ratio = static_cast<double>(linear_delayed_task.Count()) /
3211 static_cast<double>(quadratic_immediate_task.Count());
3212
3213 // This is by design, we want to enforce a strict ordering in task execution
3214 // where by delayed tasks can not skip ahead of non-delayed work.
3215 EXPECT_GT(ratio, 0.0);
3216 EXPECT_LT(ratio, 0.1);
3217 }
3218
TEST_P(SequenceManagerTest,DelayedTasksDontBadlyStarveNonDelayedWork_DifferentQueue)3219 TEST_P(SequenceManagerTest,
3220 DelayedTasksDontBadlyStarveNonDelayedWork_DifferentQueue) {
3221 auto queues = CreateTaskQueues(2u);
3222
3223 QuadraticTask quadratic_delayed_task(queues[0]->task_runner(),
3224 Milliseconds(10), this);
3225 LinearTask linear_immediate_task(queues[1]->task_runner(), TimeDelta(), this);
3226 RepeatingCallback<bool()> should_exit = BindRepeating(
3227 ShouldExit, &quadratic_delayed_task, &linear_immediate_task);
3228 quadratic_delayed_task.SetShouldExit(should_exit);
3229 linear_immediate_task.SetShouldExit(should_exit);
3230
3231 quadratic_delayed_task.Run();
3232 linear_immediate_task.Run();
3233
3234 FastForwardUntilNoTasksRemain();
3235
3236 double ratio = static_cast<double>(linear_immediate_task.Count()) /
3237 static_cast<double>(quadratic_delayed_task.Count());
3238
3239 EXPECT_GT(ratio, 0.333);
3240 EXPECT_LT(ratio, 1.1);
3241 }
3242
TEST_P(SequenceManagerTest,ImmediateWorkCanStarveDelayedTasks_DifferentQueue)3243 TEST_P(SequenceManagerTest, ImmediateWorkCanStarveDelayedTasks_DifferentQueue) {
3244 auto queues = CreateTaskQueues(2u);
3245
3246 QuadraticTask quadratic_immediate_task(queues[0]->task_runner(), TimeDelta(),
3247 this);
3248 LinearTask linear_delayed_task(queues[1]->task_runner(), Milliseconds(10),
3249 this);
3250 RepeatingCallback<bool()> should_exit = BindRepeating(
3251 &ShouldExit, &quadratic_immediate_task, &linear_delayed_task);
3252
3253 quadratic_immediate_task.SetShouldExit(should_exit);
3254 linear_delayed_task.SetShouldExit(should_exit);
3255
3256 quadratic_immediate_task.Run();
3257 linear_delayed_task.Run();
3258
3259 FastForwardUntilNoTasksRemain();
3260
3261 double ratio = static_cast<double>(linear_delayed_task.Count()) /
3262 static_cast<double>(quadratic_immediate_task.Count());
3263
3264 // This is by design, we want to enforce a strict ordering in task execution
3265 // where by delayed tasks can not skip ahead of non-delayed work.
3266 EXPECT_GT(ratio, 0.0);
3267 EXPECT_LT(ratio, 0.1);
3268 }
3269
TEST_P(SequenceManagerTest,CurrentlyExecutingTaskQueue_NoTaskRunning)3270 TEST_P(SequenceManagerTest, CurrentlyExecutingTaskQueue_NoTaskRunning) {
3271 auto queue = CreateTaskQueue();
3272
3273 EXPECT_EQ(nullptr, sequence_manager()->currently_executing_task_queue());
3274 }
3275
3276 namespace {
CurrentlyExecutingTaskQueueTestTask(SequenceManagerImpl * sequence_manager,std::vector<internal::TaskQueueImpl * > * task_sources)3277 void CurrentlyExecutingTaskQueueTestTask(
3278 SequenceManagerImpl* sequence_manager,
3279 std::vector<internal::TaskQueueImpl*>* task_sources) {
3280 task_sources->push_back(sequence_manager->currently_executing_task_queue());
3281 }
3282 } // namespace
3283
TEST_P(SequenceManagerTest,CurrentlyExecutingTaskQueue_TaskRunning)3284 TEST_P(SequenceManagerTest, CurrentlyExecutingTaskQueue_TaskRunning) {
3285 auto queues = CreateTaskQueues(2u);
3286
3287 TaskQueue* queue0 = queues[0].get();
3288 TaskQueue* queue1 = queues[1].get();
3289
3290 std::vector<internal::TaskQueueImpl*> task_sources;
3291 queue0->task_runner()->PostTask(FROM_HERE,
3292 BindOnce(&CurrentlyExecutingTaskQueueTestTask,
3293 sequence_manager(), &task_sources));
3294 queue1->task_runner()->PostTask(FROM_HERE,
3295 BindOnce(&CurrentlyExecutingTaskQueueTestTask,
3296 sequence_manager(), &task_sources));
3297 RunLoop().RunUntilIdle();
3298
3299 EXPECT_THAT(task_sources,
3300 ElementsAre(GetTaskQueueImpl(queue0), GetTaskQueueImpl(queue1)));
3301 EXPECT_EQ(nullptr, sequence_manager()->currently_executing_task_queue());
3302 }
3303
3304 namespace {
RunloopCurrentlyExecutingTaskQueueTestTask(SequenceManagerImpl * sequence_manager,std::vector<internal::TaskQueueImpl * > * task_sources,std::vector<std::pair<OnceClosure,TaskQueue * >> * tasks)3305 void RunloopCurrentlyExecutingTaskQueueTestTask(
3306 SequenceManagerImpl* sequence_manager,
3307 std::vector<internal::TaskQueueImpl*>* task_sources,
3308 std::vector<std::pair<OnceClosure, TaskQueue*>>* tasks) {
3309 task_sources->push_back(sequence_manager->currently_executing_task_queue());
3310
3311 for (std::pair<OnceClosure, TaskQueue*>& pair : *tasks) {
3312 pair.second->task_runner()->PostTask(FROM_HERE, std::move(pair.first));
3313 }
3314
3315 RunLoop(RunLoop::Type::kNestableTasksAllowed).RunUntilIdle();
3316 task_sources->push_back(sequence_manager->currently_executing_task_queue());
3317 }
3318 } // namespace
3319
TEST_P(SequenceManagerTest,CurrentlyExecutingTaskQueue_NestedLoop)3320 TEST_P(SequenceManagerTest, CurrentlyExecutingTaskQueue_NestedLoop) {
3321 auto queues = CreateTaskQueues(3u);
3322
3323 TaskQueue* queue0 = queues[0].get();
3324 TaskQueue* queue1 = queues[1].get();
3325 TaskQueue* queue2 = queues[2].get();
3326
3327 std::vector<internal::TaskQueueImpl*> task_sources;
3328 std::vector<std::pair<OnceClosure, TaskQueue*>>
3329 tasks_to_post_from_nested_loop;
3330 tasks_to_post_from_nested_loop.push_back(
3331 std::make_pair(BindOnce(&CurrentlyExecutingTaskQueueTestTask,
3332 sequence_manager(), &task_sources),
3333 queue1));
3334 tasks_to_post_from_nested_loop.push_back(
3335 std::make_pair(BindOnce(&CurrentlyExecutingTaskQueueTestTask,
3336 sequence_manager(), &task_sources),
3337 queue2));
3338
3339 queue0->task_runner()->PostTask(
3340 FROM_HERE,
3341 BindOnce(&RunloopCurrentlyExecutingTaskQueueTestTask, sequence_manager(),
3342 &task_sources, &tasks_to_post_from_nested_loop));
3343
3344 RunLoop().RunUntilIdle();
3345 EXPECT_THAT(
3346 task_sources,
3347 UnorderedElementsAre(GetTaskQueueImpl(queue0), GetTaskQueueImpl(queue1),
3348 GetTaskQueueImpl(queue2), GetTaskQueueImpl(queue0)));
3349 EXPECT_EQ(nullptr, sequence_manager()->currently_executing_task_queue());
3350 }
3351
TEST_P(SequenceManagerTest,NoWakeUpsForCanceledDelayedTasks)3352 TEST_P(SequenceManagerTest, NoWakeUpsForCanceledDelayedTasks) {
3353 auto queue = CreateTaskQueue();
3354
3355 TimeTicks start_time = sequence_manager()->NowTicks();
3356
3357 CancelableTask task1(mock_tick_clock());
3358 CancelableTask task2(mock_tick_clock());
3359 CancelableTask task3(mock_tick_clock());
3360 CancelableTask task4(mock_tick_clock());
3361 TimeDelta delay1(Seconds(5));
3362 TimeDelta delay2(Seconds(10));
3363 TimeDelta delay3(Seconds(15));
3364 TimeDelta delay4(Seconds(30));
3365 std::vector<TimeTicks> run_times;
3366 queue->task_runner()->PostDelayedTask(
3367 FROM_HERE,
3368 BindOnce(&CancelableTask::RecordTimeTask,
3369 task1.weak_factory_.GetWeakPtr(), &run_times),
3370 delay1);
3371 queue->task_runner()->PostDelayedTask(
3372 FROM_HERE,
3373 BindOnce(&CancelableTask::RecordTimeTask,
3374 task2.weak_factory_.GetWeakPtr(), &run_times),
3375 delay2);
3376 queue->task_runner()->PostDelayedTask(
3377 FROM_HERE,
3378 BindOnce(&CancelableTask::RecordTimeTask,
3379 task3.weak_factory_.GetWeakPtr(), &run_times),
3380 delay3);
3381 queue->task_runner()->PostDelayedTask(
3382 FROM_HERE,
3383 BindOnce(&CancelableTask::RecordTimeTask,
3384 task4.weak_factory_.GetWeakPtr(), &run_times),
3385 delay4);
3386
3387 task2.weak_factory_.InvalidateWeakPtrs();
3388 task3.weak_factory_.InvalidateWeakPtrs();
3389
3390 std::set<TimeTicks> wake_up_times;
3391
3392 RunUntilManagerIsIdle(BindRepeating(
3393 [](std::set<TimeTicks>* wake_up_times, const TickClock* clock) {
3394 wake_up_times->insert(clock->NowTicks());
3395 },
3396 &wake_up_times, mock_tick_clock()));
3397
3398 EXPECT_THAT(wake_up_times,
3399 ElementsAre(start_time + delay1, start_time + delay4));
3400 EXPECT_THAT(run_times, ElementsAre(start_time + delay1, start_time + delay4));
3401 }
3402
TEST_P(SequenceManagerTest,NoWakeUpsForCanceledDelayedTasksReversePostOrder)3403 TEST_P(SequenceManagerTest, NoWakeUpsForCanceledDelayedTasksReversePostOrder) {
3404 auto queue = CreateTaskQueue();
3405
3406 TimeTicks start_time = sequence_manager()->NowTicks();
3407
3408 CancelableTask task1(mock_tick_clock());
3409 CancelableTask task2(mock_tick_clock());
3410 CancelableTask task3(mock_tick_clock());
3411 CancelableTask task4(mock_tick_clock());
3412 TimeDelta delay1(Seconds(5));
3413 TimeDelta delay2(Seconds(10));
3414 TimeDelta delay3(Seconds(15));
3415 TimeDelta delay4(Seconds(30));
3416 std::vector<TimeTicks> run_times;
3417 queue->task_runner()->PostDelayedTask(
3418 FROM_HERE,
3419 BindOnce(&CancelableTask::RecordTimeTask,
3420 task4.weak_factory_.GetWeakPtr(), &run_times),
3421 delay4);
3422 queue->task_runner()->PostDelayedTask(
3423 FROM_HERE,
3424 BindOnce(&CancelableTask::RecordTimeTask,
3425 task3.weak_factory_.GetWeakPtr(), &run_times),
3426 delay3);
3427 queue->task_runner()->PostDelayedTask(
3428 FROM_HERE,
3429 BindOnce(&CancelableTask::RecordTimeTask,
3430 task2.weak_factory_.GetWeakPtr(), &run_times),
3431 delay2);
3432 queue->task_runner()->PostDelayedTask(
3433 FROM_HERE,
3434 BindOnce(&CancelableTask::RecordTimeTask,
3435 task1.weak_factory_.GetWeakPtr(), &run_times),
3436 delay1);
3437
3438 task2.weak_factory_.InvalidateWeakPtrs();
3439 task3.weak_factory_.InvalidateWeakPtrs();
3440
3441 std::set<TimeTicks> wake_up_times;
3442
3443 RunUntilManagerIsIdle(BindRepeating(
3444 [](std::set<TimeTicks>* wake_up_times, const TickClock* clock) {
3445 wake_up_times->insert(clock->NowTicks());
3446 },
3447 &wake_up_times, mock_tick_clock()));
3448
3449 EXPECT_THAT(wake_up_times,
3450 ElementsAre(start_time + delay1, start_time + delay4));
3451 EXPECT_THAT(run_times, ElementsAre(start_time + delay1, start_time + delay4));
3452 }
3453
TEST_P(SequenceManagerTest,TimeDomainWakeUpOnlyCancelledIfAllUsesCancelled)3454 TEST_P(SequenceManagerTest, TimeDomainWakeUpOnlyCancelledIfAllUsesCancelled) {
3455 auto queue = CreateTaskQueue();
3456
3457 TimeTicks start_time = sequence_manager()->NowTicks();
3458
3459 CancelableTask task1(mock_tick_clock());
3460 CancelableTask task2(mock_tick_clock());
3461 CancelableTask task3(mock_tick_clock());
3462 CancelableTask task4(mock_tick_clock());
3463 TimeDelta delay1(Seconds(5));
3464 TimeDelta delay2(Seconds(10));
3465 TimeDelta delay3(Seconds(15));
3466 TimeDelta delay4(Seconds(30));
3467 std::vector<TimeTicks> run_times;
3468 queue->task_runner()->PostDelayedTask(
3469 FROM_HERE,
3470 BindOnce(&CancelableTask::RecordTimeTask,
3471 task1.weak_factory_.GetWeakPtr(), &run_times),
3472 delay1);
3473 queue->task_runner()->PostDelayedTask(
3474 FROM_HERE,
3475 BindOnce(&CancelableTask::RecordTimeTask,
3476 task2.weak_factory_.GetWeakPtr(), &run_times),
3477 delay2);
3478 queue->task_runner()->PostDelayedTask(
3479 FROM_HERE,
3480 BindOnce(&CancelableTask::RecordTimeTask,
3481 task3.weak_factory_.GetWeakPtr(), &run_times),
3482 delay3);
3483 queue->task_runner()->PostDelayedTask(
3484 FROM_HERE,
3485 BindOnce(&CancelableTask::RecordTimeTask,
3486 task4.weak_factory_.GetWeakPtr(), &run_times),
3487 delay4);
3488
3489 // Post a non-canceled task with |delay3|. So we should still get a wake-up at
3490 // |delay3| even though we cancel |task3|.
3491 queue->task_runner()->PostDelayedTask(
3492 FROM_HERE,
3493 BindOnce(&CancelableTask::RecordTimeTask, Unretained(&task3), &run_times),
3494 delay3);
3495
3496 task2.weak_factory_.InvalidateWeakPtrs();
3497 task3.weak_factory_.InvalidateWeakPtrs();
3498 task1.weak_factory_.InvalidateWeakPtrs();
3499
3500 std::set<TimeTicks> wake_up_times;
3501
3502 RunUntilManagerIsIdle(BindRepeating(
3503 [](std::set<TimeTicks>* wake_up_times, const TickClock* clock) {
3504 wake_up_times->insert(clock->NowTicks());
3505 },
3506 &wake_up_times, mock_tick_clock()));
3507
3508 EXPECT_THAT(wake_up_times,
3509 ElementsAre(start_time + delay1, start_time + delay3,
3510 start_time + delay4));
3511
3512 EXPECT_THAT(run_times, ElementsAre(start_time + delay3, start_time + delay4));
3513 }
3514
TEST_P(SequenceManagerTest,SweepCanceledDelayedTasks)3515 TEST_P(SequenceManagerTest, SweepCanceledDelayedTasks) {
3516 auto queue = CreateTaskQueue();
3517
3518 CancelableTask task1(mock_tick_clock());
3519 CancelableTask task2(mock_tick_clock());
3520 CancelableTask task3(mock_tick_clock());
3521 CancelableTask task4(mock_tick_clock());
3522 TimeDelta delay1(Seconds(5));
3523 TimeDelta delay2(Seconds(10));
3524 TimeDelta delay3(Seconds(15));
3525 TimeDelta delay4(Seconds(30));
3526 std::vector<TimeTicks> run_times;
3527 queue->task_runner()->PostDelayedTask(
3528 FROM_HERE,
3529 BindOnce(&CancelableTask::RecordTimeTask,
3530 task1.weak_factory_.GetWeakPtr(), &run_times),
3531 delay1);
3532 queue->task_runner()->PostDelayedTask(
3533 FROM_HERE,
3534 BindOnce(&CancelableTask::RecordTimeTask,
3535 task2.weak_factory_.GetWeakPtr(), &run_times),
3536 delay2);
3537 queue->task_runner()->PostDelayedTask(
3538 FROM_HERE,
3539 BindOnce(&CancelableTask::RecordTimeTask,
3540 task3.weak_factory_.GetWeakPtr(), &run_times),
3541 delay3);
3542 queue->task_runner()->PostDelayedTask(
3543 FROM_HERE,
3544 BindOnce(&CancelableTask::RecordTimeTask,
3545 task4.weak_factory_.GetWeakPtr(), &run_times),
3546 delay4);
3547
3548 EXPECT_EQ(4u, queue->GetNumberOfPendingTasks());
3549 task2.weak_factory_.InvalidateWeakPtrs();
3550 task3.weak_factory_.InvalidateWeakPtrs();
3551 EXPECT_EQ(4u, queue->GetNumberOfPendingTasks());
3552
3553 sequence_manager()->ReclaimMemory();
3554 EXPECT_EQ(2u, queue->GetNumberOfPendingTasks());
3555
3556 task1.weak_factory_.InvalidateWeakPtrs();
3557 task4.weak_factory_.InvalidateWeakPtrs();
3558
3559 sequence_manager()->ReclaimMemory();
3560 EXPECT_EQ(0u, queue->GetNumberOfPendingTasks());
3561 }
3562
TEST_P(SequenceManagerTest,SweepCanceledDelayedTasks_ManyTasks)3563 TEST_P(SequenceManagerTest, SweepCanceledDelayedTasks_ManyTasks) {
3564 auto queue = CreateTaskQueue();
3565
3566 constexpr const int kNumTasks = 100;
3567
3568 std::vector<std::unique_ptr<CancelableTask>> tasks(100);
3569 std::vector<TimeTicks> run_times;
3570 for (int i = 0; i < kNumTasks; i++) {
3571 tasks[i] = std::make_unique<CancelableTask>(mock_tick_clock());
3572 queue->task_runner()->PostDelayedTask(
3573 FROM_HERE,
3574 BindOnce(&CancelableTask::RecordTimeTask,
3575 tasks[i]->weak_factory_.GetWeakPtr(), &run_times),
3576 Seconds(i + 1));
3577 }
3578
3579 // Invalidate ever other timer.
3580 for (int i = 0; i < kNumTasks; i++) {
3581 if (i % 2)
3582 tasks[i]->weak_factory_.InvalidateWeakPtrs();
3583 }
3584
3585 sequence_manager()->ReclaimMemory();
3586 EXPECT_EQ(50u, queue->GetNumberOfPendingTasks());
3587
3588 // Make sure the priority queue still operates as expected.
3589 FastForwardUntilNoTasksRemain();
3590 ASSERT_EQ(50u, run_times.size());
3591 for (int i = 0; i < 50; i++) {
3592 TimeTicks expected_run_time = FromStartAligned(Seconds(2 * i + 1));
3593 EXPECT_EQ(run_times[i], expected_run_time);
3594 }
3595 }
3596
TEST_P(SequenceManagerTest,DelayedTasksNotSelected)3597 TEST_P(SequenceManagerTest, DelayedTasksNotSelected) {
3598 auto queue = CreateTaskQueue();
3599 constexpr TimeDelta kDelay(Milliseconds(10));
3600 LazyNow lazy_now(mock_tick_clock());
3601 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3602 EXPECT_EQ(
3603 std::nullopt,
3604 sequence_manager()->GetPendingWakeUp(
3605 &lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3606
3607 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), kDelay);
3608
3609 // No task should be ready to execute.
3610 EXPECT_FALSE(sequence_manager()->SelectNextTask(
3611 lazy_now, SequencedTaskSource::SelectTaskOption::kDefault));
3612 EXPECT_FALSE(sequence_manager()->SelectNextTask(
3613 lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3614
3615 EXPECT_EQ((WakeUp{lazy_now.Now() + kDelay, kLeeway}),
3616 sequence_manager()->GetPendingWakeUp(&lazy_now));
3617 EXPECT_EQ(
3618 std::nullopt,
3619 sequence_manager()->GetPendingWakeUp(
3620 &lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3621
3622 AdvanceMockTickClock(kDelay);
3623 LazyNow lazy_now2(mock_tick_clock());
3624
3625 // Delayed task is ready to be executed. Consider it only if not in power
3626 // suspend state.
3627 EXPECT_FALSE(sequence_manager()->SelectNextTask(
3628 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3629 EXPECT_EQ(
3630 std::nullopt,
3631 sequence_manager()->GetPendingWakeUp(
3632 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3633
3634 // Execute the delayed task.
3635 EXPECT_TRUE(sequence_manager()->SelectNextTask(
3636 lazy_now2, SequencedTaskSource::SelectTaskOption::kDefault));
3637 sequence_manager()->DidRunTask(lazy_now2);
3638 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now2));
3639 }
3640
TEST_P(SequenceManagerTest,DelayedTasksNotSelectedWithImmediateTask)3641 TEST_P(SequenceManagerTest, DelayedTasksNotSelectedWithImmediateTask) {
3642 auto queue = CreateTaskQueue();
3643 constexpr TimeDelta kDelay(Milliseconds(10));
3644 LazyNow lazy_now(mock_tick_clock());
3645
3646 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3647 EXPECT_EQ(
3648 std::nullopt,
3649 sequence_manager()->GetPendingWakeUp(
3650 &lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3651
3652 // Post an immediate task.
3653 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3654 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), kDelay);
3655
3656 EXPECT_EQ(WakeUp{}, sequence_manager()->GetPendingWakeUp(&lazy_now));
3657 EXPECT_EQ(
3658 WakeUp{},
3659 sequence_manager()->GetPendingWakeUp(
3660 &lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3661
3662 AdvanceMockTickClock(kDelay);
3663 LazyNow lazy_now2(mock_tick_clock());
3664
3665 // An immediate task is present, even if we skip the delayed tasks.
3666 EXPECT_EQ(
3667 WakeUp{},
3668 sequence_manager()->GetPendingWakeUp(
3669 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3670
3671 // Immediate task should be ready to execute, execute it.
3672 EXPECT_TRUE(sequence_manager()->SelectNextTask(
3673 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3674 sequence_manager()->DidRunTask(lazy_now);
3675
3676 // Delayed task is ready to be executed. Consider it only if not in power
3677 // suspend state. This test differs from
3678 // SequenceManagerTest.DelayedTasksNotSelected as it confirms that delayed
3679 // tasks are ignored even if they're already in the ready queue (per having
3680 // performed task selection already before running the immediate task above).
3681 EXPECT_FALSE(sequence_manager()->SelectNextTask(
3682 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3683 EXPECT_EQ(
3684 std::nullopt,
3685 sequence_manager()->GetPendingWakeUp(
3686 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3687
3688 // Execute the delayed task.
3689 EXPECT_TRUE(sequence_manager()->SelectNextTask(
3690 lazy_now2, SequencedTaskSource::SelectTaskOption::kDefault));
3691 EXPECT_EQ(
3692 std::nullopt,
3693 sequence_manager()->GetPendingWakeUp(
3694 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3695 sequence_manager()->DidRunTask(lazy_now2);
3696 }
3697
TEST_P(SequenceManagerTest,DelayedTasksNotSelectedWithImmediateTaskWithPriority)3698 TEST_P(SequenceManagerTest,
3699 DelayedTasksNotSelectedWithImmediateTaskWithPriority) {
3700 auto queues = CreateTaskQueues(4u);
3701 queues[0]->SetQueuePriority(TestQueuePriority::kLowPriority);
3702 queues[1]->SetQueuePriority(TestQueuePriority::kNormalPriority);
3703 queues[2]->SetQueuePriority(TestQueuePriority::kHighPriority);
3704 queues[3]->SetQueuePriority(TestQueuePriority::kVeryHighPriority);
3705
3706 // Post immediate tasks.
3707 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3708 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3709
3710 // Post delayed tasks.
3711 constexpr TimeDelta kDelay(Milliseconds(10));
3712 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3713 kDelay);
3714 queues[3]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3715 kDelay);
3716
3717 LazyNow lazy_now(mock_tick_clock());
3718
3719 EXPECT_EQ(
3720 WakeUp{},
3721 sequence_manager()->GetPendingWakeUp(
3722 &lazy_now, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3723
3724 AdvanceMockTickClock(kDelay);
3725 LazyNow lazy_now2(mock_tick_clock());
3726
3727 EXPECT_EQ(
3728 WakeUp{},
3729 sequence_manager()->GetPendingWakeUp(
3730 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3731
3732 // Immediate tasks should be ready to execute, execute them.
3733 EXPECT_TRUE(sequence_manager()->SelectNextTask(
3734 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3735 sequence_manager()->DidRunTask(lazy_now2);
3736 EXPECT_TRUE(sequence_manager()->SelectNextTask(
3737 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3738 sequence_manager()->DidRunTask(lazy_now2);
3739
3740 // No immediate tasks can be executed anymore.
3741 EXPECT_FALSE(sequence_manager()->SelectNextTask(
3742 lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3743 EXPECT_EQ(
3744 std::nullopt,
3745 sequence_manager()->GetPendingWakeUp(
3746 &lazy_now2, SequencedTaskSource::SelectTaskOption::kSkipDelayedTask));
3747
3748 // Execute delayed tasks.
3749 EXPECT_TRUE(sequence_manager()->SelectNextTask(lazy_now2));
3750 sequence_manager()->DidRunTask(lazy_now2);
3751 EXPECT_TRUE(sequence_manager()->SelectNextTask(lazy_now2));
3752 sequence_manager()->DidRunTask(lazy_now2);
3753
3754 // No delayed tasks can be executed anymore.
3755 EXPECT_FALSE(sequence_manager()->SelectNextTask(lazy_now2));
3756 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now2));
3757 }
3758
TEST_P(SequenceManagerTest,GetPendingWakeUp)3759 TEST_P(SequenceManagerTest, GetPendingWakeUp) {
3760 auto queues = CreateTaskQueues(2u);
3761
3762 LazyNow lazy_now(mock_tick_clock());
3763 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3764
3765 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3766 Seconds(10));
3767
3768 EXPECT_EQ((WakeUp{lazy_now.Now() + Seconds(10), kLeeway}),
3769 sequence_manager()->GetPendingWakeUp(&lazy_now));
3770
3771 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3772 Seconds(15));
3773
3774 EXPECT_EQ((WakeUp{lazy_now.Now() + Seconds(10), kLeeway}),
3775 sequence_manager()->GetPendingWakeUp(&lazy_now));
3776
3777 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3778 Seconds(5));
3779
3780 EXPECT_EQ((WakeUp{lazy_now.Now() + Seconds(5), kLeeway}),
3781 sequence_manager()->GetPendingWakeUp(&lazy_now));
3782
3783 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3784
3785 EXPECT_EQ(WakeUp{}, sequence_manager()->GetPendingWakeUp(&lazy_now));
3786 }
3787
TEST_P(SequenceManagerTest,GetPendingWakeUp_Disabled)3788 TEST_P(SequenceManagerTest, GetPendingWakeUp_Disabled) {
3789 auto queue = CreateTaskQueue();
3790
3791 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
3792 queue->CreateQueueEnabledVoter();
3793 voter->SetVoteToEnable(false);
3794 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3795
3796 LazyNow lazy_now(mock_tick_clock());
3797 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3798 }
3799
TEST_P(SequenceManagerTest,GetPendingWakeUp_Fence)3800 TEST_P(SequenceManagerTest, GetPendingWakeUp_Fence) {
3801 auto queue = CreateTaskQueue();
3802
3803 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3804 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3805
3806 LazyNow lazy_now(mock_tick_clock());
3807 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3808 }
3809
TEST_P(SequenceManagerTest,GetPendingWakeUp_FenceUnblocking)3810 TEST_P(SequenceManagerTest, GetPendingWakeUp_FenceUnblocking) {
3811 auto queue = CreateTaskQueue();
3812
3813 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3814 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3815 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3816
3817 LazyNow lazy_now(mock_tick_clock());
3818 EXPECT_EQ(WakeUp{}, sequence_manager()->GetPendingWakeUp(&lazy_now));
3819 }
3820
TEST_P(SequenceManagerTest,GetPendingWakeUp_DelayedTaskReady)3821 TEST_P(SequenceManagerTest, GetPendingWakeUp_DelayedTaskReady) {
3822 auto queue = CreateTaskQueue();
3823
3824 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3825 Seconds(1));
3826
3827 AdvanceMockTickClock(Seconds(10));
3828
3829 LazyNow lazy_now(mock_tick_clock());
3830 EXPECT_EQ(WakeUp{}, sequence_manager()->GetPendingWakeUp(&lazy_now));
3831 }
3832
TEST_P(SequenceManagerTest,RemoveAllCanceledDelayedTasksFromFront)3833 TEST_P(SequenceManagerTest, RemoveAllCanceledDelayedTasksFromFront) {
3834 auto queue = CreateTaskQueue();
3835
3836 // Posts a cancelable task.
3837 CancelableOnceClosure cancelable_closure(base::BindOnce(&NopTask));
3838 constexpr TimeDelta kDelay = Seconds(1);
3839 queue->task_runner()->PostDelayedTask(FROM_HERE,
3840 cancelable_closure.callback(), kDelay);
3841
3842 // Ensure it is picked to calculate the next task time.
3843 LazyNow lazy_now(mock_tick_clock());
3844 EXPECT_EQ((WakeUp{lazy_now.Now() + kDelay, kLeeway}),
3845 sequence_manager()->GetPendingWakeUp(&lazy_now));
3846
3847 // Canceling the task is not sufficient to ensure it is not considered for the
3848 // next task time.
3849 cancelable_closure.Cancel();
3850 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3851 }
3852
TEST_P(SequenceManagerTest,RemoveAllCanceledDelayedTasksFromFront_MultipleQueues)3853 TEST_P(SequenceManagerTest,
3854 RemoveAllCanceledDelayedTasksFromFront_MultipleQueues) {
3855 auto queues = CreateTaskQueues(2u);
3856
3857 // Post a task in each queue such that they would be executed in order
3858 // according to their delay.
3859 CancelableOnceClosure cancelable_closure_1(base::BindOnce(&NopTask));
3860 constexpr TimeDelta kDelay1 = Seconds(1);
3861 queues[0]->task_runner()->PostDelayedTask(
3862 FROM_HERE, cancelable_closure_1.callback(), kDelay1);
3863
3864 CancelableOnceClosure cancelable_closure_2(base::BindOnce(&NopTask));
3865 constexpr TimeDelta kDelay2 = Seconds(2);
3866 queues[1]->task_runner()->PostDelayedTask(
3867 FROM_HERE, cancelable_closure_2.callback(), kDelay2);
3868
3869 // The task from the first queue is picked to calculate the next task time.
3870 LazyNow lazy_now(mock_tick_clock());
3871 EXPECT_EQ((WakeUp{lazy_now.Now() + kDelay1, kLeeway}),
3872 sequence_manager()->GetPendingWakeUp(&lazy_now));
3873
3874 // Test that calling `GetPendingWakeUp()` works when no task is canceled.
3875 EXPECT_EQ((WakeUp{lazy_now.Now() + kDelay1, kLeeway}),
3876 sequence_manager()->GetPendingWakeUp(&lazy_now));
3877
3878 // Canceling the first task which comes from the first queue.
3879 cancelable_closure_1.Cancel();
3880
3881 // Now the only task remaining is the one from the second queue.
3882 EXPECT_EQ((WakeUp{lazy_now.Now() + kDelay2, kLeeway}),
3883 sequence_manager()->GetPendingWakeUp(&lazy_now));
3884
3885 // Cancel the remaining task.
3886 cancelable_closure_2.Cancel();
3887
3888 // No more valid tasks in any queues.
3889 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3890
3891 // Test that calling `GetPendingWakeUp()` works when no task is canceled.
3892 EXPECT_EQ(std::nullopt, sequence_manager()->GetPendingWakeUp(&lazy_now));
3893 }
3894
3895 namespace {
MessageLoopTaskWithDelayedQuit(Fixture * fixture,TaskQueue * task_queue)3896 void MessageLoopTaskWithDelayedQuit(Fixture* fixture, TaskQueue* task_queue) {
3897 RunLoop run_loop(RunLoop::Type::kNestableTasksAllowed);
3898 task_queue->task_runner()->PostDelayedTask(FROM_HERE, run_loop.QuitClosure(),
3899 Milliseconds(100));
3900 fixture->AdvanceMockTickClock(Milliseconds(200));
3901 run_loop.Run();
3902 }
3903 } // namespace
3904
TEST_P(SequenceManagerTest,DelayedTaskRunsInNestedMessageLoop)3905 TEST_P(SequenceManagerTest, DelayedTaskRunsInNestedMessageLoop) {
3906 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
3907 return;
3908 auto queue = CreateTaskQueue();
3909 RunLoop run_loop;
3910 queue->task_runner()->PostTask(
3911 FROM_HERE,
3912 BindOnce(&MessageLoopTaskWithDelayedQuit, this, Unretained(queue.get())));
3913 run_loop.RunUntilIdle();
3914 }
3915
3916 namespace {
MessageLoopTaskWithImmediateQuit(OnceClosure non_nested_quit_closure,TaskQueue * task_queue)3917 void MessageLoopTaskWithImmediateQuit(OnceClosure non_nested_quit_closure,
3918 TaskQueue* task_queue) {
3919 RunLoop run_loop(RunLoop::Type::kNestableTasksAllowed);
3920 // Needed because entering the nested run loop causes a DoWork to get
3921 // posted.
3922 task_queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
3923 task_queue->task_runner()->PostTask(FROM_HERE, run_loop.QuitClosure());
3924 run_loop.Run();
3925 std::move(non_nested_quit_closure).Run();
3926 }
3927 } // namespace
3928
TEST_P(SequenceManagerTest,DelayedNestedMessageLoopDoesntPreventTasksRunning)3929 TEST_P(SequenceManagerTest, DelayedNestedMessageLoopDoesntPreventTasksRunning) {
3930 if (GetUnderlyingRunnerType() == RunnerType::kMockTaskRunner)
3931 return;
3932 auto queue = CreateTaskQueue();
3933 RunLoop run_loop;
3934 queue->task_runner()->PostDelayedTask(
3935 FROM_HERE,
3936 BindOnce(&MessageLoopTaskWithImmediateQuit, run_loop.QuitClosure(),
3937 Unretained(queue.get())),
3938 Milliseconds(100));
3939
3940 AdvanceMockTickClock(Milliseconds(200));
3941 run_loop.Run();
3942 }
3943
TEST_P(SequenceManagerTest,CouldTaskRun_DisableAndReenable)3944 TEST_P(SequenceManagerTest, CouldTaskRun_DisableAndReenable) {
3945 auto queue = CreateTaskQueue();
3946
3947 EnqueueOrder enqueue_order = sequence_manager()->GetNextSequenceNumber();
3948 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3949
3950 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
3951 queue->CreateQueueEnabledVoter();
3952 voter->SetVoteToEnable(false);
3953 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3954
3955 voter->SetVoteToEnable(true);
3956 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3957 }
3958
TEST_P(SequenceManagerTest,CouldTaskRun_Fence)3959 TEST_P(SequenceManagerTest, CouldTaskRun_Fence) {
3960 auto queue = CreateTaskQueue();
3961
3962 EnqueueOrder enqueue_order = sequence_manager()->GetNextSequenceNumber();
3963 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3964
3965 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3966 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3967
3968 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
3969 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3970
3971 queue->RemoveFence();
3972 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3973 }
3974
TEST_P(SequenceManagerTest,CouldTaskRun_FenceBeforeThenAfter)3975 TEST_P(SequenceManagerTest, CouldTaskRun_FenceBeforeThenAfter) {
3976 auto queue = CreateTaskQueue();
3977
3978 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3979
3980 EnqueueOrder enqueue_order = sequence_manager()->GetNextSequenceNumber();
3981 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3982
3983 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
3984 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->CouldTaskRun(enqueue_order));
3985 }
3986
TEST_P(SequenceManagerTest,DelayedDoWorkNotPostedForDisabledQueue)3987 TEST_P(SequenceManagerTest, DelayedDoWorkNotPostedForDisabledQueue) {
3988 auto queue = CreateTaskQueue();
3989
3990 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
3991 Milliseconds(1));
3992 EXPECT_EQ(FromStartAligned(Milliseconds(1)), NextPendingTaskTime());
3993
3994 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
3995 queue->CreateQueueEnabledVoter();
3996 voter->SetVoteToEnable(false);
3997
3998 EXPECT_EQ(TimeTicks::Max(), NextPendingTaskTime());
3999
4000 voter->SetVoteToEnable(true);
4001 EXPECT_EQ(FromStartAligned(Milliseconds(1)), NextPendingTaskTime());
4002 }
4003
TEST_P(SequenceManagerTest,DisablingQueuesChangesDelayTillNextDoWork)4004 TEST_P(SequenceManagerTest, DisablingQueuesChangesDelayTillNextDoWork) {
4005 auto queues = CreateTaskQueues(3u);
4006 queues[0]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4007 Milliseconds(1));
4008 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4009 Milliseconds(10));
4010 queues[2]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4011 Milliseconds(100));
4012
4013 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter0 =
4014 queues[0]->CreateQueueEnabledVoter();
4015 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter1 =
4016 queues[1]->CreateQueueEnabledVoter();
4017 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter2 =
4018 queues[2]->CreateQueueEnabledVoter();
4019
4020 EXPECT_EQ(FromStartAligned(Milliseconds(1)), NextPendingTaskTime());
4021
4022 voter0->SetVoteToEnable(false);
4023 EXPECT_EQ(FromStartAligned(Milliseconds(10)), NextPendingTaskTime());
4024
4025 voter1->SetVoteToEnable(false);
4026 EXPECT_EQ(FromStartAligned(Milliseconds(100)), NextPendingTaskTime());
4027
4028 voter2->SetVoteToEnable(false);
4029 EXPECT_EQ(TimeTicks::Max(), NextPendingTaskTime());
4030 }
4031
TEST_P(SequenceManagerTest,GetNextDesiredWakeUp)4032 TEST_P(SequenceManagerTest, GetNextDesiredWakeUp) {
4033 auto queue = CreateTaskQueue();
4034
4035 EXPECT_EQ(std::nullopt, queue->GetNextDesiredWakeUp());
4036
4037 TimeTicks start_time = sequence_manager()->NowTicks();
4038 TimeDelta delay1 = Milliseconds(10);
4039 TimeDelta delay2 = Milliseconds(2);
4040
4041 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay1);
4042 EXPECT_EQ(start_time + delay1, queue->GetNextDesiredWakeUp()->time);
4043
4044 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay2);
4045 EXPECT_EQ(start_time + delay2, queue->GetNextDesiredWakeUp()->time);
4046
4047 // We don't have wake-ups scheduled for disabled queues.
4048 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
4049 queue->CreateQueueEnabledVoter();
4050 voter->SetVoteToEnable(false);
4051 EXPECT_EQ(std::nullopt, queue->GetNextDesiredWakeUp());
4052
4053 voter->SetVoteToEnable(true);
4054 EXPECT_EQ(start_time + delay2, queue->GetNextDesiredWakeUp()->time);
4055
4056 // Immediate tasks shouldn't make any difference.
4057 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4058 EXPECT_EQ(start_time + delay2, queue->GetNextDesiredWakeUp()->time);
4059
4060 // Neither should fences.
4061 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
4062 EXPECT_EQ(start_time + delay2, queue->GetNextDesiredWakeUp()->time);
4063 }
4064
TEST_P(SequenceManagerTest,SetTimeDomainForDisabledQueue)4065 TEST_P(SequenceManagerTest, SetTimeDomainForDisabledQueue) {
4066 StrictMock<MockTaskQueueThrottler> throttler;
4067 auto queue = CreateTaskQueue();
4068 queue->SetThrottler(&throttler);
4069
4070 TimeTicks start_time = sequence_manager()->NowTicks();
4071 TimeDelta delay(Milliseconds(1));
4072
4073 EXPECT_CALL(throttler,
4074 GetNextAllowedWakeUp_DesiredWakeUpTime(start_time + delay));
4075 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask), delay);
4076 Mock::VerifyAndClearExpectations(&throttler);
4077
4078 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
4079 queue->CreateQueueEnabledVoter();
4080 voter->SetVoteToEnable(false);
4081
4082 // We should not get a notification for a disabled queue.
4083 std::unique_ptr<MockTimeDomain> domain =
4084 std::make_unique<MockTimeDomain>(sequence_manager()->NowTicks());
4085 sequence_manager()->SetTimeDomain(domain.get());
4086
4087 // Tidy up.
4088 queue.reset();
4089 sequence_manager()->ResetTimeDomain();
4090 }
4091
4092 namespace {
SetOnTaskHandlers(TaskQueue * task_queue,int * start_counter,int * complete_counter)4093 void SetOnTaskHandlers(TaskQueue* task_queue,
4094 int* start_counter,
4095 int* complete_counter) {
4096 GetTaskQueueImpl(task_queue)
4097 ->SetOnTaskStartedHandler(BindRepeating(
4098 [](int* counter, const Task& task,
4099 const TaskQueue::TaskTiming& task_timing) { ++(*counter); },
4100 start_counter));
4101 GetTaskQueueImpl(task_queue)
4102 ->SetOnTaskCompletedHandler(BindRepeating(
4103 [](int* counter, const Task& task, TaskQueue::TaskTiming* task_timing,
4104 LazyNow* lazy_now) { ++(*counter); },
4105 complete_counter));
4106 }
4107
UnsetOnTaskHandlers(TaskQueue * task_queue)4108 void UnsetOnTaskHandlers(TaskQueue* task_queue) {
4109 GetTaskQueueImpl(task_queue)
4110 ->SetOnTaskStartedHandler(
4111 internal::TaskQueueImpl::OnTaskStartedHandler());
4112 GetTaskQueueImpl(task_queue)
4113 ->SetOnTaskCompletedHandler(
4114 internal::TaskQueueImpl::OnTaskCompletedHandler());
4115 }
4116 } // namespace
4117
TEST_P(SequenceManagerTest,ProcessTasksWithoutTaskTimeObservers)4118 TEST_P(SequenceManagerTest, ProcessTasksWithoutTaskTimeObservers) {
4119 auto queue = CreateTaskQueue();
4120 int start_counter = 0;
4121 int complete_counter = 0;
4122 std::vector<EnqueueOrder> run_order;
4123 SetOnTaskHandlers(queue.get(), &start_counter, &complete_counter);
4124 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4125 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
4126 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
4127 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
4128
4129 RunLoop().RunUntilIdle();
4130 EXPECT_EQ(start_counter, 3);
4131 EXPECT_EQ(complete_counter, 3);
4132 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u));
4133
4134 UnsetOnTaskHandlers(queue.get());
4135 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4136 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order));
4137 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 5, &run_order));
4138 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 6, &run_order));
4139
4140 RunLoop().RunUntilIdle();
4141 EXPECT_EQ(start_counter, 3);
4142 EXPECT_EQ(complete_counter, 3);
4143 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u, 6u));
4144 }
4145
TEST_P(SequenceManagerTest,ProcessTasksWithTaskTimeObservers)4146 TEST_P(SequenceManagerTest, ProcessTasksWithTaskTimeObservers) {
4147 TestTaskTimeObserver test_task_time_observer;
4148 auto queue = CreateTaskQueue();
4149 int start_counter = 0;
4150 int complete_counter = 0;
4151
4152 sequence_manager()->AddTaskTimeObserver(&test_task_time_observer);
4153 SetOnTaskHandlers(queue.get(), &start_counter, &complete_counter);
4154 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4155 std::vector<EnqueueOrder> run_order;
4156 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 1, &run_order));
4157 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 2, &run_order));
4158
4159 RunLoop().RunUntilIdle();
4160 EXPECT_EQ(start_counter, 2);
4161 EXPECT_EQ(complete_counter, 2);
4162 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
4163
4164 UnsetOnTaskHandlers(queue.get());
4165 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4166 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 3, &run_order));
4167 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 4, &run_order));
4168
4169 RunLoop().RunUntilIdle();
4170 EXPECT_EQ(start_counter, 2);
4171 EXPECT_EQ(complete_counter, 2);
4172 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u));
4173
4174 sequence_manager()->RemoveTaskTimeObserver(&test_task_time_observer);
4175 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 5, &run_order));
4176 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 6, &run_order));
4177
4178 RunLoop().RunUntilIdle();
4179 EXPECT_EQ(start_counter, 2);
4180 EXPECT_EQ(complete_counter, 2);
4181 EXPECT_FALSE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4182 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u, 6u));
4183
4184 SetOnTaskHandlers(queue.get(), &start_counter, &complete_counter);
4185 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 7, &run_order));
4186 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&TestTask, 8, &run_order));
4187
4188 RunLoop().RunUntilIdle();
4189 EXPECT_EQ(start_counter, 4);
4190 EXPECT_EQ(complete_counter, 4);
4191 EXPECT_TRUE(GetTaskQueueImpl(queue.get())->RequiresTaskTiming());
4192 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u, 5u, 6u, 7u, 8u));
4193 UnsetOnTaskHandlers(queue.get());
4194 }
4195
TEST_P(SequenceManagerTest,ObserverNotFiredAfterTaskQueueDestructed)4196 TEST_P(SequenceManagerTest, ObserverNotFiredAfterTaskQueueDestructed) {
4197 StrictMock<MockTaskQueueThrottler> throttler;
4198 auto queue = CreateTaskQueue();
4199 queue->SetThrottler(&throttler);
4200
4201 // We don't expect the throttler to be notified if the TaskQueue gets
4202 // destructed.
4203 auto task_runner = queue->task_runner();
4204 queue.reset();
4205 task_runner->PostTask(FROM_HERE, BindOnce(&NopTask));
4206
4207 FastForwardUntilNoTasksRemain();
4208 }
4209
TEST_P(SequenceManagerTest,OnQueueNextWakeUpChangedNotFiredForDisabledQueuePostTask)4210 TEST_P(SequenceManagerTest,
4211 OnQueueNextWakeUpChangedNotFiredForDisabledQueuePostTask) {
4212 StrictMock<MockTaskQueueThrottler> throttler;
4213 auto queue = CreateTaskQueue();
4214 queue->SetThrottler(&throttler);
4215
4216 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
4217 queue->CreateQueueEnabledVoter();
4218 voter->SetVoteToEnable(false);
4219
4220 // We don't expect the OnHasImmediateTask to be called if the TaskQueue gets
4221 // disabled.
4222 auto task_runner = queue->task_runner();
4223 task_runner->PostTask(FROM_HERE, BindOnce(&NopTask));
4224
4225 FastForwardUntilNoTasksRemain();
4226 // When |voter| goes out of scope the queue will become enabled and the
4227 // observer will fire. We're not interested in testing that however.
4228 Mock::VerifyAndClearExpectations(&throttler);
4229 }
4230
TEST_P(SequenceManagerTest,OnQueueNextWakeUpChangedNotFiredForCrossThreadDisabledQueuePostTask)4231 TEST_P(SequenceManagerTest,
4232 OnQueueNextWakeUpChangedNotFiredForCrossThreadDisabledQueuePostTask) {
4233 StrictMock<MockTaskQueueThrottler> throttler;
4234 auto queue = CreateTaskQueue();
4235 queue->SetThrottler(&throttler);
4236
4237 std::unique_ptr<TaskQueue::QueueEnabledVoter> voter =
4238 queue->CreateQueueEnabledVoter();
4239 voter->SetVoteToEnable(false);
4240
4241 // We don't expect OnHasImmediateTask to be called if the TaskQueue gets
4242 // blocked.
4243 auto task_runner = queue->task_runner();
4244 WaitableEvent done_event;
4245 Thread thread("TestThread");
4246 thread.Start();
4247 thread.task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
4248 // Should not fire the observer.
4249 task_runner->PostTask(FROM_HERE,
4250 BindOnce(&NopTask));
4251 done_event.Signal();
4252 }));
4253 done_event.Wait();
4254 thread.Stop();
4255
4256 FastForwardUntilNoTasksRemain();
4257 // When |voter| goes out of scope the queue will become enabled and the
4258 // observer will fire. We're not interested in testing that however.
4259 Mock::VerifyAndClearExpectations(&throttler);
4260 }
4261
TEST_P(SequenceManagerTest,GracefulShutdown_ManagerDeletedInFlight)4262 TEST_P(SequenceManagerTest, GracefulShutdown_ManagerDeletedInFlight) {
4263 std::vector<TimeTicks> run_times;
4264 TaskQueue::Handle control_tq = CreateTaskQueue();
4265 std::vector<TaskQueue::Handle> main_tqs;
4266
4267 // There might be a race condition - async task queues should be unregistered
4268 // first. Increase the number of task queues to surely detect that.
4269 // The problem is that pointers are compared in a set and generally for
4270 // a small number of allocations value of the pointers increases
4271 // monotonically. 100 is large enough to force allocations from different
4272 // pages.
4273 const int N = 100;
4274 for (int i = 0; i < N; ++i) {
4275 main_tqs.push_back(CreateTaskQueue());
4276 }
4277
4278 for (int i = 1; i <= 5; ++i) {
4279 main_tqs[0]->task_runner()->PostDelayedTask(
4280 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
4281 Milliseconds(i * 100));
4282 }
4283 FastForwardBy(Milliseconds(250));
4284
4285 main_tqs.clear();
4286
4287 // No leaks should occur when TQM was destroyed before processing
4288 // shutdown task and TaskQueueImpl should be safely deleted on a correct
4289 // thread.
4290 DestroySequenceManager();
4291
4292 if (GetUnderlyingRunnerType() != RunnerType::kMessagePump) {
4293 FastForwardUntilNoTasksRemain();
4294 }
4295
4296 EXPECT_THAT(run_times, ElementsAre(FromStartAligned(Milliseconds(100)),
4297 FromStartAligned(Milliseconds(200))));
4298 }
4299
TEST_P(SequenceManagerTest,SequenceManagerDeletedWithQueuesToDelete)4300 TEST_P(SequenceManagerTest, SequenceManagerDeletedWithQueuesToDelete) {
4301 std::vector<TimeTicks> run_times;
4302 TaskQueue::Handle main_tq = CreateTaskQueue();
4303 RefCountedCallbackFactory counter;
4304
4305 EXPECT_EQ(1u, sequence_manager()->ActiveQueuesCount());
4306 EXPECT_EQ(0u, sequence_manager()->QueuesToDeleteCount());
4307
4308 for (int i = 1; i <= 5; ++i) {
4309 main_tq->task_runner()->PostDelayedTask(
4310 FROM_HERE,
4311 counter.WrapCallback(
4312 BindOnce(&RecordTimeTask, &run_times, mock_tick_clock())),
4313 Milliseconds(i * 100));
4314 }
4315 FastForwardBy(Milliseconds(250));
4316
4317 main_tq.reset();
4318
4319 EXPECT_EQ(0u, sequence_manager()->ActiveQueuesCount());
4320 EXPECT_EQ(1u, sequence_manager()->QueuesToDeleteCount());
4321
4322 // Ensure that all queues-to-gracefully-shutdown are properly unregistered.
4323 DestroySequenceManager();
4324
4325 if (GetUnderlyingRunnerType() != RunnerType::kMessagePump) {
4326 FastForwardUntilNoTasksRemain();
4327 }
4328
4329 EXPECT_THAT(run_times, ElementsAre(FromStartAligned(Milliseconds(100)),
4330 FromStartAligned(Milliseconds(200))));
4331 EXPECT_FALSE(counter.HasReferences());
4332 }
4333
TEST(SequenceManagerBasicTest,DefaultTaskRunnerSupport)4334 TEST(SequenceManagerBasicTest, DefaultTaskRunnerSupport) {
4335 auto base_sequence_manager =
4336 sequence_manager::CreateSequenceManagerOnCurrentThreadWithPump(
4337 MessagePump::Create(MessagePumpType::DEFAULT));
4338 auto queue = base_sequence_manager->CreateTaskQueue(
4339 sequence_manager::TaskQueue::Spec(QueueName::DEFAULT_TQ));
4340 base_sequence_manager->SetDefaultTaskRunner(queue->task_runner());
4341
4342 scoped_refptr<SingleThreadTaskRunner> original_task_runner =
4343 SingleThreadTaskRunner::GetCurrentDefault();
4344 scoped_refptr<SingleThreadTaskRunner> custom_task_runner =
4345 MakeRefCounted<TestSimpleTaskRunner>();
4346 {
4347 std::unique_ptr<SequenceManager> manager =
4348 CreateSequenceManagerOnCurrentThread(SequenceManager::Settings());
4349
4350 manager->SetDefaultTaskRunner(custom_task_runner);
4351 DCHECK_EQ(custom_task_runner, SingleThreadTaskRunner::GetCurrentDefault());
4352 }
4353 DCHECK_EQ(original_task_runner, SingleThreadTaskRunner::GetCurrentDefault());
4354 }
4355
TEST_P(SequenceManagerTest,CanceledTasksInQueueCantMakeOtherTasksSkipAhead)4356 TEST_P(SequenceManagerTest, CanceledTasksInQueueCantMakeOtherTasksSkipAhead) {
4357 auto queues = CreateTaskQueues(2u);
4358
4359 CancelableTask task1(mock_tick_clock());
4360 CancelableTask task2(mock_tick_clock());
4361 std::vector<TimeTicks> run_times;
4362
4363 queues[0]->task_runner()->PostTask(
4364 FROM_HERE, BindOnce(&CancelableTask::RecordTimeTask,
4365 task1.weak_factory_.GetWeakPtr(), &run_times));
4366 queues[0]->task_runner()->PostTask(
4367 FROM_HERE, BindOnce(&CancelableTask::RecordTimeTask,
4368 task2.weak_factory_.GetWeakPtr(), &run_times));
4369
4370 std::vector<EnqueueOrder> run_order;
4371 queues[1]->task_runner()->PostTask(FROM_HERE,
4372 BindOnce(&TestTask, 1, &run_order));
4373
4374 queues[0]->task_runner()->PostTask(FROM_HERE,
4375 BindOnce(&TestTask, 2, &run_order));
4376
4377 task1.weak_factory_.InvalidateWeakPtrs();
4378 task2.weak_factory_.InvalidateWeakPtrs();
4379 RunLoop().RunUntilIdle();
4380
4381 EXPECT_THAT(run_order, ElementsAre(1u, 2u));
4382 }
4383
TEST_P(SequenceManagerTest,TaskQueueDeleted)4384 TEST_P(SequenceManagerTest, TaskQueueDeleted) {
4385 std::vector<TimeTicks> run_times;
4386 TaskQueue::Handle main_tq = CreateTaskQueue();
4387 scoped_refptr<TaskRunner> main_task_runner =
4388 main_tq->CreateTaskRunner(kTaskTypeNone);
4389
4390 TaskQueue::Handle other_tq = CreateTaskQueue();
4391 scoped_refptr<TaskRunner> other_task_runner =
4392 other_tq->CreateTaskRunner(kTaskTypeNone);
4393
4394 int start_counter = 0;
4395 int complete_counter = 0;
4396 SetOnTaskHandlers(main_tq.get(), &start_counter, &complete_counter);
4397
4398 EXPECT_EQ(2u, sequence_manager()->ActiveQueuesCount());
4399 EXPECT_EQ(0u, sequence_manager()->QueuesToDeleteCount());
4400
4401 for (int i = 1; i <= 5; ++i) {
4402 main_task_runner->PostDelayedTask(
4403 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
4404 Milliseconds(i * 100));
4405 }
4406
4407 other_task_runner->PostDelayedTask(
4408 FROM_HERE, BindOnce(&RecordTimeTask, &run_times, mock_tick_clock()),
4409 Milliseconds(600));
4410
4411 // TODO(altimin): do not do this after switching to weak pointer-based
4412 // task handlers.
4413 UnsetOnTaskHandlers(main_tq.get());
4414
4415 main_tq.reset();
4416
4417 EXPECT_EQ(1u, sequence_manager()->ActiveQueuesCount());
4418 EXPECT_EQ(1u, sequence_manager()->QueuesToDeleteCount());
4419
4420 FastForwardUntilNoTasksRemain();
4421
4422 // Only tasks on `other_tq` will run, which will also trigger deleting the
4423 // `main_tq`'s impl.
4424 EXPECT_THAT(run_times, ElementsAre(FromStartAligned(Milliseconds(600))));
4425
4426 EXPECT_EQ(1u, sequence_manager()->ActiveQueuesCount());
4427 EXPECT_EQ(0u, sequence_manager()->QueuesToDeleteCount());
4428 }
4429
4430 namespace {
4431
4432 class RunOnDestructionHelper {
4433 public:
RunOnDestructionHelper(base::OnceClosure task)4434 explicit RunOnDestructionHelper(base::OnceClosure task)
4435 : task_(std::move(task)) {}
4436
~RunOnDestructionHelper()4437 ~RunOnDestructionHelper() { std::move(task_).Run(); }
4438
4439 private:
4440 base::OnceClosure task_;
4441 };
4442
RunOnDestruction(base::OnceClosure task)4443 base::OnceClosure RunOnDestruction(base::OnceClosure task) {
4444 return base::BindOnce(
4445 [](std::unique_ptr<RunOnDestructionHelper>) {},
4446 std::make_unique<RunOnDestructionHelper>(std::move(task)));
4447 }
4448
PostOnDestruction(TaskQueue * task_queue,base::OnceClosure task)4449 base::OnceClosure PostOnDestruction(TaskQueue* task_queue,
4450 base::OnceClosure task) {
4451 return RunOnDestruction(base::BindOnce(
4452 [](base::OnceClosure task, TaskQueue* task_queue) {
4453 task_queue->task_runner()->PostTask(FROM_HERE, std::move(task));
4454 },
4455 std::move(task), Unretained(task_queue)));
4456 }
4457
4458 } // namespace
4459
TEST_P(SequenceManagerTest,TaskQueueUsedInTaskDestructorAfterShutdown)4460 TEST_P(SequenceManagerTest, TaskQueueUsedInTaskDestructorAfterShutdown) {
4461 // This test checks that when a task is posted to a shutdown queue and
4462 // destroyed, it can try to post a task to the same queue without deadlocks.
4463 TaskQueue::Handle main_tq = CreateTaskQueue();
4464
4465 WaitableEvent test_executed(WaitableEvent::ResetPolicy::MANUAL,
4466 WaitableEvent::InitialState::NOT_SIGNALED);
4467 std::unique_ptr<Thread> thread = std::make_unique<Thread>("test thread");
4468 thread->StartAndWaitForTesting();
4469
4470 DestroySequenceManager();
4471
4472 thread->task_runner()->PostTask(
4473 FROM_HERE, BindOnce(
4474 [](TaskQueue* task_queue, WaitableEvent* test_executed) {
4475 task_queue->task_runner()->PostTask(
4476 FROM_HERE, PostOnDestruction(
4477 task_queue, base::BindOnce([]() {})));
4478 test_executed->Signal();
4479 },
4480 Unretained(main_tq.get()), &test_executed));
4481 test_executed.Wait();
4482 }
4483
TEST_P(SequenceManagerTest,TaskQueueTaskRunnerDetach)4484 TEST_P(SequenceManagerTest, TaskQueueTaskRunnerDetach) {
4485 scoped_refptr<SingleThreadTaskRunner> task_runner;
4486 {
4487 TaskQueue::Handle queue1 = CreateTaskQueue();
4488 task_runner = queue1->task_runner();
4489 EXPECT_TRUE(task_runner->PostTask(FROM_HERE, BindOnce(&NopTask)));
4490 }
4491 EXPECT_FALSE(task_runner->PostTask(FROM_HERE, BindOnce(&NopTask)));
4492
4493 // Create without a sequence manager.
4494 std::unique_ptr<TaskQueueImpl> queue2 = std::make_unique<TaskQueueImpl>(
4495 nullptr, nullptr, TaskQueue::Spec(QueueName::TEST_TQ));
4496 scoped_refptr<SingleThreadTaskRunner> task_runner2 =
4497 queue2->CreateTaskRunner(0);
4498 EXPECT_FALSE(task_runner2->PostTask(FROM_HERE, BindOnce(&NopTask)));
4499
4500 // Tidy up.
4501 queue2->UnregisterTaskQueue();
4502 }
4503
TEST_P(SequenceManagerTest,DestructorPostChainDuringShutdown)4504 TEST_P(SequenceManagerTest, DestructorPostChainDuringShutdown) {
4505 // Checks that a chain of closures which post other closures on destruction do
4506 // thing on shutdown.
4507 TaskQueue::Handle task_queue = CreateTaskQueue();
4508 bool run = false;
4509 task_queue->task_runner()->PostTask(
4510 FROM_HERE,
4511 PostOnDestruction(
4512 task_queue.get(),
4513 PostOnDestruction(task_queue.get(),
4514 RunOnDestruction(base::BindOnce(
4515 [](bool* run) { *run = true; }, &run)))));
4516
4517 DestroySequenceManager();
4518
4519 EXPECT_TRUE(run);
4520 }
4521
TEST_P(SequenceManagerTest,DestructorPostsViaTaskRunnerHandleDuringShutdown)4522 TEST_P(SequenceManagerTest, DestructorPostsViaTaskRunnerHandleDuringShutdown) {
4523 TaskQueue::Handle task_queue = CreateTaskQueue();
4524 bool run = false;
4525 task_queue->task_runner()->PostTask(
4526 FROM_HERE, RunOnDestruction(BindLambdaForTesting([&]() {
4527 SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
4528 FROM_HERE, base::BindOnce(&NopTask));
4529 run = true;
4530 })));
4531
4532 // Should not DCHECK when SingleThreadTaskRunner::GetCurrentDefault() is
4533 // invoked.
4534 DestroySequenceManager();
4535 EXPECT_TRUE(run);
4536 }
4537
TEST_P(SequenceManagerTest,CreateUnboundSequenceManagerWhichIsNeverBound)4538 TEST_P(SequenceManagerTest, CreateUnboundSequenceManagerWhichIsNeverBound) {
4539 // This should not crash.
4540 CreateUnboundSequenceManager();
4541 }
4542
TEST_P(SequenceManagerTest,HasPendingHighResolutionTasks)4543 TEST_P(SequenceManagerTest, HasPendingHighResolutionTasks) {
4544 auto queue = CreateTaskQueue();
4545 bool supports_high_res = false;
4546 #if BUILDFLAG(IS_WIN)
4547 supports_high_res = true;
4548 #endif
4549
4550 // Only the third task needs high resolution timing.
4551 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4552 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4553 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4554 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4555 Milliseconds(100));
4556 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4557 queue->task_runner()->PostDelayedTaskAt(
4558 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE, BindOnce(&NopTask),
4559 sequence_manager()->NowTicks() + Milliseconds(10),
4560 subtle::DelayPolicy::kPrecise);
4561 EXPECT_EQ(sequence_manager()->HasPendingHighResolutionTasks(),
4562 supports_high_res);
4563
4564 // Running immediate tasks doesn't affect pending high resolution tasks.
4565 RunLoop().RunUntilIdle();
4566 EXPECT_EQ(sequence_manager()->HasPendingHighResolutionTasks(),
4567 supports_high_res);
4568
4569 // Advancing to just before a pending low resolution task doesn't mean that we
4570 // have pending high resolution work.
4571 AdvanceMockTickClock(Milliseconds(99));
4572 RunLoop().RunUntilIdle();
4573 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4574
4575 AdvanceMockTickClock(Milliseconds(100));
4576 RunLoop().RunUntilIdle();
4577 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4578 }
4579
TEST_P(SequenceManagerTest,HasPendingHighResolutionTasksLowPriority)4580 TEST_P(SequenceManagerTest, HasPendingHighResolutionTasksLowPriority) {
4581 auto queue = CreateTaskQueue();
4582 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
4583 bool supports_high_res = false;
4584 #if BUILDFLAG(IS_WIN)
4585 supports_high_res = true;
4586 #endif
4587
4588 // No task should be considered high resolution in a low priority queue.
4589 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4590 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4591 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4592 queue->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4593 Milliseconds(100));
4594 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4595 queue->task_runner()->PostDelayedTaskAt(
4596 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE, BindOnce(&NopTask),
4597 sequence_manager()->NowTicks() + Milliseconds(10),
4598 subtle::DelayPolicy::kPrecise);
4599 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4600
4601 // Increasing queue priority should enable high resolution timer.
4602 queue->SetQueuePriority(TestQueuePriority::kNormalPriority);
4603 EXPECT_EQ(sequence_manager()->HasPendingHighResolutionTasks(),
4604 supports_high_res);
4605 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
4606 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4607
4608 // Running immediate tasks doesn't affect pending high resolution tasks.
4609 RunLoop().RunUntilIdle();
4610 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4611
4612 // Advancing to just before a pending low resolution task doesn't mean that we
4613 // have pending high resolution work.
4614 AdvanceMockTickClock(Milliseconds(99));
4615 RunLoop().RunUntilIdle();
4616 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4617
4618 AdvanceMockTickClock(Milliseconds(100));
4619 RunLoop().RunUntilIdle();
4620 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4621 }
4622
TEST_P(SequenceManagerTest,HasPendingHighResolutionTasksLowAndNormalPriorityQueues)4623 TEST_P(SequenceManagerTest,
4624 HasPendingHighResolutionTasksLowAndNormalPriorityQueues) {
4625 auto queueLow = CreateTaskQueue();
4626 queueLow->SetQueuePriority(TestQueuePriority::kLowPriority);
4627 auto queueNormal = CreateTaskQueue();
4628 queueNormal->SetQueuePriority(TestQueuePriority::kNormalPriority);
4629 bool supports_high_res = false;
4630 #if BUILDFLAG(IS_WIN)
4631 supports_high_res = true;
4632 #endif
4633
4634 // No task should be considered high resolution in a low priority queue.
4635 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4636 queueLow->task_runner()->PostDelayedTaskAt(
4637 subtle::PostDelayedTaskPassKeyForTesting(), FROM_HERE, BindOnce(&NopTask),
4638 sequence_manager()->NowTicks() + Milliseconds(10),
4639 subtle::DelayPolicy::kPrecise);
4640 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4641 queueNormal->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4642 Milliseconds(100));
4643 EXPECT_FALSE(sequence_manager()->HasPendingHighResolutionTasks());
4644
4645 // Increasing queue priority should enable high resolution timer.
4646 queueLow->SetQueuePriority(TestQueuePriority::kNormalPriority);
4647 EXPECT_EQ(sequence_manager()->HasPendingHighResolutionTasks(),
4648 supports_high_res);
4649 }
4650
4651 namespace {
4652
4653 class PostTaskWhenDeleted;
4654 void CallbackWithDestructor(std::unique_ptr<PostTaskWhenDeleted>);
4655
4656 class PostTaskWhenDeleted {
4657 public:
PostTaskWhenDeleted(std::string name,scoped_refptr<SingleThreadTaskRunner> task_runner,size_t depth,std::set<std::string> * tasks_alive,std::vector<std::string> * tasks_deleted)4658 PostTaskWhenDeleted(std::string name,
4659 scoped_refptr<SingleThreadTaskRunner> task_runner,
4660 size_t depth,
4661 std::set<std::string>* tasks_alive,
4662 std::vector<std::string>* tasks_deleted)
4663 : name_(name),
4664 task_runner_(std::move(task_runner)),
4665 depth_(depth),
4666 tasks_alive_(tasks_alive),
4667 tasks_deleted_(tasks_deleted) {
4668 tasks_alive_->insert(full_name());
4669 }
4670
~PostTaskWhenDeleted()4671 ~PostTaskWhenDeleted() {
4672 CHECK(tasks_alive_->find(full_name()) != tasks_alive_->end(),
4673 base::NotFatalUntil::M125);
4674 tasks_alive_->erase(full_name());
4675 tasks_deleted_->push_back(full_name());
4676
4677 if (depth_ > 0) {
4678 task_runner_->PostTask(
4679 FROM_HERE, base::BindOnce(&CallbackWithDestructor,
4680 std::make_unique<PostTaskWhenDeleted>(
4681 name_, task_runner_, depth_ - 1,
4682 tasks_alive_, tasks_deleted_)));
4683 }
4684 }
4685
4686 private:
full_name()4687 std::string full_name() { return name_ + " " + NumberToString(depth_); }
4688
4689 std::string name_;
4690 scoped_refptr<base::SingleThreadTaskRunner> task_runner_;
4691 int depth_;
4692 raw_ptr<std::set<std::string>> tasks_alive_;
4693 raw_ptr<std::vector<std::string>> tasks_deleted_;
4694 };
4695
CallbackWithDestructor(std::unique_ptr<PostTaskWhenDeleted> object)4696 void CallbackWithDestructor(std::unique_ptr<PostTaskWhenDeleted> object) {}
4697
4698 } // namespace
4699
TEST_P(SequenceManagerTest,DoesNotRecordQueueTimeIfSettingFalse)4700 TEST_P(SequenceManagerTest, DoesNotRecordQueueTimeIfSettingFalse) {
4701 auto queue = CreateTaskQueue();
4702
4703 QueueTimeTaskObserver observer;
4704 sequence_manager()->AddTaskObserver(&observer);
4705
4706 // We do not record task queue time when the setting is false.
4707 sequence_manager()->SetAddQueueTimeToTasks(false);
4708 AdvanceMockTickClock(Milliseconds(99));
4709 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4710 RunLoop().RunUntilIdle();
4711 EXPECT_THAT(observer.queue_times(), ElementsAre(TimeTicks()));
4712
4713 sequence_manager()->RemoveTaskObserver(&observer);
4714 }
4715
TEST_P(SequenceManagerTest,RecordsQueueTimeIfSettingTrue)4716 TEST_P(SequenceManagerTest, RecordsQueueTimeIfSettingTrue) {
4717 const auto kStartTime = mock_tick_clock()->NowTicks();
4718 auto queue = CreateTaskQueue();
4719
4720 QueueTimeTaskObserver observer;
4721 sequence_manager()->AddTaskObserver(&observer);
4722
4723 // We correctly record task queue time when the setting is true.
4724 sequence_manager()->SetAddQueueTimeToTasks(true);
4725 AdvanceMockTickClock(Milliseconds(99));
4726 queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4727 RunLoop().RunUntilIdle();
4728 EXPECT_THAT(observer.queue_times(),
4729 ElementsAre(kStartTime + Milliseconds(99)));
4730
4731 sequence_manager()->RemoveTaskObserver(&observer);
4732 }
4733
4734 namespace {
4735
4736 // Inject a test point for recording the destructor calls for OnceClosure
4737 // objects sent to PostTask(). It is awkward usage since we are trying to hook
4738 // the actual destruction, which is not a common operation.
4739 class DestructionObserverProbe : public RefCounted<DestructionObserverProbe> {
4740 public:
DestructionObserverProbe(bool * task_destroyed,bool * destruction_observer_called)4741 DestructionObserverProbe(bool* task_destroyed,
4742 bool* destruction_observer_called)
4743 : task_destroyed_(task_destroyed),
4744 destruction_observer_called_(destruction_observer_called) {}
Run()4745 virtual void Run() {
4746 // This task should never run.
4747 ADD_FAILURE();
4748 }
4749
4750 private:
4751 friend class RefCounted<DestructionObserverProbe>;
4752
~DestructionObserverProbe()4753 virtual ~DestructionObserverProbe() {
4754 EXPECT_FALSE(*destruction_observer_called_);
4755 *task_destroyed_ = true;
4756 }
4757
4758 raw_ptr<bool> task_destroyed_;
4759 raw_ptr<bool> destruction_observer_called_;
4760 };
4761
4762 class SMDestructionObserver : public CurrentThread::DestructionObserver {
4763 public:
SMDestructionObserver(bool * task_destroyed,bool * destruction_observer_called)4764 SMDestructionObserver(bool* task_destroyed, bool* destruction_observer_called)
4765 : task_destroyed_(task_destroyed),
4766 destruction_observer_called_(destruction_observer_called),
4767 task_destroyed_before_message_loop_(false) {}
WillDestroyCurrentMessageLoop()4768 void WillDestroyCurrentMessageLoop() override {
4769 task_destroyed_before_message_loop_ = *task_destroyed_;
4770 *destruction_observer_called_ = true;
4771 }
task_destroyed_before_message_loop() const4772 bool task_destroyed_before_message_loop() const {
4773 return task_destroyed_before_message_loop_;
4774 }
4775
4776 private:
4777 raw_ptr<bool> task_destroyed_;
4778 raw_ptr<bool> destruction_observer_called_;
4779 bool task_destroyed_before_message_loop_;
4780 };
4781
4782 } // namespace
4783
TEST_P(SequenceManagerTest,DestructionObserverTest)4784 TEST_P(SequenceManagerTest, DestructionObserverTest) {
4785 auto queue = CreateTaskQueue();
4786
4787 // Verify that the destruction observer gets called at the very end (after
4788 // all the pending tasks have been destroyed).
4789 const TimeDelta kDelay = Milliseconds(100);
4790
4791 bool task_destroyed = false;
4792 bool destruction_observer_called = false;
4793
4794 SMDestructionObserver observer(&task_destroyed, &destruction_observer_called);
4795 sequence_manager()->AddDestructionObserver(&observer);
4796 queue->task_runner()->PostDelayedTask(
4797 FROM_HERE,
4798 BindOnce(&DestructionObserverProbe::Run,
4799 base::MakeRefCounted<DestructionObserverProbe>(
4800 &task_destroyed, &destruction_observer_called)),
4801 kDelay);
4802
4803 DestroySequenceManager();
4804
4805 EXPECT_TRUE(observer.task_destroyed_before_message_loop());
4806 // The task should have been destroyed when we deleted the loop.
4807 EXPECT_TRUE(task_destroyed);
4808 EXPECT_TRUE(destruction_observer_called);
4809 }
4810
TEST_P(SequenceManagerTest,GetMessagePump)4811 TEST_P(SequenceManagerTest, GetMessagePump) {
4812 switch (GetUnderlyingRunnerType()) {
4813 default:
4814 EXPECT_THAT(sequence_manager()->GetMessagePump(), testing::IsNull());
4815 break;
4816 case RunnerType::kMessagePump:
4817 EXPECT_THAT(sequence_manager()->GetMessagePump(), testing::NotNull());
4818 break;
4819 }
4820 }
4821
4822 namespace {
4823
4824 class MockTimeDomain : public TimeDomain {
4825 public:
4826 MockTimeDomain() = default;
4827 MockTimeDomain(const MockTimeDomain&) = delete;
4828 MockTimeDomain& operator=(const MockTimeDomain&) = delete;
4829 ~MockTimeDomain() override = default;
4830
4831 // TickClock:
NowTicks() const4832 TimeTicks NowTicks() const override { return now_; }
4833
4834 // TimeDomain:
MaybeFastForwardToWakeUp(std::optional<WakeUp> wakeup,bool quit_when_idle_requested)4835 bool MaybeFastForwardToWakeUp(std::optional<WakeUp> wakeup,
4836 bool quit_when_idle_requested) override {
4837 return MaybeFastForwardToWakeUp(quit_when_idle_requested);
4838 }
4839
4840 MOCK_METHOD1(MaybeFastForwardToWakeUp, bool(bool quit_when_idle_requested));
4841
GetName() const4842 const char* GetName() const override { return "Test"; }
4843
4844 private:
4845 TimeTicks now_;
4846 };
4847
4848 } // namespace
4849
TEST_P(SequenceManagerTest,OnIdleTimeDomainNotification)4850 TEST_P(SequenceManagerTest, OnIdleTimeDomainNotification) {
4851 if (GetUnderlyingRunnerType() != RunnerType::kMessagePump)
4852 return;
4853
4854 auto queue = CreateTaskQueue();
4855
4856 // If we call OnIdle, we expect registered TimeDomains to receive a call to
4857 // MaybeFastForwardToWakeUp. If no run loop has requested quit on idle, the
4858 // parameter passed in should be false.
4859 StrictMock<MockTimeDomain> mock_time_domain;
4860 sequence_manager()->SetTimeDomain(&mock_time_domain);
4861 EXPECT_CALL(mock_time_domain, MaybeFastForwardToWakeUp(false))
4862 .WillOnce(Return(false));
4863 sequence_manager()->OnIdle();
4864 sequence_manager()->ResetTimeDomain();
4865 Mock::VerifyAndClearExpectations(&mock_time_domain);
4866
4867 // However if RunUntilIdle is called it should be true.
4868 queue->task_runner()->PostTask(
4869 FROM_HERE, BindLambdaForTesting([&]() {
4870 StrictMock<MockTimeDomain> mock_time_domain;
4871 EXPECT_CALL(mock_time_domain, MaybeFastForwardToWakeUp(true))
4872 .WillOnce(Return(false));
4873 sequence_manager()->SetTimeDomain(&mock_time_domain);
4874 sequence_manager()->OnIdle();
4875 sequence_manager()->ResetTimeDomain();
4876 }));
4877
4878 RunLoop().RunUntilIdle();
4879 }
4880
TEST_P(SequenceManagerTest,CreateTaskQueue)4881 TEST_P(SequenceManagerTest, CreateTaskQueue) {
4882 TaskQueue::Handle task_queue =
4883 sequence_manager()->CreateTaskQueue(TaskQueue::Spec(QueueName::TEST_TQ));
4884 EXPECT_THAT(task_queue.get(), testing::NotNull());
4885
4886 task_queue->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4887 EXPECT_EQ(1u, sequence_manager()->GetPendingTaskCountForTesting());
4888 }
4889
TEST_P(SequenceManagerTest,GetPendingTaskCountForTesting)4890 TEST_P(SequenceManagerTest, GetPendingTaskCountForTesting) {
4891 auto queues = CreateTaskQueues(3u);
4892
4893 EXPECT_EQ(0u, sequence_manager()->GetPendingTaskCountForTesting());
4894
4895 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4896 EXPECT_EQ(1u, sequence_manager()->GetPendingTaskCountForTesting());
4897
4898 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4899 EXPECT_EQ(2u, sequence_manager()->GetPendingTaskCountForTesting());
4900
4901 queues[0]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4902 EXPECT_EQ(3u, sequence_manager()->GetPendingTaskCountForTesting());
4903
4904 queues[1]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4905 EXPECT_EQ(4u, sequence_manager()->GetPendingTaskCountForTesting());
4906
4907 queues[2]->task_runner()->PostTask(FROM_HERE, BindOnce(&NopTask));
4908 EXPECT_EQ(5u, sequence_manager()->GetPendingTaskCountForTesting());
4909
4910 queues[1]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4911 Milliseconds(10));
4912 EXPECT_EQ(6u, sequence_manager()->GetPendingTaskCountForTesting());
4913
4914 queues[2]->task_runner()->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4915 Milliseconds(20));
4916 EXPECT_EQ(7u, sequence_manager()->GetPendingTaskCountForTesting());
4917
4918 RunLoop().RunUntilIdle();
4919 EXPECT_EQ(2u, sequence_manager()->GetPendingTaskCountForTesting());
4920
4921 AdvanceMockTickClock(Milliseconds(10));
4922 RunLoop().RunUntilIdle();
4923 EXPECT_EQ(1u, sequence_manager()->GetPendingTaskCountForTesting());
4924
4925 AdvanceMockTickClock(Milliseconds(10));
4926 RunLoop().RunUntilIdle();
4927 EXPECT_EQ(0u, sequence_manager()->GetPendingTaskCountForTesting());
4928 }
4929
TEST_P(SequenceManagerTest,PostDelayedTaskFromOtherThread)4930 TEST_P(SequenceManagerTest, PostDelayedTaskFromOtherThread) {
4931 TaskQueue::Handle main_tq = CreateTaskQueue();
4932 scoped_refptr<TaskRunner> task_runner =
4933 main_tq->CreateTaskRunner(kTaskTypeNone);
4934 sequence_manager()->SetAddQueueTimeToTasks(true);
4935
4936 Thread thread("test thread");
4937 thread.StartAndWaitForTesting();
4938
4939 WaitableEvent task_posted(WaitableEvent::ResetPolicy::MANUAL,
4940 WaitableEvent::InitialState::NOT_SIGNALED);
4941 thread.task_runner()->PostTask(
4942 FROM_HERE, BindOnce(
4943 [](scoped_refptr<TaskRunner> task_runner,
4944 WaitableEvent* task_posted) {
4945 task_runner->PostDelayedTask(FROM_HERE,
4946 BindOnce(&NopTask),
4947 base::Milliseconds(10));
4948 task_posted->Signal();
4949 },
4950 std::move(task_runner), &task_posted));
4951 task_posted.Wait();
4952 FastForwardUntilNoTasksRemain();
4953 RunLoop().RunUntilIdle();
4954 thread.Stop();
4955 }
4956
4957 namespace {
4958
PostTaskA(scoped_refptr<TaskRunner> task_runner)4959 void PostTaskA(scoped_refptr<TaskRunner> task_runner) {
4960 task_runner->PostTask(FROM_HERE, BindOnce(&NopTask));
4961 task_runner->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4962 base::Milliseconds(10));
4963 }
4964
PostTaskB(scoped_refptr<TaskRunner> task_runner)4965 void PostTaskB(scoped_refptr<TaskRunner> task_runner) {
4966 task_runner->PostTask(FROM_HERE, BindOnce(&NopTask));
4967 task_runner->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4968 base::Milliseconds(20));
4969 }
4970
PostTaskC(scoped_refptr<TaskRunner> task_runner)4971 void PostTaskC(scoped_refptr<TaskRunner> task_runner) {
4972 task_runner->PostTask(FROM_HERE, BindOnce(&NopTask));
4973 task_runner->PostDelayedTask(FROM_HERE, BindOnce(&NopTask),
4974 base::Milliseconds(30));
4975 }
4976
4977 } // namespace
4978
TEST_P(SequenceManagerTest,DescribeAllPendingTasks)4979 TEST_P(SequenceManagerTest, DescribeAllPendingTasks) {
4980 auto queues = CreateTaskQueues(3u);
4981
4982 PostTaskA(queues[0]->task_runner());
4983 PostTaskB(queues[1]->task_runner());
4984 PostTaskC(queues[2]->task_runner());
4985
4986 std::string description = sequence_manager()->DescribeAllPendingTasks();
4987 EXPECT_THAT(description, HasSubstr("PostTaskA@"));
4988 EXPECT_THAT(description, HasSubstr("PostTaskB@"));
4989 EXPECT_THAT(description, HasSubstr("PostTaskC@"));
4990 }
4991
TEST_P(SequenceManagerTest,TaskPriortyInterleaving)4992 TEST_P(SequenceManagerTest, TaskPriortyInterleaving) {
4993 auto queues = CreateTaskQueues(
4994 static_cast<size_t>(TestQueuePriority::kQueuePriorityCount));
4995
4996 for (uint8_t priority = 0;
4997 priority < static_cast<uint8_t>(TestQueuePriority::kQueuePriorityCount);
4998 priority++) {
4999 if (priority != static_cast<uint8_t>(TestQueuePriority::kNormalPriority)) {
5000 queues[priority]->SetQueuePriority(
5001 static_cast<TaskQueue::QueuePriority>(priority));
5002 }
5003 }
5004
5005 std::string order;
5006 for (int i = 0; i < 60; i++) {
5007 for (uint8_t priority = 0;
5008 priority <
5009 static_cast<uint8_t>(TestQueuePriority::kQueuePriorityCount);
5010 priority++) {
5011 queues[priority]->task_runner()->PostTask(
5012 FROM_HERE,
5013 base::BindOnce([](std::string* str, char c) { str->push_back(c); },
5014 &order, '0' + priority));
5015 }
5016 }
5017
5018 RunLoop().RunUntilIdle();
5019
5020 EXPECT_EQ(order,
5021 "000000000000000000000000000000000000000000000000000000000000"
5022 "111111111111111111111111111111111111111111111111111111111111"
5023 "222222222222222222222222222222222222222222222222222222222222"
5024 "333333333333333333333333333333333333333333333333333333333333"
5025 "444444444444444444444444444444444444444444444444444444444444"
5026 "555555555555555555555555555555555555555555555555555555555555"
5027 "666666666666666666666666666666666666666666666666666666666666");
5028 }
5029
5030 namespace {
5031
5032 class CancelableTaskWithDestructionObserver {
5033 public:
CancelableTaskWithDestructionObserver()5034 CancelableTaskWithDestructionObserver() {}
5035
Task(std::unique_ptr<ScopedClosureRunner> destruction_observer)5036 void Task(std::unique_ptr<ScopedClosureRunner> destruction_observer) {
5037 destruction_observer_ = std::move(destruction_observer);
5038 }
5039
5040 std::unique_ptr<ScopedClosureRunner> destruction_observer_;
5041 WeakPtrFactory<CancelableTaskWithDestructionObserver> weak_factory_{this};
5042 };
5043
5044 } // namespace
5045
TEST_P(SequenceManagerTest,PeriodicHousekeeping)5046 TEST_P(SequenceManagerTest, PeriodicHousekeeping) {
5047 auto queue = CreateTaskQueue();
5048
5049 // Post a task that will trigger housekeeping.
5050 queue->task_runner()->PostDelayedTask(
5051 FROM_HERE, BindOnce(&NopTask),
5052 SequenceManagerImpl::kReclaimMemoryInterval);
5053
5054 // Posts some tasks set to run long in the future and then cancel some of
5055 // them.
5056 bool task1_deleted = false;
5057 bool task2_deleted = false;
5058 bool task3_deleted = false;
5059 CancelableTaskWithDestructionObserver task1;
5060 CancelableTaskWithDestructionObserver task2;
5061 CancelableTaskWithDestructionObserver task3;
5062
5063 queue->task_runner()->PostDelayedTask(
5064 FROM_HERE,
5065 BindOnce(&CancelableTaskWithDestructionObserver::Task,
5066 task1.weak_factory_.GetWeakPtr(),
5067 std::make_unique<ScopedClosureRunner>(
5068 BindLambdaForTesting([&]() { task1_deleted = true; }))),
5069 Hours(1));
5070
5071 queue->task_runner()->PostDelayedTask(
5072 FROM_HERE,
5073 BindOnce(&CancelableTaskWithDestructionObserver::Task,
5074 task2.weak_factory_.GetWeakPtr(),
5075 std::make_unique<ScopedClosureRunner>(
5076 BindLambdaForTesting([&]() { task2_deleted = true; }))),
5077 Hours(2));
5078
5079 queue->task_runner()->PostDelayedTask(
5080 FROM_HERE,
5081 BindOnce(&CancelableTaskWithDestructionObserver::Task,
5082 task3.weak_factory_.GetWeakPtr(),
5083 std::make_unique<ScopedClosureRunner>(
5084 BindLambdaForTesting([&]() { task3_deleted = true; }))),
5085 Hours(3));
5086
5087 task2.weak_factory_.InvalidateWeakPtrs();
5088 task3.weak_factory_.InvalidateWeakPtrs();
5089
5090 EXPECT_FALSE(task1_deleted);
5091 EXPECT_FALSE(task2_deleted);
5092 EXPECT_FALSE(task3_deleted);
5093
5094 // This should trigger housekeeping which will sweep away the canceled tasks.
5095 FastForwardBy(SequenceManagerImpl::kReclaimMemoryInterval);
5096
5097 EXPECT_FALSE(task1_deleted);
5098 EXPECT_TRUE(task2_deleted);
5099 EXPECT_TRUE(task3_deleted);
5100
5101 // Tidy up.
5102 FastForwardUntilNoTasksRemain();
5103 }
5104
5105 namespace {
5106
5107 class MockCrashKeyImplementation : public debug::CrashKeyImplementation {
5108 public:
5109 MOCK_METHOD2(Allocate,
5110 debug::CrashKeyString*(const char name[], debug::CrashKeySize));
5111 MOCK_METHOD2(Set, void(debug::CrashKeyString*, std::string_view));
5112 MOCK_METHOD1(Clear, void(debug::CrashKeyString*));
5113 MOCK_METHOD1(OutputCrashKeysToStream, void(std::ostream&));
5114 };
5115
5116 } // namespace
5117
TEST_P(SequenceManagerTest,CrossQueueTaskPostingWhenQueueDeleted)5118 TEST_P(SequenceManagerTest, CrossQueueTaskPostingWhenQueueDeleted) {
5119 MockTask task;
5120 auto queue_1 = CreateTaskQueue();
5121 auto queue_2 = CreateTaskQueue();
5122
5123 EXPECT_CALL(task, Run).Times(1);
5124
5125 queue_1->task_runner()->PostDelayedTask(
5126 FROM_HERE, PostOnDestruction(queue_2.get(), task.Get()), Minutes(1));
5127
5128 queue_1.reset();
5129
5130 FastForwardUntilNoTasksRemain();
5131 }
5132
TEST_P(SequenceManagerTest,UnregisterTaskQueueTriggersScheduleWork)5133 TEST_P(SequenceManagerTest, UnregisterTaskQueueTriggersScheduleWork) {
5134 constexpr auto kDelay = Minutes(1);
5135 auto queue_1 = CreateTaskQueue();
5136 auto queue_2 = CreateTaskQueue();
5137
5138 MockTask task;
5139 EXPECT_CALL(task, Run).Times(1);
5140
5141 queue_1->task_runner()->PostDelayedTask(FROM_HERE, task.Get(), kDelay);
5142 queue_2->task_runner()->PostDelayedTask(FROM_HERE, task.Get(), kDelay * 2);
5143
5144 AdvanceMockTickClock(kDelay * 2);
5145
5146 // Wakeup time needs to be adjusted to kDelay * 2 when the queue is
5147 // unregistered from the TimeDomain
5148 queue_1.reset();
5149
5150 RunLoop().RunUntilIdle();
5151 }
5152
TEST_P(SequenceManagerTest,ReclaimMemoryRemovesCorrectQueueFromSet)5153 TEST_P(SequenceManagerTest, ReclaimMemoryRemovesCorrectQueueFromSet) {
5154 auto queue1 = CreateTaskQueue();
5155 auto queue2 = CreateTaskQueue();
5156 auto queue3 = CreateTaskQueue();
5157 auto queue4 = CreateTaskQueue();
5158
5159 std::vector<int> order;
5160
5161 CancelableRepeatingClosure cancelable_closure1(
5162 BindLambdaForTesting([&]() { order.push_back(10); }));
5163 CancelableRepeatingClosure cancelable_closure2(
5164 BindLambdaForTesting([&]() { order.push_back(11); }));
5165 queue1->task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
5166 order.push_back(1);
5167 cancelable_closure1.Cancel();
5168 cancelable_closure2.Cancel();
5169 // This should remove |queue4| from the work
5170 // queue set,
5171 sequence_manager()->ReclaimMemory();
5172 }));
5173 queue2->task_runner()->PostTask(
5174 FROM_HERE, BindLambdaForTesting([&]() { order.push_back(2); }));
5175 queue3->task_runner()->PostTask(
5176 FROM_HERE, BindLambdaForTesting([&]() { order.push_back(3); }));
5177 queue4->task_runner()->PostTask(FROM_HERE, cancelable_closure1.callback());
5178 queue4->task_runner()->PostTask(FROM_HERE, cancelable_closure2.callback());
5179
5180 RunLoop().RunUntilIdle();
5181
5182 // Make sure ReclaimMemory didn't prevent the task from |queue2| from running.
5183 EXPECT_THAT(order, ElementsAre(1, 2, 3));
5184 }
5185
5186 namespace {
5187
5188 class TaskObserverExpectingNoDelayedRunTime : public TaskObserver {
5189 public:
5190 TaskObserverExpectingNoDelayedRunTime() = default;
5191 ~TaskObserverExpectingNoDelayedRunTime() override = default;
5192
num_will_process_task() const5193 int num_will_process_task() const { return num_will_process_task_; }
num_did_process_task() const5194 int num_did_process_task() const { return num_did_process_task_; }
5195
5196 private:
WillProcessTask(const base::PendingTask & pending_task,bool was_blocked_or_low_priority)5197 void WillProcessTask(const base::PendingTask& pending_task,
5198 bool was_blocked_or_low_priority) override {
5199 EXPECT_TRUE(pending_task.delayed_run_time.is_null());
5200 ++num_will_process_task_;
5201 }
DidProcessTask(const base::PendingTask & pending_task)5202 void DidProcessTask(const base::PendingTask& pending_task) override {
5203 EXPECT_TRUE(pending_task.delayed_run_time.is_null());
5204 ++num_did_process_task_;
5205 }
5206
5207 int num_will_process_task_ = 0;
5208 int num_did_process_task_ = 0;
5209 };
5210
5211 } // namespace
5212
5213 // The |delayed_run_time| must not be set for immediate tasks as that prevents
5214 // external observers from correctly identifying delayed tasks.
5215 // https://crbug.com/1029137
TEST_P(SequenceManagerTest,NoDelayedRunTimeForImmediateTask)5216 TEST_P(SequenceManagerTest, NoDelayedRunTimeForImmediateTask) {
5217 TaskObserverExpectingNoDelayedRunTime task_observer;
5218 sequence_manager()->SetAddQueueTimeToTasks(true);
5219 sequence_manager()->AddTaskObserver(&task_observer);
5220 auto queue = CreateTaskQueue();
5221
5222 base::RunLoop run_loop;
5223 queue->task_runner()->PostTask(
5224 FROM_HERE, BindLambdaForTesting([&]() { run_loop.Quit(); }));
5225 run_loop.Run();
5226
5227 EXPECT_EQ(1, task_observer.num_will_process_task());
5228 EXPECT_EQ(1, task_observer.num_did_process_task());
5229
5230 sequence_manager()->RemoveTaskObserver(&task_observer);
5231 }
5232
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_QueueDisabled)5233 TEST_P(SequenceManagerTest, TaskObserverBlockedOrLowPriority_QueueDisabled) {
5234 auto queue = CreateTaskQueue();
5235 testing::StrictMock<MockTaskObserver> observer;
5236 sequence_manager()->AddTaskObserver(&observer);
5237
5238 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5239 GetTaskQueueImpl(queue.get())->SetQueueEnabled(false);
5240 GetTaskQueueImpl(queue.get())->SetQueueEnabled(true);
5241
5242 EXPECT_CALL(observer,
5243 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5244 EXPECT_CALL(observer, DidProcessTask(_));
5245 RunLoop().RunUntilIdle();
5246
5247 sequence_manager()->RemoveTaskObserver(&observer);
5248 }
5249
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_FenceBeginningOfTime)5250 TEST_P(SequenceManagerTest,
5251 TaskObserverBlockedOrLowPriority_FenceBeginningOfTime) {
5252 auto queue = CreateTaskQueue();
5253 testing::StrictMock<MockTaskObserver> observer;
5254 sequence_manager()->AddTaskObserver(&observer);
5255
5256 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5257 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
5258 queue->RemoveFence();
5259
5260 EXPECT_CALL(observer,
5261 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5262 EXPECT_CALL(observer, DidProcessTask(_));
5263 RunLoop().RunUntilIdle();
5264
5265 sequence_manager()->RemoveTaskObserver(&observer);
5266 }
5267
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_PostedBeforeFenceNow)5268 TEST_P(SequenceManagerTest,
5269 TaskObserverBlockedOrLowPriority_PostedBeforeFenceNow) {
5270 auto queue = CreateTaskQueue();
5271 testing::StrictMock<MockTaskObserver> observer;
5272 sequence_manager()->AddTaskObserver(&observer);
5273
5274 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5275 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
5276 queue->RemoveFence();
5277
5278 EXPECT_CALL(observer,
5279 WillProcessTask(_, /*was_blocked_or_low_priority=*/false));
5280 EXPECT_CALL(observer, DidProcessTask(_));
5281 RunLoop().RunUntilIdle();
5282
5283 sequence_manager()->RemoveTaskObserver(&observer);
5284 }
5285
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_PostedAfterFenceNow)5286 TEST_P(SequenceManagerTest,
5287 TaskObserverBlockedOrLowPriority_PostedAfterFenceNow) {
5288 auto queue = CreateTaskQueue();
5289 testing::StrictMock<MockTaskObserver> observer;
5290 sequence_manager()->AddTaskObserver(&observer);
5291
5292 queue->InsertFence(TaskQueue::InsertFencePosition::kNow);
5293 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5294 queue->RemoveFence();
5295
5296 EXPECT_CALL(observer,
5297 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5298 EXPECT_CALL(observer, DidProcessTask(_));
5299 RunLoop().RunUntilIdle();
5300
5301 sequence_manager()->RemoveTaskObserver(&observer);
5302 }
5303
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_LowerPriorityWhileQueued)5304 TEST_P(SequenceManagerTest,
5305 TaskObserverBlockedOrLowPriority_LowerPriorityWhileQueued) {
5306 auto queue = CreateTaskQueue();
5307 testing::StrictMock<MockTaskObserver> observer;
5308 sequence_manager()->AddTaskObserver(&observer);
5309
5310 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5311 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
5312 queue->SetQueuePriority(TestQueuePriority::kNormalPriority);
5313
5314 EXPECT_CALL(observer,
5315 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5316 EXPECT_CALL(observer, DidProcessTask(_));
5317 RunLoop().RunUntilIdle();
5318
5319 sequence_manager()->RemoveTaskObserver(&observer);
5320 }
5321
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_LowPriorityWhenQueueing)5322 TEST_P(SequenceManagerTest,
5323 TaskObserverBlockedOrLowPriority_LowPriorityWhenQueueing) {
5324 auto queue = CreateTaskQueue();
5325 testing::StrictMock<MockTaskObserver> observer;
5326 sequence_manager()->AddTaskObserver(&observer);
5327
5328 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
5329 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5330 queue->SetQueuePriority(TestQueuePriority::kNormalPriority);
5331
5332 EXPECT_CALL(observer,
5333 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5334 EXPECT_CALL(observer, DidProcessTask(_));
5335 RunLoop().RunUntilIdle();
5336
5337 sequence_manager()->RemoveTaskObserver(&observer);
5338 }
5339
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_LowPriorityWhenRunning)5340 TEST_P(SequenceManagerTest,
5341 TaskObserverBlockedOrLowPriority_LowPriorityWhenRunning) {
5342 auto queue = CreateTaskQueue();
5343 testing::StrictMock<MockTaskObserver> observer;
5344 sequence_manager()->AddTaskObserver(&observer);
5345
5346 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5347 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
5348
5349 EXPECT_CALL(observer,
5350 WillProcessTask(_, /*was_blocked_or_low_priority=*/true));
5351 EXPECT_CALL(observer, DidProcessTask(_));
5352 RunLoop().RunUntilIdle();
5353
5354 sequence_manager()->RemoveTaskObserver(&observer);
5355 }
5356
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_TaskObserverUnblockedWithBacklog)5357 TEST_P(SequenceManagerTest,
5358 TaskObserverBlockedOrLowPriority_TaskObserverUnblockedWithBacklog) {
5359 auto queue = CreateTaskQueue();
5360 testing::StrictMock<MockTaskObserver> observer;
5361 sequence_manager()->AddTaskObserver(&observer);
5362
5363 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
5364 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5365 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
5366 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5367 queue->RemoveFence();
5368 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5369 queue->SetQueuePriority(TestQueuePriority::kNormalPriority);
5370 // Post a task while the queue is kNormalPriority and unblocked, but has a
5371 // backlog of tasks that were blocked.
5372 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5373
5374 EXPECT_CALL(observer,
5375 WillProcessTask(_, /*was_blocked_or_low_priority=*/true))
5376 .Times(3);
5377 EXPECT_CALL(observer, DidProcessTask(_)).Times(4);
5378 EXPECT_CALL(observer,
5379 WillProcessTask(_, /*was_blocked_or_low_priority=*/false));
5380 RunLoop().RunUntilIdle();
5381 testing::Mock::VerifyAndClear(&observer);
5382
5383 sequence_manager()->RemoveTaskObserver(&observer);
5384 }
5385
TEST_P(SequenceManagerTest,TaskObserverBlockedOrLowPriority_Mix)5386 TEST_P(SequenceManagerTest, TaskObserverBlockedOrLowPriority_Mix) {
5387 auto queue = CreateTaskQueue();
5388 testing::StrictMock<MockTaskObserver> observer;
5389 sequence_manager()->AddTaskObserver(&observer);
5390
5391 queue->SetQueuePriority(TestQueuePriority::kLowPriority);
5392 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5393 queue->InsertFence(TaskQueue::InsertFencePosition::kBeginningOfTime);
5394 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5395 queue->RemoveFence();
5396 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5397
5398 EXPECT_CALL(observer,
5399 WillProcessTask(_, /*was_blocked_or_low_priority=*/true))
5400 .Times(3);
5401 EXPECT_CALL(observer, DidProcessTask(_)).Times(3);
5402 RunLoop().RunUntilIdle();
5403 testing::Mock::VerifyAndClear(&observer);
5404
5405 queue->SetQueuePriority(TestQueuePriority::kNormalPriority);
5406 queue->task_runner()->PostTask(FROM_HERE, DoNothing());
5407 EXPECT_CALL(observer,
5408 WillProcessTask(_, /*was_blocked_or_low_priority=*/false));
5409 EXPECT_CALL(observer, DidProcessTask(_));
5410 RunLoop().RunUntilIdle();
5411
5412 sequence_manager()->RemoveTaskObserver(&observer);
5413 }
5414
TEST_P(SequenceManagerTest,DelayedTaskOrderFromMultipleQueues)5415 TEST_P(SequenceManagerTest, DelayedTaskOrderFromMultipleQueues) {
5416 // Regression test for crbug.com/1249857. The 4th task posted below should run
5417 // 4th despite being in queues[0].
5418 std::vector<EnqueueOrder> run_order;
5419 auto queues = CreateTaskQueues(3u);
5420
5421 queues[0]->task_runner()->PostDelayedTask(
5422 FROM_HERE, BindOnce(&TestTask, 1, &run_order), Milliseconds(9));
5423 queues[1]->task_runner()->PostDelayedTask(
5424 FROM_HERE, BindOnce(&TestTask, 2, &run_order), Milliseconds(10));
5425 queues[2]->task_runner()->PostDelayedTask(
5426 FROM_HERE, BindOnce(&TestTask, 3, &run_order), Milliseconds(10));
5427 queues[0]->task_runner()->PostDelayedTask(
5428 FROM_HERE, BindOnce(&TestTask, 4, &run_order), Milliseconds(100));
5429
5430 // All delayed tasks are now ready, but none have run.
5431 AdvanceMockTickClock(Milliseconds(100));
5432 RunLoop().RunUntilIdle();
5433
5434 EXPECT_THAT(run_order, ElementsAre(1u, 2u, 3u, 4u));
5435 }
5436
TEST_P(SequenceManagerTest,OnTaskPostedCallbacks)5437 TEST_P(SequenceManagerTest, OnTaskPostedCallbacks) {
5438 int counter1 = 0;
5439 int counter2 = 0;
5440
5441 auto queue = CreateTaskQueue();
5442
5443 std::unique_ptr<TaskQueue::OnTaskPostedCallbackHandle> handle1 =
5444 queue->AddOnTaskPostedHandler(BindRepeating(
5445 [](int* counter, const Task& task) { ++(*counter); }, &counter1));
5446
5447 queue->task_runner()->PostTask(FROM_HERE, BindOnce(NullTask));
5448 EXPECT_EQ(1, counter1);
5449 EXPECT_EQ(0, counter2);
5450
5451 std::unique_ptr<TaskQueue::OnTaskPostedCallbackHandle> handle2 =
5452 queue->AddOnTaskPostedHandler(BindRepeating(
5453 [](int* counter, const Task& task) { ++(*counter); }, &counter2));
5454
5455 queue->task_runner()->PostTask(FROM_HERE, BindOnce(NullTask));
5456 EXPECT_EQ(2, counter1);
5457 EXPECT_EQ(1, counter2);
5458
5459 handle1.reset();
5460
5461 queue->task_runner()->PostTask(FROM_HERE, BindOnce(NullTask));
5462 EXPECT_EQ(2, counter1);
5463 EXPECT_EQ(2, counter2);
5464
5465 handle2.reset();
5466
5467 queue->task_runner()->PostTask(FROM_HERE, BindOnce(NullTask));
5468 EXPECT_EQ(2, counter1);
5469 EXPECT_EQ(2, counter2);
5470 }
5471
5472 // `RunOrPostTask` is tightly integrated with `ThreadControllerWithMessagePump`
5473 // and `RunLoop` so its tests can't use `SequenceManagerTest`.
5474 class SequenceManagerRunOrPostTaskTest : public testing::Test {
5475 public:
SequenceManagerRunOrPostTaskTest()5476 SequenceManagerRunOrPostTaskTest() {
5477 auto settings = SequenceManager::Settings::Builder().Build();
5478 auto thread_controller =
5479 std::make_unique<ThreadControllerWithMessagePumpImpl>(
5480 std::make_unique<MessagePumpDefault>(), settings);
5481 sequence_manager_ = SequenceManagerForTest::Create(
5482 std::move(thread_controller), std::move(settings));
5483 queue_ =
5484 sequence_manager_->CreateTaskQueue(TaskQueue::Spec(QueueName::TEST_TQ));
5485 other_queue_ =
5486 sequence_manager_->CreateTaskQueue(TaskQueue::Spec(QueueName::TEST_TQ));
5487 sequence_manager_->SetDefaultTaskRunner(queue_->task_runner());
5488
5489 thread_.Start();
5490 }
5491
sequence_manager()5492 SequenceManagerImpl* sequence_manager() { return sequence_manager_.get(); }
queue()5493 TaskQueue* queue() { return queue_.get(); }
other_queue()5494 TaskQueue* other_queue() { return other_queue_.get(); }
task_runner()5495 SingleThreadTaskRunner* task_runner() { return queue_->task_runner().get(); }
other_task_runner()5496 SingleThreadTaskRunner* other_task_runner() {
5497 return other_queue_->task_runner().get();
5498 }
other_thread_task_runner()5499 SingleThreadTaskRunner* other_thread_task_runner() {
5500 return thread_.task_runner().get();
5501 }
5502
FlushOtherThread()5503 void FlushOtherThread() { thread_.FlushForTesting(); }
5504
5505 // Allow tasks to run synchronously. This imitates being inside a `RunLoop`,
5506 // but allows the test's body to keep running.
SimulateInsideRunLoop()5507 void SimulateInsideRunLoop() {
5508 sequence_manager_->SetRunTaskSynchronouslyAllowed(true);
5509 }
5510
5511 private:
5512 std::unique_ptr<SequenceManagerForTest> sequence_manager_;
5513 TaskQueue::Handle queue_;
5514 TaskQueue::Handle other_queue_;
5515 Thread thread_{"OtherThread"};
5516 };
5517
5518 // Verify that `RunOrPostTask` from the bound thread does not run the task
5519 // synchronously if there is no active `RunLoop`.
TEST_F(SequenceManagerRunOrPostTaskTest,FromBoundThreadOutsideRunLoop)5520 TEST_F(SequenceManagerRunOrPostTaskTest, FromBoundThreadOutsideRunLoop) {
5521 bool did_run = false;
5522 EXPECT_TRUE(task_runner()->RunOrPostTask(
5523 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5524 BindLambdaForTesting([&]() { did_run = true; })));
5525 EXPECT_FALSE(did_run);
5526 RunLoop().RunUntilIdle();
5527 EXPECT_TRUE(did_run);
5528 }
5529
5530 // Verify that `RunOrPostTask` from another thread does not run the task
5531 // synchronously if there is no active `RunLoop`.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadOutsideRunLoop)5532 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadOutsideRunLoop) {
5533 bool did_run = false;
5534 other_thread_task_runner()->PostTask(
5535 FROM_HERE, BindLambdaForTesting([&]() {
5536 EXPECT_TRUE(task_runner()->RunOrPostTask(
5537 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5538 BindLambdaForTesting([&]() { did_run = true; })));
5539 }));
5540
5541 FlushOtherThread();
5542 EXPECT_FALSE(did_run);
5543 RunLoop().RunUntilIdle();
5544 EXPECT_TRUE(did_run);
5545 }
5546
5547 // Verify that `RunOrPostTask` from a task running on the bound thread does not
5548 // run the task synchronously.
TEST_F(SequenceManagerRunOrPostTaskTest,FromInsideTask)5549 TEST_F(SequenceManagerRunOrPostTaskTest, FromInsideTask) {
5550 bool did_run = false;
5551 EXPECT_TRUE(task_runner()->PostTask(
5552 FROM_HERE, BindLambdaForTesting([&]() {
5553 EXPECT_TRUE(task_runner()->RunOrPostTask(
5554 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5555 BindLambdaForTesting([&]() { did_run = true; })));
5556 EXPECT_FALSE(did_run);
5557 })));
5558 RunLoop().RunUntilIdle();
5559 EXPECT_TRUE(did_run);
5560 }
5561
5562 // Verify that `RunOrPostTask` from another thread does not run the task
5563 // synchronously if there is a queued task.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadWithQueuedTask)5564 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadWithQueuedTask) {
5565 SimulateInsideRunLoop();
5566 EXPECT_TRUE(task_runner()->PostTask(FROM_HERE, DoNothing()));
5567
5568 bool did_run = false;
5569 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5570 FROM_HERE, BindLambdaForTesting([&]() {
5571 EXPECT_TRUE(task_runner()->RunOrPostTask(
5572 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5573 BindLambdaForTesting([&]() { did_run = true; })));
5574 EXPECT_FALSE(did_run);
5575 })));
5576
5577 FlushOtherThread();
5578 EXPECT_FALSE(did_run);
5579 RunLoop().RunUntilIdle();
5580 EXPECT_TRUE(did_run);
5581 }
5582
5583 // Verify that `RunOrPostTask` from another thread does not run the task
5584 // synchronously if there is a queued task in a different queue from the same
5585 // `SequenceManager`.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadWithQueuedTaskOtherQueue)5586 TEST_F(SequenceManagerRunOrPostTaskTest,
5587 FromOtherThreadWithQueuedTaskOtherQueue) {
5588 SimulateInsideRunLoop();
5589 EXPECT_TRUE(other_task_runner()->PostTask(FROM_HERE, DoNothing()));
5590
5591 bool did_run = false;
5592 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5593 FROM_HERE, BindLambdaForTesting([&]() {
5594 EXPECT_TRUE(task_runner()->RunOrPostTask(
5595 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5596 BindLambdaForTesting([&]() { did_run = true; })));
5597 EXPECT_FALSE(did_run);
5598 })));
5599
5600 FlushOtherThread();
5601 EXPECT_FALSE(did_run);
5602 RunLoop().RunUntilIdle();
5603 EXPECT_TRUE(did_run);
5604 }
5605
5606 // Verify that `RunOrPostTask` from another thread runs the task synchronously
5607 // if there is no queued or running task.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadNoQueuedOrRunningTask)5608 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadNoQueuedOrRunningTask) {
5609 SimulateInsideRunLoop();
5610
5611 bool did_run = false;
5612 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5613 FROM_HERE, BindLambdaForTesting([&]() {
5614 EXPECT_TRUE(task_runner()->RunOrPostTask(
5615 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5616 BindLambdaForTesting([&]() { did_run = true; })));
5617 EXPECT_TRUE(did_run);
5618 })));
5619
5620 FlushOtherThread();
5621 EXPECT_TRUE(did_run);
5622 }
5623
5624 // Verify that `RunOrPostTask` from another thread does not run the task
5625 // synchronously when "internal work" is simulated.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadInternalWork)5626 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadInternalWork) {
5627 SimulateInsideRunLoop();
5628
5629 // Simulate internal work execution in the message pump.
5630 sequence_manager()->OnBeginWork();
5631
5632 bool did_run = false;
5633 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5634 FROM_HERE, BindLambdaForTesting([&]() {
5635 EXPECT_TRUE(task_runner()->RunOrPostTask(
5636 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5637 BindLambdaForTesting([&]() { did_run = true; })));
5638 EXPECT_FALSE(did_run);
5639 })));
5640 FlushOtherThread();
5641 EXPECT_FALSE(did_run);
5642 RunLoop().RunUntilIdle();
5643 EXPECT_TRUE(did_run);
5644 }
5645
5646 // Verify that `RunOrPostTask` from another thread runs the task synchronously
5647 // if there is no running task and the only queued task is in a different queue
5648 // which is disabled.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadDisabledQueue)5649 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadDisabledQueue) {
5650 auto voter = queue()->CreateQueueEnabledVoter();
5651 voter->SetVoteToEnable(false);
5652 // Reload empty work queues (tasks can't run synchronously when there are
5653 // pending requests to reload empty work queues).
5654 RunLoop().RunUntilIdle();
5655 SimulateInsideRunLoop();
5656
5657 bool did_run = false;
5658 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5659 FROM_HERE, BindLambdaForTesting([&]() {
5660 EXPECT_TRUE(task_runner()->RunOrPostTask(
5661 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5662 BindLambdaForTesting([&]() { did_run = true; })));
5663 EXPECT_FALSE(did_run);
5664 })));
5665
5666 FlushOtherThread();
5667 EXPECT_FALSE(did_run);
5668 RunLoop().RunUntilIdle();
5669 EXPECT_FALSE(did_run);
5670 voter.reset();
5671 RunLoop().RunUntilIdle();
5672 EXPECT_TRUE(did_run);
5673 }
5674
5675 // Verify that `RunOrPostTask` from another thread runs the task synchronously
5676 // if there is no running task and the only queued task is in a different queue
5677 // which is disabled.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadQueuedTaskInDisabledOtherQueue)5678 TEST_F(SequenceManagerRunOrPostTaskTest,
5679 FromOtherThreadQueuedTaskInDisabledOtherQueue) {
5680 bool did_run_other_task = false;
5681 EXPECT_TRUE(other_task_runner()->PostTask(
5682 FROM_HERE, BindLambdaForTesting([&]() { did_run_other_task = true; })));
5683 auto voter = other_queue()->CreateQueueEnabledVoter();
5684 voter->SetVoteToEnable(false);
5685 // Reload empty work queues (tasks can't run synchronously when there are
5686 // pending requests to reload empty work queues).
5687 RunLoop().RunUntilIdle();
5688 EXPECT_FALSE(did_run_other_task);
5689 SimulateInsideRunLoop();
5690
5691 bool did_run = false;
5692 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5693 FROM_HERE, BindLambdaForTesting([&]() {
5694 EXPECT_TRUE(task_runner()->RunOrPostTask(
5695 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5696 BindLambdaForTesting([&]() { did_run = true; })));
5697 EXPECT_TRUE(did_run);
5698 })));
5699
5700 FlushOtherThread();
5701 EXPECT_TRUE(did_run);
5702 }
5703
5704 // Verify that `RunOrPostTask` from another thread does not run the task
5705 // synchronously if there is a running task.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadWithRunningTask)5706 TEST_F(SequenceManagerRunOrPostTaskTest, FromOtherThreadWithRunningTask) {
5707 WaitableEvent main_thread_task_running;
5708 WaitableEvent run_or_post_task_done;
5709 task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
5710 main_thread_task_running.Signal();
5711 run_or_post_task_done.Wait();
5712 }));
5713
5714 bool did_run = false;
5715 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5716 FROM_HERE, BindLambdaForTesting([&]() {
5717 main_thread_task_running.Wait();
5718 EXPECT_TRUE(task_runner()->RunOrPostTask(
5719 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5720 BindLambdaForTesting([&]() { did_run = true; })));
5721 EXPECT_FALSE(did_run);
5722 run_or_post_task_done.Signal();
5723 })));
5724
5725 RunLoop().RunUntilIdle();
5726 EXPECT_TRUE(did_run);
5727 }
5728
5729 // Verify that `RunOrPostTask` from another thread does not run the task
5730 // synchronously if there is a running task blocked in a nested loop.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadWithRunningTaskInNestedLoop)5731 TEST_F(SequenceManagerRunOrPostTaskTest,
5732 FromOtherThreadWithRunningTaskInNestedLoop) {
5733 WaitableEvent main_thread_task_running;
5734 RunLoop nested_run_loop(RunLoop::Type::kNestableTasksAllowed);
5735 auto nested_run_loop_quit_closure = nested_run_loop.QuitClosure();
5736 task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
5737 main_thread_task_running.Signal();
5738 nested_run_loop.Run();
5739 }));
5740
5741 thread_local bool is_main_thread = false;
5742 is_main_thread = true;
5743
5744 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5745 FROM_HERE, BindLambdaForTesting([&]() {
5746 EXPECT_FALSE(is_main_thread);
5747 main_thread_task_running.Wait();
5748 // Wait to increase chances of posting while the main thread task is in
5749 // a nested `RunLoop`.
5750 PlatformThread::Sleep(TestTimeouts::tiny_timeout());
5751 EXPECT_TRUE(task_runner()->RunOrPostTask(
5752 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5753 BindLambdaForTesting([&]() {
5754 // Should not run synchronously on the other thread.
5755 EXPECT_TRUE(is_main_thread);
5756 std::move(nested_run_loop_quit_closure).Run();
5757 })));
5758 })));
5759
5760 RunLoop().RunUntilIdle();
5761 FlushOtherThread();
5762 }
5763
5764 // Verify that `RunOrPostTask` from another thread does not run the task
5765 // synchronously if there is a running task in a different queue from the same
5766 // `SequenceManager`.
TEST_F(SequenceManagerRunOrPostTaskTest,FromOtherThreadWithRunningTaskOtherQueue)5767 TEST_F(SequenceManagerRunOrPostTaskTest,
5768 FromOtherThreadWithRunningTaskOtherQueue) {
5769 WaitableEvent main_thread_task_running;
5770 WaitableEvent run_or_post_task_done;
5771 other_task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
5772 main_thread_task_running.Signal();
5773 run_or_post_task_done.Wait();
5774 }));
5775
5776 bool did_run = false;
5777 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5778 FROM_HERE, BindLambdaForTesting([&]() {
5779 main_thread_task_running.Wait();
5780 EXPECT_TRUE(task_runner()->RunOrPostTask(
5781 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5782 BindLambdaForTesting([&]() { did_run = true; })));
5783 EXPECT_FALSE(did_run);
5784 run_or_post_task_done.Signal();
5785 })));
5786
5787 RunLoop().RunUntilIdle();
5788 EXPECT_TRUE(did_run);
5789 }
5790
5791 // Verify that a task run synchronously inside `RunOrPostTask` prevents another
5792 // task from starting on the bound thread.
TEST_F(SequenceManagerRunOrPostTaskTest,MainThreadCantStartTaskDuringRunOrPostTask)5793 TEST_F(SequenceManagerRunOrPostTaskTest,
5794 MainThreadCantStartTaskDuringRunOrPostTask) {
5795 SimulateInsideRunLoop();
5796 WaitableEvent sync_task_started;
5797 bool sync_task_done = true;
5798
5799 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5800 FROM_HERE, BindLambdaForTesting([&]() {
5801 EXPECT_TRUE(task_runner()->RunOrPostTask(
5802 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5803 BindLambdaForTesting([&]() {
5804 sync_task_started.Signal();
5805 // Wait to increase chances that the main thread will attempt to
5806 // schedule its task.
5807 PlatformThread::Sleep(TestTimeouts::tiny_timeout());
5808 sync_task_done = true;
5809 })));
5810 EXPECT_TRUE(sync_task_done);
5811 })));
5812
5813 sync_task_started.Wait();
5814 RunLoop run_loop;
5815 task_runner()->PostTask(FROM_HERE, BindLambdaForTesting([&]() {
5816 // Must deterministically run after the sync task.
5817 EXPECT_TRUE(sync_task_done);
5818 run_loop.Quit();
5819 }));
5820 run_loop.Run();
5821 FlushOtherThread();
5822 }
5823
5824 // Verify that when `RunOrPostTask` is called concurrently from multiple
5825 // threads, only one can execute its task synchronously.
TEST_F(SequenceManagerRunOrPostTaskTest,ConcurrentCalls)5826 TEST_F(SequenceManagerRunOrPostTaskTest, ConcurrentCalls) {
5827 SimulateInsideRunLoop();
5828
5829 WaitableEvent did_start_task_1;
5830 WaitableEvent did_post_task_2;
5831
5832 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5833 FROM_HERE, BindLambdaForTesting([&]() {
5834 EXPECT_TRUE(task_runner()->RunOrPostTask(
5835 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5836 BindLambdaForTesting([&]() {
5837 did_start_task_1.Signal();
5838 did_post_task_2.Wait();
5839 })));
5840 })));
5841
5842 Thread other_thread_2{"OtherThread2"};
5843 other_thread_2.Start();
5844
5845 bool did_complete_task_2 = false;
5846 EXPECT_TRUE(other_thread_2.task_runner()->PostTask(
5847 FROM_HERE, BindLambdaForTesting([&]() {
5848 did_start_task_1.Wait();
5849 EXPECT_TRUE(task_runner()->RunOrPostTask(
5850 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5851 BindLambdaForTesting([&]() { did_complete_task_2 = true; })));
5852 EXPECT_FALSE(did_complete_task_2);
5853 did_post_task_2.Signal();
5854 })));
5855
5856 FlushOtherThread();
5857 EXPECT_FALSE(did_complete_task_2);
5858 RunLoop().RunUntilIdle();
5859 EXPECT_TRUE(did_complete_task_2);
5860 }
5861
5862 // Verify the behavior of `SequenceCheckerImpl` and `ThreadCheckerImpl` in a
5863 // callback that runs synchronously in `RunOrPostTask` on another thread.
TEST_F(SequenceManagerRunOrPostTaskTest,SequenceAndThreadChecker)5864 TEST_F(SequenceManagerRunOrPostTaskTest, SequenceAndThreadChecker) {
5865 SimulateInsideRunLoop();
5866
5867 SequenceCheckerImpl sequence_checker;
5868 ThreadCheckerImpl thread_checker;
5869 std::optional<SequenceCheckerImpl> sequence_checker_bound_in_task;
5870 std::optional<ThreadCheckerImpl> thread_checker_bound_in_task;
5871
5872 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5873 FROM_HERE, BindLambdaForTesting([&]() {
5874 bool did_run = false;
5875
5876 task_runner()->RunOrPostTask(
5877 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5878 BindLambdaForTesting([&]() {
5879 EXPECT_TRUE(sequence_checker.CalledOnValidSequence());
5880 EXPECT_FALSE(thread_checker.CalledOnValidThread());
5881 sequence_checker_bound_in_task.emplace();
5882 thread_checker_bound_in_task.emplace();
5883 EXPECT_TRUE(
5884 sequence_checker_bound_in_task->CalledOnValidSequence());
5885 EXPECT_TRUE(thread_checker_bound_in_task->CalledOnValidThread());
5886 did_run = true;
5887 }));
5888 EXPECT_TRUE(did_run);
5889 EXPECT_FALSE(sequence_checker_bound_in_task->CalledOnValidSequence());
5890 EXPECT_FALSE(thread_checker_bound_in_task->CalledOnValidThread());
5891 })));
5892
5893 FlushOtherThread();
5894 EXPECT_TRUE(sequence_checker_bound_in_task->CalledOnValidSequence());
5895 EXPECT_FALSE(thread_checker_bound_in_task->CalledOnValidThread());
5896 }
5897
5898 // Same as SequenceManagerRunOrPostTaskTest.SequenceAndThreadChecker, but
5899 // `RunOrPostTask()` is invoked from a `ThreadPool` task (i.e. within a
5900 // `TaskScope`).
TEST_F(SequenceManagerRunOrPostTaskTest,SequenceAndThreadCheckerFromThreadPool)5901 TEST_F(SequenceManagerRunOrPostTaskTest,
5902 SequenceAndThreadCheckerFromThreadPool) {
5903 SimulateInsideRunLoop();
5904
5905 SequenceCheckerImpl sequence_checker;
5906 ThreadCheckerImpl thread_checker;
5907 std::optional<SequenceCheckerImpl> sequence_checker_bound_in_task;
5908 std::optional<ThreadCheckerImpl> thread_checker_bound_in_task;
5909
5910 ThreadPoolInstance::Create("TestPool");
5911 ThreadPoolInstance::Get()->Start({/* max_num_foreground_threads_in=*/1});
5912
5913 EXPECT_TRUE(ThreadPool::PostTask(
5914 FROM_HERE, BindLambdaForTesting([&]() {
5915 bool did_run = false;
5916 task_runner()->RunOrPostTask(
5917 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5918 BindLambdaForTesting([&]() {
5919 EXPECT_TRUE(sequence_checker.CalledOnValidSequence());
5920 EXPECT_FALSE(thread_checker.CalledOnValidThread());
5921 sequence_checker_bound_in_task.emplace();
5922 thread_checker_bound_in_task.emplace();
5923 EXPECT_TRUE(
5924 sequence_checker_bound_in_task->CalledOnValidSequence());
5925 EXPECT_TRUE(thread_checker_bound_in_task->CalledOnValidThread());
5926 did_run = true;
5927 }));
5928 EXPECT_TRUE(did_run);
5929 EXPECT_FALSE(sequence_checker_bound_in_task->CalledOnValidSequence());
5930 EXPECT_FALSE(thread_checker_bound_in_task->CalledOnValidThread());
5931 })));
5932
5933 ThreadPoolInstance::Get()->FlushForTesting();
5934 ThreadPoolInstance::Get()->JoinForTesting();
5935 ThreadPoolInstance::Set(nullptr);
5936
5937 EXPECT_TRUE(sequence_checker_bound_in_task->CalledOnValidSequence());
5938 EXPECT_FALSE(thread_checker_bound_in_task->CalledOnValidThread());
5939 }
5940
TEST_F(SequenceManagerRunOrPostTaskTest,CurrentDefaultTaskRunner)5941 TEST_F(SequenceManagerRunOrPostTaskTest, CurrentDefaultTaskRunner) {
5942 SimulateInsideRunLoop();
5943
5944 EXPECT_TRUE(task_runner()->RunsTasksInCurrentSequence());
5945 EXPECT_TRUE(task_runner()->BelongsToCurrentThread());
5946 EXPECT_TRUE(other_task_runner()->RunsTasksInCurrentSequence());
5947 EXPECT_TRUE(other_task_runner()->BelongsToCurrentThread());
5948
5949 EXPECT_TRUE(other_thread_task_runner()->PostTask(
5950 FROM_HERE, BindLambdaForTesting([&]() {
5951 EXPECT_TRUE(SingleThreadTaskRunner::HasCurrentDefault());
5952 EXPECT_EQ(other_thread_task_runner(),
5953 SingleThreadTaskRunner::GetCurrentDefault());
5954 EXPECT_TRUE(SequencedTaskRunner::HasCurrentDefault());
5955 EXPECT_EQ(other_thread_task_runner(),
5956 SequencedTaskRunner::GetCurrentDefault());
5957
5958 EXPECT_FALSE(task_runner()->RunsTasksInCurrentSequence());
5959 EXPECT_FALSE(task_runner()->BelongsToCurrentThread());
5960 EXPECT_FALSE(other_task_runner()->RunsTasksInCurrentSequence());
5961 EXPECT_FALSE(other_task_runner()->BelongsToCurrentThread());
5962
5963 for (auto* tested_task_runner : {task_runner(), other_task_runner()}) {
5964 bool did_run = false;
5965
5966 // The "current default" `SequencedTaskRunner` is the
5967 // `SequenceManager`'s default task runner, irrespective of the task
5968 // runner on which `RunOrPostTask` is called.
5969 tested_task_runner->RunOrPostTask(
5970 subtle::RunOrPostTaskPassKeyForTesting(), FROM_HERE,
5971 BindLambdaForTesting([&]() {
5972 did_run = true;
5973 EXPECT_FALSE(SingleThreadTaskRunner::HasCurrentDefault());
5974 EXPECT_TRUE(SequencedTaskRunner::HasCurrentDefault());
5975 EXPECT_EQ(task_runner(),
5976 SequencedTaskRunner::GetCurrentDefault());
5977
5978 EXPECT_TRUE(task_runner()->RunsTasksInCurrentSequence());
5979 EXPECT_FALSE(task_runner()->BelongsToCurrentThread());
5980 EXPECT_TRUE(other_task_runner()->RunsTasksInCurrentSequence());
5981 EXPECT_FALSE(other_task_runner()->BelongsToCurrentThread());
5982 }));
5983 EXPECT_TRUE(did_run);
5984 }
5985
5986 EXPECT_TRUE(SingleThreadTaskRunner::HasCurrentDefault());
5987 EXPECT_EQ(other_thread_task_runner(),
5988 SingleThreadTaskRunner::GetCurrentDefault());
5989 EXPECT_TRUE(SequencedTaskRunner::HasCurrentDefault());
5990 EXPECT_EQ(other_thread_task_runner(),
5991 SequencedTaskRunner::GetCurrentDefault());
5992 })));
5993
5994 FlushOtherThread();
5995 }
5996
TEST(SequenceManagerTest,CanAccessSingleThreadTaskRunnerCurrentDefaultHandleHandleDuringSequenceLocalStorageSlotDestruction)5997 TEST(
5998 SequenceManagerTest,
5999 CanAccessSingleThreadTaskRunnerCurrentDefaultHandleHandleDuringSequenceLocalStorageSlotDestruction) {
6000 auto sequence_manager =
6001 sequence_manager::CreateSequenceManagerOnCurrentThreadWithPump(
6002 MessagePump::Create(MessagePumpType::DEFAULT));
6003 auto queue = sequence_manager->CreateTaskQueue(
6004 sequence_manager::TaskQueue::Spec(QueueName::DEFAULT_TQ));
6005 sequence_manager->SetDefaultTaskRunner(queue->task_runner());
6006
6007 scoped_refptr<SingleThreadTaskRunner> expected_task_runner =
6008 SingleThreadTaskRunner::GetCurrentDefault();
6009
6010 StrictMock<MockCallback<base::OnceCallback<void()>>> cb;
6011 EXPECT_CALL(cb, Run).WillOnce(testing::Invoke([expected_task_runner]() {
6012 EXPECT_EQ(SingleThreadTaskRunner::GetCurrentDefault(),
6013 expected_task_runner);
6014 }));
6015
6016 static base::SequenceLocalStorageSlot<std::unique_ptr<DestructionCallback>>
6017 storage_slot;
6018 storage_slot.GetOrCreateValue() =
6019 std::make_unique<DestructionCallback>(cb.Get());
6020
6021 queue.reset();
6022 sequence_manager.reset();
6023 }
6024
TEST(SequenceManagerTest,BindOnDifferentThreadWithActiveVoters)6025 TEST(SequenceManagerTest, BindOnDifferentThreadWithActiveVoters) {
6026 auto sequence_manager = CreateUnboundSequenceManager();
6027 auto queue =
6028 sequence_manager->CreateTaskQueue(TaskQueue::Spec(QueueName::TEST_TQ));
6029 auto voter = queue->CreateQueueEnabledVoter();
6030 {
6031 // Create a second voter that gets destroyed while unbound.
6032 auto voter2 = queue->CreateQueueEnabledVoter();
6033 }
6034
6035 voter->SetVoteToEnable(false);
6036 EXPECT_FALSE(queue->IsQueueEnabled());
6037
6038 std::vector<bool> results;
6039 WaitableEvent done_event;
6040 Thread thread("TestThread");
6041 thread.Start();
6042 auto task = BindLambdaForTesting([&]() {
6043 // Move `voter` so it gets destroyed on the bound thread.
6044 auto scoped_voter = std::move(voter);
6045 // Bind `sequence_manager` to this thread.
6046 auto scoped_mgr = std::move(sequence_manager);
6047 scoped_mgr->BindToCurrentThread();
6048
6049 results.push_back(queue->IsQueueEnabled());
6050 scoped_voter->SetVoteToEnable(true);
6051 results.push_back(queue->IsQueueEnabled());
6052 done_event.Signal();
6053 });
6054 thread.task_runner()->PostTask(FROM_HERE, std::move(task));
6055 done_event.Wait();
6056 thread.Stop();
6057 EXPECT_THAT(results, ElementsAre(false, true));
6058 }
6059
6060 } // namespace internal
6061 } // namespace sequence_manager
6062 } // namespace base
6063