OLD | NEW |
---|---|
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 #ifndef PPAPI_TESTS_TEST_CASE_H_ | 5 #ifndef PPAPI_TESTS_TEST_CASE_H_ |
6 #define PPAPI_TESTS_TEST_CASE_H_ | 6 #define PPAPI_TESTS_TEST_CASE_H_ |
7 | 7 |
8 #include <cmath> | 8 #include <cmath> |
9 #include <limits> | 9 #include <limits> |
10 #include <set> | 10 #include <set> |
11 #include <string> | 11 #include <string> |
12 | 12 |
13 #include "ppapi/c/pp_resource.h" | 13 #include "ppapi/c/pp_resource.h" |
14 #include "ppapi/c/dev/ppb_testing_dev.h" | 14 #include "ppapi/c/dev/ppb_testing_dev.h" |
15 #include "ppapi/cpp/dev/message_loop_dev.h" | |
15 #include "ppapi/cpp/dev/scrollbar_dev.h" | 16 #include "ppapi/cpp/dev/scrollbar_dev.h" |
16 #include "ppapi/cpp/view.h" | 17 #include "ppapi/cpp/view.h" |
18 #include "ppapi/tests/pp_thread.h" | |
17 #include "ppapi/tests/test_utils.h" | 19 #include "ppapi/tests/test_utils.h" |
20 #include "ppapi/tests/testing_instance.h" | |
18 | 21 |
19 #if (defined __native_client__) | 22 #if (defined __native_client__) |
20 #include "ppapi/cpp/var.h" | 23 #include "ppapi/cpp/var.h" |
21 #else | 24 #else |
22 #include "ppapi/cpp/private/var_private.h" | 25 #include "ppapi/cpp/private/var_private.h" |
23 #endif | 26 #endif |
24 | 27 |
25 class TestingInstance; | 28 class TestingInstance; |
26 | 29 |
27 namespace pp { | 30 namespace pp { |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
71 // associated TestingInstance. Default implementation returns false. TestCases | 74 // associated TestingInstance. Default implementation returns false. TestCases |
72 // that want to handle view changes should override this method. | 75 // that want to handle view changes should override this method. |
73 virtual bool HandleInputEvent(const pp::InputEvent& event); | 76 virtual bool HandleInputEvent(const pp::InputEvent& event); |
74 | 77 |
75 void IgnoreLeakedVar(int64_t id); | 78 void IgnoreLeakedVar(int64_t id); |
76 | 79 |
77 TestingInstance* instance() { return instance_; } | 80 TestingInstance* instance() { return instance_; } |
78 | 81 |
79 const PPB_Testing_Dev* testing_interface() { return testing_interface_; } | 82 const PPB_Testing_Dev* testing_interface() { return testing_interface_; } |
80 | 83 |
84 static void QuitMainMessageLoop(PP_Instance instance); | |
85 | |
81 protected: | 86 protected: |
82 #if !(defined __native_client__) | 87 #if !(defined __native_client__) |
83 // Overridden by each test to supply a ScriptableObject corresponding to the | 88 // Overridden by each test to supply a ScriptableObject corresponding to the |
84 // test. There can only be one object created for all tests in a given class, | 89 // test. There can only be one object created for all tests in a given class, |
85 // so be sure your object is designed to be re-used. | 90 // so be sure your object is designed to be re-used. |
86 // | 91 // |
87 // This object should be created on the heap. Ownership will be passed to the | 92 // This object should be created on the heap. Ownership will be passed to the |
88 // caller. Return NULL if there is no supported test object (the default). | 93 // caller. Return NULL if there is no supported test object (the default). |
89 virtual pp::deprecated::ScriptableObject* CreateTestObject(); | 94 virtual pp::deprecated::ScriptableObject* CreateTestObject(); |
90 #endif | 95 #endif |
91 | 96 |
92 // Checks whether the testing interface is available. Returns true if it is, | 97 // Checks whether the testing interface is available. Returns true if it is, |
93 // false otherwise. If it is not available, adds a descriptive error. This is | 98 // false otherwise. If it is not available, adds a descriptive error. This is |
94 // for use by tests that require the testing interface. | 99 // for use by tests that require the testing interface. |
95 bool CheckTestingInterface(); | 100 bool CheckTestingInterface(); |
96 | 101 |
97 // Makes sure the test is run over HTTP. | 102 // Makes sure the test is run over HTTP. |
98 bool EnsureRunningOverHTTP(); | 103 bool EnsureRunningOverHTTP(); |
99 | 104 |
100 // Return true if the given test name matches the filter. This is true if | 105 // Return true if the given test name matches the filter. This is true if |
101 // (a) filter is empty or (b) test_name and filter match exactly. | 106 // (a) filter is empty or (b) test_name and filter match exactly. |
102 bool MatchesFilter(const std::string& test_name, const std::string& filter); | 107 bool MatchesFilter(const std::string& test_name, const std::string& filter); |
103 | 108 |
104 // Check for leaked resources and vars at the end of the test. If any exist, | 109 // Check for leaked resources and vars at the end of the test. If any exist, |
105 // return a string with some information about the error. Otherwise, return | 110 // return a string with some information about the error. Otherwise, return |
106 // an empty string. | 111 // an empty string. |
107 std::string CheckResourcesAndVars(); | 112 // |
113 // You should pass the error string from the test so far; if it is non-empty, | |
114 // CheckResourcesAndVars will do nothing and return the same string. | |
115 std::string CheckResourcesAndVars(std::string errors); | |
116 | |
117 // Run the given test method on a background thread and return the result. | |
118 template <class T> | |
119 std::string RunOnThread(std::string(T::*test_to_run)()) { | |
120 #ifdef ENABLE_PEPPER_THREADING | |
121 if (!testing_interface_) { | |
122 return "Testing blocking callbacks requires the testing interface. In " | |
123 "Chrome, use the --enable-pepper-testing flag."; | |
124 } | |
125 // These tests are only valid if running out-of-process (threading is not | |
126 // supported in-process). Just consider it a pass. | |
127 if (!testing_interface_->IsOutOfProcess()) | |
128 return std::string(); | |
129 ThreadedTestRunner<T> runner(instance_->pp_instance(), | |
130 static_cast<T*>(this), test_to_run); | |
131 PP_ThreadType thread; | |
132 PP_CreateThread(&thread, &ThreadedTestRunner<T>::ThreadFunction, &runner); | |
133 // Run a message loop so pepper calls can be dispatched. The background | |
134 // thread will make us Quit when it's done. | |
135 testing_interface_->RunMessageLoop(instance_->pp_instance()); | |
136 PP_JoinThread(thread); | |
137 return runner.result(); | |
138 #else | |
139 // If threading's not enabled, just treat it as success. | |
140 return std::string(); | |
141 #endif | |
142 } | |
108 | 143 |
109 // Pointer to the instance that owns us. | 144 // Pointer to the instance that owns us. |
110 TestingInstance* instance_; | 145 TestingInstance* instance_; |
111 | 146 |
112 protected: | |
113 // NULL unless InitTestingInterface is called. | 147 // NULL unless InitTestingInterface is called. |
114 const PPB_Testing_Dev* testing_interface_; | 148 const PPB_Testing_Dev* testing_interface_; |
115 | 149 |
116 // TODO(dmichael): Remove this, it's for temporary backwards compatibility so | 150 // TODO(dmichael): Remove this, it's for temporary backwards compatibility so |
117 // I don't have to change all the tests at once. | 151 // I don't have to change all the tests at once. |
118 bool force_async_; | 152 bool force_async_; |
119 | 153 |
120 void set_callback_type(CallbackType callback_type) { | 154 void set_callback_type(CallbackType callback_type) { |
121 callback_type_ = callback_type; | 155 callback_type_ = callback_type; |
122 // TODO(dmichael): Remove this; see comment on force_async_. | 156 // TODO(dmichael): Remove this; see comment on force_async_. |
123 force_async_ = (callback_type_ == PP_REQUIRED); | 157 force_async_ = (callback_type_ == PP_REQUIRED); |
124 } | 158 } |
125 CallbackType callback_type() const { | 159 CallbackType callback_type() const { |
126 return callback_type_; | 160 return callback_type_; |
127 } | 161 } |
128 | 162 |
129 private: | 163 private: |
164 template <class T> | |
165 class ThreadedTestRunner { | |
166 public: | |
167 typedef std::string(T::*TestMethodType)(); | |
168 explicit ThreadedTestRunner(PP_Instance instance, | |
169 T* test_case, | |
170 TestMethodType test_to_run) | |
171 : instance_(instance), | |
172 test_case_(test_case), | |
173 test_to_run_(test_to_run) { | |
174 } | |
175 std::string result() { return result_; } | |
176 static void ThreadFunction(void* runner) { | |
177 static_cast<ThreadedTestRunner<T>*>(runner)->Run(); | |
178 } | |
179 | |
180 private: | |
181 void Run() { | |
182 // TODO(dmichael): Create and attach a pp::MessageLoop for this thread so | |
183 // nested loops work. | |
184 result_ = (test_case_->*test_to_run_)(); | |
185 // Tell the main thread to quit its nested message loop, now that the test | |
186 // is complete. | |
187 TestCase::QuitMainMessageLoop(instance_); | |
188 } | |
189 | |
190 std::string result_; | |
191 PP_Instance instance_; | |
192 T* test_case_; | |
193 TestMethodType test_to_run_; | |
194 }; | |
195 | |
196 static void DoQuitMainMessageLoop(void* pp_instance, int32_t result); | |
197 | |
130 // Passed when creating completion callbacks in some tests. This determines | 198 // Passed when creating completion callbacks in some tests. This determines |
131 // what kind of callback we use for the test. | 199 // what kind of callback we use for the test. |
132 CallbackType callback_type_; | 200 CallbackType callback_type_; |
133 | 201 |
134 // Var ids that should be ignored when checking for leaks on shutdown. | 202 // Var ids that should be ignored when checking for leaks on shutdown. |
135 std::set<int64_t> ignored_leaked_vars_; | 203 std::set<int64_t> ignored_leaked_vars_; |
136 | 204 |
137 #if !(defined __native_client__) | 205 #if !(defined __native_client__) |
138 // Holds the test object, if any was retrieved from CreateTestObject. | 206 // Holds the test object, if any was retrieved from CreateTestObject. |
139 pp::VarPrivate test_object_; | 207 pp::VarPrivate test_object_; |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
177 static TestCaseFactory g_Test##name_factory( \ | 245 static TestCaseFactory g_Test##name_factory( \ |
178 #name, &Test##name##_FactoryMethod \ | 246 #name, &Test##name##_FactoryMethod \ |
179 ) | 247 ) |
180 | 248 |
181 // Helper macro for calling functions implementing specific tests in the | 249 // Helper macro for calling functions implementing specific tests in the |
182 // RunTest function. This assumes the function name is TestFoo where Foo is the | 250 // RunTest function. This assumes the function name is TestFoo where Foo is the |
183 // test |name|. | 251 // test |name|. |
184 #define RUN_TEST(name, test_filter) \ | 252 #define RUN_TEST(name, test_filter) \ |
185 if (MatchesFilter(#name, test_filter)) { \ | 253 if (MatchesFilter(#name, test_filter)) { \ |
186 set_callback_type(PP_OPTIONAL); \ | 254 set_callback_type(PP_OPTIONAL); \ |
187 std::string error_message = Test##name(); \ | 255 instance_->LogTest(#name, CheckResourcesAndVars(Test##name())); \ |
188 if (error_message.empty()) \ | |
189 error_message = CheckResourcesAndVars(); \ | |
190 instance_->LogTest(#name, error_message); \ | |
191 } | 256 } |
192 | 257 |
258 // Like RUN_TEST above but forces functions taking callbacks to complete | |
259 // asynchronously on success or error. | |
260 #define RUN_TEST_FORCEASYNC(name, test_filter) \ | |
261 if (MatchesFilter(#name, test_filter)) { \ | |
262 set_callback_type(PP_REQUIRED); \ | |
263 instance_->LogTest(#name"ForceAsync", \ | |
264 CheckResourcesAndVars(Test##name())); \ | |
265 } | |
266 | |
267 #define RUN_TEST_BLOCKING(test_case, name, test_filter) \ | |
268 if (MatchesFilter(#name, test_filter)) { \ | |
269 set_callback_type(PP_BLOCKING); \ | |
270 instance_->LogTest(#name"Blocking", \ | |
271 CheckResourcesAndVars(RunOnThread(&test_case::Test##name))); \ | |
272 } | |
273 | |
274 #define RUN_TEST_FORCEASYNC_AND_NOT(name, test_filter) \ | |
275 do { \ | |
276 RUN_TEST_FORCEASYNC(name, test_filter); \ | |
277 RUN_TEST(name, test_filter); \ | |
278 } while (false) | |
279 | |
280 // Run a test with all possible callback types. | |
281 #define RUN_CALLBACK_TEST(test_case, name, test_filter) \ | |
282 do { \ | |
283 RUN_TEST_FORCEASYNC(name, test_filter); \ | |
284 RUN_TEST(name, test_filter); \ | |
285 RUN_TEST_BLOCKING(test_case, name, test_filter); \ | |
286 } while (false) | |
287 | |
193 #define RUN_TEST_WITH_REFERENCE_CHECK(name, test_filter) \ | 288 #define RUN_TEST_WITH_REFERENCE_CHECK(name, test_filter) \ |
194 if (MatchesFilter(#name, test_filter)) { \ | 289 if (MatchesFilter(#name, test_filter)) { \ |
195 set_callback_type(PP_OPTIONAL); \ | 290 set_callback_type(PP_OPTIONAL); \ |
196 uint32_t objects = testing_interface_->GetLiveObjectsForInstance( \ | 291 uint32_t objects = testing_interface_->GetLiveObjectsForInstance( \ |
197 instance_->pp_instance()); \ | 292 instance_->pp_instance()); \ |
198 std::string error_message = Test##name(); \ | 293 std::string error_message = Test##name(); \ |
199 if (error_message.empty() && \ | 294 if (error_message.empty() && \ |
200 testing_interface_->GetLiveObjectsForInstance( \ | 295 testing_interface_->GetLiveObjectsForInstance( \ |
201 instance_->pp_instance()) != objects) \ | 296 instance_->pp_instance()) != objects) \ |
202 error_message = MakeFailureMessage(__FILE__, __LINE__, \ | 297 error_message = MakeFailureMessage(__FILE__, __LINE__, \ |
203 "reference leak check"); \ | 298 "reference leak check"); \ |
204 instance_->LogTest(#name, error_message); \ | 299 instance_->LogTest(#name, error_message); \ |
205 } | 300 } |
206 | 301 |
207 // Like RUN_TEST above but forces functions taking callbacks to complete | |
208 // asynchronously on success or error. | |
209 #define RUN_TEST_FORCEASYNC(name, test_filter) \ | |
210 if (MatchesFilter(#name"ForceAsync", test_filter)) { \ | |
dmichael (off chromium)
2012/04/19 20:02:00
Note the first parameter used to say '#name"ForceA
| |
211 set_callback_type(PP_REQUIRED); \ | |
212 instance_->LogTest(#name"ForceAsync", Test##name()); \ | |
213 } | |
214 | |
215 #define RUN_TEST_FORCEASYNC_AND_NOT(name, test_filter) \ | |
216 do { \ | |
217 RUN_TEST_FORCEASYNC(name, test_filter); \ | |
218 RUN_TEST(name, test_filter); \ | |
219 } while (false) | |
220 | |
221 | |
222 // Helper macros for checking values in tests, and returning a location | 302 // Helper macros for checking values in tests, and returning a location |
223 // description of the test fails. | 303 // description of the test fails. |
224 #define ASSERT_TRUE(cmd) \ | 304 #define ASSERT_TRUE(cmd) \ |
225 if (!(cmd)) { \ | 305 if (!(cmd)) { \ |
226 return MakeFailureMessage(__FILE__, __LINE__, #cmd); \ | 306 return MakeFailureMessage(__FILE__, __LINE__, #cmd); \ |
227 } | 307 } |
228 #define ASSERT_FALSE(cmd) ASSERT_TRUE(!(cmd)) | 308 #define ASSERT_FALSE(cmd) ASSERT_TRUE(!(cmd)) |
229 #define ASSERT_EQ(a, b) ASSERT_TRUE((a) == (b)) | 309 #define ASSERT_EQ(a, b) ASSERT_TRUE((a) == (b)) |
230 #define ASSERT_NE(a, b) ASSERT_TRUE((a) != (b)) | 310 #define ASSERT_NE(a, b) ASSERT_TRUE((a) != (b)) |
231 | 311 |
232 #define ASSERT_DOUBLE_EQ(a, b) ASSERT_TRUE( \ | 312 #define ASSERT_DOUBLE_EQ(a, b) ASSERT_TRUE( \ |
233 std::fabs((a)-(b)) <= std::numeric_limits<double>::epsilon()) | 313 std::fabs((a)-(b)) <= std::numeric_limits<double>::epsilon()) |
234 | 314 |
235 // Runs |function| as a subtest and asserts that it has passed. | 315 // Runs |function| as a subtest and asserts that it has passed. |
236 #define ASSERT_SUBTEST_SUCCESS(function) \ | 316 #define ASSERT_SUBTEST_SUCCESS(function) \ |
237 do { \ | 317 do { \ |
238 std::string result = (function); \ | 318 std::string result = (function); \ |
239 if (!result.empty()) \ | 319 if (!result.empty()) \ |
240 return result; \ | 320 return result; \ |
241 } while (false) | 321 } while (false) |
242 | 322 |
243 #define PASS() return std::string() | 323 #define PASS() return std::string() |
244 | 324 |
245 #endif // PPAPI_TESTS_TEST_CASE_H_ | 325 #endif // PPAPI_TESTS_TEST_CASE_H_ |
OLD | NEW |