Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(314)

Side by Side Diff: base/message_loop_unittest.cc

Issue 10479018: Add base::RunLoop and update ui_test_utils to use it to reduce flakiness (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: jar feedback, compile errors Created 8 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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 <vector> 5 #include <vector>
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/bind_helpers.h" 8 #include "base/bind_helpers.h"
9 #include "base/compiler_specific.h" 9 #include "base/compiler_specific.h"
10 #include "base/eintr_wrapper.h" 10 #include "base/eintr_wrapper.h"
11 #include "base/logging.h" 11 #include "base/logging.h"
12 #include "base/memory/ref_counted.h" 12 #include "base/memory/ref_counted.h"
13 #include "base/message_loop.h" 13 #include "base/message_loop.h"
14 #include "base/run_loop.h"
14 #include "base/thread_task_runner_handle.h" 15 #include "base/thread_task_runner_handle.h"
15 #include "base/threading/platform_thread.h" 16 #include "base/threading/platform_thread.h"
16 #include "base/threading/thread.h" 17 #include "base/threading/thread.h"
17 #include "testing/gtest/include/gtest/gtest.h" 18 #include "testing/gtest/include/gtest/gtest.h"
18 19
19 #if defined(OS_WIN) 20 #if defined(OS_WIN)
20 #include "base/message_pump_win.h" 21 #include "base/message_pump_win.h"
21 #include "base/win/scoped_handle.h" 22 #include "base/win/scoped_handle.h"
22 #endif 23 #endif
23 24
(...skipping 568 matching lines...) Expand 10 before | Expand all | Expand 10 after
592 } 593 }
593 594
594 const wchar_t* const kMessageBoxTitle = L"MessageLoop Unit Test"; 595 const wchar_t* const kMessageBoxTitle = L"MessageLoop Unit Test";
595 596
596 enum TaskType { 597 enum TaskType {
597 MESSAGEBOX, 598 MESSAGEBOX,
598 ENDDIALOG, 599 ENDDIALOG,
599 RECURSIVE, 600 RECURSIVE,
600 TIMEDMESSAGELOOP, 601 TIMEDMESSAGELOOP,
601 QUITMESSAGELOOP, 602 QUITMESSAGELOOP,
602 ORDERERD, 603 ORDERED,
603 PUMPS, 604 PUMPS,
604 SLEEP, 605 SLEEP,
606 RUNS,
605 }; 607 };
606 608
607 // Saves the order in which the tasks executed. 609 // Saves the order in which the tasks executed.
608 struct TaskItem { 610 struct TaskItem {
609 TaskItem(TaskType t, int c, bool s) 611 TaskItem(TaskType t, int c, bool s)
610 : type(t), 612 : type(t),
611 cookie(c), 613 cookie(c),
612 start(s) { 614 start(s) {
613 } 615 }
614 616
615 TaskType type; 617 TaskType type;
616 int cookie; 618 int cookie;
617 bool start; 619 bool start;
618 620
619 bool operator == (const TaskItem& other) const { 621 bool operator == (const TaskItem& other) const {
620 return type == other.type && cookie == other.cookie && start == other.start; 622 return type == other.type && cookie == other.cookie && start == other.start;
621 } 623 }
622 }; 624 };
623 625
624 std::ostream& operator <<(std::ostream& os, TaskType type) { 626 std::ostream& operator <<(std::ostream& os, TaskType type) {
625 switch (type) { 627 switch (type) {
626 case MESSAGEBOX: os << "MESSAGEBOX"; break; 628 case MESSAGEBOX: os << "MESSAGEBOX"; break;
627 case ENDDIALOG: os << "ENDDIALOG"; break; 629 case ENDDIALOG: os << "ENDDIALOG"; break;
628 case RECURSIVE: os << "RECURSIVE"; break; 630 case RECURSIVE: os << "RECURSIVE"; break;
629 case TIMEDMESSAGELOOP: os << "TIMEDMESSAGELOOP"; break; 631 case TIMEDMESSAGELOOP: os << "TIMEDMESSAGELOOP"; break;
630 case QUITMESSAGELOOP: os << "QUITMESSAGELOOP"; break; 632 case QUITMESSAGELOOP: os << "QUITMESSAGELOOP"; break;
631 case ORDERERD: os << "ORDERERD"; break; 633 case ORDERED: os << "ORDERED"; break;
632 case PUMPS: os << "PUMPS"; break; 634 case PUMPS: os << "PUMPS"; break;
633 case SLEEP: os << "SLEEP"; break; 635 case SLEEP: os << "SLEEP"; break;
634 default: 636 default:
635 NOTREACHED(); 637 NOTREACHED();
636 os << "Unknown TaskType"; 638 os << "Unknown TaskType";
637 break; 639 break;
638 } 640 }
639 return os; 641 return os;
640 } 642 }
641 643
(...skipping 25 matching lines...) Expand all
667 TaskItem Get(int n) { 669 TaskItem Get(int n) {
668 return task_list_[n]; 670 return task_list_[n];
669 } 671 }
670 672
671 private: 673 private:
672 std::vector<TaskItem> task_list_; 674 std::vector<TaskItem> task_list_;
673 }; 675 };
674 676
675 // Saves the order the tasks ran. 677 // Saves the order the tasks ran.
676 void OrderedFunc(TaskList* order, int cookie) { 678 void OrderedFunc(TaskList* order, int cookie) {
677 order->RecordStart(ORDERERD, cookie); 679 order->RecordStart(ORDERED, cookie);
678 order->RecordEnd(ORDERERD, cookie); 680 order->RecordEnd(ORDERED, cookie);
679 } 681 }
680 682
681 #if defined(OS_WIN) 683 #if defined(OS_WIN)
682 684
683 // MessageLoop implicitly start a "modal message loop". Modal dialog boxes, 685 // MessageLoop implicitly start a "modal message loop". Modal dialog boxes,
684 // common controls (like OpenFile) and StartDoc printing function can cause 686 // common controls (like OpenFile) and StartDoc printing function can cause
685 // implicit message loops. 687 // implicit message loops.
686 void MessageBoxFunc(TaskList* order, int cookie, bool is_reentrant) { 688 void MessageBoxFunc(TaskList* order, int cookie, bool is_reentrant) {
687 order->RecordStart(MESSAGEBOX, cookie); 689 order->RecordStart(MESSAGEBOX, cookie);
688 if (is_reentrant) 690 if (is_reentrant)
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after
840 MessageLoop::current()->Run(); 842 MessageLoop::current()->Run();
841 843
842 // FIFO order. 844 // FIFO order.
843 ASSERT_EQ(16U, order.Size()); 845 ASSERT_EQ(16U, order.Size());
844 EXPECT_EQ(order.Get(0), TaskItem(RECURSIVE, 1, true)); 846 EXPECT_EQ(order.Get(0), TaskItem(RECURSIVE, 1, true));
845 EXPECT_EQ(order.Get(1), TaskItem(RECURSIVE, 1, false)); 847 EXPECT_EQ(order.Get(1), TaskItem(RECURSIVE, 1, false));
846 EXPECT_EQ(order.Get(2), TaskItem(RECURSIVE, 2, true)); 848 EXPECT_EQ(order.Get(2), TaskItem(RECURSIVE, 2, true));
847 EXPECT_EQ(order.Get(3), TaskItem(RECURSIVE, 2, false)); 849 EXPECT_EQ(order.Get(3), TaskItem(RECURSIVE, 2, false));
848 EXPECT_EQ(order.Get(4), TaskItem(RECURSIVE, 1, true)); 850 EXPECT_EQ(order.Get(4), TaskItem(RECURSIVE, 1, true));
849 EXPECT_EQ(order.Get(5), TaskItem(RECURSIVE, 1, false)); 851 EXPECT_EQ(order.Get(5), TaskItem(RECURSIVE, 1, false));
850 EXPECT_EQ(order.Get(6), TaskItem(ORDERERD, 3, true)); 852 EXPECT_EQ(order.Get(6), TaskItem(ORDERED, 3, true));
851 EXPECT_EQ(order.Get(7), TaskItem(ORDERERD, 3, false)); 853 EXPECT_EQ(order.Get(7), TaskItem(ORDERED, 3, false));
852 EXPECT_EQ(order.Get(8), TaskItem(RECURSIVE, 2, true)); 854 EXPECT_EQ(order.Get(8), TaskItem(RECURSIVE, 2, true));
853 EXPECT_EQ(order.Get(9), TaskItem(RECURSIVE, 2, false)); 855 EXPECT_EQ(order.Get(9), TaskItem(RECURSIVE, 2, false));
854 EXPECT_EQ(order.Get(10), TaskItem(QUITMESSAGELOOP, 4, true)); 856 EXPECT_EQ(order.Get(10), TaskItem(QUITMESSAGELOOP, 4, true));
855 EXPECT_EQ(order.Get(11), TaskItem(QUITMESSAGELOOP, 4, false)); 857 EXPECT_EQ(order.Get(11), TaskItem(QUITMESSAGELOOP, 4, false));
856 EXPECT_EQ(order.Get(12), TaskItem(RECURSIVE, 1, true)); 858 EXPECT_EQ(order.Get(12), TaskItem(RECURSIVE, 1, true));
857 EXPECT_EQ(order.Get(13), TaskItem(RECURSIVE, 1, false)); 859 EXPECT_EQ(order.Get(13), TaskItem(RECURSIVE, 1, false));
858 EXPECT_EQ(order.Get(14), TaskItem(RECURSIVE, 2, true)); 860 EXPECT_EQ(order.Get(14), TaskItem(RECURSIVE, 2, true));
859 EXPECT_EQ(order.Get(15), TaskItem(RECURSIVE, 2, false)); 861 EXPECT_EQ(order.Get(15), TaskItem(RECURSIVE, 2, false));
860 } 862 }
861 863
(...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after
990 992
991 void FuncThatPumps(TaskList* order, int cookie) { 993 void FuncThatPumps(TaskList* order, int cookie) {
992 order->RecordStart(PUMPS, cookie); 994 order->RecordStart(PUMPS, cookie);
993 { 995 {
994 MessageLoop::ScopedNestableTaskAllower allow(MessageLoop::current()); 996 MessageLoop::ScopedNestableTaskAllower allow(MessageLoop::current());
995 MessageLoop::current()->RunAllPending(); 997 MessageLoop::current()->RunAllPending();
996 } 998 }
997 order->RecordEnd(PUMPS, cookie); 999 order->RecordEnd(PUMPS, cookie);
998 } 1000 }
999 1001
1002 void FuncThatRuns(TaskList* order, int cookie,
1003 base::WeakPtr<base::RunLoop> run_loop) {
1004 order->RecordStart(RUNS, cookie);
1005 {
1006 MessageLoop::ScopedNestableTaskAllower allow(MessageLoop::current());
1007 run_loop->Run();
1008 }
1009 order->RecordEnd(RUNS, cookie);
1010 }
1011
1012 void FuncThatQuitsNow() {
1013 MessageLoop::current()->QuitNow();
1014 }
1015
1000 // Tests that non nestable tasks run in FIFO if there are no nested loops. 1016 // Tests that non nestable tasks run in FIFO if there are no nested loops.
1001 void RunTest_NonNestableWithNoNesting( 1017 void RunTest_NonNestableWithNoNesting(
1002 MessageLoop::Type message_loop_type) { 1018 MessageLoop::Type message_loop_type) {
1003 MessageLoop loop(message_loop_type); 1019 MessageLoop loop(message_loop_type);
1004 1020
1005 TaskList order; 1021 TaskList order;
1006 1022
1007 MessageLoop::current()->PostNonNestableTask( 1023 MessageLoop::current()->PostNonNestableTask(
1008 FROM_HERE, 1024 FROM_HERE,
1009 base::Bind(&OrderedFunc, &order, 1)); 1025 base::Bind(&OrderedFunc, &order, 1));
1010 MessageLoop::current()->PostTask(FROM_HERE, 1026 MessageLoop::current()->PostTask(FROM_HERE,
1011 base::Bind(&OrderedFunc, &order, 2)); 1027 base::Bind(&OrderedFunc, &order, 2));
1012 MessageLoop::current()->PostTask(FROM_HERE, 1028 MessageLoop::current()->PostTask(FROM_HERE,
1013 base::Bind(&QuitFunc, &order, 3)); 1029 base::Bind(&QuitFunc, &order, 3));
1014 MessageLoop::current()->Run(); 1030 MessageLoop::current()->Run();
1015 1031
1016 // FIFO order. 1032 // FIFO order.
1017 ASSERT_EQ(6U, order.Size()); 1033 ASSERT_EQ(6U, order.Size());
1018 EXPECT_EQ(order.Get(0), TaskItem(ORDERERD, 1, true)); 1034 EXPECT_EQ(order.Get(0), TaskItem(ORDERED, 1, true));
1019 EXPECT_EQ(order.Get(1), TaskItem(ORDERERD, 1, false)); 1035 EXPECT_EQ(order.Get(1), TaskItem(ORDERED, 1, false));
1020 EXPECT_EQ(order.Get(2), TaskItem(ORDERERD, 2, true)); 1036 EXPECT_EQ(order.Get(2), TaskItem(ORDERED, 2, true));
1021 EXPECT_EQ(order.Get(3), TaskItem(ORDERERD, 2, false)); 1037 EXPECT_EQ(order.Get(3), TaskItem(ORDERED, 2, false));
1022 EXPECT_EQ(order.Get(4), TaskItem(QUITMESSAGELOOP, 3, true)); 1038 EXPECT_EQ(order.Get(4), TaskItem(QUITMESSAGELOOP, 3, true));
1023 EXPECT_EQ(order.Get(5), TaskItem(QUITMESSAGELOOP, 3, false)); 1039 EXPECT_EQ(order.Get(5), TaskItem(QUITMESSAGELOOP, 3, false));
1024 } 1040 }
1025 1041
1026 // Tests that non nestable tasks don't run when there's code in the call stack. 1042 // Tests that non nestable tasks don't run when there's code in the call stack.
1027 void RunTest_NonNestableInNestedLoop(MessageLoop::Type message_loop_type, 1043 void RunTest_NonNestableInNestedLoop(MessageLoop::Type message_loop_type,
1028 bool use_delayed) { 1044 bool use_delayed) {
1029 MessageLoop loop(message_loop_type); 1045 MessageLoop loop(message_loop_type);
1030 1046
1031 TaskList order; 1047 TaskList order;
(...skipping 27 matching lines...) Expand all
1059 MessageLoop::current()->PostNonNestableTask( 1075 MessageLoop::current()->PostNonNestableTask(
1060 FROM_HERE, 1076 FROM_HERE,
1061 base::Bind(&QuitFunc, &order, 6)); 1077 base::Bind(&QuitFunc, &order, 6));
1062 } 1078 }
1063 1079
1064 MessageLoop::current()->Run(); 1080 MessageLoop::current()->Run();
1065 1081
1066 // FIFO order. 1082 // FIFO order.
1067 ASSERT_EQ(12U, order.Size()); 1083 ASSERT_EQ(12U, order.Size());
1068 EXPECT_EQ(order.Get(0), TaskItem(PUMPS, 1, true)); 1084 EXPECT_EQ(order.Get(0), TaskItem(PUMPS, 1, true));
1069 EXPECT_EQ(order.Get(1), TaskItem(ORDERERD, 3, true)); 1085 EXPECT_EQ(order.Get(1), TaskItem(ORDERED, 3, true));
1070 EXPECT_EQ(order.Get(2), TaskItem(ORDERERD, 3, false)); 1086 EXPECT_EQ(order.Get(2), TaskItem(ORDERED, 3, false));
1071 EXPECT_EQ(order.Get(3), TaskItem(SLEEP, 4, true)); 1087 EXPECT_EQ(order.Get(3), TaskItem(SLEEP, 4, true));
1072 EXPECT_EQ(order.Get(4), TaskItem(SLEEP, 4, false)); 1088 EXPECT_EQ(order.Get(4), TaskItem(SLEEP, 4, false));
1073 EXPECT_EQ(order.Get(5), TaskItem(ORDERERD, 5, true)); 1089 EXPECT_EQ(order.Get(5), TaskItem(ORDERED, 5, true));
1074 EXPECT_EQ(order.Get(6), TaskItem(ORDERERD, 5, false)); 1090 EXPECT_EQ(order.Get(6), TaskItem(ORDERED, 5, false));
1075 EXPECT_EQ(order.Get(7), TaskItem(PUMPS, 1, false)); 1091 EXPECT_EQ(order.Get(7), TaskItem(PUMPS, 1, false));
1076 EXPECT_EQ(order.Get(8), TaskItem(ORDERERD, 2, true)); 1092 EXPECT_EQ(order.Get(8), TaskItem(ORDERED, 2, true));
1077 EXPECT_EQ(order.Get(9), TaskItem(ORDERERD, 2, false)); 1093 EXPECT_EQ(order.Get(9), TaskItem(ORDERED, 2, false));
1078 EXPECT_EQ(order.Get(10), TaskItem(QUITMESSAGELOOP, 6, true)); 1094 EXPECT_EQ(order.Get(10), TaskItem(QUITMESSAGELOOP, 6, true));
1079 EXPECT_EQ(order.Get(11), TaskItem(QUITMESSAGELOOP, 6, false)); 1095 EXPECT_EQ(order.Get(11), TaskItem(QUITMESSAGELOOP, 6, false));
1080 } 1096 }
1081 1097
1098 // Tests RunLoopQuit only quits the corresponding MessageLoop::Run.
1099 void RunTest_QuitNow(MessageLoop::Type message_loop_type) {
1100 MessageLoop loop(message_loop_type);
1101
1102 TaskList order;
1103
1104 base::RunLoop run_loop;
1105
1106 MessageLoop::current()->PostTask(
1107 FROM_HERE, base::Bind(&FuncThatRuns, &order, 1, run_loop.AsWeakPtr()));
1108 MessageLoop::current()->PostTask(
1109 FROM_HERE, base::Bind(&OrderedFunc, &order, 2));
1110 MessageLoop::current()->PostTask(
1111 FROM_HERE, base::Bind(&FuncThatQuitsNow));
1112 MessageLoop::current()->PostTask(
1113 FROM_HERE, base::Bind(&OrderedFunc, &order, 3));
1114 MessageLoop::current()->PostTask(
1115 FROM_HERE, base::Bind(&FuncThatQuitsNow));
1116 MessageLoop::current()->PostTask(
1117 FROM_HERE, base::Bind(&OrderedFunc, &order, 4)); // never runs
1118
1119 MessageLoop::current()->Run();
1120
1121 ASSERT_EQ(6U, order.Size());
1122 int task_index = 0;
1123 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1124 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, true));
1125 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, false));
1126 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1127 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 3, true));
1128 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 3, false));
1129 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1130 }
1131
1132 // Tests RunLoopQuit works before RunWithID.
1133 void RunTest_RunLoopQuitOrderBefore(MessageLoop::Type message_loop_type) {
1134 MessageLoop loop(message_loop_type);
1135
1136 TaskList order;
1137
1138 base::RunLoop run_loop;
1139
1140 run_loop.Quit();
1141
1142 MessageLoop::current()->PostTask(
1143 FROM_HERE, base::Bind(&OrderedFunc, &order, 1)); // never runs
1144 MessageLoop::current()->PostTask(
1145 FROM_HERE, base::Bind(&FuncThatQuitsNow)); // never runs
1146
1147 run_loop.Run();
1148
1149 ASSERT_EQ(0U, order.Size());
1150 }
1151
1152 // Tests RunLoopQuit works during RunWithID.
1153 void RunTest_RunLoopQuitOrderDuring(MessageLoop::Type message_loop_type) {
1154 MessageLoop loop(message_loop_type);
1155
1156 TaskList order;
1157
1158 base::RunLoop run_loop;
1159
1160 MessageLoop::current()->PostTask(
1161 FROM_HERE, base::Bind(&OrderedFunc, &order, 1));
1162 MessageLoop::current()->PostTask(
1163 FROM_HERE, run_loop.QuitClosure());
1164 MessageLoop::current()->PostTask(
1165 FROM_HERE, base::Bind(&OrderedFunc, &order, 2)); // never runs
1166 MessageLoop::current()->PostTask(
1167 FROM_HERE, base::Bind(&FuncThatQuitsNow)); // never runs
1168
1169 run_loop.Run();
1170
1171 ASSERT_EQ(2U, order.Size());
1172 int task_index = 0;
1173 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 1, true));
1174 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 1, false));
1175 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1176 }
1177
1178 // Tests RunLoopQuit works after RunWithID.
1179 void RunTest_RunLoopQuitOrderAfter(MessageLoop::Type message_loop_type) {
1180 MessageLoop loop(message_loop_type);
1181
1182 TaskList order;
1183
1184 base::RunLoop run_loop;
1185
1186 MessageLoop::current()->PostTask(
1187 FROM_HERE, base::Bind(&FuncThatRuns, &order, 1, run_loop.AsWeakPtr()));
1188 MessageLoop::current()->PostTask(
1189 FROM_HERE, base::Bind(&OrderedFunc, &order, 2));
1190 MessageLoop::current()->PostTask(
1191 FROM_HERE, base::Bind(&FuncThatQuitsNow));
1192 MessageLoop::current()->PostTask(
1193 FROM_HERE, base::Bind(&OrderedFunc, &order, 3));
1194 MessageLoop::current()->PostTask(
1195 FROM_HERE, run_loop.QuitClosure()); // has no affect
1196 MessageLoop::current()->PostTask(
1197 FROM_HERE, base::Bind(&OrderedFunc, &order, 4));
1198 MessageLoop::current()->PostTask(
1199 FROM_HERE, base::Bind(&FuncThatQuitsNow));
1200
1201 base::RunLoop outer_run_loop;
1202 outer_run_loop.Run();
1203
1204 ASSERT_EQ(8U, order.Size());
1205 int task_index = 0;
1206 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1207 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, true));
1208 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, false));
1209 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1210 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 3, true));
1211 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 3, false));
1212 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 4, true));
1213 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 4, false));
1214 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1215 }
1216
1217 // Tests RunLoopQuit only quits the corresponding MessageLoop::Run.
1218 void RunTest_RunLoopQuitTop(MessageLoop::Type message_loop_type) {
1219 MessageLoop loop(message_loop_type);
1220
1221 TaskList order;
1222
1223 base::RunLoop outer_run_loop;
1224 base::RunLoop nested_run_loop;
1225
1226 MessageLoop::current()->PostTask(FROM_HERE,
1227 base::Bind(&FuncThatRuns, &order, 1, nested_run_loop.AsWeakPtr()));
1228 MessageLoop::current()->PostTask(
1229 FROM_HERE, outer_run_loop.QuitClosure());
1230 MessageLoop::current()->PostTask(
1231 FROM_HERE, base::Bind(&OrderedFunc, &order, 2));
1232 MessageLoop::current()->PostTask(
1233 FROM_HERE, nested_run_loop.QuitClosure());
1234
1235 outer_run_loop.Run();
1236
1237 ASSERT_EQ(4U, order.Size());
1238 int task_index = 0;
1239 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1240 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, true));
1241 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, false));
1242 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1243 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1244 }
1245
1246 // Tests RunLoopQuit only quits the corresponding MessageLoop::Run.
1247 void RunTest_RunLoopQuitNested(MessageLoop::Type message_loop_type) {
1248 MessageLoop loop(message_loop_type);
1249
1250 TaskList order;
1251
1252 base::RunLoop outer_run_loop;
1253 base::RunLoop nested_run_loop;
1254
1255 MessageLoop::current()->PostTask(FROM_HERE,
1256 base::Bind(&FuncThatRuns, &order, 1, nested_run_loop.AsWeakPtr()));
1257 MessageLoop::current()->PostTask(
1258 FROM_HERE, nested_run_loop.QuitClosure());
1259 MessageLoop::current()->PostTask(
1260 FROM_HERE, base::Bind(&OrderedFunc, &order, 2));
1261 MessageLoop::current()->PostTask(
1262 FROM_HERE, outer_run_loop.QuitClosure());
1263
1264 outer_run_loop.Run();
1265
1266 ASSERT_EQ(4U, order.Size());
1267 int task_index = 0;
1268 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1269 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1270 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, true));
1271 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, false));
1272 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1273 }
1274
1275 // Tests RunLoopQuit only quits the corresponding MessageLoop::Run.
1276 void RunTest_RunLoopQuitBogus(MessageLoop::Type message_loop_type) {
1277 MessageLoop loop(message_loop_type);
1278
1279 TaskList order;
1280
1281 base::RunLoop outer_run_loop;
1282 base::RunLoop nested_run_loop;
1283 base::RunLoop bogus_run_loop;
1284
1285 MessageLoop::current()->PostTask(FROM_HERE,
1286 base::Bind(&FuncThatRuns, &order, 1, nested_run_loop.AsWeakPtr()));
1287 MessageLoop::current()->PostTask(
1288 FROM_HERE, bogus_run_loop.QuitClosure());
1289 MessageLoop::current()->PostTask(
1290 FROM_HERE, base::Bind(&OrderedFunc, &order, 2));
1291 MessageLoop::current()->PostTask(
1292 FROM_HERE, outer_run_loop.QuitClosure());
1293 MessageLoop::current()->PostTask(
1294 FROM_HERE, nested_run_loop.QuitClosure());
1295
1296 outer_run_loop.Run();
1297
1298 ASSERT_EQ(4U, order.Size());
1299 int task_index = 0;
1300 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1301 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, true));
1302 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 2, false));
1303 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1304 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1305 }
1306
1307 // Tests RunLoopQuit only quits the corresponding MessageLoop::Run.
1308 void RunTest_RunLoopQuitDeep(MessageLoop::Type message_loop_type) {
1309 MessageLoop loop(message_loop_type);
1310
1311 TaskList order;
1312
1313 base::RunLoop outer_run_loop;
1314 base::RunLoop nested_run_loop1;
1315 base::RunLoop nested_run_loop2;
1316 base::RunLoop nested_run_loop3;
1317 base::RunLoop nested_run_loop4;
1318
1319 MessageLoop::current()->PostTask(FROM_HERE,
1320 base::Bind(&FuncThatRuns, &order, 1, nested_run_loop1.AsWeakPtr()));
1321 MessageLoop::current()->PostTask(FROM_HERE,
1322 base::Bind(&FuncThatRuns, &order, 2, nested_run_loop2.AsWeakPtr()));
1323 MessageLoop::current()->PostTask(FROM_HERE,
1324 base::Bind(&FuncThatRuns, &order, 3, nested_run_loop3.AsWeakPtr()));
1325 MessageLoop::current()->PostTask(FROM_HERE,
1326 base::Bind(&FuncThatRuns, &order, 4, nested_run_loop4.AsWeakPtr()));
1327 MessageLoop::current()->PostTask(
1328 FROM_HERE, base::Bind(&OrderedFunc, &order, 5));
1329 MessageLoop::current()->PostTask(
1330 FROM_HERE, outer_run_loop.QuitClosure());
1331 MessageLoop::current()->PostTask(
1332 FROM_HERE, base::Bind(&OrderedFunc, &order, 6));
1333 MessageLoop::current()->PostTask(
1334 FROM_HERE, nested_run_loop1.QuitClosure());
1335 MessageLoop::current()->PostTask(
1336 FROM_HERE, base::Bind(&OrderedFunc, &order, 7));
1337 MessageLoop::current()->PostTask(
1338 FROM_HERE, nested_run_loop2.QuitClosure());
1339 MessageLoop::current()->PostTask(
1340 FROM_HERE, base::Bind(&OrderedFunc, &order, 8));
1341 MessageLoop::current()->PostTask(
1342 FROM_HERE, nested_run_loop3.QuitClosure());
1343 MessageLoop::current()->PostTask(
1344 FROM_HERE, base::Bind(&OrderedFunc, &order, 9));
1345 MessageLoop::current()->PostTask(
1346 FROM_HERE, nested_run_loop4.QuitClosure());
1347 MessageLoop::current()->PostTask(
1348 FROM_HERE, base::Bind(&OrderedFunc, &order, 10));
1349
1350 outer_run_loop.Run();
1351
1352 ASSERT_EQ(18U, order.Size());
1353 int task_index = 0;
1354 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, true));
1355 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 2, true));
1356 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 3, true));
1357 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 4, true));
1358 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 5, true));
1359 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 5, false));
1360 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 6, true));
1361 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 6, false));
1362 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 7, true));
1363 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 7, false));
1364 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 8, true));
1365 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 8, false));
1366 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 9, true));
1367 EXPECT_EQ(order.Get(task_index++), TaskItem(ORDERED, 9, false));
1368 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 4, false));
1369 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 3, false));
1370 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 2, false));
1371 EXPECT_EQ(order.Get(task_index++), TaskItem(RUNS, 1, false));
1372 EXPECT_EQ(static_cast<size_t>(task_index), order.Size());
1373 }
1374
1082 #if defined(OS_WIN) 1375 #if defined(OS_WIN)
1083 1376
1084 class DispatcherImpl : public MessageLoopForUI::Dispatcher { 1377 class DispatcherImpl : public MessageLoopForUI::Dispatcher {
1085 public: 1378 public:
1086 DispatcherImpl() : dispatch_count_(0) {} 1379 DispatcherImpl() : dispatch_count_(0) {}
1087 1380
1088 virtual bool Dispatch(const base::NativeEvent& msg) OVERRIDE { 1381 virtual bool Dispatch(const base::NativeEvent& msg) OVERRIDE {
1089 ::TranslateMessage(&msg); 1382 ::TranslateMessage(&msg);
1090 ::DispatchMessage(&msg); 1383 ::DispatchMessage(&msg);
1091 // Do not count WM_TIMER since it is not what we post and it will cause 1384 // Do not count WM_TIMER since it is not what we post and it will cause
(...skipping 335 matching lines...) Expand 10 before | Expand all | Expand 10 after
1427 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_UI, false); 1720 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_UI, false);
1428 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_IO, false); 1721 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_IO, false);
1429 } 1722 }
1430 1723
1431 TEST(MessageLoopTest, NonNestableDelayedInNestedLoop) { 1724 TEST(MessageLoopTest, NonNestableDelayedInNestedLoop) {
1432 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_DEFAULT, true); 1725 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_DEFAULT, true);
1433 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_UI, true); 1726 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_UI, true);
1434 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_IO, true); 1727 RunTest_NonNestableInNestedLoop(MessageLoop::TYPE_IO, true);
1435 } 1728 }
1436 1729
1730 TEST(MessageLoopTest, QuitNow) {
1731 RunTest_QuitNow(MessageLoop::TYPE_DEFAULT);
1732 RunTest_QuitNow(MessageLoop::TYPE_UI);
1733 RunTest_QuitNow(MessageLoop::TYPE_IO);
1734 }
1735
1736 TEST(MessageLoopTest, RunLoopQuitTop) {
1737 RunTest_RunLoopQuitTop(MessageLoop::TYPE_DEFAULT);
1738 RunTest_RunLoopQuitTop(MessageLoop::TYPE_UI);
1739 RunTest_RunLoopQuitTop(MessageLoop::TYPE_IO);
1740 }
1741
1742 TEST(MessageLoopTest, RunLoopQuitNested) {
1743 RunTest_RunLoopQuitNested(MessageLoop::TYPE_DEFAULT);
1744 RunTest_RunLoopQuitNested(MessageLoop::TYPE_UI);
1745 RunTest_RunLoopQuitNested(MessageLoop::TYPE_IO);
1746 }
1747
1748 TEST(MessageLoopTest, RunLoopQuitBogus) {
1749 RunTest_RunLoopQuitBogus(MessageLoop::TYPE_DEFAULT);
1750 RunTest_RunLoopQuitBogus(MessageLoop::TYPE_UI);
1751 RunTest_RunLoopQuitBogus(MessageLoop::TYPE_IO);
1752 }
1753
1754 TEST(MessageLoopTest, RunLoopQuitDeep) {
1755 RunTest_RunLoopQuitDeep(MessageLoop::TYPE_DEFAULT);
1756 RunTest_RunLoopQuitDeep(MessageLoop::TYPE_UI);
1757 RunTest_RunLoopQuitDeep(MessageLoop::TYPE_IO);
1758 }
1759
1760 TEST(MessageLoopTest, RunLoopQuitOrderBefore) {
1761 RunTest_RunLoopQuitOrderBefore(MessageLoop::TYPE_DEFAULT);
1762 RunTest_RunLoopQuitOrderBefore(MessageLoop::TYPE_UI);
1763 RunTest_RunLoopQuitOrderBefore(MessageLoop::TYPE_IO);
1764 }
1765
1766 TEST(MessageLoopTest, RunLoopQuitOrderDuring) {
1767 RunTest_RunLoopQuitOrderDuring(MessageLoop::TYPE_DEFAULT);
1768 RunTest_RunLoopQuitOrderDuring(MessageLoop::TYPE_UI);
1769 RunTest_RunLoopQuitOrderDuring(MessageLoop::TYPE_IO);
1770 }
1771
1772 TEST(MessageLoopTest, RunLoopQuitOrderAfter) {
1773 RunTest_RunLoopQuitOrderAfter(MessageLoop::TYPE_DEFAULT);
1774 RunTest_RunLoopQuitOrderAfter(MessageLoop::TYPE_UI);
1775 RunTest_RunLoopQuitOrderAfter(MessageLoop::TYPE_IO);
1776 }
1777
1437 void PostNTasksThenQuit(int posts_remaining) { 1778 void PostNTasksThenQuit(int posts_remaining) {
1438 if (posts_remaining > 1) { 1779 if (posts_remaining > 1) {
1439 MessageLoop::current()->PostTask( 1780 MessageLoop::current()->PostTask(
1440 FROM_HERE, 1781 FROM_HERE,
1441 base::Bind(&PostNTasksThenQuit, posts_remaining - 1)); 1782 base::Bind(&PostNTasksThenQuit, posts_remaining - 1));
1442 } else { 1783 } else {
1443 MessageLoop::current()->Quit(); 1784 MessageLoop::current()->Quit();
1444 } 1785 }
1445 } 1786 }
1446 1787
(...skipping 258 matching lines...) Expand 10 before | Expand all | Expand 10 after
1705 // Post quit task; 2046 // Post quit task;
1706 MessageLoop::current()->PostTask(FROM_HERE, base::Bind( 2047 MessageLoop::current()->PostTask(FROM_HERE, base::Bind(
1707 &MessageLoop::Quit, base::Unretained(MessageLoop::current()))); 2048 &MessageLoop::Quit, base::Unretained(MessageLoop::current())));
1708 2049
1709 // Now kick things off 2050 // Now kick things off
1710 MessageLoop::current()->Run(); 2051 MessageLoop::current()->Run();
1711 2052
1712 EXPECT_EQ(foo->test_count(), 1); 2053 EXPECT_EQ(foo->test_count(), 1);
1713 EXPECT_EQ(foo->result(), "a"); 2054 EXPECT_EQ(foo->result(), "a");
1714 } 2055 }
OLDNEW
« no previous file with comments | « base/message_loop.cc ('k') | base/message_pump_android.h » ('j') | base/message_pump_android.cc » ('J')

Powered by Google App Engine
This is Rietveld 408576698