1 #ifndef RAPIDJSON_INTERNAL_STACK_H_
2 #define RAPIDJSON_INTERNAL_STACK_H_
13 template <
typename Allocator>
16 Stack(Allocator* allocator,
size_t stack_capacity) : allocator_(allocator), own_allocator_(0), stack_(0), stack_top_(0), stack_end_(0), stack_capacity_(stack_capacity) {
19 own_allocator_ = allocator_ =
new Allocator();
20 stack_top_ = stack_ = (
char*)allocator_->Malloc(stack_capacity_);
21 stack_end_ = stack_ + stack_capacity_;
25 Allocator::Free(stack_);
26 delete own_allocator_;
29 void Clear() { stack_top_ = stack_; }
34 RAPIDJSON_FORCEINLINE T* Push(
size_t count = 1) {
36 if (stack_top_ +
sizeof(T) * count >= stack_end_)
39 T* ret =
reinterpret_cast<T*
>(stack_top_);
40 stack_top_ +=
sizeof(T) * count;
45 T* Pop(
size_t count) {
47 stack_top_ -= count *
sizeof(T);
48 return reinterpret_cast<T*
>(stack_top_);
54 return reinterpret_cast<T*
>(stack_top_ -
sizeof(T));
58 T* Bottom() {
return (T*)stack_; }
60 Allocator& GetAllocator() {
return *allocator_; }
61 bool Empty()
const {
return stack_top_ == stack_; }
62 size_t GetSize()
const {
return static_cast<size_t>(stack_top_ - stack_); }
63 size_t GetCapacity()
const {
return stack_capacity_; }
67 void Expand(
size_t count) {
68 size_t new_capacity = stack_capacity_ * 2;
69 size_t size = GetSize();
70 size_t new_size = GetSize() +
sizeof(T) * count;
71 if (new_capacity < new_size)
72 new_capacity = new_size;
73 stack_ = (
char*)allocator_->Realloc(stack_, stack_capacity_, new_capacity);
74 stack_capacity_ = new_capacity;
75 stack_top_ = stack_ + size;
76 stack_end_ = stack_ + stack_capacity_;
81 Stack& operator=(
const Stack&);
83 Allocator* allocator_;
84 Allocator* own_allocator_;
88 size_t stack_capacity_;
94 #endif // RAPIDJSON_STACK_H_