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

Side by Side Diff: cc/resource_update_controller_unittest.cc

Issue 12471007: Part 8 of cc/ directory shuffles: resources (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 7 years, 9 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
« no previous file with comments | « cc/resource_update_controller.cc ('k') | cc/resource_update_queue.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2012 The Chromium Authors. All rights reserved.
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 "cc/resource_update_controller.h"
6
7 #include "cc/prioritized_resource_manager.h"
8 #include "cc/test/fake_output_surface.h"
9 #include "cc/test/fake_proxy.h"
10 #include "cc/test/scheduler_test_common.h"
11 #include "cc/test/test_web_graphics_context_3d.h"
12 #include "cc/test/tiled_layer_test_common.h"
13 #include "cc/trees/single_thread_proxy.h" // For DebugScopedSetImplThread
14 #include "testing/gtest/include/gtest/gtest.h"
15 #include "third_party/khronos/GLES2/gl2ext.h"
16
17 using namespace WebKit;
18 using testing::Test;
19
20 namespace cc {
21 namespace {
22
23 const int kFlushPeriodFull = 4;
24 const int kFlushPeriodPartial = kFlushPeriodFull;
25
26 class ResourceUpdateControllerTest;
27
28 class WebGraphicsContext3DForUploadTest : public TestWebGraphicsContext3D {
29 public:
30 WebGraphicsContext3DForUploadTest(ResourceUpdateControllerTest *test)
31 : m_test(test)
32 , m_supportShallowFlush(true)
33 { }
34
35 virtual void flush(void);
36 virtual void shallowFlushCHROMIUM(void);
37 virtual void texSubImage2D(WGC3Denum target,
38 WGC3Dint level,
39 WGC3Dint xoffset,
40 WGC3Dint yoffset,
41 WGC3Dsizei width,
42 WGC3Dsizei height,
43 WGC3Denum format,
44 WGC3Denum type,
45 const void* pixels);
46 virtual GrGLInterface* onCreateGrGLInterface() { return 0; }
47
48 virtual WebString getString(WGC3Denum name)
49 {
50 if (m_supportShallowFlush)
51 return WebString("GL_CHROMIUM_shallow_flush");
52 return WebString("");
53 }
54
55 virtual void getQueryObjectuivEXT(WebGLId, WGC3Denum, WGC3Duint*);
56
57 private:
58 ResourceUpdateControllerTest* m_test;
59 bool m_supportShallowFlush;
60 };
61
62
63 class ResourceUpdateControllerTest : public Test {
64 public:
65 ResourceUpdateControllerTest()
66 : m_proxy(scoped_ptr<Thread>(NULL))
67 , m_queue(make_scoped_ptr(new ResourceUpdateQueue))
68 , m_resourceManager(PrioritizedResourceManager::create(&m_proxy))
69 , m_fullUploadCountExpected(0)
70 , m_partialCountExpected(0)
71 , m_totalUploadCountExpected(0)
72 , m_maxUploadCountPerUpdate(0)
73 , m_numConsecutiveFlushes(0)
74 , m_numDanglingUploads(0)
75 , m_numTotalUploads(0)
76 , m_numTotalFlushes(0)
77 , m_queryResultsAvailable(0)
78 {
79 }
80
81 virtual ~ResourceUpdateControllerTest()
82 {
83 DebugScopedSetImplThreadAndMainThreadBlocked
84 implThreadAndMainThreadBlocked(&m_proxy);
85 m_resourceManager->clearAllMemory(m_resourceProvider.get());
86 }
87
88 public:
89 void onFlush()
90 {
91 // Check for back-to-back flushes.
92 EXPECT_EQ(0, m_numConsecutiveFlushes) << "Back-to-back flushes detected. ";
93
94 m_numDanglingUploads = 0;
95 m_numConsecutiveFlushes++;
96 m_numTotalFlushes++;
97 }
98
99 void onUpload()
100 {
101 // Check for too many consecutive uploads
102 if (m_numTotalUploads < m_fullUploadCountExpected)
103 EXPECT_LT(m_numDanglingUploads, kFlushPeriodFull) << "Too many conse cutive full uploads detected.";
104 else
105 EXPECT_LT(m_numDanglingUploads, kFlushPeriodPartial) << "Too many co nsecutive partial uploads detected.";
106
107 m_numConsecutiveFlushes = 0;
108 m_numDanglingUploads++;
109 m_numTotalUploads++;
110 }
111
112 bool isQueryResultAvailable()
113 {
114 if (!m_queryResultsAvailable)
115 return false;
116
117 m_queryResultsAvailable--;
118 return true;
119 }
120
121 protected:
122 virtual void SetUp()
123 {
124 m_outputSurface = FakeOutputSurface::Create3d(scoped_ptr<WebKit::WebGrap hicsContext3D>(new WebGraphicsContext3DForUploadTest(this)));
125 m_bitmap.setConfig(SkBitmap::kARGB_8888_Config, 300, 150);
126 m_bitmap.allocPixels();
127
128 for (int i = 0; i < 4; i++) {
129 m_textures[i] = PrioritizedResource::create(
130 m_resourceManager.get(), gfx::Size(300, 150), GL_RGBA);
131 m_textures[i]->setRequestPriority(
132 PriorityCalculator::VisiblePriority(true));
133 }
134 m_resourceManager->prioritizeTextures();
135
136 m_resourceProvider = ResourceProvider::Create(m_outputSurface.get());
137 }
138
139
140 void appendFullUploadsOfIndexedTextureToUpdateQueue(int count, int textureIn dex)
141 {
142 m_fullUploadCountExpected += count;
143 m_totalUploadCountExpected += count;
144
145 const gfx::Rect rect(0, 0, 300, 150);
146 const ResourceUpdate upload = ResourceUpdate::Create(
147 m_textures[textureIndex].get(), &m_bitmap, rect, rect, gfx::Vector2d ());
148 for (int i = 0; i < count; i++)
149 m_queue->appendFullUpload(upload);
150 }
151
152 void appendFullUploadsToUpdateQueue(int count)
153 {
154 appendFullUploadsOfIndexedTextureToUpdateQueue(count, 0);
155 }
156
157 void appendPartialUploadsOfIndexedTextureToUpdateQueue(int count, int textur eIndex)
158 {
159 m_partialCountExpected += count;
160 m_totalUploadCountExpected += count;
161
162 const gfx::Rect rect(0, 0, 100, 100);
163 const ResourceUpdate upload = ResourceUpdate::Create(
164 m_textures[textureIndex].get(), &m_bitmap, rect, rect, gfx::Vector2d ());
165 for (int i = 0; i < count; i++)
166 m_queue->appendPartialUpload(upload);
167 }
168
169 void appendPartialUploadsToUpdateQueue(int count)
170 {
171 appendPartialUploadsOfIndexedTextureToUpdateQueue(count, 0);
172 }
173
174 void setMaxUploadCountPerUpdate(int count)
175 {
176 m_maxUploadCountPerUpdate = count;
177 }
178
179 void updateTextures()
180 {
181 DebugScopedSetImplThreadAndMainThreadBlocked
182 implThreadAndMainThreadBlocked(&m_proxy);
183 scoped_ptr<ResourceUpdateController> updateController =
184 ResourceUpdateController::Create(
185 NULL,
186 m_proxy.ImplThread(),
187 m_queue.Pass(),
188 m_resourceProvider.get());
189 updateController->Finalize();
190 }
191
192 void makeQueryResultAvailable()
193 {
194 m_queryResultsAvailable++;
195 }
196
197 protected:
198 // Classes required to interact and test the ResourceUpdateController
199 FakeProxy m_proxy;
200 scoped_ptr<OutputSurface> m_outputSurface;
201 scoped_ptr<ResourceProvider> m_resourceProvider;
202 scoped_ptr<ResourceUpdateQueue> m_queue;
203 scoped_ptr<PrioritizedResource> m_textures[4];
204 scoped_ptr<PrioritizedResourceManager> m_resourceManager;
205 SkBitmap m_bitmap;
206 int m_queryResultsAvailable;
207
208 // Properties / expectations of this test
209 int m_fullUploadCountExpected;
210 int m_partialCountExpected;
211 int m_totalUploadCountExpected;
212 int m_maxUploadCountPerUpdate;
213
214 // Dynamic properties of this test
215 int m_numConsecutiveFlushes;
216 int m_numDanglingUploads;
217 int m_numTotalUploads;
218 int m_numTotalFlushes;
219 };
220
221 void WebGraphicsContext3DForUploadTest::flush(void)
222 {
223 m_test->onFlush();
224 }
225
226 void WebGraphicsContext3DForUploadTest::shallowFlushCHROMIUM(void)
227 {
228 m_test->onFlush();
229 }
230
231 void WebGraphicsContext3DForUploadTest::texSubImage2D(WGC3Denum target,
232 WGC3Dint level,
233 WGC3Dint xoffset,
234 WGC3Dint yoffset,
235 WGC3Dsizei width,
236 WGC3Dsizei height,
237 WGC3Denum format,
238 WGC3Denum type,
239 const void* pixels)
240 {
241 m_test->onUpload();
242 }
243
244 void WebGraphicsContext3DForUploadTest::getQueryObjectuivEXT(
245 WebGLId,
246 WGC3Denum pname,
247 WGC3Duint* params) {
248 if (pname == GL_QUERY_RESULT_AVAILABLE_EXT)
249 *params = m_test->isQueryResultAvailable();
250 }
251
252 // ZERO UPLOADS TESTS
253 TEST_F(ResourceUpdateControllerTest, ZeroUploads)
254 {
255 appendFullUploadsToUpdateQueue(0);
256 appendPartialUploadsToUpdateQueue(0);
257 updateTextures();
258
259 EXPECT_EQ(0, m_numTotalFlushes);
260 EXPECT_EQ(0, m_numTotalUploads);
261 }
262
263
264 // ONE UPLOAD TESTS
265 TEST_F(ResourceUpdateControllerTest, OneFullUpload)
266 {
267 appendFullUploadsToUpdateQueue(1);
268 appendPartialUploadsToUpdateQueue(0);
269 updateTextures();
270
271 EXPECT_EQ(1, m_numTotalFlushes);
272 EXPECT_EQ(1, m_numTotalUploads);
273 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
274 }
275
276 TEST_F(ResourceUpdateControllerTest, OnePartialUpload)
277 {
278 appendFullUploadsToUpdateQueue(0);
279 appendPartialUploadsToUpdateQueue(1);
280 updateTextures();
281
282 EXPECT_EQ(1, m_numTotalFlushes);
283 EXPECT_EQ(1, m_numTotalUploads);
284 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
285 }
286
287 TEST_F(ResourceUpdateControllerTest, OneFullOnePartialUpload)
288 {
289 appendFullUploadsToUpdateQueue(1);
290 appendPartialUploadsToUpdateQueue(1);
291 updateTextures();
292
293 EXPECT_EQ(1, m_numTotalFlushes);
294 EXPECT_EQ(2, m_numTotalUploads);
295 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
296 }
297
298
299 // This class of tests upload a number of textures that is a multiple of the flu sh period.
300 const int fullUploadFlushMultipler = 7;
301 const int fullCount = fullUploadFlushMultipler * kFlushPeriodFull;
302
303 const int partialUploadFlushMultipler = 11;
304 const int partialCount = partialUploadFlushMultipler * kFlushPeriodPartial;
305
306 TEST_F(ResourceUpdateControllerTest, ManyFullUploads)
307 {
308 appendFullUploadsToUpdateQueue(fullCount);
309 appendPartialUploadsToUpdateQueue(0);
310 updateTextures();
311
312 EXPECT_EQ(fullUploadFlushMultipler, m_numTotalFlushes);
313 EXPECT_EQ(fullCount, m_numTotalUploads);
314 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
315 }
316
317 TEST_F(ResourceUpdateControllerTest, ManyPartialUploads)
318 {
319 appendFullUploadsToUpdateQueue(0);
320 appendPartialUploadsToUpdateQueue(partialCount);
321 updateTextures();
322
323 EXPECT_EQ(partialUploadFlushMultipler, m_numTotalFlushes);
324 EXPECT_EQ(partialCount, m_numTotalUploads);
325 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
326 }
327
328 TEST_F(ResourceUpdateControllerTest, ManyFullManyPartialUploads)
329 {
330 appendFullUploadsToUpdateQueue(fullCount);
331 appendPartialUploadsToUpdateQueue(partialCount);
332 updateTextures();
333
334 EXPECT_EQ(fullUploadFlushMultipler + partialUploadFlushMultipler, m_numTotal Flushes);
335 EXPECT_EQ(fullCount + partialCount, m_numTotalUploads);
336 EXPECT_EQ(0, m_numDanglingUploads) << "Last upload wasn't followed by a flus h.";
337 }
338
339 class FakeResourceUpdateControllerClient : public cc::ResourceUpdateControllerCl ient {
340 public:
341 FakeResourceUpdateControllerClient() { reset(); }
342 void reset() { m_readyToFinalizeCalled = false; }
343 bool readyToFinalizeCalled() const { return m_readyToFinalizeCalled; }
344
345 virtual void ReadyToFinalizeTextureUpdates() OVERRIDE { m_readyToFinalizeCal led = true; }
346
347 protected:
348 bool m_readyToFinalizeCalled;
349 };
350
351 class FakeResourceUpdateController : public cc::ResourceUpdateController {
352 public:
353 static scoped_ptr<FakeResourceUpdateController> Create(cc::ResourceUpdateCon trollerClient* client, cc::Thread* thread, scoped_ptr<ResourceUpdateQueue> queue , ResourceProvider* resourceProvider)
354 {
355 return make_scoped_ptr(new FakeResourceUpdateController(client, thread, queue.Pass(), resourceProvider));
356 }
357
358 void setNow(base::TimeTicks time) { m_now = time; }
359 virtual base::TimeTicks Now() const OVERRIDE { return m_now; }
360 void setUpdateMoreTexturesTime(base::TimeDelta time) { m_updateMoreTexturesT ime = time; }
361 virtual base::TimeDelta UpdateMoreTexturesTime() const OVERRIDE { return m_u pdateMoreTexturesTime; }
362 void setUpdateMoreTexturesSize(size_t size) { m_updateMoreTexturesSize = siz e; }
363 virtual size_t UpdateMoreTexturesSize() const OVERRIDE { return m_updateMore TexturesSize; }
364
365 protected:
366 FakeResourceUpdateController(cc::ResourceUpdateControllerClient* client, cc: :Thread* thread, scoped_ptr<ResourceUpdateQueue> queue, ResourceProvider* resour ceProvider)
367 : cc::ResourceUpdateController(client, thread, queue.Pass(), resourcePro vider)
368 , m_updateMoreTexturesSize(0) { }
369
370 base::TimeTicks m_now;
371 base::TimeDelta m_updateMoreTexturesTime;
372 size_t m_updateMoreTexturesSize;
373 };
374
375 static void runPendingTask(FakeThread* thread, FakeResourceUpdateController* con troller)
376 {
377 EXPECT_TRUE(thread->hasPendingTask());
378 controller->setNow(controller->Now() + base::TimeDelta::FromMilliseconds(thr ead->pendingDelayMs()));
379 thread->runPendingTask();
380 }
381
382 TEST_F(ResourceUpdateControllerTest, UpdateMoreTextures)
383 {
384 FakeResourceUpdateControllerClient client;
385 FakeThread thread;
386
387 setMaxUploadCountPerUpdate(1);
388 appendFullUploadsToUpdateQueue(3);
389 appendPartialUploadsToUpdateQueue(0);
390
391 DebugScopedSetImplThreadAndMainThreadBlocked
392 implThreadAndMainThreadBlocked(&m_proxy);
393 scoped_ptr<FakeResourceUpdateController> controller(FakeResourceUpdateContro ller::Create(&client, &thread, m_queue.Pass(), m_resourceProvider.get()));
394
395 controller->setNow(
396 controller->Now() + base::TimeDelta::FromMilliseconds(1));
397 controller->setUpdateMoreTexturesTime(
398 base::TimeDelta::FromMilliseconds(100));
399 controller->setUpdateMoreTexturesSize(1);
400 // Not enough time for any updates.
401 controller->PerformMoreUpdates(
402 controller->Now() + base::TimeDelta::FromMilliseconds(90));
403 EXPECT_FALSE(thread.hasPendingTask());
404
405 controller->setUpdateMoreTexturesTime(
406 base::TimeDelta::FromMilliseconds(100));
407 controller->setUpdateMoreTexturesSize(1);
408 // Only enough time for 1 update.
409 controller->PerformMoreUpdates(
410 controller->Now() + base::TimeDelta::FromMilliseconds(120));
411 EXPECT_FALSE(thread.hasPendingTask());
412 EXPECT_EQ(1, m_numTotalUploads);
413
414 // Complete one upload.
415 makeQueryResultAvailable();
416
417 controller->setUpdateMoreTexturesTime(
418 base::TimeDelta::FromMilliseconds(100));
419 controller->setUpdateMoreTexturesSize(1);
420 // Enough time for 2 updates.
421 controller->PerformMoreUpdates(
422 controller->Now() + base::TimeDelta::FromMilliseconds(220));
423 runPendingTask(&thread, controller.get());
424 EXPECT_FALSE(thread.hasPendingTask());
425 EXPECT_TRUE(client.readyToFinalizeCalled());
426 EXPECT_EQ(3, m_numTotalUploads);
427 }
428
429 TEST_F(ResourceUpdateControllerTest, NoMoreUpdates)
430 {
431 FakeResourceUpdateControllerClient client;
432 FakeThread thread;
433
434 setMaxUploadCountPerUpdate(1);
435 appendFullUploadsToUpdateQueue(2);
436 appendPartialUploadsToUpdateQueue(0);
437
438 DebugScopedSetImplThreadAndMainThreadBlocked
439 implThreadAndMainThreadBlocked(&m_proxy);
440 scoped_ptr<FakeResourceUpdateController> controller(FakeResourceUpdateContro ller::Create(&client, &thread, m_queue.Pass(), m_resourceProvider.get()));
441
442 controller->setNow(
443 controller->Now() + base::TimeDelta::FromMilliseconds(1));
444 controller->setUpdateMoreTexturesTime(
445 base::TimeDelta::FromMilliseconds(100));
446 controller->setUpdateMoreTexturesSize(1);
447 // Enough time for 3 updates but only 2 necessary.
448 controller->PerformMoreUpdates(
449 controller->Now() + base::TimeDelta::FromMilliseconds(310));
450 runPendingTask(&thread, controller.get());
451 EXPECT_FALSE(thread.hasPendingTask());
452 EXPECT_TRUE(client.readyToFinalizeCalled());
453 EXPECT_EQ(2, m_numTotalUploads);
454
455 controller->setUpdateMoreTexturesTime(
456 base::TimeDelta::FromMilliseconds(100));
457 controller->setUpdateMoreTexturesSize(1);
458 // Enough time for updates but no more updates left.
459 controller->PerformMoreUpdates(
460 controller->Now() + base::TimeDelta::FromMilliseconds(310));
461 // 0-delay task used to call readyToFinalizeTextureUpdates().
462 runPendingTask(&thread, controller.get());
463 EXPECT_FALSE(thread.hasPendingTask());
464 EXPECT_TRUE(client.readyToFinalizeCalled());
465 EXPECT_EQ(2, m_numTotalUploads);
466 }
467
468 TEST_F(ResourceUpdateControllerTest, UpdatesCompleteInFiniteTime)
469 {
470 FakeResourceUpdateControllerClient client;
471 FakeThread thread;
472
473 setMaxUploadCountPerUpdate(1);
474 appendFullUploadsToUpdateQueue(2);
475 appendPartialUploadsToUpdateQueue(0);
476
477 DebugScopedSetImplThreadAndMainThreadBlocked
478 implThreadAndMainThreadBlocked(&m_proxy);
479 scoped_ptr<FakeResourceUpdateController> controller(FakeResourceUpdateContro ller::Create(&client, &thread, m_queue.Pass(), m_resourceProvider.get()));
480
481 controller->setNow(
482 controller->Now() + base::TimeDelta::FromMilliseconds(1));
483 controller->setUpdateMoreTexturesTime(
484 base::TimeDelta::FromMilliseconds(500));
485 controller->setUpdateMoreTexturesSize(1);
486
487 for (int i = 0; i < 100; i++) {
488 if (client.readyToFinalizeCalled())
489 break;
490
491 // Not enough time for any updates.
492 controller->PerformMoreUpdates(
493 controller->Now() + base::TimeDelta::FromMilliseconds(400));
494
495 if (thread.hasPendingTask())
496 runPendingTask(&thread, controller.get());
497 }
498
499 EXPECT_FALSE(thread.hasPendingTask());
500 EXPECT_TRUE(client.readyToFinalizeCalled());
501 EXPECT_EQ(2, m_numTotalUploads);
502 }
503
504 } // namespace
505 } // namespace cc
OLDNEW
« no previous file with comments | « cc/resource_update_controller.cc ('k') | cc/resource_update_queue.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698