Bug 1462497 - Part 1: Don't crash if we find an item from the wrong list, and keep looking instead r?miko draft
authorMatt Woodrow <mwoodrow@mozilla.com>
Wed, 23 May 2018 10:59:11 +1200
changeset 798504 b591665eecfed05ccd77e731ec5e156a8cb9a2ea
parent 798503 96a6ea5ea3468b4c9e20ff8d9795a7ef136213a9
child 798505 cdf1414bc42159f134b9d38b84fbf1830b5d0bb0
push id110767
push usermwoodrow@mozilla.com
push dateTue, 22 May 2018 23:04:45 +0000
reviewersmiko
bugs1462497
milestone62.0a1
Bug 1462497 - Part 1: Don't crash if we find an item from the wrong list, and keep looking instead r?miko We will still crash in Nightly/DevEdition builds (so that we can fix the bug), but we'll just accept the possible duplication of items (and maybe minor rendering issues) for releases. MozReview-Commit-ID: LNzjO8vJjGp
layout/painting/RetainedDisplayListBuilder.cpp
layout/painting/nsDisplayList.h
--- a/layout/painting/RetainedDisplayListBuilder.cpp
+++ b/layout/painting/RetainedDisplayListBuilder.cpp
@@ -330,18 +330,19 @@ public:
 
   bool HasMatchingItemInOldList(nsDisplayItem* aItem, OldListIndex* aOutIndex)
   {
     nsIFrame::DisplayItemArray* items = aItem->Frame()->GetProperty(nsIFrame::DisplayItems());
     // Look for an item that matches aItem's frame and per-frame-key, but isn't the same item.
     for (nsDisplayItem* i : *items) {
       if (i != aItem && i->Frame() == aItem->Frame() &&
           i->GetPerFrameKey() == aItem->GetPerFrameKey()) {
-        *aOutIndex = i->GetOldListIndex(mOldList, mOuterKey);
-        return true;
+        if (i->GetOldListIndex(mOldList, mOuterKey, aOutIndex)) {
+          return true;
+        }
       }
     }
     return false;
   }
 
   bool HasModifiedFrame(nsDisplayItem* aItem) {
     return AnyContentAncestorModified(aItem->FrameForInvalidation());
   }
--- a/layout/painting/nsDisplayList.h
+++ b/layout/painting/nsDisplayList.h
@@ -2858,24 +2858,26 @@ public:
   {
 #ifdef MOZ_DIAGNOSTIC_ASSERT_ENABLED
     mOldList = reinterpret_cast<uintptr_t>(aList);
     mOldListKey = aListKey;
     mOldNestingDepth = aNestingDepth;
 #endif
     mOldListIndex = aIndex;
   }
-  OldListIndex GetOldListIndex(nsDisplayList* aList, uint32_t aListKey)
-  {
-#ifdef MOZ_DIAGNOSTIC_ASSERT_ENABLED
+  bool GetOldListIndex(nsDisplayList* aList, uint32_t aListKey, OldListIndex* aOutIndex)
+  {
     if (mOldList != reinterpret_cast<uintptr_t>(aList)) {
+#ifdef MOZ_DIAGNOSTIC_ASSERT_ENABLED
       MOZ_CRASH_UNSAFE_PRINTF("Item found was in the wrong list! type %d (outer type was %d at depth %d, now is %d)", GetPerFrameKey(), mOldListKey, mOldNestingDepth, aListKey);
+#endif
+      return false;
     }
-#endif
-    return mOldListIndex;
+    *aOutIndex = mOldListIndex;
+    return true;
   }
 
   const nsRect& GetPaintRect() const {
     return mPaintRect;
   }
 
 protected:
   nsDisplayItem() = delete;
@@ -2905,24 +2907,24 @@ private:
   // of the item. Paint implementations can use this to limit their drawing.
   // Guaranteed to be contained in GetBounds().
   nsRect    mPaintRect;
 
 protected:
 
 #ifdef MOZ_DIAGNOSTIC_ASSERT_ENABLED
 public:
-  uintptr_t mOldList = 0;
   uint32_t mOldListKey = 0;
   uint32_t mOldNestingDepth = 0;
   bool mMergedItem = false;
   bool mPreProcessedItem = false;
 protected:
 #endif
   OldListIndex mOldListIndex;
+  uintptr_t mOldList = 0;
 
   bool      mForceNotVisible;
   bool      mDisableSubpixelAA;
   bool      mReusedItem;
   bool      mBackfaceHidden;
   bool      mPaintRectValid;
 #ifdef MOZ_DUMP_PAINTING
   // True if this frame has been painted.