I've implemented a simple memory manager (actually, it's more of a memory debugger) for one of my projects. All it does is overload operator new and add some header data to every memory allocation on the heap. This info is used to get memory statistics and locate memory leaks.
Operator new is overloaded on a global basis to add allocations to a default heap, but can also be overloaded per class in order to allocate objects to specific heaps (e.g. a heap for geometry objects). However, I'm not happy with my current method for overloading operator new for desired classes. At present I'm using macro defines, which can be added to any desired class:
#define MM_DECLARE_HEAP
public:
static void* operator new(std::size_t uiSize) throw (std::bad_alloc);
private:
static Memory::Heap* s_pClassHeap;
#define MM_DEFINE_HEAP(className,heapName)
Memory::Heap* className::s_pClassHeap = 0;
void* className::operator new(std::size_t uiSize) throw (std::bad_alloc)
{
if(s_pClassHeap == 0) s_pClassHeap = Memory::HeapFactory::CreateHeap(heapName);
return ::operator new(uiSize, s_pClassHeap);
}
This feels rather clumsy though, having to add MM_DECLARE_HEAP to any class header and MM_DEFINE_HEAP to the source of any class I want to monitor. The only advantage I can see in this method is that it's easy to disable by just defining these macros as empty in release builds.
As an alternative I've been experimenting with using templates instead, as follows:
template<class T>
class MemoryManaged
{
public:
void* operator new(std::size_t uiSize) throw (std::bad_alloc)
{
if(s_pClassHeap == 0) s_pClassHeap = HeapFactory::CreateHeap("Default");
return ::operator new(uiSize, s_pClassHeap);
}
private:
static Heap* s_pClassHeap;
};
template<class T> Heap* MemoryManaged<T>::s_pClassHeap = 0;
This feels cleaner, but I'm still having some problems. Firstly, multiple inheritance is a problem - If a parent and child class both inherit from the template then operator new becomes ambiguous. I'm also unsure unsure what's the best way to pass the heapName to the template. This was obviously trivial in the macro MM_DEFINE_HEAP(className,heapName) but appears less so with a template. As I've discovered, I can't pass a string literal but could pass a globally defined string - again, feels a bit dirty. In the code above "Default" is hard coded for now.
Anyway, should I even be looking at templates as a solution or am I heading in the wrong direction? Any suggestions would be welcome :)
Cheers!
Tim
[Edited by - tharris997 on March 31, 2009 9:23:04 PM]