| Index: third_party/WebKit/Source/platform/heap/CallbackStack.h
|
| diff --git a/third_party/WebKit/Source/platform/heap/CallbackStack.h b/third_party/WebKit/Source/platform/heap/CallbackStack.h
|
| index 97fe8280fb357a70a77daa5f07fe4929bc74cded..5b835800750a7e4039e05615535319deb02baf95 100644
|
| --- a/third_party/WebKit/Source/platform/heap/CallbackStack.h
|
| +++ b/third_party/WebKit/Source/platform/heap/CallbackStack.h
|
| @@ -8,6 +8,8 @@
|
| #include "platform/heap/BlinkGC.h"
|
| #include "wtf/Allocator.h"
|
| #include "wtf/Assertions.h"
|
| +#include "wtf/Threading.h"
|
| +#include "wtf/ThreadingPrimitives.h"
|
|
|
| namespace blink {
|
|
|
| @@ -37,10 +39,10 @@ public:
|
| VisitorCallback m_callback;
|
| };
|
|
|
| - explicit CallbackStack(size_t blockSize = kDefaultBlockSize);
|
| + static std::unique_ptr<CallbackStack> create();
|
| ~CallbackStack();
|
|
|
| - void clear();
|
| + void commit();
|
| void decommit();
|
|
|
| Item* allocateEntry();
|
| @@ -53,6 +55,7 @@ public:
|
| #if ENABLE(ASSERT)
|
| bool hasCallbackForObject(const void*);
|
| #endif
|
| + bool hasJustOneBlock() const;
|
|
|
| static const size_t kMinimalBlockSize;
|
| static const size_t kDefaultBlockSize = (1 << 13);
|
| @@ -61,15 +64,12 @@ private:
|
| class Block {
|
| USING_FAST_MALLOC(Block);
|
| public:
|
| - Block(Block* next, size_t blockSize);
|
| + explicit Block(Block* next);
|
| ~Block();
|
|
|
| #if ENABLE(ASSERT)
|
| void clear();
|
| #endif
|
| - void reset();
|
| - void decommit();
|
| -
|
| Block* next() const { return m_next; }
|
| void setNext(Block* next) { m_next = next; }
|
|
|
| @@ -109,17 +109,41 @@ private:
|
| Block* m_next;
|
| };
|
|
|
| + CallbackStack();
|
| Item* popSlow();
|
| Item* allocateEntrySlow();
|
| void invokeOldestCallbacks(Block*, Block*, Visitor*);
|
| - bool hasJustOneBlock() const;
|
|
|
| Block* m_first;
|
| Block* m_last;
|
| };
|
|
|
| +class CallbackStackMemoryPool final {
|
| + USING_FAST_MALLOC(CallbackStackMemoryPool);
|
| +public:
|
| + // 2048 * 8 * sizeof(Item) = 256 KB (64bit) is pre-allocated for the
|
| + // underlying buffer of CallbackStacks.
|
| + static const size_t kBlockSize = 2048;
|
| + static const size_t kPooledBlockCount = 8;
|
| + static const size_t kBlockBytes = kBlockSize * sizeof(CallbackStack::Item);
|
| +
|
| + static CallbackStackMemoryPool& instance();
|
| +
|
| + void initialize();
|
| + void shutdown();
|
| + CallbackStack::Item* allocate();
|
| + void free(CallbackStack::Item*);
|
| +
|
| +private:
|
| + Mutex m_mutex;
|
| + int m_freeListFirst;
|
| + int m_freeListNext[kPooledBlockCount];
|
| + CallbackStack::Item* m_pooledMemory;
|
| +};
|
| +
|
| ALWAYS_INLINE CallbackStack::Item* CallbackStack::allocateEntry()
|
| {
|
| + DCHECK(m_first);
|
| Item* item = m_first->allocateEntry();
|
| if (LIKELY(!!item))
|
| return item;
|
|
|