44 class FullAllocationTracker::Helper :
public Allocatable {
47 : allocations_(*this),
49 deallocation_count_(0U),
50 allocated_bytes_count_(0U),
51 deallocated_bytes_count_(0U),
52 active_memory_bytes_count_(0U) {}
58 size_t AddAllocation(
const void* memory,
size_t size) {
60 const size_t index = allocations_.size();
61 allocations_.push_back(Allocation(memory, size));
62 DCHECK(active_map_.find(memory) == active_map_.end());
63 active_map_[memory] = index;
64 allocated_bytes_count_ += size;
65 active_memory_bytes_count_ += size;
71 size_t RemoveAllocation(
const void* memory) {
73 ActiveMap::iterator it = active_map_.find(memory);
74 if (it == active_map_.end()) {
77 const size_t index = it->second;
79 ++deallocation_count_;
80 const size_t size = allocations_[index].size;
81 deallocated_bytes_count_ += size;
82 DCHECK_LE(size, active_memory_bytes_count_);
83 active_memory_bytes_count_ -= size;
84 active_map_.erase(it);
92 return allocations_.size();
98 return deallocation_count_;
104 return allocated_bytes_count_;
109 return deallocated_bytes_count_;
115 return active_map_.size();
121 return active_memory_bytes_count_;
125 size_t GetAllocationBytesCount(
size_t index)
const {
128 return allocations_[index].size;
134 Allocation(
const void* memory_in,
size_t size_in)
135 : memory(memory_in), size(size_in) {}
141 const AllocVector<Allocation> GetActiveAllocations()
const {
146 AllocVector<Allocation> vec(*
this);
147 vec.reserve(active_map_.size());
148 for (ActiveMap::const_iterator it = active_map_.begin();
149 it != active_map_.end(); ++it) {
150 DCHECK_LT(it->second, allocations_.size());
151 vec.push_back(allocations_[it->second]);
154 std::sort(vec.begin(), vec.end(), CompareAllocations);
160 static bool CompareAllocations(
const Allocation& a0,
const Allocation& a1) {
161 return a0.memory < a1.memory;
165 AllocVector<Allocation> allocations_;
169 typedef AllocMap<const void*, size_t> ActiveMap;
170 ActiveMap active_map_;
173 size_t deallocation_count_;
176 size_t allocated_bytes_count_;
177 size_t deallocated_bytes_count_;
180 size_t active_memory_bytes_count_;
183 mutable port::Mutex
mutex_;
186 FullAllocationTracker::Helper::~Helper() {
188 const AllocVector<Allocation> allocations = GetActiveAllocations();
189 if (!allocations.empty()) {
190 LOG(
ERROR) <<
"FullAllocationTracker " <<
this <<
" destroyed with "
191 << allocations.size() <<
" active allocations:";
192 for (
size_t i = 0; i < allocations.size(); ++i) {
193 const Allocation& a = allocations[i];
194 LOG(
ERROR) <<
" [" << i <<
"] " << a.size <<
" bytes at " << a.memory;
209 tracing_ostream_(NULL) {}
217 const Allocator& allocator,
size_t requested_size,
const void* memory) {
218 const size_t index = helper_->AddAllocation(memory, requested_size);
219 if (tracing_ostream_) {
220 (*tracing_ostream_) <<
"FullAllocationTracker " <<
this <<
" [" << index
221 <<
"] Allocated " << requested_size <<
" bytes @ "
222 << memory <<
" with allocator " << &allocator <<
"\n";
227 const Allocator& allocator,
const void* memory) {
228 const size_t index = helper_->RemoveAllocation(memory);
230 LOG(
ERROR) <<
"FullAllocationTracker " <<
this <<
": pointer " << memory
231 <<
" does not correspond to an active allocation";
233 if (tracing_ostream_) {
234 const size_t size = helper_->GetAllocationBytesCount(index);
235 (*tracing_ostream_) <<
"FullAllocationTracker " <<
this <<
" [" << index
236 <<
"] Deallocated " << size <<
" bytes @ " << memory
237 <<
" with allocator " << &allocator <<
"\n";
243 return helper_->GetAllocationCount();
247 return helper_->GetDeallocationCount();
251 return helper_->GetAllocatedBytesCount();
255 return helper_->GetDeallocatedBytesCount();
259 return helper_->GetActiveAllocationCount();
263 return helper_->GetActiveAllocationBytesCount();
size_t GetActiveAllocationBytesCount() override
void SetGpuTracker(const AllocationSizeTrackerPtr &gpu_tracker) override
Sets/returns an AllocationSizeTracker instance used to track GPU memory allocations.
SharedPtr< AllocationSizeTracker > AllocationSizeTrackerPtr
Convenience typedef for shared pointer to a AllocationSizeTracker.
size_t GetAllocatedBytesCount() override
Returns the total number of memory ever allocated or deallocated, in bytes.
const size_t kInvalidIndex
kInvalidIndex is a size_t value that is very unlikely to be a valid index.
size_t GetActiveAllocationCount() override
Returns the number of active allocations or the amount of memory in bytes used by active allocations...
GenericLockGuard< port::Mutex > LockGuard
Convenient typedefs for ion::port::Mutex.
AllocationManager is a singleton class that is used to manage Allocators used to allocate Ion objects...
#define LOG(severity)
Logs the streamed message unconditionally with a severity of severity.
size_t GetDeallocationCount() override
size_t GetDeallocatedBytesCount() override
AllocationSizeTrackerPtr GetGpuTracker() override
Allocator is an abstract base class for a memory allocator used for Ion objects derived from Allocata...
void TrackAllocation(const Allocator &allocator, size_t requested_size, const void *memory) override
AllocationTracker interface implementations.
Copyright 2016 Google Inc.
FullAllocationTracker()
FullAllocationTracker functions.
void TrackDeallocation(const Allocator &allocator, const void *memory) override
TrackDeallocation() is called immediately before an Allocator deallocates memory. ...
size_t GetAllocationCount() override
Returns the total number of tracked allocations or deallocations.
#define DCHECK_LE(val1, val2)
port::Mutex mutex_
Protects shared access to the Allocator and FT_Library.
~FullAllocationTracker() override
The destructor is protected because all instances should be managed through SharedPtr.
A SharedPtr is a smart shared pointer to an instance of some class that implements reference counting...
#define DCHECK_LT(val1, val2)