1/* 2 * Copyright 2015 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8#include "SkVarAlloc.h" 9 10// We use non-standard malloc diagnostic methods to make sure our allocations are sized well. 11#if defined(SK_BUILD_FOR_MAC) 12 #include <malloc/malloc.h> 13#elif defined(SK_BUILD_FOR_UNIX) || defined(SK_BUILD_FOR_WIN32) 14 #include <malloc.h> 15#endif 16 17struct SkVarAlloc::Block { 18 Block* prev; 19 char* data() { return (char*)(this + 1); } 20 21 static Block* Alloc(Block* prev, size_t size, unsigned flags) { 22 SkASSERT(size >= sizeof(Block)); 23 Block* b = (Block*)sk_malloc_flags(size, flags); 24 b->prev = prev; 25 return b; 26 } 27}; 28 29SkVarAlloc::SkVarAlloc(size_t minLgSize) 30 : fBytesAllocated(0) 31 , fByte(NULL) 32 , fRemaining(0) 33 , fLgSize(minLgSize) 34 , fBlock(NULL) {} 35 36SkVarAlloc::SkVarAlloc(size_t minLgSize, char* storage, size_t len) 37 : fBytesAllocated(0) 38 , fByte(storage) 39 , fRemaining(len) 40 , fLgSize(minLgSize) 41 , fBlock(NULL) {} 42 43SkVarAlloc::~SkVarAlloc() { 44 Block* b = fBlock; 45 while (b) { 46 Block* prev = b->prev; 47 sk_free(b); 48 b = prev; 49 } 50} 51 52void SkVarAlloc::makeSpace(size_t bytes, unsigned flags) { 53 SkASSERT(SkIsAlignPtr(bytes)); 54 55 size_t alloc = 1<<fLgSize++; 56 while (alloc < bytes + sizeof(Block)) { 57 alloc *= 2; 58 } 59 fBytesAllocated += alloc; 60 fBlock = Block::Alloc(fBlock, alloc, flags); 61 fByte = fBlock->data(); 62 fRemaining = alloc - sizeof(Block); 63 64#if defined(SK_BUILD_FOR_MAC) 65 SkASSERT(alloc == malloc_good_size(alloc)); 66#elif defined(SK_BUILD_FOR_UNIX) && !defined(__UCLIBC__) 67 // TODO(mtklein): tune so we can assert something like this 68 //SkASSERT(alloc == malloc_usable_size(fBlock)); 69#endif 70} 71