Changeset 245218 in webkit


Ignore:
Timestamp:
May 12, 2019 8:01:25 PM (5 years ago)
Author:
Simon Fraser
Message:

Refactor composited backing-sharing code
https://bugs.webkit.org/show_bug.cgi?id=197824

Reviewed by Zalan Bujtas.

Clean up the backing-sharing code to share more code, and make it easier to understand.

Moves more logic into member functions on BackingSharingState, which are named to make
their functions clearer: startBackingSharingSequence/endBackingSharingSequence.

computeCompositingRequirements() and traverseUnchangedSubtree() now just call
updateBeforeDescendantTraversal/updateAfterDescendantTraversal.

No behavior change.

  • rendering/RenderLayerBacking.cpp:

(WebCore::RenderLayerBacking::willBeDestroyed):
(WebCore::RenderLayerBacking::setBackingSharingLayers): Remove the early return, since
we need to call setBackingProviderLayer() on the sharing layers in both code paths.
(WebCore::RenderLayerBacking::removeBackingSharingLayer):
(WebCore::RenderLayerBacking::clearBackingSharingLayers):

  • rendering/RenderLayerCompositor.cpp:

(WebCore::RenderLayerCompositor::BackingSharingState::backingProviderCandidate const):
(WebCore::RenderLayerCompositor::BackingSharingState::appendSharingLayer):
(WebCore::RenderLayerCompositor::BackingSharingState::startBackingSharingSequence):
(WebCore::RenderLayerCompositor::BackingSharingState::endBackingSharingSequence):
(WebCore::RenderLayerCompositor::BackingSharingState::updateBeforeDescendantTraversal):
(WebCore::RenderLayerCompositor::BackingSharingState::updateAfterDescendantTraversal):
(WebCore::RenderLayerCompositor::computeCompositingRequirements):
(WebCore::RenderLayerCompositor::traverseUnchangedSubtree):
(WebCore::RenderLayerCompositor::BackingSharingState::resetBackingProviderCandidate): Deleted.

  • rendering/RenderLayerCompositor.h:
Location:
trunk/Source/WebCore
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r245217 r245218  
     12019-05-12  Simon Fraser  <simon.fraser@apple.com>
     2
     3        Refactor composited backing-sharing code
     4        https://bugs.webkit.org/show_bug.cgi?id=197824
     5
     6        Reviewed by Zalan Bujtas.
     7
     8        Clean up the backing-sharing code to share more code, and make it easier to understand.
     9       
     10        Moves more logic into member functions on BackingSharingState, which are named to make
     11        their functions clearer: startBackingSharingSequence/endBackingSharingSequence.
     12       
     13        computeCompositingRequirements() and traverseUnchangedSubtree() now just call
     14        updateBeforeDescendantTraversal/updateAfterDescendantTraversal.
     15
     16        No behavior change.
     17
     18        * rendering/RenderLayerBacking.cpp:
     19        (WebCore::RenderLayerBacking::willBeDestroyed):
     20        (WebCore::RenderLayerBacking::setBackingSharingLayers): Remove the early return, since
     21        we need to call setBackingProviderLayer() on the sharing layers in both code paths.
     22        (WebCore::RenderLayerBacking::removeBackingSharingLayer):
     23        (WebCore::RenderLayerBacking::clearBackingSharingLayers):
     24        * rendering/RenderLayerCompositor.cpp:
     25        (WebCore::RenderLayerCompositor::BackingSharingState::backingProviderCandidate const):
     26        (WebCore::RenderLayerCompositor::BackingSharingState::appendSharingLayer):
     27        (WebCore::RenderLayerCompositor::BackingSharingState::startBackingSharingSequence):
     28        (WebCore::RenderLayerCompositor::BackingSharingState::endBackingSharingSequence):
     29        (WebCore::RenderLayerCompositor::BackingSharingState::updateBeforeDescendantTraversal):
     30        (WebCore::RenderLayerCompositor::BackingSharingState::updateAfterDescendantTraversal):
     31        (WebCore::RenderLayerCompositor::computeCompositingRequirements):
     32        (WebCore::RenderLayerCompositor::traverseUnchangedSubtree):
     33        (WebCore::RenderLayerCompositor::BackingSharingState::resetBackingProviderCandidate): Deleted.
     34        * rendering/RenderLayerCompositor.h:
     35
    1362019-05-12  Youenn Fablet  <youenn@apple.com>
    237
  • trunk/Source/WebCore/rendering/RenderLayerBacking.cpp

    r245208 r245218  
    261261    compositor().removeFromScrollCoordinatedLayers(m_owningLayer);
    262262
    263     LOG(Compositing, "RenderLayer(backing) %p willBeDestroyed", &m_owningLayer);
    264 
    265263    clearBackingSharingLayers();
    266264}
     
    283281void RenderLayerBacking::setBackingSharingLayers(Vector<WeakPtr<RenderLayer>>&& sharingLayers)
    284282{
    285     if (m_backingSharingLayers == sharingLayers) {
    286         sharingLayers.clear();
    287         return;
    288     }
    289 
    290283    clearBackingSharingLayerProviders(m_backingSharingLayers);
    291284    m_backingSharingLayers = WTFMove(sharingLayers);
     285
    292286    for (auto& layerWeakPtr : m_backingSharingLayers)
    293287        layerWeakPtr->setBackingProviderLayer(&m_owningLayer);
     
    296290void RenderLayerBacking::removeBackingSharingLayer(RenderLayer& layer)
    297291{
    298     LOG(Compositing, "RenderLayer %p removeBackingSharingLayer %p", &m_owningLayer, &layer);
    299 
    300292    layer.setBackingProviderLayer(nullptr);
    301293    m_backingSharingLayers.removeAll(&layer);
     
    304296void RenderLayerBacking::clearBackingSharingLayers()
    305297{
    306     LOG(Compositing, "RenderLayer %p clearBackingSharingLayers", &m_owningLayer);
    307 
    308298    clearBackingSharingLayerProviders(m_backingSharingLayers);
    309299    m_backingSharingLayers.clear();
  • trunk/Source/WebCore/rendering/RenderLayerCompositor.cpp

    r245206 r245218  
    285285};
    286286
    287 struct RenderLayerCompositor::BackingSharingState {
    288     RenderLayer* backingProviderCandidate { nullptr };
    289     RenderLayer* backingProviderStackingContext { nullptr };
    290     Vector<WeakPtr<RenderLayer>> backingSharingLayers;
    291 
    292     void resetBackingProviderCandidate(RenderLayer* candidateLayer = nullptr, RenderLayer* candidateStackingContext = nullptr)
     287class RenderLayerCompositor::BackingSharingState {
     288    WTF_MAKE_NONCOPYABLE(BackingSharingState);
     289public:
     290    BackingSharingState() = default;
     291
     292    RenderLayer* backingProviderCandidate() const { return m_backingProviderCandidate; };
     293   
     294    void appendSharingLayer(RenderLayer& layer)
    293295    {
    294         if (!backingSharingLayers.isEmpty()) {
    295             ASSERT(backingProviderCandidate);
    296             backingProviderCandidate->backing()->setBackingSharingLayers(WTFMove(backingSharingLayers));
    297         }
    298         backingProviderCandidate = candidateLayer;
    299         backingProviderStackingContext = candidateLayer ? candidateStackingContext : nullptr;
    300     }
     296        LOG_WITH_STREAM(Compositing, stream << &layer << " appendSharingLayer " << &layer << " for backing provider " << m_backingProviderCandidate);
     297        m_backingSharingLayers.append(makeWeakPtr(layer));
     298    }
     299
     300    void updateBeforeDescendantTraversal(RenderLayer&, bool willBeComposited);
     301    void updateAfterDescendantTraversal(RenderLayer&, RenderLayer* stackingContextAncestor);
     302
     303private:
     304    void layerWillBeComposited(RenderLayer&);
     305
     306    void startBackingSharingSequence(RenderLayer& candidateLayer, RenderLayer* candidateStackingContext);
     307    void endBackingSharingSequence();
     308
     309    RenderLayer* m_backingProviderCandidate { nullptr };
     310    RenderLayer* m_backingProviderStackingContext { nullptr };
     311    Vector<WeakPtr<RenderLayer>> m_backingSharingLayers;
    301312};
     313
     314void RenderLayerCompositor::BackingSharingState::startBackingSharingSequence(RenderLayer& candidateLayer, RenderLayer* candidateStackingContext)
     315{
     316    ASSERT(!m_backingProviderCandidate);
     317    ASSERT(m_backingSharingLayers.isEmpty());
     318
     319    m_backingProviderCandidate = &candidateLayer;
     320    m_backingProviderStackingContext = candidateStackingContext;
     321}
     322
     323void RenderLayerCompositor::BackingSharingState::endBackingSharingSequence()
     324{
     325    if (m_backingProviderCandidate) {
     326        m_backingProviderCandidate->backing()->setBackingSharingLayers(WTFMove(m_backingSharingLayers));
     327        m_backingSharingLayers.clear();
     328    }
     329   
     330    m_backingProviderCandidate = nullptr;
     331}
     332
     333void RenderLayerCompositor::BackingSharingState::updateBeforeDescendantTraversal(RenderLayer& layer, bool willBeComposited)
     334{
     335    layer.setBackingProviderLayer(nullptr);
     336
     337    // A layer that composites resets backing-sharing, since subsequent layers need to composite to overlap it.
     338    if (willBeComposited) {
     339        m_backingSharingLayers.removeAll(&layer);
     340        LOG_WITH_STREAM(Compositing, stream << "Pre-descendant compositing of " << &layer << ", ending sharing sequence for " << m_backingProviderCandidate << " with " << m_backingSharingLayers.size() << " sharing layers");
     341        endBackingSharingSequence();
     342    }
     343}
     344
     345void RenderLayerCompositor::BackingSharingState::updateAfterDescendantTraversal(RenderLayer& layer, RenderLayer* stackingContextAncestor)
     346{
     347    if (layer.isComposited()) {
     348        // If this layer is being composited, clean up sharing-related state.
     349        layer.disconnectFromBackingProviderLayer();
     350        m_backingSharingLayers.removeAll(&layer);
     351    }
     352
     353    if (m_backingProviderCandidate && &layer == m_backingProviderStackingContext) {
     354        LOG_WITH_STREAM(Compositing, stream << "End of stacking context for backing provider " << m_backingProviderCandidate << ", ending sharing sequence with " << m_backingSharingLayers.size() << " sharing layers");
     355        endBackingSharingSequence();
     356    } else if (!m_backingProviderCandidate && layer.isComposited()) {
     357        LOG_WITH_STREAM(Compositing, stream << "Post-descendant compositing of " << &layer << ", ending sharing sequence for " << m_backingProviderCandidate << " with " << m_backingSharingLayers.size() << " sharing layers");
     358        endBackingSharingSequence();
     359        startBackingSharingSequence(layer, stackingContextAncestor);
     360    }
     361   
     362    if (&layer != m_backingProviderCandidate && layer.isComposited())
     363        layer.backing()->clearBackingSharingLayers();
     364}
    302365
    303366struct RenderLayerCompositor::OverlapExtent {
     
    881944
    882945#if ENABLE(TREE_DEBUGGING)
    883     LOG(Compositing, "%*p %s computeCompositingRequirements (backing provider candidate %p)", 12 + compositingState.depth * 2, &layer, layer.isNormalFlowOnly() ? "n" : "s", backingSharingState.backingProviderCandidate);
     946    LOG(Compositing, "%*p %s computeCompositingRequirements (backing provider candidate %p)", 12 + compositingState.depth * 2, &layer, layer.isNormalFlowOnly() ? "n" : "s", backingSharingState.backingProviderCandidate());
    884947#endif
    885948
     
    892955
    893956    layer.setHasCompositingDescendant(false);
    894     layer.setBackingProviderLayer(nullptr);
    895957
    896958    // We updated compositing for direct reasons in layerStyleChanged(). Here, check for compositing that can only be evaluated after layout.
     
    922984        // If we're testing for overlap, we only need to composite if we overlap something that is already composited.
    923985        if (overlapMap.overlapsLayers(layerExtent.bounds)) {
    924             if (backingSharingState.backingProviderCandidate && canBeComposited(layer) && backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate, layer)) {
    925                 backingSharingState.backingSharingLayers.append(makeWeakPtr(layer));
    926                 LOG(Compositing, " layer %p can share with %p", &layer, backingSharingState.backingProviderCandidate);
     986            if (backingSharingState.backingProviderCandidate() && canBeComposited(layer) && backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate(), layer)) {
     987                backingSharingState.appendSharingLayer(layer);
     988                LOG(Compositing, " layer %p can share with %p", &layer, backingSharingState.backingProviderCandidate());
    927989                compositingReason = RenderLayer::IndirectCompositingReason::None;
    928990                layerPaintsIntoProvidedBacking = true;
     
    9681030        childState.testingOverlap = true;
    9691031        willBeComposited = true;
    970 
    9711032        layerPaintsIntoProvidedBacking = false;
    972         layer.disconnectFromBackingProviderLayer();
    973         backingSharingState.backingSharingLayers.removeAll(&layer);
    9741033    };
    9751034
     
    9841043        // Too hard to compute animated bounds if both us and some ancestor is animating transform.
    9851044        layerExtent.animationCausesExtentUncertainty |= layerExtent.hasTransformAnimation && compositingState.ancestorHasTransformAnimation;
    986 
    987         // Compositing for any reason disables backing sharing.
    988         LOG_WITH_STREAM(Compositing, stream << &layer << " is compositing - flushing sharing to " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    989         backingSharingState.resetBackingProviderCandidate();
    9901045    } else if (layerPaintsIntoProvidedBacking) {
    9911046        childState.backingSharingAncestor = &layer;
    9921047        overlapMap.pushCompositingContainer();
    9931048    }
     1049
     1050    backingSharingState.updateBeforeDescendantTraversal(layer, willBeComposited);
    9941051
    9951052#if !ASSERT_DISABLED
     
    11011158        // The composited bounds of enclosing layers depends on which descendants are composited, so they need a geometry update.
    11021159        layer.setNeedsCompositingGeometryUpdateOnAncestors();
    1103     } else if (layer.isComposited())
    1104         layer.backing()->clearBackingSharingLayers();
    1105 
    1106     if (backingSharingState.backingProviderCandidate && &layer == backingSharingState.backingProviderStackingContext) {
    1107         LOG_WITH_STREAM(Compositing, stream << &layer << " popping stacking context " << backingSharingState.backingProviderStackingContext << ", flushing candidate " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    1108         backingSharingState.resetBackingProviderCandidate();
    1109     } else if (!backingSharingState.backingProviderCandidate && layer.isComposited()) {
    1110         LOG_WITH_STREAM(Compositing, stream << &layer << " compositing - sharing candidate " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    1111         // Flush out any earlier candidate in this stacking context. This layer becomes a candidate.
    1112         backingSharingState.resetBackingProviderCandidate(&layer, compositingState.stackingContextAncestor);
    1113     }
     1160    }
     1161
     1162    backingSharingState.updateAfterDescendantTraversal(layer, compositingState.stackingContextAncestor);
    11141163
    11151164    if (layer.reflectionLayer() && updateLayerCompositingState(*layer.reflectionLayer(), queryData, CompositingChangeRepaintNow))
     
    11251174
    11261175#if ENABLE(TREE_DEBUGGING)
    1127     LOG(Compositing, "%*p computeCompositingRequirements - willBeComposited %d (backing provider candidate %p)", 12 + compositingState.depth * 2, &layer, willBeComposited, backingSharingState.backingProviderCandidate);
     1176    LOG(Compositing, "%*p computeCompositingRequirements - willBeComposited %d (backing provider candidate %p)", 12 + compositingState.depth * 2, &layer, willBeComposited, backingSharingState.backingProviderCandidate());
    11281177#endif
    11291178
     
    11611210
    11621211    if (layer.paintsIntoProvidedBacking()) {
    1163         ASSERT(backingSharingState.backingProviderCandidate);
    1164         ASSERT(backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate, layer));
    1165         backingSharingState.backingSharingLayers.append(makeWeakPtr(layer));
     1212        ASSERT(backingSharingState.backingProviderCandidate());
     1213        ASSERT(backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate(), layer));
     1214        backingSharingState.appendSharingLayer(layer);
    11661215    }
    11671216
     
    11831232        // Too hard to compute animated bounds if both us and some ancestor is animating transform.
    11841233        layerExtent.animationCausesExtentUncertainty |= layerExtent.hasTransformAnimation && compositingState.ancestorHasTransformAnimation;
    1185 
    1186         // Compositing for any reason disables backing sharing.
    1187         LOG_WITH_STREAM(Compositing, stream << "tus: " << &layer << " is compositing - flushing sharing to " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    1188         backingSharingState.resetBackingProviderCandidate();
    1189     }
     1234    }
     1235
     1236    backingSharingState.updateBeforeDescendantTraversal(layer, layerIsComposited);
    11901237
    11911238#if !ASSERT_DISABLED
     
    12411288        overlapMap.popCompositingContainer();
    12421289
    1243     if (layer.isComposited())
    1244         layer.backing()->clearBackingSharingLayers();
    1245 
    1246     if (backingSharingState.backingProviderCandidate && &layer == backingSharingState.backingProviderStackingContext) {
    1247         LOG_WITH_STREAM(Compositing, stream << &layer << " tus: popping stacking context " << backingSharingState.backingProviderStackingContext << ", flushing candidate " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    1248         backingSharingState.resetBackingProviderCandidate();
    1249     } else if (!backingSharingState.backingProviderCandidate && layer.isComposited()) {
    1250         LOG_WITH_STREAM(Compositing, stream << &layer << " tus: compositing - sharing candidate " << backingSharingState.backingProviderCandidate << " with " << backingSharingState.backingSharingLayers.size() << " sharing layers");
    1251         // Flush out any earlier candidate in this stacking context. This layer becomes a candidate.
    1252         backingSharingState.resetBackingProviderCandidate(&layer, compositingState.stackingContextAncestor);
    1253     }
     1290    backingSharingState.updateAfterDescendantTraversal(layer, compositingState.stackingContextAncestor);
    12541291
    12551292    descendantHas3DTransform |= anyDescendantHas3DTransform || layer.has3DTransform();
  • trunk/Source/WebCore/rendering/RenderLayerCompositor.h

    r245170 r245218  
    368368
    369369private:
     370    class BackingSharingState;
    370371    class OverlapMap;
    371372    struct CompositingState;
    372     struct BackingSharingState;
    373373    struct OverlapExtent;
    374374
Note: See TracChangeset for help on using the changeset viewer.