BufferAllocator-inl.h (4561B)
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- 2 * vim: set ts=8 sts=2 et sw=2 tw=80: 3 * This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef gc_BufferAllocator_inl_h 8 #define gc_BufferAllocator_inl_h 9 10 #include "gc/BufferAllocator.h" 11 12 #include "mozilla/MathAlgorithms.h" 13 14 #include "ds/SlimLinkedList.h" 15 #include "js/HeapAPI.h" 16 17 #include "gc/Allocator-inl.h" 18 19 namespace js::gc { 20 21 /* static */ 22 inline bool BufferAllocator::IsSmallAllocSize(size_t bytes) { 23 return bytes <= MaxSmallAllocSize; 24 } 25 26 /* static */ 27 inline bool BufferAllocator::IsLargeAllocSize(size_t bytes) { 28 return bytes > MaxMediumAllocSize; 29 } 30 31 /* static */ 32 inline size_t BufferAllocator::GetGoodAllocSize(size_t requiredBytes) { 33 requiredBytes = std::max(requiredBytes, MinAllocSize); 34 35 if (IsLargeAllocSize(requiredBytes)) { 36 return RoundUp(requiredBytes, ChunkSize); 37 } 38 39 if (IsSmallAllocSize(requiredBytes)) { 40 return RoundUp(requiredBytes, SmallAllocGranularity); 41 } 42 43 return RoundUp(requiredBytes, MediumAllocGranularity); 44 } 45 46 /* static */ 47 size_t BufferAllocator::GetGoodPower2AllocSize(size_t requiredBytes) { 48 requiredBytes = std::max(requiredBytes, MinAllocSize); 49 50 return mozilla::RoundUpPow2(requiredBytes); 51 } 52 53 /* static */ 54 size_t BufferAllocator::GetGoodElementCount(size_t requiredElements, 55 size_t elementSize) { 56 size_t requiredBytes = requiredElements * elementSize; 57 size_t goodSize = GetGoodAllocSize(requiredBytes); 58 return goodSize / elementSize; 59 } 60 61 /* static */ 62 size_t BufferAllocator::GetGoodPower2ElementCount(size_t requiredElements, 63 size_t elementSize) { 64 size_t requiredBytes = requiredElements * elementSize; 65 size_t goodSize = GetGoodPower2AllocSize(requiredBytes); 66 return goodSize / elementSize; 67 } 68 69 inline size_t GetGoodAllocSize(size_t requiredBytes) { 70 return BufferAllocator::GetGoodAllocSize(requiredBytes); 71 } 72 73 inline size_t GetGoodElementCount(size_t requiredCount, size_t elementSize) { 74 return BufferAllocator::GetGoodElementCount(requiredCount, elementSize); 75 } 76 77 inline size_t GetGoodPower2AllocSize(size_t requiredBytes) { 78 return BufferAllocator::GetGoodPower2AllocSize(requiredBytes); 79 } 80 81 inline size_t GetGoodPower2ElementCount(size_t requiredCount, 82 size_t elementSize) { 83 return BufferAllocator::GetGoodPower2ElementCount(requiredCount, elementSize); 84 } 85 86 inline void* AllocBuffer(JS::Zone* zone, size_t bytes, bool nurseryOwned) { 87 if (js::oom::ShouldFailWithOOM()) { 88 return nullptr; 89 } 90 91 return zone->bufferAllocator.alloc(bytes, nurseryOwned); 92 } 93 94 inline void* AllocBufferInGC(JS::Zone* zone, size_t bytes, bool nurseryOwned) { 95 return zone->bufferAllocator.allocInGC(bytes, nurseryOwned); 96 } 97 98 inline void* ReallocBuffer(JS::Zone* zone, void* alloc, size_t bytes, 99 bool nurseryOwned) { 100 if (js::oom::ShouldFailWithOOM()) { 101 return nullptr; 102 } 103 104 return zone->bufferAllocator.realloc(alloc, bytes, nurseryOwned); 105 } 106 107 inline void FreeBuffer(JS::Zone* zone, void* alloc) { 108 return zone->bufferAllocator.free(alloc); 109 } 110 111 inline bool IsBufferAlloc(void* alloc) { 112 return BufferAllocator::IsBufferAlloc(alloc); 113 } 114 115 #ifdef DEBUG 116 inline bool IsBufferAllocInZone(void* alloc, JS::Zone* zone) { 117 return zone->bufferAllocator.hasAlloc(alloc); 118 } 119 #endif 120 121 inline size_t GetAllocSize(JS::Zone* zone, const void* alloc) { 122 return zone->bufferAllocator.getAllocSize(const_cast<void*>(alloc)); 123 } 124 125 inline bool IsNurseryOwned(JS::Zone* zone, void* alloc) { 126 return zone->bufferAllocator.isNurseryOwned(alloc); 127 } 128 129 inline bool IsBufferAllocMarkedBlack(JS::Zone* zone, void* alloc) { 130 return zone->bufferAllocator.isMarkedBlack(alloc); 131 } 132 133 inline void TraceBufferEdgeInternal(JSTracer* trc, Cell* owner, void** bufferp, 134 const char* name) { 135 owner->zoneFromAnyThread()->bufferAllocator.traceEdge(trc, owner, bufferp, 136 name); 137 } 138 inline void TraceBufferEdgeInternal(JSTracer* trc, JS::Zone* zone, 139 void** bufferp, const char* name) { 140 zone->bufferAllocator.traceEdge(trc, nullptr, bufferp, name); 141 } 142 143 inline void MarkTenuredBuffer(JS::Zone* zone, void* alloc) { 144 zone->bufferAllocator.markTenuredAlloc(alloc); 145 } 146 147 } // namespace js::gc 148 149 #endif // gc_BufferAllocator_inl_h