//
// Copyright (C) 2000-2002 Andrey Slepuhin <pooh@msu.ru>
//
// libp++ is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// libp++ is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with libp++; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
//
// $Source$
// $Revision$
// $Date$
// Author: Andrey Slepuhin <pooh@msu.ru>

#ifndef __pxx_default_allocator_hh__
#define __pxx_default_allocator_hh__

#include "pxx_allocator.hh"
#include "pxx_malloc_allocator.hh"

namespace pxx
{

//
// Default allocator implementation
class DefaultAllocator :
  public Allocator
{

private:

  //
  // Real allocator used as default
  Allocator* allocator ;
  //
  // MallocAllocator used if no allocator is set
  static MallocAllocator default_malloc_allocator ;

  NO_COPY_CTOR(DefaultAllocator)
  NO_ASSIGN(DefaultAllocator)

public:
  //
  // Constructor
  inline DefaultAllocator () ;
  //
  // Destructor
  inline ~DefaultAllocator () ;
  //
  // Allocate memory block of _size bytes
  inline void* allocate (size_t _size) ;
  //
  // Free memory block at _ptr
  inline void deallocate (void* _ptr) ;
  //
  // Resize memory block at _ptr to _size bytes
  inline void* reallocate (void* _ptr, size_t _size) ;
  //
  // Get real allocator to use
  inline Allocator& get () ;
  //
  // Set real allocator to use
  inline void set (Allocator& _allocator) ;
  //
  // Returns (if possible) a real size (probably larger then given)
  // of memory block to be allocated
  inline size_t get_real_size (size_t _size) const ;
  //
  // Returns (if possible) the start address of allocated block containing a
  // pointer, otherwise returns null
  inline void* get_block (void* _ptr) ;
  //
  // The same as previous, but using block size
  inline void* get_block (void* _ptr, size_t _size) ;
  //
  // Checks whether an address is in allocator address range
  inline bool is_dyn_addr (void* _ptr) ;

};

extern DefaultAllocator default_allocator ;

}

#endif // __pxx_default_allocator_hh__
