Bug 640272 - Check load status for border images before trying to render them. r=bzbarsky a=dveditz
authorMats Palmgren <matspal@gmail.com>
Sat, 09 Apr 2011 11:00:32 +0200
changeset 63393 c6f059547a023868e19588e11ac8a701bee19047
parent 63392 abab3297c82f5719b9ae44132bf0222c73c92b2f
child 63394 8f41e6f646cf8b19226652b4d960e53846b51c16
push id48
push usermpalmgren@mozilla.com
push dateSat, 09 Apr 2011 09:00:39 +0000
reviewersbzbarsky, dveditz
bugs640272
milestone2.0.1pre
Bug 640272 - Check load status for border images before trying to render them. r=bzbarsky a=dveditz
layout/base/crashtests/640272-empty.html
layout/base/crashtests/640272-ref.html
layout/base/crashtests/640272.html
layout/base/crashtests/crashtests.list
layout/base/nsCSSRendering.cpp
layout/style/nsStyleStructInlines.h
new file mode 100644
new file mode 100644
--- /dev/null
+++ b/layout/base/crashtests/640272-ref.html
@@ -0,0 +1,14 @@
+<!DOCTYPE HTML>
+<html><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase for bug 640272</title>
+<style>
+#waBackButton {
+	border: 1px solid blue;
+}
+</style>
+</head>
+<body>
+      <a href="index.html" id="waBackButton">Indietro</a>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/base/crashtests/640272.html
@@ -0,0 +1,15 @@
+<!DOCTYPE HTML>
+<html><head>
+    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+    <title>Testcase for bug 640272</title>
+<style>
+#waBackButton {
+	border: 1px solid blue;
+	-moz-border-image: url(640272-empty.html) 0 10 0 15;
+}
+</style>
+</head>
+<body>
+      <a href="index.html" id="waBackButton">Indietro</a>
+</body>
+</html>
--- a/layout/base/crashtests/crashtests.list
+++ b/layout/base/crashtests/crashtests.list
@@ -321,8 +321,9 @@ load 595039-1.html
 load 606432-1.html
 load 609821-1.xhtml
 load 615146-1.html
 load 615781-1.xhtml
 load 616495-single-side-composite-color-border.html
 load 629035-1.html
 load 629908-1.html
 load 635329.html
+== 640272.html 640272-ref.html
--- a/layout/base/nsCSSRendering.cpp
+++ b/layout/base/nsCSSRendering.cpp
@@ -2727,46 +2727,39 @@ nsCSSRendering::GetBackgroundLayerRect(n
 static void
 DrawBorderImage(nsPresContext*       aPresContext,
                 nsIRenderingContext& aRenderingContext,
                 nsIFrame*            aForFrame,
                 const nsRect&        aBorderArea,
                 const nsStyleBorder& aStyleBorder,
                 const nsRect&        aDirtyRect)
 {
+  NS_PRECONDITION(aStyleBorder.IsBorderImageLoaded(),
+                  "drawing border image that isn't successfully loaded");
+
   if (aDirtyRect.IsEmpty())
     return;
 
   // Ensure we get invalidated for loads and animations of the image.
   // We need to do this here because this might be the only code that
   // knows about the association of the style data with the frame.
   // XXX We shouldn't really... since if anybody is passing in a
   // different style, they'll potentially have the wrong size for the
   // border too.
   aPresContext->SetupBorderImageLoaders(aForFrame, &aStyleBorder);
 
   imgIRequest *req = aStyleBorder.GetBorderImage();
 
-#ifdef DEBUG
-  {
-    PRUint32 status = imgIRequest::STATUS_ERROR;
-    if (req)
-      req->GetImageStatus(&status);
-
-    NS_ASSERTION(req && (status & imgIRequest::STATUS_LOAD_COMPLETE),
-                 "no image to draw");
-  }
-#endif
-
   // Get the actual image, and determine where the split points are.
   // Note that mBorderImageSplit is in image pixels, not necessarily
   // CSS pixels.
 
   nsCOMPtr<imgIContainer> imgContainer;
   req->GetImage(getter_AddRefs(imgContainer));
+  NS_ASSERTION(imgContainer, "no image to draw");
 
   nsIntSize imageSize;
   if (NS_FAILED(imgContainer->GetWidth(&imageSize.width))) {
     imageSize.width =
       nsPresContext::AppUnitsToIntCSSPixels(aBorderArea.width);
   }
   if (NS_FAILED(imgContainer->GetHeight(&imageSize.height))) {
     imageSize.height =
--- a/layout/style/nsStyleStructInlines.h
+++ b/layout/style/nsStyleStructInlines.h
@@ -63,17 +63,18 @@ nsStyleBorder::GetBorderImage() const
   return mBorderImage;
 }
 
 inline PRBool nsStyleBorder::IsBorderImageLoaded() const
 {
   PRUint32 status;
   return mBorderImage &&
          NS_SUCCEEDED(mBorderImage->GetImageStatus(&status)) &&
-         (status & imgIRequest::STATUS_LOAD_COMPLETE);
+         (status & imgIRequest::STATUS_LOAD_COMPLETE) &&
+         !(status & imgIRequest::STATUS_ERROR);
 }
 
 inline void
 nsStyleBorder::SetSubImage(PRUint8 aIndex, imgIContainer* aSubImage) const
 {
   const_cast<nsStyleBorder*>(this)->mSubImages.ReplaceObjectAt(aSubImage, aIndex);
 }