1*6777b538SAndroid Build Coastguard Worker // Copyright 2012 The Chromium Authors
2*6777b538SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
3*6777b538SAndroid Build Coastguard Worker // found in the LICENSE file.
4*6777b538SAndroid Build Coastguard Worker
5*6777b538SAndroid Build Coastguard Worker #include "net/quic/test_task_runner.h"
6*6777b538SAndroid Build Coastguard Worker
7*6777b538SAndroid Build Coastguard Worker #include <algorithm>
8*6777b538SAndroid Build Coastguard Worker #include <utility>
9*6777b538SAndroid Build Coastguard Worker
10*6777b538SAndroid Build Coastguard Worker #include "base/time/time.h"
11*6777b538SAndroid Build Coastguard Worker #include "net/third_party/quiche/src/quiche/quic/test_tools/mock_clock.h"
12*6777b538SAndroid Build Coastguard Worker #include "testing/gtest/include/gtest/gtest.h"
13*6777b538SAndroid Build Coastguard Worker
14*6777b538SAndroid Build Coastguard Worker namespace net::test {
15*6777b538SAndroid Build Coastguard Worker
16*6777b538SAndroid Build Coastguard Worker namespace {
17*6777b538SAndroid Build Coastguard Worker
NowInTicks(const quic::MockClock & clock)18*6777b538SAndroid Build Coastguard Worker base::TimeTicks NowInTicks(const quic::MockClock& clock) {
19*6777b538SAndroid Build Coastguard Worker base::TimeTicks ticks;
20*6777b538SAndroid Build Coastguard Worker return ticks + base::Microseconds(
21*6777b538SAndroid Build Coastguard Worker (clock.Now() - quic::QuicTime::Zero()).ToMicroseconds());
22*6777b538SAndroid Build Coastguard Worker }
23*6777b538SAndroid Build Coastguard Worker
24*6777b538SAndroid Build Coastguard Worker } // namespace
25*6777b538SAndroid Build Coastguard Worker
TestTaskRunner(quic::MockClock * clock)26*6777b538SAndroid Build Coastguard Worker TestTaskRunner::TestTaskRunner(quic::MockClock* clock) : clock_(clock) {}
27*6777b538SAndroid Build Coastguard Worker
28*6777b538SAndroid Build Coastguard Worker TestTaskRunner::~TestTaskRunner() = default;
29*6777b538SAndroid Build Coastguard Worker
PostDelayedTask(const base::Location & from_here,base::OnceClosure task,base::TimeDelta delay)30*6777b538SAndroid Build Coastguard Worker bool TestTaskRunner::PostDelayedTask(const base::Location& from_here,
31*6777b538SAndroid Build Coastguard Worker base::OnceClosure task,
32*6777b538SAndroid Build Coastguard Worker base::TimeDelta delay) {
33*6777b538SAndroid Build Coastguard Worker EXPECT_GE(delay, base::TimeDelta());
34*6777b538SAndroid Build Coastguard Worker tasks_.emplace_back(from_here, std::move(task), NowInTicks(*clock_), delay,
35*6777b538SAndroid Build Coastguard Worker base::TestPendingTask::NESTABLE);
36*6777b538SAndroid Build Coastguard Worker return true;
37*6777b538SAndroid Build Coastguard Worker }
38*6777b538SAndroid Build Coastguard Worker
PostNonNestableDelayedTask(const base::Location & from_here,base::OnceClosure task,base::TimeDelta delay)39*6777b538SAndroid Build Coastguard Worker bool TestTaskRunner::PostNonNestableDelayedTask(const base::Location& from_here,
40*6777b538SAndroid Build Coastguard Worker base::OnceClosure task,
41*6777b538SAndroid Build Coastguard Worker base::TimeDelta delay) {
42*6777b538SAndroid Build Coastguard Worker return PostDelayedTask(from_here, std::move(task), delay);
43*6777b538SAndroid Build Coastguard Worker }
44*6777b538SAndroid Build Coastguard Worker
RunsTasksInCurrentSequence() const45*6777b538SAndroid Build Coastguard Worker bool TestTaskRunner::RunsTasksInCurrentSequence() const {
46*6777b538SAndroid Build Coastguard Worker return true;
47*6777b538SAndroid Build Coastguard Worker }
48*6777b538SAndroid Build Coastguard Worker
GetPostedTasks() const49*6777b538SAndroid Build Coastguard Worker const std::vector<PostedTask>& TestTaskRunner::GetPostedTasks() const {
50*6777b538SAndroid Build Coastguard Worker return tasks_;
51*6777b538SAndroid Build Coastguard Worker }
52*6777b538SAndroid Build Coastguard Worker
NextPendingTaskDelay()53*6777b538SAndroid Build Coastguard Worker quic::QuicTime::Delta TestTaskRunner::NextPendingTaskDelay() {
54*6777b538SAndroid Build Coastguard Worker if (tasks_.empty())
55*6777b538SAndroid Build Coastguard Worker return quic::QuicTime::Delta::Infinite();
56*6777b538SAndroid Build Coastguard Worker
57*6777b538SAndroid Build Coastguard Worker auto next = FindNextTask();
58*6777b538SAndroid Build Coastguard Worker return quic::QuicTime::Delta::FromMicroseconds(
59*6777b538SAndroid Build Coastguard Worker (next->GetTimeToRun() - NowInTicks(*clock_)).InMicroseconds());
60*6777b538SAndroid Build Coastguard Worker }
61*6777b538SAndroid Build Coastguard Worker
RunNextTask()62*6777b538SAndroid Build Coastguard Worker void TestTaskRunner::RunNextTask() {
63*6777b538SAndroid Build Coastguard Worker auto next = FindNextTask();
64*6777b538SAndroid Build Coastguard Worker DCHECK(next != tasks_.end());
65*6777b538SAndroid Build Coastguard Worker clock_->AdvanceTime(quic::QuicTime::Delta::FromMicroseconds(
66*6777b538SAndroid Build Coastguard Worker (next->GetTimeToRun() - NowInTicks(*clock_)).InMicroseconds()));
67*6777b538SAndroid Build Coastguard Worker PostedTask task = std::move(*next);
68*6777b538SAndroid Build Coastguard Worker tasks_.erase(next);
69*6777b538SAndroid Build Coastguard Worker std::move(task.task).Run();
70*6777b538SAndroid Build Coastguard Worker }
71*6777b538SAndroid Build Coastguard Worker
FastForwardBy(quic::QuicTime::Delta delta)72*6777b538SAndroid Build Coastguard Worker void TestTaskRunner::FastForwardBy(quic::QuicTime::Delta delta) {
73*6777b538SAndroid Build Coastguard Worker DCHECK_GE(delta, quic::QuicTime::Delta::Zero());
74*6777b538SAndroid Build Coastguard Worker
75*6777b538SAndroid Build Coastguard Worker quic::QuicTime end_timestamp = clock_->Now() + delta;
76*6777b538SAndroid Build Coastguard Worker
77*6777b538SAndroid Build Coastguard Worker while (NextPendingTaskDelay() <= end_timestamp - clock_->Now()) {
78*6777b538SAndroid Build Coastguard Worker RunNextTask();
79*6777b538SAndroid Build Coastguard Worker }
80*6777b538SAndroid Build Coastguard Worker
81*6777b538SAndroid Build Coastguard Worker if (clock_->Now() != end_timestamp)
82*6777b538SAndroid Build Coastguard Worker clock_->AdvanceTime(end_timestamp - clock_->Now());
83*6777b538SAndroid Build Coastguard Worker
84*6777b538SAndroid Build Coastguard Worker while (NextPendingTaskDelay() <= quic::QuicTime::Delta::Zero()) {
85*6777b538SAndroid Build Coastguard Worker RunNextTask();
86*6777b538SAndroid Build Coastguard Worker }
87*6777b538SAndroid Build Coastguard Worker return;
88*6777b538SAndroid Build Coastguard Worker }
89*6777b538SAndroid Build Coastguard Worker
RunUntilIdle()90*6777b538SAndroid Build Coastguard Worker void TestTaskRunner::RunUntilIdle() {
91*6777b538SAndroid Build Coastguard Worker while (!tasks_.empty())
92*6777b538SAndroid Build Coastguard Worker RunNextTask();
93*6777b538SAndroid Build Coastguard Worker }
94*6777b538SAndroid Build Coastguard Worker namespace {
95*6777b538SAndroid Build Coastguard Worker
96*6777b538SAndroid Build Coastguard Worker struct ShouldRunBeforeLessThan {
operator ()net::test::__anonf98dfd770211::ShouldRunBeforeLessThan97*6777b538SAndroid Build Coastguard Worker bool operator()(const PostedTask& task1, const PostedTask& task2) const {
98*6777b538SAndroid Build Coastguard Worker return task1.ShouldRunBefore(task2);
99*6777b538SAndroid Build Coastguard Worker }
100*6777b538SAndroid Build Coastguard Worker };
101*6777b538SAndroid Build Coastguard Worker
102*6777b538SAndroid Build Coastguard Worker } // namespace
103*6777b538SAndroid Build Coastguard Worker
FindNextTask()104*6777b538SAndroid Build Coastguard Worker std::vector<PostedTask>::iterator TestTaskRunner::FindNextTask() {
105*6777b538SAndroid Build Coastguard Worker return std::min_element(tasks_.begin(), tasks_.end(),
106*6777b538SAndroid Build Coastguard Worker ShouldRunBeforeLessThan());
107*6777b538SAndroid Build Coastguard Worker }
108*6777b538SAndroid Build Coastguard Worker
109*6777b538SAndroid Build Coastguard Worker } // namespace net::test
110