Bug 1777411 - Improve error messages when cloning ImageBitmap. r=gfx-reviewers,lsalzman

Differential Revision: https://phabricator.services.mozilla.com/D150697
This commit is contained in:
Andrew Osmond 2022-06-30 13:36:34 +00:00
Родитель eea090b829
Коммит 2b5b6c5a20
3 изменённых файлов: 20 добавлений и 17 удалений

Просмотреть файл

@ -1059,15 +1059,13 @@ bool StructuredCloneHolder::CustomWriteHandler(
{ {
ImageBitmap* imageBitmap = nullptr; ImageBitmap* imageBitmap = nullptr;
if (NS_SUCCEEDED(UNWRAP_OBJECT(ImageBitmap, &obj, imageBitmap))) { if (NS_SUCCEEDED(UNWRAP_OBJECT(ImageBitmap, &obj, imageBitmap))) {
if (imageBitmap->IsWriteOnly()) {
return false;
}
SameProcessScopeRequired(aSameProcessScopeRequired); SameProcessScopeRequired(aSameProcessScopeRequired);
if (CloneScope() == StructuredCloneScope::SameProcess) { if (CloneScope() == StructuredCloneScope::SameProcess) {
return ImageBitmap::WriteStructuredClone(aWriter, GetSurfaces(), ErrorResult rv;
imageBitmap); ImageBitmap::WriteStructuredClone(aWriter, GetSurfaces(), imageBitmap,
rv);
return !rv.MaybeSetPendingException(aCx);
} }
return false; return false;
} }

Просмотреть файл

@ -1734,16 +1734,20 @@ JSObject* ImageBitmap::ReadStructuredClone(
} }
/*static*/ /*static*/
bool ImageBitmap::WriteStructuredClone( void ImageBitmap::WriteStructuredClone(
JSStructuredCloneWriter* aWriter, JSStructuredCloneWriter* aWriter,
nsTArray<RefPtr<DataSourceSurface>>& aClonedSurfaces, nsTArray<RefPtr<DataSourceSurface>>& aClonedSurfaces,
ImageBitmap* aImageBitmap) { ImageBitmap* aImageBitmap, ErrorResult& aRv) {
MOZ_ASSERT(aWriter); MOZ_ASSERT(aWriter);
MOZ_ASSERT(aImageBitmap); MOZ_ASSERT(aImageBitmap);
if (aImageBitmap->IsWriteOnly()) {
return aRv.ThrowDataCloneError("Cannot clone ImageBitmap, is write-only");
}
if (!aImageBitmap->mData) { if (!aImageBitmap->mData) {
// A closed image cannot be cloned. // A closed image cannot be cloned.
return false; return aRv.ThrowDataCloneError("Cannot clone ImageBitmap, is closed");
} }
const uint32_t picRectX = BitwiseCast<uint32_t>(aImageBitmap->mPictureRect.x); const uint32_t picRectX = BitwiseCast<uint32_t>(aImageBitmap->mPictureRect.x);
@ -1762,17 +1766,18 @@ bool ImageBitmap::WriteStructuredClone(
NS_WARN_IF(!JS_WriteUint32Pair(aWriter, picRectWidth, picRectHeight)) || NS_WARN_IF(!JS_WriteUint32Pair(aWriter, picRectWidth, picRectHeight)) ||
NS_WARN_IF( NS_WARN_IF(
!JS_WriteUint32Pair(aWriter, alphaType, aImageBitmap->mWriteOnly))) { !JS_WriteUint32Pair(aWriter, alphaType, aImageBitmap->mWriteOnly))) {
return false; return aRv.ThrowDataCloneError(
"Cannot clone ImageBitmap, failed to write params");
} }
RefPtr<SourceSurface> surface = aImageBitmap->mData->GetAsSourceSurface(); RefPtr<SourceSurface> surface = aImageBitmap->mData->GetAsSourceSurface();
if (NS_WARN_IF(!surface)) { if (NS_WARN_IF(!surface)) {
return false; return aRv.ThrowDataCloneError("Cannot clone ImageBitmap, no surface");
} }
RefPtr<DataSourceSurface> snapshot = surface->GetDataSurface(); RefPtr<DataSourceSurface> snapshot = surface->GetDataSurface();
if (NS_WARN_IF(!snapshot)) { if (NS_WARN_IF(!snapshot)) {
return false; return aRv.ThrowDataCloneError("Cannot clone ImageBitmap, no data surface");
} }
RefPtr<DataSourceSurface> dstDataSurface; RefPtr<DataSourceSurface> dstDataSurface;
@ -1782,18 +1787,18 @@ bool ImageBitmap::WriteStructuredClone(
// directly, using ScopedMap to get stride. // directly, using ScopedMap to get stride.
DataSourceSurface::ScopedMap map(snapshot, DataSourceSurface::READ); DataSourceSurface::ScopedMap map(snapshot, DataSourceSurface::READ);
if (NS_WARN_IF(!map.IsMapped())) { if (NS_WARN_IF(!map.IsMapped())) {
return false; return aRv.ThrowDataCloneError(
"Cannot clone ImageBitmap, cannot map surface");
} }
dstDataSurface = Factory::CreateDataSourceSurfaceWithStride( dstDataSurface = Factory::CreateDataSourceSurfaceWithStride(
snapshot->GetSize(), snapshot->GetFormat(), map.GetStride(), true); snapshot->GetSize(), snapshot->GetFormat(), map.GetStride(), true);
} }
if (NS_WARN_IF(!dstDataSurface)) { if (NS_WARN_IF(!dstDataSurface)) {
return false; return aRv.ThrowDataCloneError("Cannot clone ImageBitmap, out of memory");
} }
Factory::CopyDataSourceSurface(snapshot, dstDataSurface); Factory::CopyDataSourceSurface(snapshot, dstDataSurface);
aClonedSurfaces.AppendElement(dstDataSurface); aClonedSurfaces.AppendElement(dstDataSurface);
return true;
} }
size_t ImageBitmap::GetAllocatedSize() const { size_t ImageBitmap::GetAllocatedSize() const {

Просмотреть файл

@ -130,10 +130,10 @@ class ImageBitmap final : public nsISupports, public nsWrapperCache {
const nsTArray<RefPtr<gfx::DataSourceSurface>>& aClonedSurfaces, const nsTArray<RefPtr<gfx::DataSourceSurface>>& aClonedSurfaces,
uint32_t aIndex); uint32_t aIndex);
static bool WriteStructuredClone( static void WriteStructuredClone(
JSStructuredCloneWriter* aWriter, JSStructuredCloneWriter* aWriter,
nsTArray<RefPtr<gfx::DataSourceSurface>>& aClonedSurfaces, nsTArray<RefPtr<gfx::DataSourceSurface>>& aClonedSurfaces,
ImageBitmap* aImageBitmap); ImageBitmap* aImageBitmap, ErrorResult& aRv);
friend CreateImageBitmapFromBlob; friend CreateImageBitmapFromBlob;
friend CreateImageBitmapFromBlobTask; friend CreateImageBitmapFromBlobTask;