How to track memory usage with EASTL?

The Electronic Arts EASTL library east::allocatorrequires the user to implement a special operator new(as shown in this sample ). This statement newhas const char* name, which is supposed to be used to record information about the application-specific memory allocation of the EASTL containers. The EASTL Best Practices manual also mentions the need to “Name containers to track memory usage.”

However, it seems that there is no corresponding const char* name, transmitted eastl::allocator::deallocate, so there is no built-in way to write deallocoding .

How should this EASTL debugging feature be used? I think I'm missing something. EA's software engineer also gave a related presentation in 2015, where he showed some internal tools developed by EA for memory debugging, and seems to suggest that they track both allocation and release (for example, to free memory for "game level 1" "when" game level 2 "begins).

+1
source share
1 answer

Distributors using EASTL maintain state and are bound to the container instance; that is, they are defined at the instance level:

EASTL, , . , EASTL , , ..

EASTL , . , A B, . , B B . , , operator ==; EASTL , , - .

from https://github.com/questor/eastl/blob/master/doc/EASTL%20Design.html

, allocator , :

#ifndef EASTL_CUSTOM_ALLOCATOR_H_
#define EASTL_CUSTOM_ALLOCATOR_H_

#include "new_implementation.hpp"
#include <EASTL/list.h>
#include <iostream>

#define DEBUG_MACRO

class EASTL_CustomAllocator {
public:
    EASTL_CustomAllocator(const char* pName = EASTL_NAME_VAL(EASTL_ALLOCATOR_DEFAULT_NAME))
        : m_pName(pName), m_totalAmountOfBytesAllocated(0) {
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": default construct allocator" << std::endl;
#endif
    }
    EASTL_CustomAllocator(const EASTL_CustomAllocator& x)
        : m_pName(x.m_pName),
          m_totalAmountOfBytesAllocated(x.m_totalAmountOfBytesAllocated) {
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": copy construct allocator" << std::endl;
#endif
    }
    EASTL_CustomAllocator(const EASTL_CustomAllocator& x, const char* pName)
        : m_pName(pName),
          m_totalAmountOfBytesAllocated(x.m_totalAmountOfBytesAllocated) {
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": copy construct allocator" << std::endl;
#endif
    }

    EASTL_CustomAllocator& operator=(const EASTL_CustomAllocator& x) {
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": copy assignment" << std::endl;
#endif
        m_pName = x.m_pName;
        m_totalAmountOfBytesAllocated = x.m_totalAmountOfBytesAllocated;
        return *this;
    }

    void* allocate(size_t num_of_bytes, int flags = 0) {
        m_totalAmountOfBytesAllocated += num_of_bytes;
        void* p = ::new((char*)0, flags, 0, (char*)0,        0) char[num_of_bytes];
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": allocate " << num_of_bytes << " bytes" << " at: " << (void*) p << std::endl;
#endif
        return p;
    }
    void* allocate(size_t num_of_bytes, size_t alignment, size_t offset, int flags = 0) {
        m_totalAmountOfBytesAllocated += num_of_bytes;
        void* p = ::new(alignment, offset, (char*)0, flags, 0, (char*)0,        0) char[num_of_bytes];
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": allocate " << num_of_bytes << " bytes" << " at: " << (void*) p << std::endl;
#endif
        return p;
    }
    void  deallocate(void* p, size_t num_of_bytes) {
        m_totalAmountOfBytesAllocated -= num_of_bytes;
#ifdef DEBUG_MACRO
        std::cout << m_pName << ": deallocate " << num_of_bytes << " bytes" << " at: " << (void*) p << std::endl;
#endif
        delete[](char*)p;
    }

    const char* get_name() const {
        return m_pName;
    }
    void        set_name(const char* pName) {
        m_pName = pName;
    }
    size_t get_totalAmountOfBytesAllocated() const {
        return m_totalAmountOfBytesAllocated;
    }

protected:
    const char* m_pName;    // Debug name, used to track memory.
    size_t m_totalAmountOfBytesAllocated;   // keeps track of the memory currently allocated
};


bool operator==(const EASTL_CustomAllocator& a, const EASTL_CustomAllocator& b) {
    if (&a == &b) {
        return true;    // allocator a and b are equal if they are the same
    }
    else {
        return false;   // otherwhise, return false, because the state m_totalAmountOfBytesAllocated needs to be increased/decreased on splice and swap
    }
}
bool operator!=(const EASTL_CustomAllocator& a, const EASTL_CustomAllocator& b) {
    return false;
}


#endif /* EASTL_CUSTOM_ALLOCATOR_H_ */

eastl, ( set_allocator()):

eastl::list<int, EASTL_CustomAllocator> 
list(EASTL_CustomAllocator("EASTL Some Name"));

, .

0

Source: https://habr.com/ru/post/1674110/


All Articles