1 // Copyright 2013 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/trees/layer_tree_host.h" 6 7 #include "base/bind.h" 8 #include "cc/layers/delegated_renderer_layer.h" 9 #include "cc/layers/delegated_renderer_layer_client.h" 10 #include "cc/layers/delegated_renderer_layer_impl.h" 11 #include "cc/output/compositor_frame.h" 12 #include "cc/output/compositor_frame_ack.h" 13 #include "cc/output/delegated_frame_data.h" 14 #include "cc/quads/shared_quad_state.h" 15 #include "cc/quads/texture_draw_quad.h" 16 #include "cc/test/fake_delegated_renderer_layer.h" 17 #include "cc/test/fake_delegated_renderer_layer_impl.h" 18 #include "cc/test/fake_output_surface.h" 19 #include "cc/test/layer_tree_test.h" 20 #include "cc/trees/layer_tree_impl.h" 21 #include "gpu/GLES2/gl2extchromium.h" 22 23 namespace cc { 24 namespace { 25 26 // These tests deal with delegated renderer layers. 27 class LayerTreeHostDelegatedTest : public LayerTreeTest { 28 protected: 29 scoped_ptr<DelegatedFrameData> CreateFrameData(gfx::Rect root_output_rect, 30 gfx::Rect root_damage_rect) { 31 scoped_ptr<DelegatedFrameData> frame(new DelegatedFrameData); 32 33 scoped_ptr<RenderPass> root_pass(RenderPass::Create()); 34 root_pass->SetNew(RenderPass::Id(1, 1), 35 root_output_rect, 36 root_damage_rect, 37 gfx::Transform()); 38 frame->render_pass_list.push_back(root_pass.Pass()); 39 return frame.Pass(); 40 } 41 42 scoped_ptr<DelegatedFrameData> CreateInvalidFrameData( 43 gfx::Rect root_output_rect, 44 gfx::Rect root_damage_rect) { 45 scoped_ptr<DelegatedFrameData> frame(new DelegatedFrameData); 46 47 scoped_ptr<RenderPass> root_pass(RenderPass::Create()); 48 root_pass->SetNew(RenderPass::Id(1, 1), 49 root_output_rect, 50 root_damage_rect, 51 gfx::Transform()); 52 53 scoped_ptr<SharedQuadState> shared_quad_state = SharedQuadState::Create(); 54 55 gfx::Rect rect = root_output_rect; 56 gfx::Rect opaque_rect = root_output_rect; 57 // An invalid resource id! The resource isn't part of the frame. 58 unsigned resource_id = 5; 59 bool premultiplied_alpha = false; 60 gfx::PointF uv_top_left = gfx::PointF(0.f, 0.f); 61 gfx::PointF uv_bottom_right = gfx::PointF(1.f, 1.f); 62 SkColor background_color = 0; 63 float vertex_opacity[4] = {1.f, 1.f, 1.f, 1.f}; 64 bool flipped = false; 65 66 scoped_ptr<TextureDrawQuad> invalid_draw_quad = TextureDrawQuad::Create(); 67 invalid_draw_quad->SetNew(shared_quad_state.get(), 68 rect, 69 opaque_rect, 70 resource_id, 71 premultiplied_alpha, 72 uv_top_left, 73 uv_bottom_right, 74 background_color, 75 vertex_opacity, 76 flipped); 77 root_pass->quad_list.push_back(invalid_draw_quad.PassAs<DrawQuad>()); 78 79 root_pass->shared_quad_state_list.push_back(shared_quad_state.Pass()); 80 81 frame->render_pass_list.push_back(root_pass.Pass()); 82 return frame.Pass(); 83 } 84 85 void AddTransferableResource(DelegatedFrameData* frame, 86 ResourceProvider::ResourceId resource_id) { 87 TransferableResource resource; 88 resource.id = resource_id; 89 frame->resource_list.push_back(resource); 90 } 91 92 void AddTextureQuad(DelegatedFrameData* frame, 93 ResourceProvider::ResourceId resource_id) { 94 scoped_ptr<SharedQuadState> sqs = SharedQuadState::Create(); 95 scoped_ptr<TextureDrawQuad> quad = TextureDrawQuad::Create(); 96 float vertex_opacity[4] = { 1.f, 1.f, 1.f, 1.f }; 97 quad->SetNew(sqs.get(), 98 gfx::Rect(0, 0, 10, 10), 99 gfx::Rect(0, 0, 10, 10), 100 resource_id, 101 false, 102 gfx::PointF(0.f, 0.f), 103 gfx::PointF(1.f, 1.f), 104 SK_ColorTRANSPARENT, 105 vertex_opacity, 106 false); 107 frame->render_pass_list[0]->shared_quad_state_list.push_back(sqs.Pass()); 108 frame->render_pass_list[0]->quad_list.push_back(quad.PassAs<DrawQuad>()); 109 } 110 111 scoped_ptr<DelegatedFrameData> CreateEmptyFrameData() { 112 scoped_ptr<DelegatedFrameData> frame(new DelegatedFrameData); 113 return frame.Pass(); 114 } 115 116 117 static ResourceProvider::ResourceId AppendResourceId( 118 std::vector<ResourceProvider::ResourceId>* resources_in_last_sent_frame, 119 ResourceProvider::ResourceId resource_id) { 120 resources_in_last_sent_frame->push_back(resource_id); 121 return resource_id; 122 } 123 124 void ReturnUnusedResourcesFromParent(LayerTreeHostImpl* host_impl) { 125 DelegatedFrameData* delegated_frame_data = 126 output_surface()->last_sent_frame().delegated_frame_data.get(); 127 if (!delegated_frame_data) 128 return; 129 130 std::vector<ResourceProvider::ResourceId> resources_in_last_sent_frame; 131 for (size_t i = 0; i < delegated_frame_data->render_pass_list.size(); ++i) { 132 RenderPass* pass = delegated_frame_data->render_pass_list.at(i); 133 for (size_t j = 0; j < pass->quad_list.size(); ++j) { 134 DrawQuad* quad = pass->quad_list[j]; 135 quad->IterateResources(base::Bind(&AppendResourceId, 136 &resources_in_last_sent_frame)); 137 } 138 } 139 140 std::vector<ResourceProvider::ResourceId> resources_to_return; 141 142 const TransferableResourceArray& resources_held_by_parent = 143 output_surface()->resources_held_by_parent(); 144 for (size_t i = 0; i < resources_held_by_parent.size(); ++i) { 145 ResourceProvider::ResourceId resource_in_parent = 146 resources_held_by_parent[i].id; 147 bool resource_in_parent_is_not_part_of_frame = 148 std::find(resources_in_last_sent_frame.begin(), 149 resources_in_last_sent_frame.end(), 150 resource_in_parent) == resources_in_last_sent_frame.end(); 151 if (resource_in_parent_is_not_part_of_frame) 152 resources_to_return.push_back(resource_in_parent); 153 } 154 155 if (resources_to_return.empty()) 156 return; 157 158 CompositorFrameAck ack; 159 for (size_t i = 0; i < resources_to_return.size(); ++i) 160 output_surface()->ReturnResource(resources_to_return[i], &ack); 161 host_impl->OnSwapBuffersComplete(&ack); 162 } 163 }; 164 165 class LayerTreeHostDelegatedTestCaseSingleDelegatedLayer 166 : public LayerTreeHostDelegatedTest, 167 public DelegatedRendererLayerClient { 168 public: 169 virtual void SetupTree() OVERRIDE { 170 root_ = Layer::Create(); 171 root_->SetAnchorPoint(gfx::PointF()); 172 root_->SetBounds(gfx::Size(10, 10)); 173 174 delegated_ = FakeDelegatedRendererLayer::Create(this); 175 delegated_->SetAnchorPoint(gfx::PointF()); 176 delegated_->SetBounds(gfx::Size(10, 10)); 177 delegated_->SetIsDrawable(true); 178 179 root_->AddChild(delegated_); 180 layer_tree_host()->SetRootLayer(root_); 181 LayerTreeHostDelegatedTest::SetupTree(); 182 } 183 184 virtual void BeginTest() OVERRIDE { 185 PostSetNeedsCommitToMainThread(); 186 } 187 188 virtual void AfterTest() OVERRIDE {} 189 190 virtual void DidCommitFrameData() OVERRIDE {} 191 192 protected: 193 scoped_refptr<Layer> root_; 194 scoped_refptr<DelegatedRendererLayer> delegated_; 195 }; 196 197 class LayerTreeHostDelegatedTestClientDidCommitCallback 198 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 199 public: 200 LayerTreeHostDelegatedTestClientDidCommitCallback() 201 : LayerTreeHostDelegatedTestCaseSingleDelegatedLayer(), 202 num_did_commit_frame_data_(0) {} 203 204 virtual void DidCommit() OVERRIDE { 205 if (TestEnded()) 206 return; 207 208 EXPECT_EQ(1, num_did_commit_frame_data_); 209 EndTest(); 210 } 211 212 virtual void BeginTest() OVERRIDE { 213 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 1, 1), 214 gfx::Rect(0, 0, 1, 1))); 215 PostSetNeedsCommitToMainThread(); 216 } 217 218 virtual void DidCommitFrameData() OVERRIDE { 219 num_did_commit_frame_data_++; 220 } 221 222 protected: 223 int num_did_commit_frame_data_; 224 }; 225 226 SINGLE_AND_MULTI_THREAD_TEST_F( 227 LayerTreeHostDelegatedTestClientDidCommitCallback); 228 229 class LayerTreeHostDelegatedTestCreateChildId 230 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 231 public: 232 LayerTreeHostDelegatedTestCreateChildId() 233 : LayerTreeHostDelegatedTestCaseSingleDelegatedLayer(), 234 num_activates_(0), 235 did_reset_child_id_(false) {} 236 237 virtual void DidCommit() OVERRIDE { 238 if (TestEnded()) 239 return; 240 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 1, 1), 241 gfx::Rect(0, 0, 1, 1))); 242 } 243 244 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 245 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 246 FakeDelegatedRendererLayerImpl* delegated_impl = 247 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 248 249 WebKit::WebGraphicsContext3D* context = 250 host_impl->resource_provider()->GraphicsContext3D(); 251 252 ++num_activates_; 253 switch (num_activates_) { 254 case 2: 255 EXPECT_TRUE(delegated_impl->ChildId()); 256 EXPECT_FALSE(did_reset_child_id_); 257 258 context->loseContextCHROMIUM(GL_GUILTY_CONTEXT_RESET_ARB, 259 GL_INNOCENT_CONTEXT_RESET_ARB); 260 break; 261 case 3: 262 EXPECT_TRUE(delegated_impl->ChildId()); 263 EXPECT_TRUE(did_reset_child_id_); 264 EndTest(); 265 break; 266 } 267 } 268 269 virtual void InitializedRendererOnThread(LayerTreeHostImpl* host_impl, 270 bool success) OVERRIDE { 271 EXPECT_TRUE(success); 272 273 if (num_activates_ < 2) 274 return; 275 276 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 277 FakeDelegatedRendererLayerImpl* delegated_impl = 278 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 279 280 EXPECT_EQ(2, num_activates_); 281 EXPECT_FALSE(delegated_impl->ChildId()); 282 did_reset_child_id_ = true; 283 } 284 285 virtual void AfterTest() OVERRIDE {} 286 287 protected: 288 int num_activates_; 289 bool did_reset_child_id_; 290 }; 291 292 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestCreateChildId); 293 294 class LayerTreeHostDelegatedTestLayerUsesFrameDamage 295 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 296 public: 297 LayerTreeHostDelegatedTestLayerUsesFrameDamage() 298 : LayerTreeHostDelegatedTestCaseSingleDelegatedLayer(), 299 first_draw_for_source_frame_(true) {} 300 301 virtual void DidCommit() OVERRIDE { 302 int next_source_frame_number = layer_tree_host()->source_frame_number(); 303 switch (next_source_frame_number) { 304 case 1: 305 // The first time the layer gets a frame the whole layer should be 306 // damaged. 307 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 1, 1), 308 gfx::Rect(0, 0, 1, 1))); 309 break; 310 case 2: 311 // Should create a total amount of gfx::Rect(2, 2, 10, 6) damage. 312 // The frame size is 20x20 while the layer is 10x10, so this should 313 // produce a gfx::Rect(1, 1, 5, 3) damage rect. 314 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 20, 20), 315 gfx::Rect(2, 2, 5, 5))); 316 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 20, 20), 317 gfx::Rect(7, 2, 5, 6))); 318 break; 319 case 3: 320 // Should create zero damage. 321 layer_tree_host()->SetNeedsCommit(); 322 break; 323 case 4: 324 // Should damage the full viewport. 325 delegated_->SetBounds(gfx::Size(2, 2)); 326 break; 327 case 5: 328 // Should create zero damage. 329 layer_tree_host()->SetNeedsCommit(); 330 break; 331 case 6: 332 // Should damage the full layer. 333 delegated_->SetBounds(gfx::Size(6, 6)); 334 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 5, 5), 335 gfx::Rect(1, 1, 2, 2))); 336 break; 337 case 7: 338 // Should create zero damage. 339 layer_tree_host()->SetNeedsCommit(); 340 break; 341 case 8: 342 // Should damage the full layer. 343 delegated_->SetDisplaySize(gfx::Size(10, 10)); 344 break; 345 case 9: 346 // Should create zero damage. 347 layer_tree_host()->SetNeedsCommit(); 348 break; 349 case 10: 350 // Setting an empty frame should damage the whole layer the 351 // first time. 352 delegated_->SetFrameData(CreateEmptyFrameData()); 353 break; 354 case 11: 355 // Setting an empty frame shouldn't damage anything after the 356 // first time. 357 delegated_->SetFrameData(CreateEmptyFrameData()); 358 break; 359 case 12: 360 // Having valid content to display agains should damage the whole layer. 361 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 10, 10), 362 gfx::Rect(5, 5, 1, 1))); 363 break; 364 case 13: 365 // An invalid frame isn't used, so it should not cause damage. 366 delegated_->SetFrameData(CreateInvalidFrameData(gfx::Rect(0, 0, 10, 10), 367 gfx::Rect(5, 5, 1, 1))); 368 break; 369 case 14: 370 // Should create gfx::Rect(1, 1, 2, 2) of damage. The frame size is 371 // 5x5 and the display size is now set to 10x10, so this should result 372 // in a gfx::Rect(2, 2, 4, 4) damage rect. 373 delegated_->SetFrameData(CreateFrameData(gfx::Rect(0, 0, 5, 5), 374 gfx::Rect(1, 1, 2, 2))); 375 break; 376 case 15: 377 // Should create zero damage. 378 layer_tree_host()->SetNeedsCommit(); 379 break; 380 } 381 first_draw_for_source_frame_ = true; 382 } 383 384 virtual bool PrepareToDrawOnThread(LayerTreeHostImpl* host_impl, 385 LayerTreeHostImpl::FrameData* frame, 386 bool result) OVERRIDE { 387 EXPECT_TRUE(result); 388 389 if (!first_draw_for_source_frame_) 390 return result; 391 392 gfx::RectF damage_rect; 393 if (!frame->has_no_damage) { 394 damage_rect = frame->render_passes.back()->damage_rect; 395 } else { 396 // If there is no damage, then we have no render passes to send. 397 EXPECT_TRUE(frame->render_passes.empty()); 398 } 399 400 switch (host_impl->active_tree()->source_frame_number()) { 401 case 0: 402 // First frame is damaged because of viewport resize. 403 EXPECT_EQ(gfx::RectF(0.f, 0.f, 10.f, 10.f).ToString(), 404 damage_rect.ToString()); 405 break; 406 case 1: 407 EXPECT_EQ(gfx::RectF(0.f, 0.f, 10.f, 10.f).ToString(), 408 damage_rect.ToString()); 409 break; 410 case 2: 411 EXPECT_EQ(gfx::RectF(1.f, 1.f, 5.f, 3.f).ToString(), 412 damage_rect.ToString()); 413 break; 414 case 3: 415 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 416 damage_rect.ToString()); 417 break; 418 case 4: 419 EXPECT_EQ(gfx::RectF(0.f, 0.f, 10.f, 10.f).ToString(), 420 damage_rect.ToString()); 421 break; 422 case 5: 423 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 424 damage_rect.ToString()); 425 break; 426 case 6: 427 EXPECT_EQ(gfx::RectF(0.f, 0.f, 6.f, 6.f).ToString(), 428 damage_rect.ToString()); 429 break; 430 case 7: 431 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 432 damage_rect.ToString()); 433 break; 434 case 8: 435 EXPECT_EQ(gfx::RectF(0.f, 0.f, 6.f, 6.f).ToString(), 436 damage_rect.ToString()); 437 break; 438 case 9: 439 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 440 damage_rect.ToString()); 441 break; 442 case 10: 443 EXPECT_EQ(gfx::RectF(0.f, 0.f, 6.f, 6.f).ToString(), 444 damage_rect.ToString()); 445 break; 446 case 11: 447 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 448 damage_rect.ToString()); 449 break; 450 case 12: 451 EXPECT_EQ(gfx::RectF(0.f, 0.f, 6.f, 6.f).ToString(), 452 damage_rect.ToString()); 453 break; 454 case 13: 455 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 456 damage_rect.ToString()); 457 break; 458 case 14: 459 EXPECT_EQ(gfx::RectF(2.f, 2.f, 4.f, 4.f).ToString(), 460 damage_rect.ToString()); 461 break; 462 case 15: 463 EXPECT_EQ(gfx::RectF(0.f, 0.f, 0.f, 0.f).ToString(), 464 damage_rect.ToString()); 465 EndTest(); 466 break; 467 } 468 469 return result; 470 } 471 472 protected: 473 bool first_draw_for_source_frame_; 474 }; 475 476 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestLayerUsesFrameDamage); 477 478 class LayerTreeHostDelegatedTestMergeResources 479 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 480 public: 481 virtual void BeginTest() OVERRIDE { 482 // Push two frames to the delegated renderer layer with no commit between. 483 484 // The first frame has resource 999. 485 scoped_ptr<DelegatedFrameData> frame1 = 486 CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 487 AddTextureQuad(frame1.get(), 999); 488 AddTransferableResource(frame1.get(), 999); 489 delegated_->SetFrameData(frame1.Pass()); 490 491 // The second frame uses resource 999 still, but also adds 555. 492 scoped_ptr<DelegatedFrameData> frame2 = 493 CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 494 AddTextureQuad(frame2.get(), 999); 495 AddTextureQuad(frame2.get(), 555); 496 AddTransferableResource(frame2.get(), 555); 497 delegated_->SetFrameData(frame2.Pass()); 498 499 PostSetNeedsCommitToMainThread(); 500 } 501 502 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 503 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 504 FakeDelegatedRendererLayerImpl* delegated_impl = 505 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 506 507 const ResourceProvider::ResourceIdMap& map = 508 host_impl->resource_provider()->GetChildToParentMap( 509 delegated_impl->ChildId()); 510 511 // Both frames' resources should be in the parent's resource provider. 512 EXPECT_EQ(2u, map.size()); 513 EXPECT_EQ(1u, map.count(999)); 514 EXPECT_EQ(1u, map.count(555)); 515 516 EXPECT_EQ(2u, delegated_impl->Resources().size()); 517 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 518 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 519 520 EndTest(); 521 } 522 523 virtual void AfterTest() OVERRIDE {} 524 }; 525 526 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestMergeResources); 527 528 class LayerTreeHostDelegatedTestRemapResourcesInQuads 529 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 530 public: 531 virtual void BeginTest() OVERRIDE { 532 // Generate a frame with two resources in it. 533 scoped_ptr<DelegatedFrameData> frame = 534 CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 535 AddTextureQuad(frame.get(), 999); 536 AddTransferableResource(frame.get(), 999); 537 AddTextureQuad(frame.get(), 555); 538 AddTransferableResource(frame.get(), 555); 539 delegated_->SetFrameData(frame.Pass()); 540 541 PostSetNeedsCommitToMainThread(); 542 } 543 544 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 545 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 546 FakeDelegatedRendererLayerImpl* delegated_impl = 547 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 548 549 const ResourceProvider::ResourceIdMap& map = 550 host_impl->resource_provider()->GetChildToParentMap( 551 delegated_impl->ChildId()); 552 553 // The frame's resource should be in the parent's resource provider. 554 EXPECT_EQ(2u, map.size()); 555 EXPECT_EQ(1u, map.count(999)); 556 EXPECT_EQ(1u, map.count(555)); 557 558 ResourceProvider::ResourceId parent_resource_id1 = map.find(999)->second; 559 EXPECT_NE(parent_resource_id1, 999u); 560 ResourceProvider::ResourceId parent_resource_id2 = map.find(555)->second; 561 EXPECT_NE(parent_resource_id2, 555u); 562 563 // The resources in the quads should be remapped to the parent's namespace. 564 const TextureDrawQuad* quad1 = TextureDrawQuad::MaterialCast( 565 delegated_impl->RenderPassesInDrawOrder()[0]->quad_list[0]); 566 EXPECT_EQ(parent_resource_id1, quad1->resource_id); 567 const TextureDrawQuad* quad2 = TextureDrawQuad::MaterialCast( 568 delegated_impl->RenderPassesInDrawOrder()[0]->quad_list[1]); 569 EXPECT_EQ(parent_resource_id2, quad2->resource_id); 570 571 EndTest(); 572 } 573 574 virtual void AfterTest() OVERRIDE {} 575 }; 576 577 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestRemapResourcesInQuads); 578 579 class LayerTreeHostDelegatedTestReturnUnusedResources 580 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 581 public: 582 virtual void BeginTest() OVERRIDE { 583 PostSetNeedsCommitToMainThread(); 584 } 585 586 virtual void DidCommitAndDrawFrame() OVERRIDE { 587 scoped_ptr<DelegatedFrameData> frame; 588 TransferableResourceArray resources; 589 590 int next_source_frame_number = layer_tree_host()->source_frame_number(); 591 switch (next_source_frame_number) { 592 case 1: 593 // Generate a frame with two resources in it. 594 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 595 AddTextureQuad(frame.get(), 999); 596 AddTransferableResource(frame.get(), 999); 597 AddTextureQuad(frame.get(), 555); 598 AddTransferableResource(frame.get(), 555); 599 delegated_->SetFrameData(frame.Pass()); 600 break; 601 case 2: 602 // Retrieve unused resources to the main thread. 603 // TODO(danakj): Shouldn't need to commit to get resources. 604 layer_tree_host()->SetNeedsCommit(); 605 return; 606 case 3: 607 // All of the resources are in use. 608 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 609 EXPECT_EQ(0u, resources.size()); 610 611 // Keep using 999 but stop using 555. 612 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 613 AddTextureQuad(frame.get(), 999); 614 AddTextureQuad(frame.get(), 444); 615 AddTransferableResource(frame.get(), 444); 616 delegated_->SetFrameData(frame.Pass()); 617 break; 618 case 4: 619 // Retrieve unused resources to the main thread. 620 // TODO(danakj): Shouldn't need to commit to get resources. 621 layer_tree_host()->SetNeedsCommit(); 622 return; 623 case 5: 624 // 555 is no longer in use. 625 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 626 EXPECT_EQ(1u, resources.size()); 627 EXPECT_EQ(555u, resources[0].id); 628 629 // Stop using any resources. 630 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 631 delegated_->SetFrameData(frame.Pass()); 632 break; 633 case 6: 634 // Postpone collecting resources for a frame. They should still be there 635 // the next frame. 636 layer_tree_host()->SetNeedsCommit(); 637 return; 638 case 7: 639 // 444 and 999 are no longer in use. 640 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 641 EXPECT_EQ(2u, resources.size()); 642 if (resources[0].id == 999) { 643 EXPECT_EQ(999u, resources[0].id); 644 EXPECT_EQ(444u, resources[1].id); 645 } else { 646 EXPECT_EQ(444u, resources[0].id); 647 EXPECT_EQ(999u, resources[1].id); 648 } 649 EndTest(); 650 break; 651 } 652 653 // Resource are never immediately released. 654 TransferableResourceArray empty_resources; 655 delegated_->TakeUnusedResourcesForChildCompositor(&empty_resources); 656 EXPECT_TRUE(empty_resources.empty()); 657 } 658 659 virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, 660 bool result) OVERRIDE { 661 ReturnUnusedResourcesFromParent(host_impl); 662 } 663 664 virtual void AfterTest() OVERRIDE {} 665 }; 666 667 SINGLE_AND_MULTI_THREAD_TEST_F( 668 LayerTreeHostDelegatedTestReturnUnusedResources); 669 670 class LayerTreeHostDelegatedTestReusedResources 671 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 672 public: 673 virtual void BeginTest() OVERRIDE { 674 PostSetNeedsCommitToMainThread(); 675 } 676 677 virtual void DidCommitAndDrawFrame() OVERRIDE { 678 scoped_ptr<DelegatedFrameData> frame; 679 TransferableResourceArray resources; 680 681 int next_source_frame_number = layer_tree_host()->source_frame_number(); 682 switch (next_source_frame_number) { 683 case 1: 684 // Generate a frame with some resources in it. 685 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 686 AddTextureQuad(frame.get(), 999); 687 AddTransferableResource(frame.get(), 999); 688 AddTextureQuad(frame.get(), 555); 689 AddTransferableResource(frame.get(), 555); 690 AddTextureQuad(frame.get(), 444); 691 AddTransferableResource(frame.get(), 444); 692 delegated_->SetFrameData(frame.Pass()); 693 break; 694 case 2: 695 // Retrieve unused resources to the main thread. 696 // TODO(danakj): Shouldn't need to commit to get resources. 697 layer_tree_host()->SetNeedsCommit(); 698 return; 699 case 3: 700 // All of the resources are in use. 701 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 702 EXPECT_EQ(0u, resources.size()); 703 704 // Keep using 999 but stop using 555 and 444. 705 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 706 AddTextureQuad(frame.get(), 999); 707 delegated_->SetFrameData(frame.Pass()); 708 709 // Resource are not immediately released. 710 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 711 EXPECT_EQ(0u, resources.size()); 712 713 // Now using 555 and 444 again, but not 999. 714 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 715 AddTextureQuad(frame.get(), 555); 716 AddTextureQuad(frame.get(), 444); 717 delegated_->SetFrameData(frame.Pass()); 718 break; 719 case 4: 720 // Retrieve unused resources to the main thread. 721 // TODO(danakj): Shouldn't need to commit to get resources. 722 layer_tree_host()->SetNeedsCommit(); 723 return; 724 case 5: 725 // The 999 resource is the only unused one. 726 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 727 EXPECT_EQ(1u, resources.size()); 728 EXPECT_EQ(999u, resources[0].id); 729 EndTest(); 730 break; 731 } 732 } 733 734 virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, 735 bool result) OVERRIDE { 736 ReturnUnusedResourcesFromParent(host_impl); 737 } 738 739 virtual void AfterTest() OVERRIDE {} 740 }; 741 742 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestReusedResources); 743 744 class LayerTreeHostDelegatedTestFrameBeforeAck 745 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 746 public: 747 virtual void BeginTest() OVERRIDE { 748 PostSetNeedsCommitToMainThread(); 749 } 750 751 virtual void DidCommitAndDrawFrame() OVERRIDE { 752 scoped_ptr<DelegatedFrameData> frame; 753 TransferableResourceArray resources; 754 755 int next_source_frame_number = layer_tree_host()->source_frame_number(); 756 switch (next_source_frame_number) { 757 case 1: 758 // Generate a frame with some resources in it. 759 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 760 AddTextureQuad(frame.get(), 999); 761 AddTransferableResource(frame.get(), 999); 762 AddTextureQuad(frame.get(), 555); 763 AddTransferableResource(frame.get(), 555); 764 AddTextureQuad(frame.get(), 444); 765 AddTransferableResource(frame.get(), 444); 766 delegated_->SetFrameData(frame.Pass()); 767 break; 768 case 2: 769 // Retrieve unused resources to the main thread. 770 // TODO(danakj): Shouldn't need to commit to get resources. 771 layer_tree_host()->SetNeedsCommit(); 772 return; 773 case 3: 774 // All of the resources are in use. 775 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 776 EXPECT_EQ(0u, resources.size()); 777 778 // Keep using 999 but stop using 555 and 444. 779 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 780 AddTextureQuad(frame.get(), 999); 781 delegated_->SetFrameData(frame.Pass()); 782 783 // Resource are not immediately released. 784 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 785 EXPECT_EQ(0u, resources.size()); 786 787 // The parent compositor (this one) does a commit. 788 break; 789 case 4: 790 // Retrieve unused resources to the main thread. 791 // TODO(danakj): Shouldn't need to commit to get resources. 792 layer_tree_host()->SetNeedsCommit(); 793 return; 794 case 5: 795 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 796 EXPECT_EQ(2u, resources.size()); 797 if (resources[0].id == 555) { 798 EXPECT_EQ(555u, resources[0].id); 799 EXPECT_EQ(444u, resources[1].id); 800 } else { 801 EXPECT_EQ(444u, resources[0].id); 802 EXPECT_EQ(555u, resources[1].id); 803 } 804 805 // The child compositor sends a frame before receiving an for the 806 // second frame. It uses 999, 444, and 555 again. 807 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 808 AddTextureQuad(frame.get(), 999); 809 AddTextureQuad(frame.get(), 555); 810 AddTextureQuad(frame.get(), 444); 811 delegated_->SetFrameData(frame.Pass()); 812 break; 813 } 814 } 815 816 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 817 if (host_impl->active_tree()->source_frame_number() != 5) 818 return; 819 820 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 821 FakeDelegatedRendererLayerImpl* delegated_impl = 822 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 823 824 const ResourceProvider::ResourceIdMap& map = 825 host_impl->resource_provider()->GetChildToParentMap( 826 delegated_impl->ChildId()); 827 828 // The bad frame should be dropped. So we should only have one quad (the 829 // one with resource 999) on the impl tree. And only 999 will be present 830 // in the parent's resource provider. 831 EXPECT_EQ(1u, map.size()); 832 EXPECT_EQ(1u, map.count(999)); 833 834 EXPECT_EQ(1u, delegated_impl->Resources().size()); 835 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 836 837 const RenderPass* pass = delegated_impl->RenderPassesInDrawOrder()[0]; 838 EXPECT_EQ(1u, pass->quad_list.size()); 839 const TextureDrawQuad* quad = TextureDrawQuad::MaterialCast( 840 pass->quad_list[0]); 841 EXPECT_EQ(map.find(999)->second, quad->resource_id); 842 843 EndTest(); 844 } 845 846 virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, 847 bool result) OVERRIDE { 848 ReturnUnusedResourcesFromParent(host_impl); 849 } 850 851 virtual void AfterTest() OVERRIDE {} 852 }; 853 854 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestFrameBeforeAck); 855 856 class LayerTreeHostDelegatedTestFrameBeforeTakeResources 857 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 858 public: 859 virtual void BeginTest() OVERRIDE { 860 PostSetNeedsCommitToMainThread(); 861 } 862 863 virtual void DidCommitAndDrawFrame() OVERRIDE { 864 scoped_ptr<DelegatedFrameData> frame; 865 TransferableResourceArray resources; 866 867 int next_source_frame_number = layer_tree_host()->source_frame_number(); 868 switch (next_source_frame_number) { 869 case 1: 870 // Generate a frame with some resources in it. 871 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 872 AddTextureQuad(frame.get(), 999); 873 AddTransferableResource(frame.get(), 999); 874 AddTextureQuad(frame.get(), 555); 875 AddTransferableResource(frame.get(), 555); 876 AddTextureQuad(frame.get(), 444); 877 AddTransferableResource(frame.get(), 444); 878 delegated_->SetFrameData(frame.Pass()); 879 break; 880 case 2: 881 // Retrieve unused resources to the main thread. 882 // TODO(danakj): Shouldn't need to commit to get resources. 883 layer_tree_host()->SetNeedsCommit(); 884 return; 885 case 3: 886 // All of the resources are in use. 887 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 888 EXPECT_EQ(0u, resources.size()); 889 890 // Keep using 999 but stop using 555 and 444. 891 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 892 AddTextureQuad(frame.get(), 999); 893 delegated_->SetFrameData(frame.Pass()); 894 895 // Resource are not immediately released. 896 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 897 EXPECT_EQ(0u, resources.size()); 898 899 // The parent compositor (this one) does a commit. 900 break; 901 case 4: 902 // Retrieve unused resources to the main thread. 903 // TODO(danakj): Shouldn't need to commit to get resources. 904 layer_tree_host()->SetNeedsCommit(); 905 return; 906 case 5: 907 // The child compositor sends a frame before taking resources back 908 // from the previous commit. This frame makes use of the resources 555 909 // and 444, which were just released during commit. 910 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 911 AddTextureQuad(frame.get(), 999); 912 AddTextureQuad(frame.get(), 555); 913 AddTextureQuad(frame.get(), 444); 914 delegated_->SetFrameData(frame.Pass()); 915 916 // The resources are used by the new frame so are not returned. 917 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 918 EXPECT_EQ(0u, resources.size()); 919 break; 920 case 6: 921 // Retrieve unused resources to the main thread. 922 // TODO(danakj): Shouldn't need to commit to get resources. 923 layer_tree_host()->SetNeedsCommit(); 924 return; 925 case 7: 926 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 927 EXPECT_EQ(0u, resources.size()); 928 EndTest(); 929 break; 930 } 931 } 932 933 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 934 if (host_impl->active_tree()->source_frame_number() != 5) 935 return; 936 937 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 938 FakeDelegatedRendererLayerImpl* delegated_impl = 939 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 940 941 const ResourceProvider::ResourceIdMap& map = 942 host_impl->resource_provider()->GetChildToParentMap( 943 delegated_impl->ChildId()); 944 945 // The third frame has all of the resources in it again, the delegated 946 // renderer layer should continue to own the resources for it. 947 EXPECT_EQ(3u, map.size()); 948 EXPECT_EQ(1u, map.count(999)); 949 EXPECT_EQ(1u, map.count(555)); 950 EXPECT_EQ(1u, map.count(444)); 951 952 EXPECT_EQ(3u, delegated_impl->Resources().size()); 953 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 954 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 955 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(444)->second)); 956 957 const RenderPass* pass = delegated_impl->RenderPassesInDrawOrder()[0]; 958 EXPECT_EQ(3u, pass->quad_list.size()); 959 const TextureDrawQuad* quad1 = TextureDrawQuad::MaterialCast( 960 pass->quad_list[0]); 961 EXPECT_EQ(map.find(999)->second, quad1->resource_id); 962 const TextureDrawQuad* quad2 = TextureDrawQuad::MaterialCast( 963 pass->quad_list[1]); 964 EXPECT_EQ(map.find(555)->second, quad2->resource_id); 965 const TextureDrawQuad* quad3 = TextureDrawQuad::MaterialCast( 966 pass->quad_list[2]); 967 EXPECT_EQ(map.find(444)->second, quad3->resource_id); 968 } 969 970 virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, 971 bool result) OVERRIDE { 972 ReturnUnusedResourcesFromParent(host_impl); 973 } 974 975 virtual void AfterTest() OVERRIDE {} 976 }; 977 978 SINGLE_AND_MULTI_THREAD_TEST_F( 979 LayerTreeHostDelegatedTestFrameBeforeTakeResources); 980 981 class LayerTreeHostDelegatedTestBadFrame 982 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 983 public: 984 virtual void BeginTest() OVERRIDE { 985 PostSetNeedsCommitToMainThread(); 986 } 987 988 virtual void DidCommitAndDrawFrame() OVERRIDE { 989 scoped_ptr<DelegatedFrameData> frame; 990 TransferableResourceArray resources; 991 992 int next_source_frame_number = layer_tree_host()->source_frame_number(); 993 switch (next_source_frame_number) { 994 case 1: 995 // Generate a frame with some resources in it. 996 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 997 AddTextureQuad(frame.get(), 999); 998 AddTransferableResource(frame.get(), 999); 999 AddTextureQuad(frame.get(), 555); 1000 AddTransferableResource(frame.get(), 555); 1001 delegated_->SetFrameData(frame.Pass()); 1002 break; 1003 case 2: 1004 // Retrieve unused resources to the main thread. 1005 // TODO(danakj): Shouldn't need to commit to get resources. 1006 layer_tree_host()->SetNeedsCommit(); 1007 return; 1008 case 3: 1009 // All of the resources are in use. 1010 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1011 EXPECT_EQ(0u, resources.size()); 1012 1013 // Generate a bad frame with a resource the layer doesn't have. The 1014 // 885 and 775 resources are unknown, while ownership of the legit 444 1015 // resource is passed in here. The bad frame does not use any of the 1016 // previous resources, 999 or 555. 1017 // A bad quad is present both before and after the good quad. 1018 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1019 AddTextureQuad(frame.get(), 885); 1020 AddTextureQuad(frame.get(), 444); 1021 AddTransferableResource(frame.get(), 444); 1022 AddTextureQuad(frame.get(), 775); 1023 delegated_->SetFrameData(frame.Pass()); 1024 1025 // The parent compositor (this one) does a commit. 1026 break; 1027 case 4: 1028 // Retrieve unused resources to the main thread. 1029 // TODO(danakj): Shouldn't need to commit to get resources. 1030 layer_tree_host()->SetNeedsCommit(); 1031 return; 1032 case 5: 1033 // The bad frame's resource is given back to the child compositor. 1034 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1035 EXPECT_EQ(1u, resources.size()); 1036 EXPECT_EQ(444u, resources[0].id); 1037 1038 // Now send a good frame with 999 again. 1039 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1040 AddTextureQuad(frame.get(), 999); 1041 delegated_->SetFrameData(frame.Pass()); 1042 break; 1043 case 6: 1044 // Retrieve unused resources to the main thread. 1045 // TODO(danakj): Shouldn't need to commit to get resources. 1046 layer_tree_host()->SetNeedsCommit(); 1047 return; 1048 case 7: 1049 // The unused 555 from the last good frame is now released. 1050 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1051 EXPECT_EQ(1u, resources.size()); 1052 EXPECT_EQ(555u, resources[0].id); 1053 1054 EndTest(); 1055 break; 1056 } 1057 } 1058 1059 virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, 1060 bool result) OVERRIDE { 1061 if (host_impl->active_tree()->source_frame_number() < 1) 1062 return; 1063 1064 ReturnUnusedResourcesFromParent(host_impl); 1065 1066 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 1067 FakeDelegatedRendererLayerImpl* delegated_impl = 1068 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 1069 1070 const ResourceProvider::ResourceIdMap& map = 1071 host_impl->resource_provider()->GetChildToParentMap( 1072 delegated_impl->ChildId()); 1073 1074 switch (host_impl->active_tree()->source_frame_number()) { 1075 case 1: { 1076 // We have the first good frame with just 990 and 555 in it. 1077 // layer. 1078 EXPECT_EQ(2u, map.size()); 1079 EXPECT_EQ(1u, map.count(999)); 1080 EXPECT_EQ(1u, map.count(555)); 1081 1082 EXPECT_EQ(2u, delegated_impl->Resources().size()); 1083 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1084 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1085 1086 const RenderPass* pass = delegated_impl->RenderPassesInDrawOrder()[0]; 1087 EXPECT_EQ(2u, pass->quad_list.size()); 1088 const TextureDrawQuad* quad1 = TextureDrawQuad::MaterialCast( 1089 pass->quad_list[0]); 1090 EXPECT_EQ(map.find(999)->second, quad1->resource_id); 1091 const TextureDrawQuad* quad2 = TextureDrawQuad::MaterialCast( 1092 pass->quad_list[1]); 1093 EXPECT_EQ(map.find(555)->second, quad2->resource_id); 1094 break; 1095 } 1096 case 3: { 1097 // We only keep resources from the last valid frame. 1098 EXPECT_EQ(2u, map.size()); 1099 EXPECT_EQ(1u, map.count(999)); 1100 EXPECT_EQ(1u, map.count(555)); 1101 1102 EXPECT_EQ(2u, delegated_impl->Resources().size()); 1103 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1104 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1105 1106 // The bad frame is dropped though, we still have the frame with 999 and 1107 // 555 in it. 1108 const RenderPass* pass = delegated_impl->RenderPassesInDrawOrder()[0]; 1109 EXPECT_EQ(2u, pass->quad_list.size()); 1110 const TextureDrawQuad* quad1 = TextureDrawQuad::MaterialCast( 1111 pass->quad_list[0]); 1112 EXPECT_EQ(map.find(999)->second, quad1->resource_id); 1113 const TextureDrawQuad* quad2 = TextureDrawQuad::MaterialCast( 1114 pass->quad_list[1]); 1115 EXPECT_EQ(map.find(555)->second, quad2->resource_id); 1116 break; 1117 } 1118 case 5: 1119 // Resources given to our parent compositor will be returned now, but 1120 // the DelegatedRendererLayerImpl doesn't know about it until the next 1121 // commit. 1122 // TODO(danakj): Shouldn't need a commit to return resources to the 1123 // DelegatedRendererLayerImpl or to the main thread. 1124 break; 1125 case 6: { 1126 // We have the new good frame with just 999 in it. 1127 EXPECT_EQ(1u, map.size()); 1128 EXPECT_EQ(1u, map.count(999)); 1129 1130 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1131 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1132 1133 const RenderPass* pass = delegated_impl->RenderPassesInDrawOrder()[0]; 1134 EXPECT_EQ(1u, pass->quad_list.size()); 1135 const TextureDrawQuad* quad1 = TextureDrawQuad::MaterialCast( 1136 pass->quad_list[0]); 1137 EXPECT_EQ(map.find(999)->second, quad1->resource_id); 1138 break; 1139 } 1140 } 1141 } 1142 1143 virtual void AfterTest() OVERRIDE {} 1144 }; 1145 1146 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestBadFrame); 1147 1148 class LayerTreeHostDelegatedTestUnnamedResource 1149 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 1150 public: 1151 virtual void BeginTest() OVERRIDE { 1152 PostSetNeedsCommitToMainThread(); 1153 } 1154 1155 virtual void DidCommit() OVERRIDE { 1156 scoped_ptr<DelegatedFrameData> frame; 1157 TransferableResourceArray resources; 1158 1159 int next_source_frame_number = layer_tree_host()->source_frame_number(); 1160 switch (next_source_frame_number) { 1161 case 1: 1162 // This frame includes two resources in it, but only uses one. 1163 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1164 AddTransferableResource(frame.get(), 999); 1165 AddTextureQuad(frame.get(), 555); 1166 AddTransferableResource(frame.get(), 555); 1167 delegated_->SetFrameData(frame.Pass()); 1168 break; 1169 case 2: 1170 // The unused resource should be returned. 1171 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1172 EXPECT_EQ(1u, resources.size()); 1173 EXPECT_EQ(999u, resources[0].id); 1174 1175 EndTest(); 1176 break; 1177 } 1178 } 1179 1180 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 1181 if (host_impl->active_tree()->source_frame_number() != 1) 1182 return; 1183 1184 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 1185 FakeDelegatedRendererLayerImpl* delegated_impl = 1186 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 1187 1188 const ResourceProvider::ResourceIdMap& map = 1189 host_impl->resource_provider()->GetChildToParentMap( 1190 delegated_impl->ChildId()); 1191 1192 // The layer only held on to the resource that was used. 1193 EXPECT_EQ(1u, map.size()); 1194 EXPECT_EQ(1u, map.count(555)); 1195 1196 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1197 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1198 } 1199 1200 virtual void AfterTest() OVERRIDE {} 1201 }; 1202 1203 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestUnnamedResource); 1204 1205 class LayerTreeHostDelegatedTestDontLeakResource 1206 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 1207 public: 1208 virtual void BeginTest() OVERRIDE { 1209 PostSetNeedsCommitToMainThread(); 1210 } 1211 1212 virtual void DidCommit() OVERRIDE { 1213 scoped_ptr<DelegatedFrameData> frame; 1214 TransferableResourceArray resources; 1215 1216 int next_source_frame_number = layer_tree_host()->source_frame_number(); 1217 switch (next_source_frame_number) { 1218 case 1: 1219 // This frame includes two resources in it. 1220 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1221 AddTextureQuad(frame.get(), 999); 1222 AddTransferableResource(frame.get(), 999); 1223 AddTextureQuad(frame.get(), 555); 1224 AddTransferableResource(frame.get(), 555); 1225 delegated_->SetFrameData(frame.Pass()); 1226 1227 // But then we immediately stop using 999. 1228 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1229 AddTextureQuad(frame.get(), 555); 1230 delegated_->SetFrameData(frame.Pass()); 1231 break; 1232 case 2: 1233 // The unused resource should be returned. 1234 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1235 EXPECT_EQ(1u, resources.size()); 1236 EXPECT_EQ(999u, resources[0].id); 1237 1238 EndTest(); 1239 break; 1240 } 1241 } 1242 1243 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 1244 if (host_impl->active_tree()->source_frame_number() != 1) 1245 return; 1246 1247 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 1248 FakeDelegatedRendererLayerImpl* delegated_impl = 1249 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 1250 1251 const ResourceProvider::ResourceIdMap& map = 1252 host_impl->resource_provider()->GetChildToParentMap( 1253 delegated_impl->ChildId()); 1254 1255 // The layer only held on to the resource that was used. 1256 EXPECT_EQ(1u, map.size()); 1257 EXPECT_EQ(1u, map.count(555)); 1258 1259 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1260 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1261 } 1262 1263 virtual void AfterTest() OVERRIDE {} 1264 }; 1265 1266 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestDontLeakResource); 1267 1268 class LayerTreeHostDelegatedTestResourceSentToParent 1269 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 1270 public: 1271 virtual void DidCommitAndDrawFrame() OVERRIDE { 1272 scoped_ptr<DelegatedFrameData> frame; 1273 TransferableResourceArray resources; 1274 1275 int next_source_frame_number = layer_tree_host()->source_frame_number(); 1276 switch (next_source_frame_number) { 1277 case 1: 1278 // This frame includes two resources in it. 1279 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1280 AddTextureQuad(frame.get(), 999); 1281 AddTransferableResource(frame.get(), 999); 1282 AddTextureQuad(frame.get(), 555); 1283 AddTransferableResource(frame.get(), 555); 1284 delegated_->SetFrameData(frame.Pass()); 1285 break; 1286 case 2: 1287 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1288 EXPECT_EQ(0u, resources.size()); 1289 1290 // 999 is in use in the grandparent compositor, generate a frame without 1291 // it present. 1292 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1293 AddTextureQuad(frame.get(), 555); 1294 delegated_->SetFrameData(frame.Pass()); 1295 break; 1296 case 3: 1297 // Since 999 is in the grandparent it is not returned. 1298 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1299 EXPECT_EQ(0u, resources.size()); 1300 1301 // The impl side will get back the resource at some point. 1302 // TODO(danakj): The test should work without this. 1303 layer_tree_host()->SetNeedsCommit(); 1304 break; 1305 case 4: 1306 // 999 was returned from the grandparent and could be released. 1307 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1308 EXPECT_EQ(1u, resources.size()); 1309 EXPECT_EQ(999u, resources[0].id); 1310 1311 EndTest(); 1312 break; 1313 } 1314 } 1315 1316 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 1317 if (host_impl->active_tree()->source_frame_number() < 1) 1318 return; 1319 1320 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 1321 FakeDelegatedRendererLayerImpl* delegated_impl = 1322 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 1323 1324 const ResourceProvider::ResourceIdMap& map = 1325 host_impl->resource_provider()->GetChildToParentMap( 1326 delegated_impl->ChildId()); 1327 1328 switch (host_impl->active_tree()->source_frame_number()) { 1329 case 1: { 1330 EXPECT_EQ(2u, map.size()); 1331 EXPECT_EQ(1u, map.count(999)); 1332 EXPECT_EQ(1u, map.count(555)); 1333 1334 EXPECT_EQ(2u, delegated_impl->Resources().size()); 1335 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1336 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1337 1338 // The 999 resource will be sent to a grandparent compositor. 1339 break; 1340 } 1341 case 2: { 1342 EXPECT_EQ(2u, map.size()); 1343 EXPECT_EQ(1u, map.count(999)); 1344 EXPECT_EQ(1u, map.count(555)); 1345 1346 // 999 is in the parent, so not held by delegated renderer layer. 1347 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1348 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1349 1350 // Receive 999 back from the grandparent. 1351 CompositorFrameAck ack; 1352 output_surface()->ReturnResource(map.find(999)->second, &ack); 1353 host_impl->OnSwapBuffersComplete(&ack); 1354 break; 1355 } 1356 case 3: 1357 // 999 should be released. 1358 EXPECT_EQ(1u, map.size()); 1359 EXPECT_EQ(1u, map.count(555)); 1360 1361 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1362 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1363 break; 1364 } 1365 } 1366 1367 virtual void AfterTest() OVERRIDE {} 1368 1369 TransferableResource resource_in_grandparent; 1370 }; 1371 1372 SINGLE_AND_MULTI_THREAD_DELEGATING_RENDERER_TEST_F( 1373 LayerTreeHostDelegatedTestResourceSentToParent); 1374 1375 class LayerTreeHostDelegatedTestCommitWithoutTake 1376 : public LayerTreeHostDelegatedTestCaseSingleDelegatedLayer { 1377 public: 1378 virtual void BeginTest() OVERRIDE { 1379 // Prevent drawing with resources that are sent to the grandparent. 1380 layer_tree_host()->SetViewportSize(gfx::Size()); 1381 PostSetNeedsCommitToMainThread(); 1382 } 1383 1384 virtual void DidCommit() OVERRIDE { 1385 scoped_ptr<DelegatedFrameData> frame; 1386 TransferableResourceArray resources; 1387 1388 int next_source_frame_number = layer_tree_host()->source_frame_number(); 1389 switch (next_source_frame_number) { 1390 case 1: 1391 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1392 AddTextureQuad(frame.get(), 999); 1393 AddTransferableResource(frame.get(), 999); 1394 AddTextureQuad(frame.get(), 555); 1395 AddTransferableResource(frame.get(), 555); 1396 AddTextureQuad(frame.get(), 444); 1397 AddTransferableResource(frame.get(), 444); 1398 delegated_->SetFrameData(frame.Pass()); 1399 break; 1400 case 2: 1401 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1402 EXPECT_EQ(0u, resources.size()); 1403 1404 // Stop using 999 and 444 in this frame and commit. 1405 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1406 AddTextureQuad(frame.get(), 555); 1407 delegated_->SetFrameData(frame.Pass()); 1408 break; 1409 case 3: 1410 // Don't take resources here, but set a new frame that uses 999 again. 1411 frame = CreateFrameData(gfx::Rect(0, 0, 1, 1), gfx::Rect(0, 0, 1, 1)); 1412 AddTextureQuad(frame.get(), 999); 1413 AddTextureQuad(frame.get(), 555); 1414 delegated_->SetFrameData(frame.Pass()); 1415 break; 1416 case 4: 1417 // 999 and 555 are in use, but 444 should be returned now. 1418 delegated_->TakeUnusedResourcesForChildCompositor(&resources); 1419 EXPECT_EQ(1u, resources.size()); 1420 EXPECT_EQ(444u, resources[0].id); 1421 1422 EndTest(); 1423 break; 1424 } 1425 } 1426 1427 virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE { 1428 if (host_impl->active_tree()->source_frame_number() < 1) 1429 return; 1430 1431 LayerImpl* root_impl = host_impl->active_tree()->root_layer(); 1432 FakeDelegatedRendererLayerImpl* delegated_impl = 1433 static_cast<FakeDelegatedRendererLayerImpl*>(root_impl->children()[0]); 1434 1435 const ResourceProvider::ResourceIdMap& map = 1436 host_impl->resource_provider()->GetChildToParentMap( 1437 delegated_impl->ChildId()); 1438 1439 switch (host_impl->active_tree()->source_frame_number()) { 1440 case 1: 1441 EXPECT_EQ(3u, map.size()); 1442 EXPECT_EQ(1u, map.count(999)); 1443 EXPECT_EQ(1u, map.count(555)); 1444 EXPECT_EQ(1u, map.count(444)); 1445 1446 EXPECT_EQ(3u, delegated_impl->Resources().size()); 1447 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1448 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1449 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(444)->second)); 1450 break; 1451 case 2: 1452 EXPECT_EQ(1u, map.size()); 1453 EXPECT_EQ(1u, map.count(555)); 1454 1455 EXPECT_EQ(1u, delegated_impl->Resources().size()); 1456 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1457 break; 1458 case 3: 1459 EXPECT_EQ(2u, map.size()); 1460 EXPECT_EQ(1u, map.count(999)); 1461 EXPECT_EQ(1u, map.count(555)); 1462 1463 EXPECT_EQ(2u, delegated_impl->Resources().size()); 1464 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(999)->second)); 1465 EXPECT_EQ(1u, delegated_impl->Resources().count(map.find(555)->second)); 1466 } 1467 } 1468 1469 virtual void AfterTest() OVERRIDE {} 1470 }; 1471 1472 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostDelegatedTestCommitWithoutTake); 1473 1474 } // namespace 1475 } // namespace cc 1476