Bug 653497 - Once bug 335998 is fixed, SVGPathDataAndOwner::mElement leaks documents, r=dholbert
authorOlli Pettay <Olli.Pettay@helsinki.fi>
Fri, 29 Apr 2011 15:33:11 +0300
changeset 68750 b15803d8aee8f15e3bc255ce8499ca8e09bca1bf
parent 68749 5fe9c33c0c8f4cce776e3d12e16a822ab5090e68
child 68751 c39785cf8fb8da0a1f8d13e27cf115931f041537
push idunknown
push userunknown
push dateunknown
reviewersdholbert
bugs653497, 335998
milestone6.0a1
Bug 653497 - Once bug 335998 is fixed, SVGPathDataAndOwner::mElement leaks documents, r=dholbert
content/svg/content/src/SVGLengthList.h
content/svg/content/src/SVGPathData.h
content/svg/content/src/SVGPointList.h
--- a/content/svg/content/src/SVGLengthList.h
+++ b/content/svg/content/src/SVGLengthList.h
@@ -35,16 +35,17 @@
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef MOZILLA_SVGLENGTHLIST_H__
 #define MOZILLA_SVGLENGTHLIST_H__
 
 #include "SVGLength.h"
 #include "nsTArray.h"
 #include "nsSVGElement.h"
+#include "nsIWeakReferenceUtils.h"
 
 namespace mozilla {
 
 /**
  * ATTENTION! WARNING! WATCH OUT!!
  *
  * Consumers that modify objects of this type absolutely MUST keep the DOM
  * wrappers for those lists (if any) in sync!! That's why this class is so
@@ -201,29 +202,30 @@ public:
 
   SVGLengthListAndInfo()
     : mElement(nsnull)
     , mAxis(0)
     , mCanZeroPadList(PR_FALSE)
   {}
 
   SVGLengthListAndInfo(nsSVGElement *aElement, PRUint8 aAxis, PRBool aCanZeroPadList)
-    : mElement(aElement)
+    : mElement(do_GetWeakReference(static_cast<nsINode*>(aElement)))
     , mAxis(aAxis)
     , mCanZeroPadList(aCanZeroPadList)
   {}
 
   void SetInfo(nsSVGElement *aElement, PRUint8 aAxis, PRBool aCanZeroPadList) {
-    mElement = aElement;
+    mElement = do_GetWeakReference(static_cast<nsINode*>(aElement));
     mAxis = aAxis;
     mCanZeroPadList = aCanZeroPadList;
   }
 
   nsSVGElement* Element() const {
-    return mElement; // .get();
+    nsCOMPtr<nsIContent> e = do_QueryReferent(mElement);
+    return static_cast<nsSVGElement*>(e.get());
   }
 
   PRUint8 Axis() const {
     NS_ABORT_IF_FALSE(mElement, "Axis() isn't valid");
     return mAxis;
   }
 
   /**
@@ -286,20 +288,21 @@ public:
   SVGLength& operator[](PRUint32 aIndex) {
     return SVGLengthList::operator[](aIndex);
   }
   PRBool SetLength(PRUint32 aNumberOfItems) {
     return SVGLengthList::SetLength(aNumberOfItems);
   }
 
 private:
-  // We must keep a strong reference to our element because we may belong to a
+  // We must keep a weak reference to our element because we may belong to a
   // cached baseVal nsSMILValue. See the comments starting at:
   // https://bugzilla.mozilla.org/show_bug.cgi?id=515116#c15
-  nsRefPtr<nsSVGElement> mElement;
+  // See also https://bugzilla.mozilla.org/show_bug.cgi?id=653497
+  nsWeakPtr mElement;
   PRUint8 mAxis;
   PRPackedBool mCanZeroPadList;
 };
 
 
 /**
  * This class wraps SVGLengthList objects to allow frame consumers to process
  * SVGLengthList objects as if they were simply a list of float values in user
--- a/content/svg/content/src/SVGPathData.h
+++ b/content/svg/content/src/SVGPathData.h
@@ -35,16 +35,17 @@
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef MOZILLA_SVGPATHDATA_H__
 #define MOZILLA_SVGPATHDATA_H__
 
 #include "SVGPathSegUtils.h"
 #include "nsTArray.h"
 #include "nsSVGElement.h"
+#include "nsIWeakReferenceUtils.h"
 
 class gfxContext;
 struct gfxMatrix;
 class gfxFlattenedPath;
 class nsSVGPathDataParserToInternal;
 struct nsSVGMark;
 
 namespace mozilla {
@@ -240,25 +241,26 @@ protected:
  * Instances of this class do not have DOM wrappers that need to be kept in
  * sync, so we can safely expose any protected base class methods required by
  * the SMIL code.
  */
 class SVGPathDataAndOwner : public SVGPathData
 {
 public:
   SVGPathDataAndOwner(nsSVGElement *aElement = nsnull)
-    : mElement(aElement)
+    : mElement(do_GetWeakReference(static_cast<nsINode*>(aElement)))
   {}
 
   void SetElement(nsSVGElement *aElement) {
-    mElement = aElement;
+    mElement = do_GetWeakReference(static_cast<nsINode*>(aElement));
   }
 
   nsSVGElement* Element() const {
-    return mElement;
+    nsCOMPtr<nsIContent> e = do_QueryReferent(mElement);
+    return static_cast<nsSVGElement*>(e.get());
   }
 
   nsresult CopyFrom(const SVGPathDataAndOwner& rhs) {
     mElement = rhs.mElement;
     return SVGPathData::CopyFrom(rhs);
   }
 
   PRBool IsIdentity() const {
@@ -279,17 +281,18 @@ public:
   // Exposed since SVGPathData objects can be modified.
   using SVGPathData::iterator;
   using SVGPathData::operator[];
   using SVGPathData::SetLength;
   using SVGPathData::begin;
   using SVGPathData::end;
 
 private:
-  // We must keep a strong reference to our element because we may belong to a
+  // We must keep a weak reference to our element because we may belong to a
   // cached baseVal nsSMILValue. See the comments starting at:
   // https://bugzilla.mozilla.org/show_bug.cgi?id=515116#c15
-  nsRefPtr<nsSVGElement> mElement;
+  // See also https://bugzilla.mozilla.org/show_bug.cgi?id=653497
+  nsWeakPtr mElement;
 };
 
 } // namespace mozilla
 
 #endif // MOZILLA_SVGPATHDATA_H__
--- a/content/svg/content/src/SVGPointList.h
+++ b/content/svg/content/src/SVGPointList.h
@@ -35,16 +35,17 @@
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef MOZILLA_SVGPOINTLIST_H__
 #define MOZILLA_SVGPOINTLIST_H__
 
 #include "SVGPoint.h"
 #include "nsTArray.h"
 #include "nsSVGElement.h"
+#include "nsIWeakReferenceUtils.h"
 
 namespace mozilla {
 
 /**
  * ATTENTION! WARNING! WATCH OUT!!
  *
  * Consumers that modify objects of this type absolutely MUST keep the DOM
  * wrappers for those lists (if any) in sync!! That's why this class is so
@@ -179,25 +180,26 @@ protected:
  * Holding a strong reference to the element here prevents the element from
  * disappearing out from under the SMIL code unexpectedly.
  */
 class SVGPointListAndInfo : public SVGPointList
 {
 public:
 
   SVGPointListAndInfo(nsSVGElement *aElement = nsnull)
-    : mElement(aElement)
+    : mElement(do_GetWeakReference(static_cast<nsINode*>(aElement)))
   {}
 
   void SetInfo(nsSVGElement *aElement) {
-    mElement = aElement;
+    mElement = do_GetWeakReference(static_cast<nsINode*>(aElement));
   }
 
   nsSVGElement* Element() const {
-    return mElement;
+    nsCOMPtr<nsIContent> e = do_QueryReferent(mElement);
+    return static_cast<nsSVGElement*>(e.get());
   }
 
   nsresult CopyFrom(const SVGPointListAndInfo& rhs) {
     mElement = rhs.mElement;
     return SVGPointList::CopyFrom(rhs);
   }
 
   /**
@@ -214,17 +216,18 @@ public:
   SVGPoint& operator[](PRUint32 aIndex) {
     return SVGPointList::operator[](aIndex);
   }
   PRBool SetLength(PRUint32 aNumberOfItems) {
     return SVGPointList::SetLength(aNumberOfItems);
   }
 
 private:
-  // We must keep a strong reference to our element because we may belong to a
+  // We must keep a weak reference to our element because we may belong to a
   // cached baseVal nsSMILValue. See the comments starting at:
   // https://bugzilla.mozilla.org/show_bug.cgi?id=515116#c15
-  nsRefPtr<nsSVGElement> mElement;
+  // See also https://bugzilla.mozilla.org/show_bug.cgi?id=653497
+  nsWeakPtr mElement;
 };
 
 } // namespace mozilla
 
 #endif // MOZILLA_SVGPOINTLIST_H__