13 #ifndef LLVM_CLANG_AST_INTERP_INTERPSTACK_H
14 #define LLVM_CLANG_AST_INTERP_INTERPSTACK_H
30 template <
typename T,
typename... Tys>
void push(Tys &&... Args) {
31 new (grow(aligned_size<T>())) T(std::forward<Tys>(Args)...);
35 template <
typename T> T
pop() {
36 auto *Ptr = &peek<T>();
37 auto Value = std::move(*Ptr);
39 shrink(aligned_size<T>());
45 auto *Ptr = &peek<T>();
47 shrink(aligned_size<T>());
51 template <
typename T> T &
peek() {
52 return *
reinterpret_cast<T *
>(
peek(aligned_size<T>()));
56 void *
top() {
return Chunk ?
peek(0) :
nullptr; }
59 size_t size()
const {
return StackSize; }
67 template <
typename T> constexpr
size_t aligned_size()
const {
68 constexpr
size_t PtrAlign =
alignof(
void *);
69 return ((
sizeof(T) + PtrAlign - 1) / PtrAlign) * PtrAlign;
73 void *grow(
size_t Size);
75 void *
peek(
size_t Size);
77 void shrink(
size_t Size);
80 static constexpr
size_t ChunkSize = 1024 * 1024;
93 StackChunk(StackChunk *Prev =
nullptr)
94 : Next(nullptr), Prev(Prev),
End(reinterpret_cast<char *>(this + 1)) {}
97 size_t size() {
return End - start(); }
100 char *start() {
return reinterpret_cast<char *
>(
this + 1); }
102 static_assert(
sizeof(StackChunk) < ChunkSize,
"Invalid chunk size");
105 StackChunk *Chunk =
nullptr;
107 size_t StackSize = 0;