Loading services/surfaceflinger/CompositionEngine/include/compositionengine/impl/planner/CachedSet.h +1 −0 Original line number Diff line number Diff line Loading @@ -78,6 +78,7 @@ public: size_t getDisplayCost() const; bool hasBufferUpdate() const; bool hasRenderedBuffer() const { return mTexture != nullptr; } bool hasReadyBuffer() const; // Decomposes this CachedSet into a vector of its layers as individual CachedSets Loading services/surfaceflinger/CompositionEngine/src/planner/Flattener.cpp +6 −1 Original line number Diff line number Diff line Loading @@ -91,7 +91,7 @@ NonBufferHash Flattener::flattenLayers(const std::vector<const LayerState*>& lay void Flattener::renderCachedSets(renderengine::RenderEngine& renderEngine, const OutputCompositionState& outputState) { if (!mNewCachedSet) { if (!mNewCachedSet || mNewCachedSet->hasRenderedBuffer()) { return; } Loading Loading @@ -393,6 +393,11 @@ void Flattener::buildCachedSets(time_point now) { return; } // Don't try to build a new cached set if we already have a new one in progress if (mNewCachedSet) { return; } std::vector<Run> runs = findCandidateRuns(now); std::optional<Run> bestRun = findBestRun(runs); Loading services/surfaceflinger/CompositionEngine/tests/planner/CachedSetTest.cpp +1 −0 Original line number Diff line number Diff line Loading @@ -134,6 +134,7 @@ void expectReadyBuffer(const CachedSet& cachedSet) { EXPECT_NE(nullptr, cachedSet.getBuffer()); EXPECT_NE(nullptr, cachedSet.getDrawFence()); EXPECT_TRUE(cachedSet.hasReadyBuffer()); EXPECT_TRUE(cachedSet.hasRenderedBuffer()); } TEST_F(CachedSetTest, createFromLayer) { Loading services/surfaceflinger/CompositionEngine/tests/planner/FlattenerTest.cpp +40 −0 Original line number Diff line number Diff line Loading @@ -786,5 +786,45 @@ TEST_F(FlattenerTest, flattenLayers_flattenSkipsLayerWithBlurBehind) { EXPECT_EQ(overrideBuffer3, overrideBuffer4); } TEST_F(FlattenerTest, flattenLayers_renderCachedSets_doesNotRenderTwice) { auto& layerState1 = mTestLayers[0]->layerState; auto& layerState2 = mTestLayers[1]->layerState; const auto& overrideBuffer1 = layerState1->getOutputLayer()->getState().overrideInfo.buffer; const auto& overrideBuffer2 = layerState2->getOutputLayer()->getState().overrideInfo.buffer; const std::vector<const LayerState*> layers = { layerState1.get(), layerState2.get(), }; initializeFlattener(layers); // Mark the layers inactive mTime += 200ms; // layers would be flattened but the buffer would not be overridden EXPECT_CALL(mRenderEngine, drawLayers(_, _, _, _, _, _)).WillOnce(Return(NO_ERROR)); initializeOverrideBuffer(layers); EXPECT_EQ(getNonBufferHash(layers), mFlattener->flattenLayers(layers, getNonBufferHash(layers), mTime)); mFlattener->renderCachedSets(mRenderEngine, mOutputState); EXPECT_EQ(nullptr, overrideBuffer1); EXPECT_EQ(nullptr, overrideBuffer2); // Simulate attempting to render prior to merging the new cached set with the layer stack. // Here we should not try to re-render. EXPECT_CALL(mRenderEngine, drawLayers(_, _, _, _, _, _)).Times(0); mFlattener->renderCachedSets(mRenderEngine, mOutputState); // We provide the override buffer now that it's rendered EXPECT_NE(getNonBufferHash(layers), mFlattener->flattenLayers(layers, getNonBufferHash(layers), mTime)); mFlattener->renderCachedSets(mRenderEngine, mOutputState); EXPECT_NE(nullptr, overrideBuffer1); EXPECT_EQ(overrideBuffer2, overrideBuffer1); } } // namespace } // namespace android::compositionengine Loading
services/surfaceflinger/CompositionEngine/include/compositionengine/impl/planner/CachedSet.h +1 −0 Original line number Diff line number Diff line Loading @@ -78,6 +78,7 @@ public: size_t getDisplayCost() const; bool hasBufferUpdate() const; bool hasRenderedBuffer() const { return mTexture != nullptr; } bool hasReadyBuffer() const; // Decomposes this CachedSet into a vector of its layers as individual CachedSets Loading
services/surfaceflinger/CompositionEngine/src/planner/Flattener.cpp +6 −1 Original line number Diff line number Diff line Loading @@ -91,7 +91,7 @@ NonBufferHash Flattener::flattenLayers(const std::vector<const LayerState*>& lay void Flattener::renderCachedSets(renderengine::RenderEngine& renderEngine, const OutputCompositionState& outputState) { if (!mNewCachedSet) { if (!mNewCachedSet || mNewCachedSet->hasRenderedBuffer()) { return; } Loading Loading @@ -393,6 +393,11 @@ void Flattener::buildCachedSets(time_point now) { return; } // Don't try to build a new cached set if we already have a new one in progress if (mNewCachedSet) { return; } std::vector<Run> runs = findCandidateRuns(now); std::optional<Run> bestRun = findBestRun(runs); Loading
services/surfaceflinger/CompositionEngine/tests/planner/CachedSetTest.cpp +1 −0 Original line number Diff line number Diff line Loading @@ -134,6 +134,7 @@ void expectReadyBuffer(const CachedSet& cachedSet) { EXPECT_NE(nullptr, cachedSet.getBuffer()); EXPECT_NE(nullptr, cachedSet.getDrawFence()); EXPECT_TRUE(cachedSet.hasReadyBuffer()); EXPECT_TRUE(cachedSet.hasRenderedBuffer()); } TEST_F(CachedSetTest, createFromLayer) { Loading
services/surfaceflinger/CompositionEngine/tests/planner/FlattenerTest.cpp +40 −0 Original line number Diff line number Diff line Loading @@ -786,5 +786,45 @@ TEST_F(FlattenerTest, flattenLayers_flattenSkipsLayerWithBlurBehind) { EXPECT_EQ(overrideBuffer3, overrideBuffer4); } TEST_F(FlattenerTest, flattenLayers_renderCachedSets_doesNotRenderTwice) { auto& layerState1 = mTestLayers[0]->layerState; auto& layerState2 = mTestLayers[1]->layerState; const auto& overrideBuffer1 = layerState1->getOutputLayer()->getState().overrideInfo.buffer; const auto& overrideBuffer2 = layerState2->getOutputLayer()->getState().overrideInfo.buffer; const std::vector<const LayerState*> layers = { layerState1.get(), layerState2.get(), }; initializeFlattener(layers); // Mark the layers inactive mTime += 200ms; // layers would be flattened but the buffer would not be overridden EXPECT_CALL(mRenderEngine, drawLayers(_, _, _, _, _, _)).WillOnce(Return(NO_ERROR)); initializeOverrideBuffer(layers); EXPECT_EQ(getNonBufferHash(layers), mFlattener->flattenLayers(layers, getNonBufferHash(layers), mTime)); mFlattener->renderCachedSets(mRenderEngine, mOutputState); EXPECT_EQ(nullptr, overrideBuffer1); EXPECT_EQ(nullptr, overrideBuffer2); // Simulate attempting to render prior to merging the new cached set with the layer stack. // Here we should not try to re-render. EXPECT_CALL(mRenderEngine, drawLayers(_, _, _, _, _, _)).Times(0); mFlattener->renderCachedSets(mRenderEngine, mOutputState); // We provide the override buffer now that it's rendered EXPECT_NE(getNonBufferHash(layers), mFlattener->flattenLayers(layers, getNonBufferHash(layers), mTime)); mFlattener->renderCachedSets(mRenderEngine, mOutputState); EXPECT_NE(nullptr, overrideBuffer1); EXPECT_EQ(overrideBuffer2, overrideBuffer1); } } // namespace } // namespace android::compositionengine