Fix crashes in GC creating a document fragment on a background thread
authorcommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 3 Aug 2017 03:49:53 +0000 (03:49 +0000)
committercommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 3 Aug 2017 03:49:53 +0000 (03:49 +0000)
https://bugs.webkit.org/show_bug.cgi?id=175111

Patch by Sam Weinig <sam@webkit.org> on 2017-08-02
Reviewed by Chris Dumez.

r220095 (https://webkit.org/b/175006) change JSHTMLTemplateElement from using a
private name + property to manager the lifetime of the reference DocumentFragment
to using the idiomatic visitAdditionalChildren. Unfortunately, the function to access
the DocumentFragment lazily creates it. If this lazy creation happens on a GC thread,
badness ensues. This introduces an accessor that returns the DocumentFragment if it
has been created or null if it has not.

* bindings/js/JSHTMLTemplateElementCustom.cpp:
(WebCore::JSHTMLTemplateElement::visitAdditionalChildren):
* html/HTMLTemplateElement.cpp:
(WebCore::HTMLTemplateElement::contentIfAvailable):
* html/HTMLTemplateElement.h:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@220177 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebCore/ChangeLog
Source/WebCore/bindings/js/JSHTMLTemplateElementCustom.cpp
Source/WebCore/html/HTMLTemplateElement.cpp
Source/WebCore/html/HTMLTemplateElement.h

index adb5f9d4652ac267217beec1b920a54de3711b11..a8190f17b55f769479828bafdc22a5fe441036fe 100644 (file)
@@ -1,3 +1,23 @@
+2017-08-02  Sam Weinig  <sam@webkit.org>
+
+        Fix crashes in GC creating a document fragment on a background thread
+        https://bugs.webkit.org/show_bug.cgi?id=175111
+
+        Reviewed by Chris Dumez.
+
+        r220095 (https://webkit.org/b/175006) change JSHTMLTemplateElement from using a
+        private name + property to manager the lifetime of the reference DocumentFragment
+        to using the idiomatic visitAdditionalChildren. Unfortunately, the function to access
+        the DocumentFragment lazily creates it. If this lazy creation happens on a GC thread,
+        badness ensues. This introduces an accessor that returns the DocumentFragment if it
+        has been created or null if it has not.
+
+        * bindings/js/JSHTMLTemplateElementCustom.cpp:
+        (WebCore::JSHTMLTemplateElement::visitAdditionalChildren):
+        * html/HTMLTemplateElement.cpp:
+        (WebCore::HTMLTemplateElement::contentIfAvailable):
+        * html/HTMLTemplateElement.h:
+
 2017-08-02  Sam Weinig  <sam@webkit.org>
 
         [WebIDL] Simplify [EnabledBySettings] extended attribute code to not require passing a global object to finishCreation
index 1dc13123cc10063161b0dfc117e4c9ef53b36ded..6d81e280015ccc4754f4a7e37e312a22031c1070 100644 (file)
@@ -39,7 +39,8 @@ namespace WebCore {
 
 void JSHTMLTemplateElement::visitAdditionalChildren(JSC::SlotVisitor& visitor)
 {
-    visitor.addOpaqueRoot(root(&wrapped().content()));
+    if (auto* content = wrapped().contentIfAvailable())
+        visitor.addOpaqueRoot(root(content));
 }
 
 } // namespace WebCore
index 3a297ed00a22a46e763c50c73cab6c72cc5ad809..242fc1a585ff3db9b24f1f2027a1e17cca902b58 100644 (file)
@@ -56,6 +56,11 @@ Ref<HTMLTemplateElement> HTMLTemplateElement::create(const QualifiedName& tagNam
     return adoptRef(*new HTMLTemplateElement(tagName, document));
 }
 
+DocumentFragment* HTMLTemplateElement::contentIfAvailable() const
+{
+    return m_content.get();
+}
+
 DocumentFragment& HTMLTemplateElement::content() const
 {
     if (!m_content)
index 107de0265897495b99854d7be143b75085ccf7d1..9413bd440e5d7f9c7cb444428e65bc5c42cbd944 100644 (file)
@@ -43,6 +43,7 @@ public:
     virtual ~HTMLTemplateElement();
 
     DocumentFragment& content() const;
+    DocumentFragment* contentIfAvailable() const;
 
 private:
     HTMLTemplateElement(const QualifiedName&, Document&);