Index: cc/texture_layer_unittest.cc |
diff --git a/cc/texture_layer_unittest.cc b/cc/texture_layer_unittest.cc |
index c58ae90bb56f1bdd19cf26687ebd1389257a174a..85d90b22f89e67fa3575b78593803d5619b4c96d 100644 |
--- a/cc/texture_layer_unittest.cc |
+++ b/cc/texture_layer_unittest.cc |
@@ -4,11 +4,16 @@ |
#include "cc/texture_layer.h" |
+#include <string> |
+ |
+#include "base/callback.h" |
#include "cc/layer_tree_host.h" |
+#include "cc/layer_tree_impl.h" |
#include "cc/single_thread_proxy.h" |
#include "cc/test/fake_impl_proxy.h" |
#include "cc/test/fake_layer_tree_host_client.h" |
#include "cc/test/fake_layer_tree_host_impl.h" |
+#include "cc/test/layer_tree_test_common.h" |
#include "cc/texture_layer_impl.h" |
#include "cc/thread.h" |
#include "testing/gmock/include/gmock/gmock.h" |
@@ -100,7 +105,7 @@ TEST_F(TextureLayerTest, syncImplWhenDrawing) |
scoped_refptr<TextureLayer> testLayer = TextureLayer::create(0); |
ASSERT_TRUE(testLayer); |
scoped_ptr<TextureLayerImpl> implLayer; |
- implLayer = TextureLayerImpl::create(m_hostImpl.activeTree(), 1); |
+ implLayer = TextureLayerImpl::create(m_hostImpl.activeTree(), 1, false); |
ASSERT_TRUE(implLayer); |
EXPECT_CALL(*m_layerTreeHost, acquireLayerTextures()).Times(AnyNumber()); |
@@ -184,5 +189,215 @@ TEST_F(TextureLayerTest, syncImplWhenRemovingFromTree) |
Mock::VerifyAndClearExpectations(m_layerTreeHost.get()); |
} |
+class MockMailboxCallback { |
+public: |
+ MOCK_METHOD2(Release, void(const std::string& mailbox, unsigned syncPoint)); |
+}; |
+ |
+struct CommonMailboxObjects { |
+ CommonMailboxObjects() |
+ : m_mailbox1(64, '1') |
+ , m_mailbox2(64, '2') |
+ { |
+ m_releaseMailbox1 = base::Bind(&MockMailboxCallback::Release, |
+ base::Unretained(&m_mockCallback), |
+ m_mailbox1); |
+ m_releaseMailbox2 = base::Bind(&MockMailboxCallback::Release, |
+ base::Unretained(&m_mockCallback), |
+ m_mailbox2); |
+ } |
+ |
+ std::string m_mailbox1; |
+ std::string m_mailbox2; |
+ MockMailboxCallback m_mockCallback; |
+ TextureLayer::MailboxCallback m_releaseMailbox1; |
+ TextureLayer::MailboxCallback m_releaseMailbox2; |
+}; |
+ |
+class TextureLayerWithMailboxTest : public TextureLayerTest { |
+protected: |
+ virtual void TearDown() |
+ { |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ TextureLayerTest::TearDown(); |
+ } |
+ |
+ CommonMailboxObjects m_testData; |
+}; |
+ |
+TEST_F(TextureLayerWithMailboxTest, replaceMailboxOnMainThreadBeforeCommit) |
+{ |
+ scoped_refptr<TextureLayer> testLayer = TextureLayer::createForMailbox(); |
+ ASSERT_TRUE(testLayer); |
+ |
+ EXPECT_CALL(*m_layerTreeHost, acquireLayerTextures()).Times(0); |
+ EXPECT_CALL(*m_layerTreeHost, setNeedsCommit()).Times(AnyNumber()); |
+ m_layerTreeHost->setRootLayer(testLayer); |
+ Mock::VerifyAndClearExpectations(m_layerTreeHost.get()); |
+ |
+ EXPECT_CALL(*m_layerTreeHost, acquireLayerTextures()).Times(0); |
+ EXPECT_CALL(*m_layerTreeHost, setNeedsCommit()).Times(AtLeast(1)); |
+ testLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+ Mock::VerifyAndClearExpectations(m_layerTreeHost.get()); |
+ |
+ EXPECT_CALL(*m_layerTreeHost, acquireLayerTextures()).Times(0); |
+ EXPECT_CALL(*m_layerTreeHost, setNeedsCommit()).Times(AtLeast(1)); |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ testLayer->setTextureMailbox(m_testData.m_mailbox2, |
+ m_testData.m_releaseMailbox2); |
+ Mock::VerifyAndClearExpectations(m_layerTreeHost.get()); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ |
+ EXPECT_CALL(*m_layerTreeHost, acquireLayerTextures()).Times(0); |
+ EXPECT_CALL(*m_layerTreeHost, setNeedsCommit()).Times(AtLeast(1)); |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox2, _)).Times(1); |
+ testLayer->setTextureMailbox(std::string(), |
+ TextureLayer::MailboxCallback()); |
+ Mock::VerifyAndClearExpectations(m_layerTreeHost.get()); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ |
+ // Test destructor. |
+ EXPECT_CALL(*m_layerTreeHost, setNeedsCommit()).Times(AtLeast(1)); |
+ testLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+} |
+ |
+class TextureLayerImplWithMailboxThreadedCallback : public ThreadedTest { |
+public: |
+ TextureLayerImplWithMailboxThreadedCallback() |
+ : m_resetMailbox(false) |
+ { |
+ } |
+ |
+ // Make sure callback is received on main and doesn't block the impl thread. |
+ void releaseCallback(unsigned syncPoint) { |
+ EXPECT_EQ(true, proxy()->isMainThread()); |
+ endTest(); |
+ } |
+ |
+ virtual void beginTest() OVERRIDE |
+ { |
+ m_layer = TextureLayer::createForMailbox(); |
+ m_layer->setIsDrawable(true); |
+ m_layerTreeHost->setRootLayer(m_layer); |
+ m_layer->setTextureMailbox( |
+ std::string(64, '1'), |
+ base::Bind( |
+ &TextureLayerImplWithMailboxThreadedCallback::releaseCallback, |
+ base::Unretained(this))); |
+ postSetNeedsCommitToMainThread(); |
+ } |
+ |
+ virtual void didCommit() OVERRIDE |
+ { |
+ if (m_resetMailbox) |
+ return; |
+ |
+ m_layer->setTextureMailbox(std::string(), |
+ TextureLayer::MailboxCallback()); |
+ m_resetMailbox = true; |
+ } |
+ |
+ virtual void afterTest() OVERRIDE |
+ { |
+ } |
+ |
+private: |
+ bool m_resetMailbox; |
+ scoped_refptr<TextureLayer> m_layer; |
+}; |
+ |
+SINGLE_AND_MULTI_THREAD_TEST_F(TextureLayerImplWithMailboxThreadedCallback); |
+ |
+class TextureLayerImplWithMailboxTest : public TextureLayerTest { |
+protected: |
+ virtual void SetUp() |
+ { |
+ TextureLayerTest::SetUp(); |
+ m_layerTreeHost.reset(new MockLayerImplTreeHost); |
+ EXPECT_TRUE(m_hostImpl.initializeRenderer(createFakeOutputSurface())); |
+ } |
+ |
+ CommonMailboxObjects m_testData; |
+}; |
+ |
+TEST_F(TextureLayerImplWithMailboxTest, testImplLayerCallbacks) |
+{ |
+ scoped_ptr<TextureLayerImpl> implLayer; |
+ implLayer = TextureLayerImpl::create(m_hostImpl.activeTree(), 1, true); |
+ ASSERT_TRUE(implLayer); |
+ |
+ // Test setting identical mailbox. |
+ EXPECT_CALL(m_testData.m_mockCallback, Release(_, _)).Times(0); |
+ implLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+ implLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ |
+ // Test multiple commits without a draw. |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ implLayer->setTextureMailbox(m_testData.m_mailbox2, |
+ m_testData.m_releaseMailbox2); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ |
+ // Test resetting the mailbox. |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox2, _)).Times(1); |
+ implLayer->setTextureMailbox(std::string(), |
+ TextureLayer::MailboxCallback()); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ |
+ // Test destructor. |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ implLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+} |
+ |
+TEST_F(TextureLayerImplWithMailboxTest, testDestructorCallbackOnCreatedResource) |
+{ |
+ scoped_ptr<TextureLayerImpl> implLayer; |
+ implLayer = TextureLayerImpl::create(m_hostImpl.activeTree(), 1, true); |
+ ASSERT_TRUE(implLayer); |
+ |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ implLayer->setTextureMailbox(m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+ implLayer->willDraw(m_hostImpl.activeTree()->resource_provider()); |
+ implLayer->didDraw(m_hostImpl.activeTree()->resource_provider()); |
+ implLayer->setTextureMailbox(std::string(), |
+ TextureLayer::MailboxCallback()); |
+} |
+ |
+TEST_F(TextureLayerImplWithMailboxTest, testCallbackOnInUseResource) |
+{ |
+ ResourceProvider *provider = m_hostImpl.activeTree()->resource_provider(); |
+ ResourceProvider::ResourceId id = |
+ provider->createResourceFromTextureMailbox( |
+ m_testData.m_mailbox1, |
+ m_testData.m_releaseMailbox1); |
+ |
+ // Transfer some resources to the parent. |
+ ResourceProvider::ResourceIdArray resourceIdsToTransfer; |
+ resourceIdsToTransfer.push_back(id); |
+ TransferableResourceList list; |
+ provider->prepareSendToParent(resourceIdsToTransfer, &list); |
+ EXPECT_TRUE(provider->inUseByConsumer(id)); |
+ EXPECT_CALL(m_testData.m_mockCallback, Release(_, _)).Times(0); |
+ provider->deleteResource(id); |
+ Mock::VerifyAndClearExpectations(&m_testData.m_mockCallback); |
+ EXPECT_CALL(m_testData.m_mockCallback, |
+ Release(m_testData.m_mailbox1, _)).Times(1); |
+ provider->receiveFromParent(list); |
+} |
+ |
} // namespace |
} // namespace cc |