diff options
| -rw-r--r-- | services/surfaceflinger/BufferLayer.cpp | 21 | ||||
| -rw-r--r-- | services/surfaceflinger/BufferLayer.h | 1 | ||||
| -rw-r--r-- | services/surfaceflinger/ColorLayer.cpp | 26 | ||||
| -rw-r--r-- | services/surfaceflinger/ColorLayer.h | 1 | ||||
| -rw-r--r-- | services/surfaceflinger/ContainerLayer.cpp | 2 | ||||
| -rw-r--r-- | services/surfaceflinger/ContainerLayer.h | 1 | ||||
| -rw-r--r-- | services/surfaceflinger/DisplayDevice.cpp | 5 | ||||
| -rw-r--r-- | services/surfaceflinger/DisplayDevice.h | 3 | ||||
| -rw-r--r-- | services/surfaceflinger/DisplayHardware/HWComposer.cpp | 30 | ||||
| -rw-r--r-- | services/surfaceflinger/DisplayHardware/HWComposer.h | 4 | ||||
| -rw-r--r-- | services/surfaceflinger/Layer.h | 11 | ||||
| -rw-r--r-- | services/surfaceflinger/LayerBE.cpp | 17 | ||||
| -rw-r--r-- | services/surfaceflinger/LayerBE.h | 7 | ||||
| -rw-r--r-- | services/surfaceflinger/SurfaceFlinger.cpp | 32 |
14 files changed, 61 insertions, 100 deletions
diff --git a/services/surfaceflinger/BufferLayer.cpp b/services/surfaceflinger/BufferLayer.cpp index d0ccabbe4b..44305df11e 100644 --- a/services/surfaceflinger/BufferLayer.cpp +++ b/services/surfaceflinger/BufferLayer.cpp @@ -138,8 +138,6 @@ void BufferLayer::onDraw(const RenderArea& renderArea, const Region& clip, bool useIdentityTransform) { ATRACE_CALL(); - CompositionInfo& compositionInfo = getBE().compositionInfo; - if (CC_UNLIKELY(mActiveBuffer == 0)) { // the texture has not been created yet, this Layer has // in fact never been drawn into. This happens frequently with @@ -221,7 +219,6 @@ void BufferLayer::onDraw(const RenderArea& renderArea, const Region& clip, mTexture.setDimensions(mActiveBuffer->getWidth(), mActiveBuffer->getHeight()); mTexture.setFiltering(useFiltering); mTexture.setMatrix(textureMatrix); - compositionInfo.re.texture = mTexture; engine.setupLayerTexturing(mTexture); } else { @@ -231,23 +228,6 @@ void BufferLayer::onDraw(const RenderArea& renderArea, const Region& clip, engine.disableTexturing(); } -void BufferLayer::drawNow(const RenderArea& renderArea, bool useIdentityTransform) { - CompositionInfo& compositionInfo = getBE().compositionInfo; - auto& engine(mFlinger->getRenderEngine()); - - draw(renderArea, useIdentityTransform); - - engine.setupLayerTexturing(compositionInfo.re.texture); - engine.setupLayerBlending(compositionInfo.re.preMultipliedAlpha, compositionInfo.re.opaque, - false, compositionInfo.re.color); - engine.setSourceDataSpace(compositionInfo.hwc.dataspace); - engine.setSourceY410BT2020(compositionInfo.re.Y410BT2020); - engine.drawMesh(getBE().getMesh()); - engine.disableBlending(); - engine.disableTexturing(); - engine.setSourceY410BT2020(false); -} - bool BufferLayer::isHdrY410() const { // pixel format is HDR Y410 masquerading as RGBA_1010102 return (mCurrentDataSpace == ui::Dataspace::BT2020_ITU_PQ && @@ -340,6 +320,7 @@ bool BufferLayer::onPreComposition(nsecs_t refreshStartTime) { bool BufferLayer::onPostComposition(const std::shared_ptr<FenceTime>& glDoneFence, const std::shared_ptr<FenceTime>& presentFence, const CompositorTiming& compositorTiming) { + // mFrameLatencyNeeded is true when a new frame was latched for the // composition. if (!mFrameLatencyNeeded) return false; diff --git a/services/surfaceflinger/BufferLayer.h b/services/surfaceflinger/BufferLayer.h index 3319a98025..3d06dede10 100644 --- a/services/surfaceflinger/BufferLayer.h +++ b/services/surfaceflinger/BufferLayer.h @@ -77,7 +77,6 @@ public: // onDraw - draws the surface. void onDraw(const RenderArea& renderArea, const Region& clip, bool useIdentityTransform) override; - void drawNow(const RenderArea& renderArea, bool useIdentityTransform); bool isHdrY410() const override; diff --git a/services/surfaceflinger/ColorLayer.cpp b/services/surfaceflinger/ColorLayer.cpp index c29698b823..24e3d94ecb 100644 --- a/services/surfaceflinger/ColorLayer.cpp +++ b/services/surfaceflinger/ColorLayer.cpp @@ -45,27 +45,17 @@ void ColorLayer::onDraw(const RenderArea& renderArea, const Region& /* clip */, bool useIdentityTransform) { half4 color = getColor(); if (color.a > 0) { - computeGeometry(renderArea, getBE().mMesh, useIdentityTransform); - getBE().compositionInfo.re.preMultipliedAlpha = getPremultipledAlpha(); - getBE().compositionInfo.re.opaque = false; - getBE().compositionInfo.re.disableTexture = true; - getBE().compositionInfo.re.color = color; + Mesh mesh(Mesh::TRIANGLE_FAN, 4, 2); + computeGeometry(renderArea, mesh, useIdentityTransform); + auto& engine(mFlinger->getRenderEngine()); + engine.setupLayerBlending(getPremultipledAlpha(), false /* opaque */, + true /* disableTexture */, color); + engine.setSourceDataSpace(mCurrentDataSpace); + engine.drawMesh(mesh); + engine.disableBlending(); } } -void ColorLayer::drawNow(const RenderArea& renderArea, bool useIdentityTransform) { - CompositionInfo& compositionInfo = getBE().compositionInfo; - auto& engine(mFlinger->getRenderEngine()); - - draw(renderArea, useIdentityTransform); - - engine.setupLayerBlending(compositionInfo.re.preMultipliedAlpha, compositionInfo.re.opaque, - compositionInfo.re.disableTexture, compositionInfo.re.color); - engine.setSourceDataSpace(compositionInfo.hwc.dataspace); - engine.drawMesh(getBE().getMesh()); - engine.disableBlending(); -} - bool ColorLayer::isVisible() const { return !isHiddenByPolicy() && getAlpha() > 0.0f; } diff --git a/services/surfaceflinger/ColorLayer.h b/services/surfaceflinger/ColorLayer.h index 429ad79a05..aa6b049aed 100644 --- a/services/surfaceflinger/ColorLayer.h +++ b/services/surfaceflinger/ColorLayer.h @@ -32,7 +32,6 @@ public: virtual const char* getTypeId() const { return "ColorLayer"; } virtual void onDraw(const RenderArea& renderArea, const Region& clip, bool useIdentityTransform); - void drawNow(const RenderArea&, bool); bool isVisible() const override; void setPerFrameData(const sp<const DisplayDevice>& display) override; diff --git a/services/surfaceflinger/ContainerLayer.cpp b/services/surfaceflinger/ContainerLayer.cpp index 5ad5d562a8..e9f3059d11 100644 --- a/services/surfaceflinger/ContainerLayer.cpp +++ b/services/surfaceflinger/ContainerLayer.cpp @@ -30,8 +30,6 @@ ContainerLayer::ContainerLayer(SurfaceFlinger* flinger, const sp<Client>& client void ContainerLayer::onDraw(const RenderArea&, const Region& /* clip */, bool) {} -void ContainerLayer::drawNow(const RenderArea&, bool) {} - bool ContainerLayer::isVisible() const { return !isHiddenByPolicy(); } diff --git a/services/surfaceflinger/ContainerLayer.h b/services/surfaceflinger/ContainerLayer.h index 051e76523c..0b4a181d65 100644 --- a/services/surfaceflinger/ContainerLayer.h +++ b/services/surfaceflinger/ContainerLayer.h @@ -32,7 +32,6 @@ public: const char* getTypeId() const override { return "ContainerLayer"; } void onDraw(const RenderArea& renderArea, const Region& clip, bool useIdentityTransform) override; - void drawNow(const RenderArea& renderArea, bool useIdentityTransform) override; bool isVisible() const override; void setPerFrameData(const sp<const DisplayDevice>& display) override; diff --git a/services/surfaceflinger/DisplayDevice.cpp b/services/surfaceflinger/DisplayDevice.cpp index 0fbd4594f8..aab6c22819 100644 --- a/services/surfaceflinger/DisplayDevice.cpp +++ b/services/surfaceflinger/DisplayDevice.cpp @@ -334,8 +334,9 @@ status_t DisplayDevice::beginFrame(bool mustRecompose) const { return mDisplaySurface->beginFrame(mustRecompose); } -status_t DisplayDevice::prepareFrame(HWComposer& hwc) { - status_t error = hwc.prepare(*this); +status_t DisplayDevice::prepareFrame(HWComposer& hwc, + std::vector<CompositionInfo>& compositionData) { + status_t error = hwc.prepare(*this, compositionData); if (error != NO_ERROR) { return error; } diff --git a/services/surfaceflinger/DisplayDevice.h b/services/surfaceflinger/DisplayDevice.h index 42909880c7..ddb09c5086 100644 --- a/services/surfaceflinger/DisplayDevice.h +++ b/services/surfaceflinger/DisplayDevice.h @@ -49,6 +49,7 @@ class IGraphicBufferProducer; class Layer; class SurfaceFlinger; class HWComposer; +struct CompositionInfo; class DisplayDevice : public LightRefBase<DisplayDevice> { @@ -141,7 +142,7 @@ public: // We pass in mustRecompose so we can keep VirtualDisplaySurface's state // machine happy without actually queueing a buffer if nothing has changed status_t beginFrame(bool mustRecompose) const; - status_t prepareFrame(HWComposer& hwc); + status_t prepareFrame(HWComposer& hwc, std::vector<CompositionInfo>& compositionInfo); bool hasWideColorGamut() const { return mHasWideColorGamut; } // Whether h/w composer has native support for specific HDR type. diff --git a/services/surfaceflinger/DisplayHardware/HWComposer.cpp b/services/surfaceflinger/DisplayHardware/HWComposer.cpp index 630cc0b9a7..873de251ed 100644 --- a/services/surfaceflinger/DisplayHardware/HWComposer.cpp +++ b/services/surfaceflinger/DisplayHardware/HWComposer.cpp @@ -417,7 +417,8 @@ status_t HWComposer::setClientTarget(int32_t displayId, uint32_t slot, return NO_ERROR; } -status_t HWComposer::prepare(DisplayDevice& display) { +status_t HWComposer::prepare(DisplayDevice& display, + std::vector<CompositionInfo>& compositionData) { ATRACE_CALL(); Mutex::Autolock _l(mDisplayLock); @@ -488,18 +489,19 @@ status_t HWComposer::prepare(DisplayDevice& display) { displayData.hasClientComposition = false; displayData.hasDeviceComposition = false; - for (auto& layer : display.getVisibleLayersSortedByZ()) { - auto hwcLayer = layer->getHwcLayer(displayId); + for (auto& compositionInfo : compositionData) { + auto hwcLayer = compositionInfo.hwc.hwcLayer; - if (changedTypes.count(hwcLayer) != 0) { + if (changedTypes.count(&*hwcLayer) != 0) { // We pass false so we only update our state and don't call back // into the HWC device - validateChange(layer->getCompositionType(displayId), - changedTypes[hwcLayer]); - layer->setCompositionType(displayId, changedTypes[hwcLayer], false); + validateChange(compositionInfo.compositionType, + changedTypes[&*hwcLayer]); + compositionInfo.compositionType = changedTypes[&*hwcLayer]; + compositionInfo.layer->mLayer->setCompositionType(displayId, compositionInfo.compositionType, false); } - switch (layer->getCompositionType(displayId)) { + switch (compositionInfo.compositionType) { case HWC2::Composition::Client: displayData.hasClientComposition = true; break; @@ -513,17 +515,17 @@ status_t HWComposer::prepare(DisplayDevice& display) { break; } - if (layerRequests.count(hwcLayer) != 0 && - layerRequests[hwcLayer] == + if (layerRequests.count(&*hwcLayer) != 0 && + layerRequests[&*hwcLayer] == HWC2::LayerRequest::ClearClientTarget) { - layer->setClearClientTarget(displayId, true); + compositionInfo.hwc.clearClientTarget = true; } else { - if (layerRequests.count(hwcLayer) != 0) { + if (layerRequests.count(&*hwcLayer) != 0) { LOG_DISPLAY_ERROR(displayId, - ("Unknown layer request " + to_string(layerRequests[hwcLayer])) + ("Unknown layer request " + to_string(layerRequests[&*hwcLayer])) .c_str()); } - layer->setClearClientTarget(displayId, false); + compositionInfo.hwc.clearClientTarget = false; } } diff --git a/services/surfaceflinger/DisplayHardware/HWComposer.h b/services/surfaceflinger/DisplayHardware/HWComposer.h index 9e01626862..cca1f3bdc8 100644 --- a/services/surfaceflinger/DisplayHardware/HWComposer.h +++ b/services/surfaceflinger/DisplayHardware/HWComposer.h @@ -61,6 +61,7 @@ class NativeHandle; class Region; class String8; class TestableSurfaceFlinger; +struct CompositionInfo; namespace Hwc2 { class Composer; @@ -92,7 +93,8 @@ public: void destroyLayer(int32_t displayId, HWC2::Layer* layer); // Asks the HAL what it can do - status_t prepare(DisplayDevice& display); + status_t prepare(DisplayDevice& display, + std::vector<CompositionInfo>& compositionData); status_t setClientTarget(int32_t displayId, uint32_t slot, const sp<Fence>& acquireFence, diff --git a/services/surfaceflinger/Layer.h b/services/surfaceflinger/Layer.h index 443f410fe7..604ec656fc 100644 --- a/services/surfaceflinger/Layer.h +++ b/services/surfaceflinger/Layer.h @@ -76,6 +76,7 @@ class Layer : public virtual RefBase { static int32_t sSequence; public: + friend class LayerBE; LayerBE& getBE() { return mBE; } LayerBE& getBE() const { return mBE; } mutable bool contentDirty; @@ -415,16 +416,6 @@ public: void draw(const RenderArea& renderArea); /* - * drawNow uses the renderEngine to draw the layer. This is different than the - * draw function as with the FE/BE split, the draw function runs in the FE and - * sets up state for the BE to do the actual drawing. drawNow is used to tell - * the layer to skip the state setup and just go ahead and draw the layer. This - * is used for screen captures which happens separately from the frame - * compositing path. - */ - virtual void drawNow(const RenderArea& renderArea, bool useIdentityTransform) = 0; - - /* * doTransaction - process the transaction. This is a good place to figure * out which attributes of the surface have changed. */ diff --git a/services/surfaceflinger/LayerBE.cpp b/services/surfaceflinger/LayerBE.cpp index 3e04f266af..9c6534e0d9 100644 --- a/services/surfaceflinger/LayerBE.cpp +++ b/services/surfaceflinger/LayerBE.cpp @@ -46,6 +46,11 @@ void LayerBE::onLayerDisplayed(const sp<Fence>& releaseFence) { mLayer->onLayerDisplayed(releaseFence); } +void LayerBE::clear(RE::RenderEngine& engine) { + engine.setupFillWithColor(0, 0, 0, 0); + engine.drawMesh(mMesh); +} + void CompositionInfo::dump(const char* tag) const { std::string logString; @@ -89,22 +94,12 @@ void CompositionInfo::dumpRe(std::string& result, const char* tag) const { result += base::StringPrintf("[%s]RenderEngine parameters:\n", tag); } - Mesh& mesh = layer->getMesh(); result += base::StringPrintf("\tblackoutLayer=%d\n", re.blackoutLayer); result += base::StringPrintf("\tclearArea=%d\n", re.clearArea); result += base::StringPrintf("\tpreMultipliedAlpha=%d\n", re.preMultipliedAlpha); result += base::StringPrintf("\topaque=%d\n", re.opaque); result += base::StringPrintf("\tdisableTexture=%d\n", re.disableTexture); - result += base::StringPrintf("\ttexture:name(%d), target(%d), size(%d/%d)\n", re.texture.getTextureName(), re.texture.getTextureTarget(), (unsigned int)re.texture.getWidth(), (unsigned int)re.texture.getHeight()); result += base::StringPrintf("\tuseIdentityTransform=%d\n", re.useIdentityTransform); - Mesh::VertexArray<vec2> positions(mesh.getPositionArray<vec2>()); - result += base::StringPrintf("\tpositions[(%6.1f,%6.1f), (%6.1f,%6.1f), (%6.1f,%6.1f), (%6.1f,%6.1f)]\n", - positions[0][0], positions[0][1], positions[1][0], positions[1][1], - positions[2][0], positions[2][1], positions[3][0], positions[3][1]); - Mesh::VertexArray<vec2> texCoords(mesh.getTexCoordArray<vec2>()); - result += base::StringPrintf("\ttexCoords[(%6.1f,%6.1f), (%6.1f,%6.1f),(%6.1f,%6.1f),(%6.1f,%6.1f)]\n", - texCoords[0][0], texCoords[0][1], texCoords[1][0], texCoords[1][1], - texCoords[2][0], texCoords[2][1], texCoords[3][0], texCoords[3][1]); } void CompositionInfo::dump(std::string& result, const char* tag) const @@ -134,6 +129,4 @@ void CompositionInfo::dump(std::string& result, const char* tag) const } } - - }; // namespace android diff --git a/services/surfaceflinger/LayerBE.h b/services/surfaceflinger/LayerBE.h index e5110b7bea..21e7b5c9c2 100644 --- a/services/surfaceflinger/LayerBE.h +++ b/services/surfaceflinger/LayerBE.h @@ -20,6 +20,7 @@ #include <sys/types.h> #include <renderengine/Mesh.h> +#include <renderengine/RenderEngine.h> #include <renderengine/Texture.h> #include <ui/Region.h> @@ -34,6 +35,7 @@ class LayerBE; struct CompositionInfo { std::string layerName; HWC2::Composition compositionType; + bool firstClear = false; sp<GraphicBuffer> mBuffer = nullptr; int mBufferSlot = BufferQueue::INVALID_BUFFER_SLOT; std::shared_ptr<LayerBE> layer; @@ -59,14 +61,12 @@ struct CompositionInfo { HdrMetadata hdrMetadata; } hwc; struct { - Mesh* mesh; bool blackoutLayer = false; bool clearArea = false; bool preMultipliedAlpha = false; bool opaque = false; bool disableTexture = false; half4 color; - Texture texture; bool useIdentityTransform = false; bool Y410BT2020 = false; } re; @@ -90,10 +90,11 @@ public: explicit LayerBE(const LayerBE& layer); void onLayerDisplayed(const sp<Fence>& releaseFence); + void clear(RE::RenderEngine& renderEngine); Mesh& getMesh() { return mMesh; } -private: Layer*const mLayer; +private: // The mesh used to draw the layer in GLES composition mode Mesh mMesh; diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp index 5acfe59c4e..5ff73e62bf 100644 --- a/services/surfaceflinger/SurfaceFlinger.cpp +++ b/services/surfaceflinger/SurfaceFlinger.cpp @@ -1609,6 +1609,7 @@ void SurfaceFlinger::calculateWorkingSet() { void SurfaceFlinger::doDebugFlashRegions(const sp<DisplayDevice>& display, bool repaintEverything) { + const auto displayId = display->getId(); // is debugging enabled if (CC_LIKELY(!mDebugRegion)) return; @@ -1636,7 +1637,8 @@ void SurfaceFlinger::doDebugFlashRegions(const sp<DisplayDevice>& display, bool } if (display->isPoweredOn()) { - status_t result = display->prepareFrame(*getBE().mHwc); + status_t result = display->prepareFrame( + *getBE().mHwc, getBE().mCompositionInfo[displayId]); ALOGE_IF(result != NO_ERROR, "prepareFrame for display %d failed:" " %d (%s)", @@ -2035,11 +2037,13 @@ void SurfaceFlinger::beginFrame(const sp<DisplayDevice>& display) void SurfaceFlinger::prepareFrame(const sp<DisplayDevice>& display) { + const auto displayId = display->getId(); if (!display->isPoweredOn()) { return; } - status_t result = display->prepareFrame(*getBE().mHwc); + status_t result = display->prepareFrame( + *getBE().mHwc, getBE().mCompositionInfo[displayId]); ALOGE_IF(result != NO_ERROR, "prepareFrame for display %d failed:" " %d (%s)", @@ -2967,29 +2971,29 @@ bool SurfaceFlinger::doComposeSurfaces(const sp<const DisplayDevice>& display) { ALOGV("Rendering client layers"); const ui::Transform& displayTransform = display->getTransform(); bool firstLayer = true; - for (auto& layer : display->getVisibleLayersSortedByZ()) { + for (auto& compositionInfo : getBE().mCompositionInfo[displayId]) { + const Region bounds(display->bounds()); const Region clip(bounds.intersect( - displayTransform.transform(layer->visibleRegion))); - ALOGV("Layer: %s", layer->getName().string()); - ALOGV(" Composition type: %s", to_string(layer->getCompositionType(displayId)).c_str()); + displayTransform.transform(compositionInfo.layer->mLayer->visibleRegion))); + ALOGV("Layer: %s", compositionInfo.layerName.c_str()); if (!clip.isEmpty()) { - switch (layer->getCompositionType(displayId)) { + switch (compositionInfo.compositionType) { case HWC2::Composition::Cursor: case HWC2::Composition::Device: case HWC2::Composition::Sideband: case HWC2::Composition::SolidColor: { - const Layer::State& state(layer->getDrawingState()); - if (layer->getClearClientTarget(displayId) && !firstLayer && - layer->isOpaque(state) && (layer->getAlpha() == 1.0f) && - hasClientComposition) { + const Layer::State& state(compositionInfo.layer->mLayer->getDrawingState()); + const bool opaque = compositionInfo.layer->mLayer->isOpaque(state); + if (compositionInfo.hwc.clearClientTarget && !firstLayer && + opaque && (state.color.a == 1.0f) && hasClientComposition) { // never clear the very first layer since we're // guaranteed the FB is already cleared - layer->clearWithOpenGL(renderArea); + compositionInfo.layer->mLayer->clearWithOpenGL(renderArea); } break; } case HWC2::Composition::Client: { - layer->draw(renderArea, clip); + compositionInfo.layer->mLayer->draw(renderArea, clip); break; } default: @@ -5273,7 +5277,7 @@ void SurfaceFlinger::renderScreenImplLocked(const RenderArea& renderArea, traverseLayers([&](Layer* layer) { if (filtering) layer->setFiltering(true); - layer->drawNow(renderArea, useIdentityTransform); + layer->draw(renderArea, useIdentityTransform); if (filtering) layer->setFiltering(false); }); } |