Bug 1431255 - (To be replaced by bug 1450250) Allow Shadow DOM in SVG <use> subtree creation draft
authorTimothy Guan-tin Chien <timdream@gmail.com>
Wed, 11 Jul 2018 18:30:53 +0800
changeset 819541 25298d96e1357c4279a9d69b4140b1dfa65490e5
parent 819540 85be8bf504114bb7548758c04c03b677610230eb
child 819542 be4b70c06f7ee12547dff3e6ac3b46189ad6e877
push id116577
push usertimdream@gmail.com
push dateWed, 18 Jul 2018 03:35:27 +0000
bugs1431255, 1450250, 1282985
milestone63.0a1
Bug 1431255 - (To be replaced by bug 1450250) Allow Shadow DOM in SVG <use> subtree creation Before calling into restyle when attaching shadow root, checking if the element is in a SVG <use> subtree. This prevents us from recurring into frame construction when the video element is bound into a SVG <use> subtree. Specifically, this allow UA Widget to pass in dom/svg/crashtests/1282985-1.svg. MozReview-Commit-ID: FobLm20Rhie
dom/base/Element.cpp
--- a/dom/base/Element.cpp
+++ b/dom/base/Element.cpp
@@ -1224,19 +1224,24 @@ Element::AttachShadowWithoutNameChecks(S
 {
   nsAutoScriptBlocker scriptBlocker;
 
   RefPtr<mozilla::dom::NodeInfo> nodeInfo =
     mNodeInfo->NodeInfoManager()->GetNodeInfo(
       nsGkAtoms::documentFragmentNodeName, nullptr, kNameSpaceID_None,
       DOCUMENT_FRAGMENT_NODE);
 
-  if (nsIDocument* doc = GetComposedDoc()) {
-    if (nsIPresShell* shell = doc->GetShell()) {
-      shell->DestroyFramesForAndRestyle(this);
+  bool inSVGUseSubtree =
+    IsInAnonymousSubtree() && IsAnonymousContentInSVGUseSubtree();
+
+  if (!inSVGUseSubtree) {
+    if (nsIDocument* doc = GetComposedDoc()) {
+      if (nsIPresShell* shell = doc->GetShell()) {
+        shell->DestroyFramesForAndRestyle(this);
+      }
     }
   }
   MOZ_ASSERT(!GetPrimaryFrame());
 
   /**
    * 4. Let shadow be a new shadow root whose node document is
    *    context object’s node document, host is context object,
    *    and mode is init’s mode.
@@ -1272,19 +1277,24 @@ void
 Element::UnattachShadow()
 {
   if (!GetShadowRoot()) {
     return;
   }
 
   nsAutoScriptBlocker scriptBlocker;
 
-  if (nsIDocument* doc = GetComposedDoc()) {
-    if (nsIPresShell* shell = doc->GetShell()) {
-      shell->DestroyFramesForAndRestyle(this);
+  bool inSVGUseSubtree =
+    IsInAnonymousSubtree() && IsAnonymousContentInSVGUseSubtree();
+
+  if (!inSVGUseSubtree) {
+    if (nsIDocument* doc = GetComposedDoc()) {
+      if (nsIPresShell* shell = doc->GetShell()) {
+        shell->DestroyFramesForAndRestyle(this);
+      }
     }
   }
   MOZ_ASSERT(!GetPrimaryFrame());
 
   // Simply unhook the shadow root from the element.
   MOZ_ASSERT(!GetShadowRoot()->HasSlots(), "Won't work when shadow root has slots!");
   SetShadowRoot(nullptr);
 }