1 // -*- C++ -*- 2 // Testing allocator for the C++ library testsuite. 3 // 4 // Copyright (C) 2002, 2003 Free Software Foundation, Inc. 5 // 6 // This file is part of the GNU ISO C++ Library. This library is free 7 // software; you can redistribute it and/or modify it under the 8 // terms of the GNU General Public License as published by the 9 // Free Software Foundation; either version 2, or (at your option) 10 // any later version. 11 // 12 // This library is distributed in the hope that it will be useful, 13 // but WITHOUT ANY WARRANTY; without even the implied warranty of 14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 // GNU General Public License for more details. 16 // 17 // You should have received a copy of the GNU General Public License along 18 // with this library; see the file COPYING. If not, write to the Free 19 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, 20 // USA. 21 // 22 // As a special exception, you may use this file as part of a free software 23 // library without restriction. Specifically, if other files instantiate 24 // templates or use macros or inline functions from this file, or you compile 25 // this file and link it with other files to produce an executable, this 26 // file does not by itself cause the resulting executable to be covered by 27 // the GNU General Public License. This exception does not however 28 // invalidate any other reasons why the executable file might be covered by 29 // the GNU General Public License. 30 31 // This file provides an test instrumentation allocator that can be 32 // used to verify allocation functionality of standard library 33 // containers. 2002.11.25 smw 34 35 #ifndef _GLIBCXX_TESTSUITE_ALLOCATOR_H 36 #define _GLIBCXX_TESTSUITE_ALLOCATOR_H 37 38 #include <cstddef> 39 #include <limits> 40 41 namespace __gnu_test 42 { 43 class allocation_tracker 44 { 45 public: 46 typedef std::size_t size_type; 47 48 static void* allocate(size_type blocksize)49 allocate(size_type blocksize) 50 { 51 allocationTotal_ += blocksize; 52 return ::operator new(blocksize); 53 } 54 55 static void construct()56 construct() { constructCount_++; } 57 58 static void destroy()59 destroy() { destructCount_++; } 60 61 static void deallocate(void * p,size_type blocksize)62 deallocate(void* p, size_type blocksize) 63 { 64 ::operator delete(p); 65 deallocationTotal_ += blocksize; 66 } 67 68 static size_type allocationTotal()69 allocationTotal() { return allocationTotal_; } 70 71 static size_type deallocationTotal()72 deallocationTotal() { return deallocationTotal_; } 73 74 static int constructCount()75 constructCount() { return constructCount_; } 76 77 static int destructCount()78 destructCount() { return destructCount_; } 79 80 static void resetCounts()81 resetCounts() 82 { 83 allocationTotal_ = 0; 84 deallocationTotal_ = 0; 85 constructCount_ = 0; 86 destructCount_ = 0; 87 } 88 89 private: 90 static size_type allocationTotal_; 91 static size_type deallocationTotal_; 92 static int constructCount_; 93 static int destructCount_; 94 }; 95 96 // A simple basic allocator that just forwards to the 97 // allocation_tracker to fulfill memory requests. This class is 98 // templated on the target object type, but tracker isn't. 99 template<class T> 100 class tracker_alloc 101 { 102 public: 103 typedef T value_type; 104 typedef T* pointer; 105 typedef const T* const_pointer; 106 typedef T& reference; 107 typedef const T& const_reference; 108 typedef std::size_t size_type; 109 typedef std::ptrdiff_t difference_type; 110 111 template<class U> struct rebind { typedef tracker_alloc<U> other; }; 112 113 pointer address(reference value)114 address(reference value) const 115 { return &value; } 116 117 const_pointer address(const_reference value)118 address(const_reference value) const 119 { return &value; } 120 throw()121 tracker_alloc() throw() 122 { } 123 throw()124 tracker_alloc(const tracker_alloc&) throw() 125 { } 126 127 template<class U> tracker_alloc(const tracker_alloc<U> &)128 tracker_alloc(const tracker_alloc<U>&) throw() 129 { } 130 throw()131 ~tracker_alloc() throw() 132 { } 133 134 size_type max_size()135 max_size() const throw() 136 { return std::numeric_limits<std::size_t>::max() / sizeof(T); } 137 138 pointer 139 allocate(size_type n, const void* = 0) 140 { 141 return static_cast<pointer>(allocation_tracker::allocate(n * sizeof(T))); 142 } 143 144 void construct(pointer p,const T & value)145 construct(pointer p, const T& value) 146 { 147 new (p) T(value); 148 allocation_tracker::construct(); 149 } 150 151 void destroy(pointer p)152 destroy(pointer p) 153 { 154 p->~T(); 155 allocation_tracker::destroy(); 156 } 157 158 void deallocate(pointer p,size_type num)159 deallocate(pointer p, size_type num) 160 { allocation_tracker::deallocate(p, num * sizeof(T)); } 161 }; 162 163 template<class T1, class T2> 164 bool 165 operator==(const tracker_alloc<T1>&, const tracker_alloc<T2>&) throw() 166 { return true; } 167 168 template<class T1, class T2> 169 bool 170 operator!=(const tracker_alloc<T1>&, const tracker_alloc<T2>&) throw() 171 { return false; } 172 }; // namespace __gnu_test 173 174 #endif // _GLIBCXX_TESTSUITE_ALLOCATOR_H 175 176