/ src / leveldb / util / arena.h
arena.h
 1  // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
 2  // Use of this source code is governed by a BSD-style license that can be
 3  // found in the LICENSE file. See the AUTHORS file for names of contributors.
 4  
 5  #ifndef STORAGE_LEVELDB_UTIL_ARENA_H_
 6  #define STORAGE_LEVELDB_UTIL_ARENA_H_
 7  
 8  #include <atomic>
 9  #include <cassert>
10  #include <cstddef>
11  #include <cstdint>
12  #include <vector>
13  
14  namespace leveldb {
15  
16  class Arena {
17   public:
18    Arena();
19  
20    Arena(const Arena&) = delete;
21    Arena& operator=(const Arena&) = delete;
22  
23    ~Arena();
24  
25    // Return a pointer to a newly allocated memory block of "bytes" bytes.
26    char* Allocate(size_t bytes);
27  
28    // Allocate memory with the normal alignment guarantees provided by malloc.
29    char* AllocateAligned(size_t bytes);
30  
31    // Returns an estimate of the total memory usage of data allocated
32    // by the arena.
33    size_t MemoryUsage() const {
34      return memory_usage_.load(std::memory_order_relaxed);
35    }
36  
37   private:
38    char* AllocateFallback(size_t bytes);
39    char* AllocateNewBlock(size_t block_bytes);
40  
41    // Allocation state
42    char* alloc_ptr_;
43    size_t alloc_bytes_remaining_;
44  
45    // Array of new[] allocated memory blocks
46    std::vector<char*> blocks_;
47  
48    // Total memory usage of the arena.
49    //
50    // TODO(costan): This member is accessed via atomics, but the others are
51    //               accessed without any locking. Is this OK?
52    std::atomic<size_t> memory_usage_;
53  };
54  
55  inline char* Arena::Allocate(size_t bytes) {
56    // The semantics of what to return are a bit messy if we allow
57    // 0-byte allocations, so we disallow them here (we don't need
58    // them for our internal use).
59    assert(bytes > 0);
60    if (bytes <= alloc_bytes_remaining_) {
61      char* result = alloc_ptr_;
62      alloc_ptr_ += bytes;
63      alloc_bytes_remaining_ -= bytes;
64      return result;
65    }
66    return AllocateFallback(bytes);
67  }
68  
69  }  // namespace leveldb
70  
71  #endif  // STORAGE_LEVELDB_UTIL_ARENA_H_