SF: Move/Refactor prepareFrame to CompositionEngine
This refactors both the SurfaceFlinger::prepareFrame() and
HWComposer::prepare() logic, moving things to to
compositionEngine::Output and compositionEngine::Display.
Along the way, the composition related state is moved out of HWComposer
up to compositionengine::OutputCompositionState.
As there were some subtleties, tests are also added to cover the
refactored logic.
Test: atest libsurfaceflinger_unittest libcompositionengine_test
Bug: 121291683
Change-Id: I2713e9e52751ca0523f6348ffdb51ead8bca5235
diff --git a/services/surfaceflinger/CompositionEngine/tests/OutputTest.cpp b/services/surfaceflinger/CompositionEngine/tests/OutputTest.cpp
index 6f087d9..aa35d25 100644
--- a/services/surfaceflinger/CompositionEngine/tests/OutputTest.cpp
+++ b/services/surfaceflinger/CompositionEngine/tests/OutputTest.cpp
@@ -17,6 +17,7 @@
#include <cmath>
#include <compositionengine/impl/Output.h>
+#include <compositionengine/impl/OutputCompositionState.h>
#include <compositionengine/mock/CompositionEngine.h>
#include <compositionengine/mock/DisplayColorProfile.h>
#include <compositionengine/mock/Layer.h>
@@ -37,8 +38,7 @@
using testing::ReturnRef;
using testing::StrictMock;
-class OutputTest : public testing::Test {
-public:
+struct OutputTest : public testing::Test {
OutputTest() {
mOutput.setDisplayColorProfileForTest(
std::unique_ptr<DisplayColorProfile>(mDisplayColorProfile));
@@ -46,7 +46,6 @@
mOutput.editState().bounds = kDefaultDisplaySize;
}
- ~OutputTest() override = default;
static const Rect kDefaultDisplaySize;
@@ -58,7 +57,7 @@
const Rect OutputTest::kDefaultDisplaySize{100, 200};
-/* ------------------------------------------------------------------------
+/*
* Basic construction
*/
@@ -77,7 +76,7 @@
EXPECT_FALSE(mOutput.isValid());
}
-/* ------------------------------------------------------------------------
+/*
* Output::setCompositionEnabled()
*/
@@ -108,7 +107,7 @@
EXPECT_THAT(mOutput.getState().dirtyRegion, RegionEq(Region(kDefaultDisplaySize)));
}
-/* ------------------------------------------------------------------------
+/*
* Output::setProjection()
*/
@@ -130,7 +129,7 @@
EXPECT_EQ(needsFiltering, mOutput.getState().needsFiltering);
}
-/* ------------------------------------------------------------------------
+/*
* Output::setBounds()
*/
@@ -147,7 +146,7 @@
EXPECT_THAT(mOutput.getState().dirtyRegion, RegionEq(Region(Rect(displaySize))));
}
-/* ------------------------------------------------------------------------
+/*
* Output::setLayerStackFilter()
*/
@@ -161,7 +160,7 @@
EXPECT_THAT(mOutput.getState().dirtyRegion, RegionEq(Region(kDefaultDisplaySize)));
}
-/* ------------------------------------------------------------------------
+/*
* Output::setColorTransform
*/
@@ -200,7 +199,7 @@
EXPECT_THAT(mOutput.getState().dirtyRegion, RegionEq(Region(kDefaultDisplaySize)));
}
-/* ------------------------------------------------------------------------
+/*
* Output::setColorMode
*/
@@ -239,7 +238,7 @@
EXPECT_THAT(mOutput.getState().dirtyRegion, RegionEq(Region()));
}
-/* ------------------------------------------------------------------------
+/*
* Output::setRenderSurface()
*/
@@ -254,7 +253,7 @@
EXPECT_EQ(Rect(newDisplaySize), mOutput.getState().bounds);
}
-/* ------------------------------------------------------------------------
+/*
* Output::getDirtyRegion()
*/
@@ -283,7 +282,7 @@
}
}
-/* ------------------------------------------------------------------------
+/*
* Output::belongsInOutput()
*/
@@ -310,7 +309,7 @@
EXPECT_FALSE(mOutput.belongsInOutput(layerStack2, false));
}
-/* ------------------------------------------------------------------------
+/*
* Output::getOutputLayerForLayer()
*/
@@ -342,7 +341,7 @@
EXPECT_EQ(nullptr, mOutput.getOutputLayerForLayer(&layer));
}
-/* ------------------------------------------------------------------------
+/*
* Output::getOrCreateOutputLayer()
*/
@@ -389,5 +388,63 @@
}
}
+/*
+ * Output::prepareFrame()
+ */
+
+struct OutputPrepareFrameTest : public testing::Test {
+ struct OutputPartialMock : public impl::Output {
+ OutputPartialMock(const compositionengine::CompositionEngine& compositionEngine)
+ : impl::Output(compositionEngine) {}
+
+ // Sets up the helper functions called by prepareFrame to use a mock
+ // implementations.
+ MOCK_METHOD0(chooseCompositionStrategy, void());
+ };
+
+ OutputPrepareFrameTest() {
+ mOutput.setDisplayColorProfileForTest(
+ std::unique_ptr<DisplayColorProfile>(mDisplayColorProfile));
+ mOutput.setRenderSurfaceForTest(std::unique_ptr<RenderSurface>(mRenderSurface));
+ }
+
+ StrictMock<mock::CompositionEngine> mCompositionEngine;
+ mock::DisplayColorProfile* mDisplayColorProfile = new StrictMock<mock::DisplayColorProfile>();
+ mock::RenderSurface* mRenderSurface = new StrictMock<mock::RenderSurface>();
+ StrictMock<OutputPartialMock> mOutput{mCompositionEngine};
+};
+
+TEST_F(OutputPrepareFrameTest, takesEarlyOutIfNotEnabled) {
+ mOutput.editState().isEnabled = false;
+
+ mOutput.prepareFrame();
+}
+
+TEST_F(OutputPrepareFrameTest, delegatesToChooseCompositionStrategyAndRenderSurface) {
+ mOutput.editState().isEnabled = true;
+ mOutput.editState().usesClientComposition = false;
+ mOutput.editState().usesDeviceComposition = true;
+
+ EXPECT_CALL(mOutput, chooseCompositionStrategy()).Times(1);
+ EXPECT_CALL(*mRenderSurface, prepareFrame(false, true));
+
+ mOutput.prepareFrame();
+}
+
+// Note: Use OutputTest and not OutputPrepareFrameTest, so the real
+// base chooseCompositionStrategy() is invoked.
+TEST_F(OutputTest, prepareFrameSetsClientCompositionOnlyByDefault) {
+ mOutput.editState().isEnabled = true;
+ mOutput.editState().usesClientComposition = false;
+ mOutput.editState().usesDeviceComposition = true;
+
+ EXPECT_CALL(*mRenderSurface, prepareFrame(true, false));
+
+ mOutput.prepareFrame();
+
+ EXPECT_TRUE(mOutput.getState().usesClientComposition);
+ EXPECT_FALSE(mOutput.getState().usesDeviceComposition);
+}
+
} // namespace
} // namespace android::compositionengine