This is an automated email from the git hooks/post-receive script.
richard pushed a commit to branch tor-browser-91.8.0esr-11.0-1 in repository tor-browser.
commit 4ed1d7ab3cfe4cf806746d560cc6917b15bee767 Author: Andrew Osmond aosmond@mozilla.com AuthorDate: Mon Mar 21 09:15:45 2022 -0400
Bug 1691774 - Check shmem allocation/mapping failures in ClientWebGLContext. r=jgilbert, a=RyanVM
We use webgl::RaiiShmem in a few places to read in pixel buffers from a call to the compositor process. Shmems might fail to be mapped into our process, probably due to virtual memory constraints, and we should check for that condition.
Differential Revision: https://phabricator.services.mozilla.com/D136365 --- dom/canvas/ClientWebGLContext.cpp | 27 ++++++++++++++++++++------- dom/canvas/ClientWebGLContext.h | 3 ++- 2 files changed, 22 insertions(+), 8 deletions(-)
diff --git a/dom/canvas/ClientWebGLContext.cpp b/dom/canvas/ClientWebGLContext.cpp index dfe2550d047d3..7f7dc1e85c307 100644 --- a/dom/canvas/ClientWebGLContext.cpp +++ b/dom/canvas/ClientWebGLContext.cpp @@ -909,6 +909,7 @@ RefPtrgfx::SourceSurface ClientWebGLContext::GetFrontBufferSnapshot( } const auto& surfSize = res.surfSize; const webgl::RaiiShmem shmem{child, res.shmem}; + if (!shmem) return nullptr; const auto& shmemBytes = shmem.ByteRange(); if (!surfSize.x) return nullptr; // Zero means failure.
@@ -1002,7 +1003,7 @@ RefPtrgfx::DataSourceSurface ClientWebGLContext::BackBufferSnapshot() {
const auto desc = webgl::ReadPixelsDesc{{0, 0}, size}; const auto range = Range<uint8_t>(map.GetData(), stride * size.y); - DoReadPixels(desc, range); + if (!DoReadPixels(desc, range)) return nullptr;
const auto begin = range.begin().get();
@@ -3099,6 +3100,10 @@ void ClientWebGLContext::GetBufferSubData(GLenum target, GLintptr srcByteOffset, return; } const webgl::RaiiShmem shmem{child, rawShmem}; + if (!shmem) { + EnqueueError(LOCAL_GL_OUT_OF_MEMORY, "Failed to map in sub data buffer."); + return; + }
const auto shmemView = shmem.ByteRange(); MOZ_RELEASE_ASSERT(shmemView.length() == 1 + destView.length()); @@ -4575,18 +4580,20 @@ void ClientWebGLContext::ReadPixels(GLint x, GLint y, GLsizei width, {format, type}, state.mPixelPackState}; const auto range = Range<uint8_t>(bytes, byteLen); - DoReadPixels(desc, range); + if (!DoReadPixels(desc, range)) { + return; + } }
-void ClientWebGLContext::DoReadPixels(const webgl::ReadPixelsDesc& desc, +bool ClientWebGLContext::DoReadPixels(const webgl::ReadPixelsDesc& desc, const Range<uint8_t> dest) const { const auto notLost = mNotLost; // Hold a strong-ref to prevent LoseContext=>UAF. - if (!notLost) return; + if (!notLost) return false; const auto& inProcess = notLost->inProcess; if (inProcess) { inProcess->ReadPixelsInto(desc, dest); - return; + return true; } const auto& child = notLost->outOfProcess; child->FlushPendingCmds(); @@ -4594,16 +4601,20 @@ void ClientWebGLContext::DoReadPixels(const webgl::ReadPixelsDesc& desc, if (!child->SendReadPixels(desc, dest.length(), &res)) { res = {}; } - if (!res.byteStride) return; + if (!res.byteStride) return false; const auto& byteStride = res.byteStride; const auto& subrect = res.subrect; const webgl::RaiiShmem shmem{child, res.shmem}; const auto& shmemBytes = shmem.ByteRange(); + if (!shmem) { + EnqueueError(LOCAL_GL_OUT_OF_MEMORY, "Failed to map in back buffer."); + return false; + }
uint8_t bpp; if (!GetBytesPerPixel(desc.pi, &bpp)) { MOZ_ASSERT(false); - return; + return false; }
const auto& packing = desc.packState; @@ -4628,6 +4639,8 @@ void ClientWebGLContext::DoReadPixels(const webgl::ReadPixelsDesc& desc, } Memcpy(destItr, srcItr, xByteSize); } + + return true; }
bool ClientWebGLContext::ReadPixels_SharedPrecheck( diff --git a/dom/canvas/ClientWebGLContext.h b/dom/canvas/ClientWebGLContext.h index 12e5d5782be49..c9f185dd1c790 100644 --- a/dom/canvas/ClientWebGLContext.h +++ b/dom/canvas/ClientWebGLContext.h @@ -1009,7 +1009,8 @@ class ClientWebGLContext final : public nsICanvasRenderingContextInternal,
private: RefPtrgfx::DataSourceSurface BackBufferSnapshot(); - void DoReadPixels(const webgl::ReadPixelsDesc&, Range<uint8_t>) const; + [[nodiscard]] bool DoReadPixels(const webgl::ReadPixelsDesc&, + Range<uint8_t>) const; uvec2 DrawingBufferSize();
void AfterDrawCall() {