From 6229b1240aae8961a4bf34493b964d944a0a06ee Mon Sep 17 00:00:00 2001 From: Ben Wagner Date: Mon, 24 Jul 2017 16:11:31 -0400 Subject: Control crash ArenaAlloc for unsatisfiable requests. BUG=chromium:747043 Change-Id: I24b757d75098a1125dcdf908a3aeffe98b16e66d Reviewed-on: https://skia-review.googlesource.com/26372 Commit-Queue: Ben Wagner Reviewed-by: Mike Klein --- src/core/SkArenaAlloc.cpp | 23 ++++++++++++++++++----- 1 file changed, 18 insertions(+), 5 deletions(-) (limited to 'src/core/SkArenaAlloc.cpp') diff --git a/src/core/SkArenaAlloc.cpp b/src/core/SkArenaAlloc.cpp index 5d02d85368..450f0dac6e 100644 --- a/src/core/SkArenaAlloc.cpp +++ b/src/core/SkArenaAlloc.cpp @@ -8,6 +8,7 @@ #include #include #include "SkArenaAlloc.h" +#include "SkTypes.h" static char* end_chain(char*) { return nullptr; } @@ -109,19 +110,31 @@ void SkArenaAlloc::ensureSpace(uint32_t size, uint32_t alignment) { // This must be conservative to add the right amount of extra memory to handle the alignment // padding. constexpr uint32_t alignof_max_align_t = 8; - uint32_t objSizeAndOverhead = size + headerSize + sizeof(Footer); + constexpr uint32_t maxSize = std::numeric_limits::max(); + constexpr uint32_t overhead = headerSize + sizeof(Footer); + SkASSERT_RELEASE(size <= maxSize - overhead); + uint32_t objSizeAndOverhead = size + overhead; if (alignment > alignof_max_align_t) { - objSizeAndOverhead += alignment - 1; + uint32_t alignmentOverhead = alignment - 1; + SkASSERT_RELEASE(objSizeAndOverhead <= maxSize - alignmentOverhead); + objSizeAndOverhead += alignmentOverhead; } - uint32_t allocationSize = std::max(objSizeAndOverhead, fExtraSize * fFib0); - fFib0 += fFib1; - std::swap(fFib0, fFib1); + uint32_t minAllocationSize; + if (fExtraSize <= maxSize / fFib0) { + minAllocationSize = fExtraSize * fFib0; + fFib0 += fFib1; + std::swap(fFib0, fFib1); + } else { + minAllocationSize = maxSize; + } + uint32_t allocationSize = std::max(objSizeAndOverhead, minAllocationSize); // Round up to a nice size. If > 32K align to 4K boundary else up to max_align_t. The > 32K // heuristic is from the JEMalloc behavior. { uint32_t mask = allocationSize > (1 << 15) ? (1 << 12) - 1 : 16 - 1; + SkASSERT_RELEASE(allocationSize <= maxSize - mask); allocationSize = (allocationSize + mask) & ~mask; } -- cgit v1.2.3