Bug 1879651 - Ensure CreateImageBitmapInternal copies DataSourceSurface before modifying it. r=aosmond

Differential Revision: https://phabricator.services.mozilla.com/D202554
This commit is contained in:
Lee Salzman 2024-02-23 16:09:21 +00:00
parent d7b3cec4b4
commit 581a972ff7

View File

@ -362,6 +362,7 @@ static DataSourceSurface* FlipYDataSourceSurface(DataSourceSurface* aSurface) {
return nullptr;
}
const int bpp = BytesPerPixel(aSurface->GetFormat());
const IntSize srcSize = aSurface->GetSize();
uint8_t* srcBufferPtr = srcMap.GetData();
const uint32_t stride = srcMap.GetStride();
@ -372,7 +373,8 @@ static DataSourceSurface* FlipYDataSourceSurface(DataSourceSurface* aSurface) {
}
for (int i = 0; i < srcSize.height / 2; ++i) {
std::swap_ranges(srcBufferPtr + stride * i, srcBufferPtr + stride * (i + 1),
std::swap_ranges(srcBufferPtr + stride * i,
srcBufferPtr + stride * i + srcSize.width * bpp,
srcBufferPtr + stride * (srcSize.height - 1 - i));
}
@ -1018,7 +1020,6 @@ already_AddRefed<ImageBitmap> ImageBitmap::CreateImageBitmapInternal(
// handle alpha premultiplication if surface not of correct type
gfxAlphaType alphaType = aAlphaType;
bool mustCopy = aMustCopy;
bool requiresPremultiply = false;
bool requiresUnpremultiply = false;
@ -1027,29 +1028,26 @@ already_AddRefed<ImageBitmap> ImageBitmap::CreateImageBitmapInternal(
aOptions.mPremultiplyAlpha == PremultiplyAlpha::None) {
requiresUnpremultiply = true;
alphaType = gfxAlphaType::NonPremult;
if (!aAllocatedImageData) {
mustCopy = true;
}
} else if (aAlphaType == gfxAlphaType::NonPremult &&
aOptions.mPremultiplyAlpha == PremultiplyAlpha::Premultiply) {
requiresPremultiply = true;
alphaType = gfxAlphaType::Premult;
if (!aAllocatedImageData) {
mustCopy = true;
}
}
}
/*
* if we don't own the data and need to create a new buffer to flip Y.
* if we don't own the data and need to modify the buffer.
* or
* we need to crop and flip, where crop must come first.
* or
* Or the caller demands a copy (WebGL contexts).
* the caller demands a copy (WebGL contexts).
*/
if ((aOptions.mImageOrientation == ImageOrientation::FlipY &&
(!aAllocatedImageData || aCropRect.isSome())) ||
mustCopy) {
bool willModify = aOptions.mImageOrientation == ImageOrientation::FlipY ||
requiresPremultiply || requiresUnpremultiply;
if ((willModify && !aAllocatedImageData) ||
(aOptions.mImageOrientation == ImageOrientation::FlipY &&
aCropRect.isSome()) ||
aMustCopy) {
dataSurface = surface->GetDataSurface();
dataSurface = CropAndCopyDataSourceSurface(dataSurface, cropRect);
@ -1430,7 +1428,7 @@ already_AddRefed<ImageBitmap> ImageBitmap::CreateInternal(
return nullptr;
}
bool needToReportMemoryAllocation = true;
bool needToReportMemoryAllocation = false;
return CreateImageBitmapInternal(aGlobal, surface, aCropRect, aOptions,
writeOnly, needToReportMemoryAllocation,