1 #ifndef TEST_ALLOCATOR_H 2 #define TEST_ALLOCATOR_H 3 4 #include <cstddef> 5 #include <type_traits> 6 #include <cstdlib> 7 #include <new> 8 #include <climits> 9 #include <cassert> 10 11 class test_alloc_base 12 { 13 protected: 14 static int time_to_throw; 15 public: 16 static int throw_after; 17 static int count; 18 static int alloc_count; 19 }; 20 21 int test_alloc_base::count = 0; 22 int test_alloc_base::time_to_throw = 0; 23 int test_alloc_base::alloc_count = 0; 24 int test_alloc_base::throw_after = INT_MAX; 25 26 template <class T> 27 class test_allocator 28 : public test_alloc_base 29 { 30 int data_; 31 32 template <class U> friend class test_allocator; 33 public: 34 35 typedef unsigned size_type; 36 typedef int difference_type; 37 typedef T value_type; 38 typedef value_type* pointer; 39 typedef const value_type* const_pointer; 40 typedef typename std::add_lvalue_reference<value_type>::type reference; 41 typedef typename std::add_lvalue_reference<const value_type>::type const_reference; 42 43 template <class U> struct rebind {typedef test_allocator<U> other;}; 44 45 test_allocator() throw() : data_(0) {++count;} 46 explicit test_allocator(int i) throw() : data_(i) {++count;} 47 test_allocator(const test_allocator& a) throw() 48 : data_(a.data_) {++count;} 49 template <class U> test_allocator(const test_allocator<U>& a) throw() 50 : data_(a.data_) {++count;} 51 ~test_allocator() throw() {assert(data_ >= 0); --count; data_ = -1;} 52 pointer address(reference x) const {return &x;} 53 const_pointer address(const_reference x) const {return &x;} 54 pointer allocate(size_type n, const void* = 0) 55 { 56 assert(data_ >= 0); 57 if (time_to_throw >= throw_after) 58 throw std::bad_alloc(); 59 ++time_to_throw; 60 ++alloc_count; 61 return (pointer)std::malloc(n * sizeof(T)); 62 } 63 void deallocate(pointer p, size_type n) 64 {assert(data_ >= 0); --alloc_count; std::free(p);} 65 size_type max_size() const throw() 66 {return UINT_MAX / sizeof(T);} 67 void construct(pointer p, const T& val) 68 {::new(p) T(val);} 69 void destroy(pointer p) {p->~T();} 70 71 friend bool operator==(const test_allocator& x, const test_allocator& y) 72 {return x.data_ == y.data_;} 73 friend bool operator!=(const test_allocator& x, const test_allocator& y) 74 {return !(x == y);} 75 }; 76 77 #endif // TEST_ALLOCATOR_H 78