OLD | NEW |
---|---|
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "base/threading/post_task_and_reply_impl.h" | 5 #include "base/threading/post_task_and_reply_impl.h" |
6 | 6 |
7 #include <utility> | 7 #include <utility> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
11 #include "base/macros.h" | 11 #include "base/macros.h" |
12 #include "base/memory/ref_counted.h" | 12 #include "base/memory/ref_counted.h" |
13 #include "base/single_thread_task_runner.h" | |
13 #include "base/test/test_simple_task_runner.h" | 14 #include "base/test/test_simple_task_runner.h" |
14 #include "base/threading/thread_task_runner_handle.h" | 15 #include "base/threading/thread_task_runner_handle.h" |
15 #include "testing/gmock/include/gmock/gmock.h" | 16 #include "testing/gmock/include/gmock/gmock.h" |
16 #include "testing/gtest/include/gtest/gtest.h" | 17 #include "testing/gtest/include/gtest/gtest.h" |
17 | 18 |
18 using ::testing::_; | 19 using ::testing::_; |
19 | 20 |
20 namespace base { | 21 namespace base { |
21 namespace internal { | 22 namespace internal { |
22 | 23 |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
64 EXPECT_TRUE(*delete_flag); | 65 EXPECT_TRUE(*delete_flag); |
65 ReplyMock(); | 66 ReplyMock(); |
66 } | 67 } |
67 | 68 |
68 MOCK_METHOD0(ReplyMock, void()); | 69 MOCK_METHOD0(ReplyMock, void()); |
69 | 70 |
70 private: | 71 private: |
71 DISALLOW_COPY_AND_ASSIGN(MockObject); | 72 DISALLOW_COPY_AND_ASSIGN(MockObject); |
72 }; | 73 }; |
73 | 74 |
75 class WrappedTaskRunner : public SingleThreadTaskRunner { | |
gab
2017/03/29 18:21:35
Hmmm sorry I wasn't clear, I didn't mean to make t
tzik
2017/03/30 09:01:18
Ah, sorry for confusion. Updated the test.
| |
76 public: | |
77 explicit WrappedTaskRunner( | |
78 scoped_refptr<SingleThreadTaskRunner> underlying_task_runner) | |
79 : underlying_task_runner_(std::move(underlying_task_runner)) {} | |
80 | |
81 bool PostDelayedTask(const tracked_objects::Location& from_here, | |
82 Closure task, | |
83 base::TimeDelta delay) override { | |
84 if (post_task_hook_) | |
85 std::move(post_task_hook_).Run(); | |
86 return underlying_task_runner_->PostDelayedTask(from_here, std::move(task), | |
87 delay); | |
88 } | |
89 | |
90 bool PostNonNestableDelayedTask(const tracked_objects::Location& from_here, | |
91 Closure task, | |
92 base::TimeDelta delay) override { | |
93 if (post_task_hook_) | |
94 std::move(post_task_hook_).Run(); | |
95 return underlying_task_runner_->PostNonNestableDelayedTask( | |
96 from_here, std::move(task), delay); | |
97 } | |
98 | |
99 void set_post_task_hook(OnceClosure hook) { | |
100 post_task_hook_ = std::move(hook); | |
101 } | |
102 | |
103 bool has_post_task_hook() const { return !post_task_hook_.is_null(); } | |
104 | |
105 bool RunsTasksOnCurrentThread() const override { | |
106 return underlying_task_runner_->RunsTasksOnCurrentThread(); | |
107 } | |
108 | |
109 private: | |
110 ~WrappedTaskRunner() override {} | |
111 | |
112 scoped_refptr<SingleThreadTaskRunner> underlying_task_runner_; | |
113 OnceClosure post_task_hook_; | |
114 | |
115 DISALLOW_COPY_AND_ASSIGN(WrappedTaskRunner); | |
116 }; | |
117 | |
74 } // namespace | 118 } // namespace |
75 | 119 |
76 TEST(PostTaskAndReplyImplTest, PostTaskAndReply) { | 120 TEST(PostTaskAndReplyImplTest, PostTaskAndReply) { |
77 scoped_refptr<TestSimpleTaskRunner> post_runner(new TestSimpleTaskRunner); | 121 scoped_refptr<TestSimpleTaskRunner> post_runner(new TestSimpleTaskRunner); |
78 scoped_refptr<TestSimpleTaskRunner> reply_runner(new TestSimpleTaskRunner); | 122 scoped_refptr<TestSimpleTaskRunner> reply_runner(new TestSimpleTaskRunner); |
79 ThreadTaskRunnerHandle task_runner_handle(reply_runner); | 123 scoped_refptr<WrappedTaskRunner> wrapped_reply_runner( |
124 new WrappedTaskRunner(reply_runner)); | |
125 ThreadTaskRunnerHandle task_runner_handle(wrapped_reply_runner); | |
80 | 126 |
81 testing::StrictMock<MockObject> mock_object; | 127 testing::StrictMock<MockObject> mock_object; |
82 bool delete_flag = false; | 128 bool delete_flag = false; |
83 | 129 |
130 auto expect_true = [](bool* delete_flag) { EXPECT_TRUE(*delete_flag); }; | |
131 | |
132 // Expect the posted callback is destroyed before the reply task is scheduled. | |
133 wrapped_reply_runner->set_post_task_hook( | |
134 base::BindOnce(expect_true, &delete_flag)); | |
135 | |
84 EXPECT_TRUE( | 136 EXPECT_TRUE( |
85 PostTaskAndReplyTaskRunner(post_runner.get()) | 137 PostTaskAndReplyTaskRunner(post_runner.get()) |
86 .PostTaskAndReply( | 138 .PostTaskAndReply( |
87 FROM_HERE, | 139 FROM_HERE, |
88 Bind(&MockObject::Task, Unretained(&mock_object), | 140 Bind(&MockObject::Task, Unretained(&mock_object), |
89 make_scoped_refptr(new ObjectToDelete(&delete_flag))), | 141 make_scoped_refptr(new ObjectToDelete(&delete_flag))), |
90 Bind(&MockObject::Reply, Unretained(&mock_object), | 142 Bind(&MockObject::Reply, Unretained(&mock_object), |
91 Unretained(&delete_flag)))); | 143 Unretained(&delete_flag)))); |
92 | 144 |
93 // Expect no reply in |reply_runner|. | 145 // Expect no reply in |reply_runner|. |
94 EXPECT_FALSE(reply_runner->HasPendingTask()); | 146 EXPECT_FALSE(reply_runner->HasPendingTask()); |
95 | 147 |
96 // Expect the task to be posted to |post_runner|. | 148 // Expect the task to be posted to |post_runner|. |
97 EXPECT_TRUE(post_runner->HasPendingTask()); | 149 EXPECT_TRUE(post_runner->HasPendingTask()); |
98 EXPECT_CALL(mock_object, Task(_)); | 150 EXPECT_CALL(mock_object, Task(_)); |
99 post_runner->RunUntilIdle(); | 151 post_runner->RunUntilIdle(); |
100 testing::Mock::VerifyAndClear(&mock_object); | 152 testing::Mock::VerifyAndClear(&mock_object); |
101 | 153 |
102 // Expect the task's argument not to have been deleted yet. | 154 // Expect the task's argument to have been deleted. |
103 EXPECT_FALSE(delete_flag); | 155 EXPECT_FALSE(wrapped_reply_runner->has_post_task_hook()); |
156 EXPECT_TRUE(delete_flag); | |
104 | 157 |
105 // Expect the reply to be posted to |reply_runner|. | 158 // Expect the reply to be posted to |reply_runner|. |
106 EXPECT_FALSE(post_runner->HasPendingTask()); | 159 EXPECT_FALSE(post_runner->HasPendingTask()); |
107 EXPECT_TRUE(reply_runner->HasPendingTask()); | 160 EXPECT_TRUE(reply_runner->HasPendingTask()); |
108 EXPECT_CALL(mock_object, ReplyMock()); | 161 EXPECT_CALL(mock_object, ReplyMock()); |
109 reply_runner->RunUntilIdle(); | 162 reply_runner->RunUntilIdle(); |
110 testing::Mock::VerifyAndClear(&mock_object); | 163 testing::Mock::VerifyAndClear(&mock_object); |
111 EXPECT_TRUE(delete_flag); | 164 EXPECT_TRUE(delete_flag); |
112 | 165 |
113 // Expect no pending task in |post_runner| and |reply_runner|. | 166 // Expect no pending task in |post_runner| and |reply_runner|. |
114 EXPECT_FALSE(post_runner->HasPendingTask()); | 167 EXPECT_FALSE(post_runner->HasPendingTask()); |
115 EXPECT_FALSE(reply_runner->HasPendingTask()); | 168 EXPECT_FALSE(reply_runner->HasPendingTask()); |
116 } | 169 } |
117 | 170 |
118 } // namespace internal | 171 } // namespace internal |
119 } // namespace base | 172 } // namespace base |
OLD | NEW |