# HG changeset patch # User Timothy Nikkel # Parent 226514e8fef7671276b0dd7bd4f1b80b56e15e23 Bug 1242093. Fix assertion in Downscaler::ClearRow. The starting column can be the last column, and we handle that correctly. Also split function into ClearRow and ClearRestOfRow. diff --git a/image/Downscaler.cpp b/image/Downscaler.cpp --- a/image/Downscaler.cpp +++ b/image/Downscaler.cpp @@ -197,19 +197,19 @@ GetFilterOffsetAndLength(UniquePtrnum_values()); aFilter->FilterForValue(aOutputImagePosition, aFilterOffsetOut, aFilterLengthOut); } void -Downscaler::ClearRow(uint32_t aStartingAtCol) +Downscaler::ClearRestOfRow(uint32_t aStartingAtCol) { - MOZ_ASSERT(int64_t(mOriginalSize.width) > int64_t(aStartingAtCol)); + MOZ_ASSERT(int64_t(aStartingAtCol) <= int64_t(mOriginalSize.width)); uint32_t bytesToClear = (mOriginalSize.width - aStartingAtCol) * sizeof(uint32_t); memset(mRowBuffer.get() + (aStartingAtCol * sizeof(uint32_t)), 0, bytesToClear); } void Downscaler::CommitRow() diff --git a/image/Downscaler.h b/image/Downscaler.h --- a/image/Downscaler.h +++ b/image/Downscaler.h @@ -87,18 +87,21 @@ public: bool IsFrameComplete() const { return mCurrentInLine >= mOriginalSize.height; } /// Retrieves the buffer into which the Decoder should write each row. uint8_t* RowBuffer() { return mRowBuffer.get() + mFrameRect.x * sizeof(uint32_t); } - /// Clears the current row buffer (optionally starting at @aStartingAtCol). - void ClearRow(uint32_t aStartingAtCol = 0); + /// Clears the current row buffer. + void ClearRow() { ClearRestOfRow(0); } + + /// Clears the current row buffer starting at @aStartingAtCol. + void ClearRestOfRow(uint32_t aStartingAtCol); /// Signals that the decoder has finished writing a row into the row buffer. void CommitRow(); /// Returns true if there is a non-empty invalid rect available. bool HasInvalidation() const; /// Takes the Downscaler's current invalid rect and resets it. @@ -161,17 +164,18 @@ public: nsresult BeginFrame(const nsIntSize&, const Maybe&, uint8_t*, bool, bool = false) { return NS_ERROR_FAILURE; } bool IsFrameComplete() const { return false; } uint8_t* RowBuffer() { return nullptr; } - void ClearRow(uint32_t = 0) { } + void ClearRow() { } + void ClearRestOfRow(uint32_t) { } void CommitRow() { } bool HasInvalidation() const { return false; } DownscalerInvalidRect TakeInvalidRect() { return DownscalerInvalidRect(); } void ResetForNextProgressivePass() { } const nsIntSize FrameSize() const { return nsIntSize(0, 0); } }; #endif // MOZ_ENABLE_SKIA diff --git a/image/decoders/nsBMPDecoder.cpp b/image/decoders/nsBMPDecoder.cpp --- a/image/decoders/nsBMPDecoder.cpp +++ b/image/decoders/nsBMPDecoder.cpp @@ -981,17 +981,17 @@ nsBMPDecoder::ReadRLEDelta(const char* a // Delta encoding makes it possible to skip pixels making part of the image // transparent. MOZ_ASSERT(mMayHaveTransparency); mDoesHaveTransparency = true; if (mDownscaler) { // Clear the skipped pixels. (This clears to the end of the row, // which is perfect if there's a Y delta and harmless if not). - mDownscaler->ClearRow(/* aStartingAtCol = */ mCurrentPos); + mDownscaler->ClearRestOfRow(/* aStartingAtCol = */ mCurrentPos); } // Handle the XDelta. mCurrentPos += uint8_t(aData[0]); if (mCurrentPos > mH.mWidth) { mCurrentPos = mH.mWidth; } diff --git a/image/test/crashtests/1242093-1.html b/image/test/crashtests/1242093-1.html new file mode 100644 --- /dev/null +++ b/image/test/crashtests/1242093-1.html @@ -0,0 +1,22 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/image/test/crashtests/crashtests.list b/image/test/crashtests/crashtests.list --- a/image/test/crashtests/crashtests.list +++ b/image/test/crashtests/crashtests.list @@ -12,16 +12,17 @@ load 732319-1.html load 844403-1.html load 856616.gif skip-if(B2G) load 944353.jpg load 1205923-1.html load 1212954-1.svg load 1235605.gif load 1241728-1.html load 1241729-1.html +load 1242093-1.html load 1242778-1.png load colormap-range.gif HTTP load delayedframe.sjs # A 3-frame animated GIF with an inordinate delay between the second and third frame # Animated gifs with a very large canvas, but tiny actual content. skip-if(B2G) load delaytest.html?523528-1.gif skip-if(B2G) load delaytest.html?523528-2.gif