Add logging for ComputeRebuildRegion
authorMatt Woodrow <mwoodrow@mozilla.com>
Tue, 19 Sep 2017 11:34:31 +1200
changeset 685640 3e66c3bb56881547abf5c8e0fcc4190d13fa392a
parent 685639 4dbe9ae4248c0f5205342494ba4031539bc1e991
child 685641 224aa41383ca2b5483a5eec16823877ef4ea5fa7
push id86010
push userbmo:ethlin@mozilla.com
push dateWed, 25 Oct 2017 00:44:42 +0000
milestone57.0a1
Add logging for ComputeRebuildRegion
layout/base/nsLayoutUtils.cpp
--- a/layout/base/nsLayoutUtils.cpp
+++ b/layout/base/nsLayoutUtils.cpp
@@ -4056,38 +4056,49 @@ GetModifiedFrames(nsIFrame* aDisplayRoot
 
   if (rootdoc) {
     rootdoc->EnumerateSubDocuments(SubDocEnumCb, &modifiedFrames);
   }
 
   return modifiedFrames;
 }
 
+// ComputeRebuildRegion  debugging
+// #define CRR_DEBUG 0
+#if CRR_DEBUG
+#  define CRR_LOG(...) printf_stderr(__VA_ARGS__)
+#else
+#  define CRR_LOG(...)
+#endif
+
 static bool
 ComputeRebuildRegion(nsDisplayListBuilder& aBuilder,
                      std::vector<WeakFrame>& aModifiedFrames,
                      nsIFrame* aDisplayRootFrame,
                      const nsRect& aRootDirtyRect,
                      nsRect* aOutDirty,
                      AnimatedGeometryRoot** aOutModifiedAGR,
                      nsTArray<nsIFrame*>* aOutFramesWithProps)
 {
+  CRR_LOG("Computing rebuild regions for %d frames:\n", aModifiedFrames.size());
   for (nsIFrame* f : aModifiedFrames) {
     if (!f) {
       continue;
     }
 
     if (f->HasOverrideDirtyRegion()) {
       aOutFramesWithProps->AppendElement(f);
     }
 
     // TODO: There is almost certainly a faster way of doing this, probably can be combined with the ancestor
     // walk for TransformFrameRectToAncestor.
     AnimatedGeometryRoot* agr = aBuilder.FindAnimatedGeometryRootFor(f)->GetAsyncAGR();
 
+    CRR_LOG("Processing frame %p with agr %p\n", f, agr->mFrame);
+
 
     // Convert the frame's overflow rect into the coordinate space
     // of the nearest stacking context that has an existing display item.
     // We store the overflow rect on that stacking context so that we build
     // all items that intersect that changed frame within the stacking context,
     // and then we use MarkFrameForDisplayIfVisible to make sure the stacking
     // context itself gets built. We don't need to build items that intersect outside
     // of the stacking context, since we know the stacking context item exists in
@@ -4098,16 +4109,17 @@ ComputeRebuildRegion(nsDisplayListBuilde
     while (currentFrame != aDisplayRootFrame) {
       overflow = nsLayoutUtils::TransformFrameRectToAncestor(currentFrame, overflow, aDisplayRootFrame,
                                                              nullptr, nullptr,
                                                              /* aStopAtStackingContextAndDisplayPort = */ true,
                                                              &currentFrame);
       MOZ_ASSERT(currentFrame);
 
       if (nsLayoutUtils::FrameHasDisplayPort(currentFrame)) {
+        CRR_LOG("Frame belongs to displayport frame %p\n", currentFrame);
         nsIScrollableFrame* sf = do_QueryFrame(currentFrame);
         MOZ_ASSERT(sf);
         nsRect displayPort;
         DebugOnly<bool> hasDisplayPort =
           nsLayoutUtils::GetDisplayPort(currentFrame->GetContent(), &displayPort, RelativeTo::ScrollPort);
         MOZ_ASSERT(hasDisplayPort);
         // get it relative to the scrollport (from the scrollframe)
         nsRect r = overflow - sf->GetScrollPortRect().TopLeft();
@@ -4117,29 +4129,31 @@ ComputeRebuildRegion(nsDisplayListBuilde
             currentFrame->GetProperty(nsDisplayListBuilder::DisplayListBuildingDisplayPortRect());
           if (!rect) {
             rect = new nsRect();
             currentFrame->SetProperty(nsDisplayListBuilder::DisplayListBuildingDisplayPortRect(), rect);
             currentFrame->SetHasOverrideDirtyRegion(true);
           }
           rect->UnionRect(*rect, r);
           aOutFramesWithProps->AppendElement(currentFrame);
+          CRR_LOG("Adding area to displayport draw area: %d %d %d %d\n", r.x, r.y, r.width, r.height);
 
           // TODO: Can we just use MarkFrameForDisplayIfVisible, plus MarkFramesForDifferentAGR to
           // ensure that this displayport, plus any items that move relative to it get rebuilt,
           // and then not contribute to the root dirty area?
           overflow = sf->GetScrollPortRect();
         } else {
           // Don't contribute to the root dirty area at all.
           overflow.SetEmpty();
           break;
         }
       }
 
       if (currentFrame->IsStackingContext()) {
+        CRR_LOG("Frame belongs to stacking context frame %p\n", currentFrame);
         // If we found an intermediate stacking context with an existing display item
         // then we can store the dirty rect there and stop.
         if (currentFrame != aDisplayRootFrame &&
             currentFrame->RealDisplayItemData().Length() != 0) {
           aBuilder.MarkFrameForDisplayIfVisible(currentFrame);
 
           // Store the stacking context relative dirty area such
           // that display list building will pick it up when it
@@ -4148,38 +4162,42 @@ ComputeRebuildRegion(nsDisplayListBuilde
             currentFrame->GetProperty(nsDisplayListBuilder::DisplayListBuildingRect());
           if (!data) {
             data = new nsDisplayListBuilder::DisplayListBuildingData;
             currentFrame->SetProperty(nsDisplayListBuilder::DisplayListBuildingRect(), data);
             currentFrame->SetHasOverrideDirtyRegion(true);
             aOutFramesWithProps->AppendElement(currentFrame);
           }
           data->mDirtyRect.UnionRect(data->mDirtyRect, overflow);
+          CRR_LOG("Adding area to stacking context draw area: %d %d %d %d\n", overflow.x, overflow.y, overflow.width, overflow.height);
           if (!data->mModifiedAGR) {
             data->mModifiedAGR = agr;
           } else if (data->mModifiedAGR != agr) {
             data->mDirtyRect = currentFrame->GetVisualOverflowRectRelativeToSelf();
+            CRR_LOG("Found multiple modified AGRs within this stacking context, giving up\n");
           }
 
           // Don't contribute to the root dirty area at all.
           agr = nullptr;
           overflow.SetEmpty();
           break;
         }
       }
     }
     aOutDirty->UnionRect(*aOutDirty, overflow);
+    CRR_LOG("Adding area to root draw area: %d %d %d %d\n", overflow.x, overflow.y, overflow.width, overflow.height);
 
     // If we get changed frames from multiple AGRS, then just give up as it gets really complex to
     // track which items would need to be marked in MarkFramesForDifferentAGR.
     // TODO: We should store the modifiedAGR on the per-stacking context data and only do the
     // marking within the scope of the current stacking context.
     if (!*aOutModifiedAGR) {
       *aOutModifiedAGR = agr;
     } else if (agr && *aOutModifiedAGR != agr) {
+      CRR_LOG("Found multiple AGRs in root stacking context, giving up\n");
       return false;
     }
   }
 
   return true;
 }
 
 void MarkFramesWithItemsAndImagesModified(nsDisplayList* aList)