Go to the documentation of this file.00001 #ifndef QPID_INLINEALLOCATOR_H
00002 #define QPID_INLINEALLOCATOR_H
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include <memory>
00026 #include <assert.h>
00027 #include <boost/type_traits/type_with_alignment.hpp>
00028 #include <boost/type_traits/alignment_of.hpp>
00029
00030 namespace qpid {
00031
00032 template <typename RequestedType, typename InlineType, typename BaseAllocator, size_t Max>
00033 struct InlineRebind;
00034
00035
00040 template <class BaseAllocator, size_t Max>
00041 class InlineAllocator : public BaseAllocator {
00042 public:
00043 typedef typename BaseAllocator::pointer pointer;
00044 typedef typename BaseAllocator::size_type size_type;
00045 typedef typename BaseAllocator::value_type value_type;
00046
00047 InlineAllocator() : allocated(false) {}
00048 InlineAllocator(const InlineAllocator& x) : BaseAllocator(x), allocated(false) {}
00049
00050 pointer allocate(size_type n) {
00051 if (n <= Max && !allocated) {
00052 allocated=true;
00053 return reinterpret_cast<value_type*>(address());
00054 }
00055 else
00056 return BaseAllocator::allocate(n, 0);
00057 }
00058
00059 void deallocate(pointer p, size_type n) {
00060 if (p == address()) {
00061 assert(allocated);
00062 allocated=false;
00063 }
00064 else
00065 BaseAllocator::deallocate(p, n);
00066 }
00067
00068 template<typename T1>
00069 struct rebind {
00070 typedef typename InlineRebind<T1, value_type, BaseAllocator, Max>::other other;
00071 };
00072
00073 private:
00074
00075 static const size_t ALIGNMENT=boost::alignment_of<value_type>::value;
00076 typedef typename boost::type_with_alignment<ALIGNMENT>::type Aligner;
00077 union Store {
00078 Aligner aligner_;
00079 char sizer_[sizeof(value_type)*Max];
00080 } store;
00081 value_type* address() { return reinterpret_cast<value_type*>(&store); }
00082 bool allocated;
00083 };
00084
00085
00086
00087
00088
00089 template <typename RequestedType, typename InlineType, typename BaseAllocator, size_t Max>
00090 struct InlineRebind {
00091 typedef typename BaseAllocator::template rebind<RequestedType>::other other;
00092 };
00093
00094 template <typename T, typename BaseAllocator, size_t Max>
00095 struct InlineRebind<T, T, BaseAllocator, Max> {
00096 typedef typename qpid::InlineAllocator<BaseAllocator, Max> other;
00097 };
00098
00099 }
00100
00101 #endif