00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014 #ifndef STXXL_TYPED_BLOCK_HEADER
00015 #define STXXL_TYPED_BLOCK_HEADER
00016
00017 #include <stxxl/bits/io/request.h>
00018 #include <stxxl/bits/common/aligned_alloc.h>
00019 #include <stxxl/bits/mng/bid.h>
00020
00021 #ifndef STXXL_VERBOSE_TYPED_BLOCK
00022 #define STXXL_VERBOSE_TYPED_BLOCK STXXL_VERBOSE2
00023 #endif
00024
00025
00026 __STXXL_BEGIN_NAMESPACE
00027
00030
00031
00032 template <unsigned bytes>
00033 class filler_struct__
00034 {
00035 typedef unsigned char byte_type;
00036 byte_type filler_array_[bytes];
00037
00038 public:
00039 filler_struct__() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] filler_struct__ is constructed"); }
00040 };
00041
00042 template <>
00043 class filler_struct__<0>
00044 {
00045 typedef unsigned char byte_type;
00046
00047 public:
00048 filler_struct__() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] filler_struct__<> is constructed"); }
00049 };
00050
00052 template <class T, unsigned Size_>
00053 class element_block
00054 {
00055 public:
00056 typedef T type;
00057 typedef T value_type;
00058 typedef T & reference;
00059 typedef const T & const_reference;
00060 typedef type * pointer;
00061 typedef pointer iterator;
00062 typedef const type * const_iterator;
00063
00064 enum
00065 {
00066 size = Size_
00067 };
00068
00070 T elem[size];
00071
00072 element_block() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] element_block is constructed"); }
00073
00075 reference operator [] (int i)
00076 {
00077 return elem[i];
00078 }
00079
00081 iterator begin()
00082 {
00083 return elem;
00084 }
00085
00087 const_iterator begin() const
00088 {
00089 return elem;
00090 }
00091
00093 const_iterator cbegin() const
00094 {
00095 return begin();
00096 }
00097
00099 iterator end()
00100 {
00101 return elem + size;
00102 }
00103
00105 const_iterator end() const
00106 {
00107 return elem + size;
00108 }
00109
00111 const_iterator cend() const
00112 {
00113 return end();
00114 }
00115 };
00116
00118 template <class T, unsigned Size_, unsigned RawSize_, unsigned NBids_ = 0>
00119 class block_w_bids : public element_block<T, Size_>
00120 {
00121 public:
00122 enum
00123 {
00124 raw_size = RawSize_,
00125 nbids = NBids_
00126 };
00127
00128 typedef BID<raw_size> bid_type;
00129
00131 bid_type ref[nbids];
00132
00134 bid_type & operator () (int i)
00135 {
00136 return ref[i];
00137 }
00138
00139 block_w_bids() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] block_w_bids is constructed"); }
00140 };
00141
00142 template <class T, unsigned Size_, unsigned RawSize_>
00143 class block_w_bids<T, Size_, RawSize_, 0>: public element_block<T, Size_>
00144 {
00145 public:
00146 enum
00147 {
00148 raw_size = RawSize_,
00149 nbids = 0
00150 };
00151
00152 typedef BID<raw_size> bid_type;
00153
00154 block_w_bids() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] block_w_bids<> is constructed"); }
00155 };
00156
00158 template <class T_, unsigned RawSize_, unsigned NBids_, class InfoType_ = void>
00159 class block_w_info :
00160 public block_w_bids<T_, ((RawSize_ - sizeof(BID<RawSize_>) * NBids_ - sizeof(InfoType_)) / sizeof(T_)), RawSize_, NBids_>
00161 {
00162 public:
00164 typedef InfoType_ info_type;
00165
00167 info_type info;
00168
00169 block_w_info() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] block_w_info is constructed"); }
00170 };
00171
00172 template <class T_, unsigned RawSize_, unsigned NBids_>
00173 class block_w_info<T_, RawSize_, NBids_, void>:
00174 public block_w_bids<T_, ((RawSize_ - sizeof(BID<RawSize_>) * NBids_) / sizeof(T_)), RawSize_, NBids_>
00175 {
00176 public:
00177 typedef void info_type;
00178
00179 block_w_info() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] block_w_info<> is constructed"); }
00180 };
00181
00183 template <typename BaseType_, unsigned FillSize_ = 0>
00184 class add_filler :
00185 public BaseType_
00186 {
00187 private:
00189 filler_struct__<FillSize_> filler;
00190
00191 public:
00192 add_filler() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] add_filler is constructed"); }
00193 };
00194
00195 template <typename BaseType_>
00196 class add_filler<BaseType_, 0>:
00197 public BaseType_
00198 {
00199 public:
00200 add_filler() { STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] add_filler<> is constructed"); }
00201 };
00202
00204 template <typename Tp_, unsigned RawSize_>
00205 class expand_struct :
00206 public add_filler<Tp_, RawSize_ - sizeof(Tp_)>
00207 { };
00208
00210
00222 template <unsigned RawSize_, class T_, unsigned NRef_ = 0, class InfoType_ = void>
00223 class typed_block :
00224 public expand_struct<block_w_info<T_, RawSize_, NRef_, InfoType_>, RawSize_>
00225 {
00226 typedef expand_struct<block_w_info<T_, RawSize_, NRef_, InfoType_>, RawSize_> Base;
00227
00228 public:
00229 typedef T_ value_type;
00230 typedef value_type & reference;
00231 typedef const value_type & const_reference;
00232 typedef value_type * pointer;
00233 typedef pointer iterator;
00234 typedef const value_type * const_pointer;
00235 typedef const_pointer const_iterator;
00236
00237 enum constants
00238 {
00239 raw_size = RawSize_,
00240 size = Base::size,
00241 has_only_data = (raw_size == (size * sizeof(value_type)))
00242 };
00243
00244 typedef BID<raw_size> bid_type;
00245
00246 typed_block()
00247 {
00248 STXXL_STATIC_ASSERT(sizeof(typed_block) == raw_size);
00249 STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] typed_block is constructed");
00250 #if 0
00251 assert(((long)this) % BLOCK_ALIGN == 0);
00252 #endif
00253 }
00254
00255 #if 0
00256 typed_block(const typed_block & tb)
00257 {
00258 STXXL_STATIC_ASSERT(sizeof(typed_block) == raw_size);
00259 STXXL_MSG("[" << (void *)this << "] typed_block is copy constructed from [" << (void *)&tb << "]");
00260 STXXL_UNUSED(tb);
00261 }
00262 #endif
00263
00269 request_ptr write(const bid_type & bid,
00270 completion_handler on_cmpl = default_completion_handler())
00271 {
00272 STXXL_VERBOSE_BLOCK_LIFE_CYCLE("BLC:write " << FMT_BID(bid));
00273 return bid.storage->awrite(this, bid.offset, raw_size, on_cmpl);
00274 }
00275
00281 request_ptr read(const bid_type & bid,
00282 completion_handler on_cmpl = default_completion_handler())
00283 {
00284 STXXL_VERBOSE_BLOCK_LIFE_CYCLE("BLC:read " << FMT_BID(bid));
00285 return bid.storage->aread(this, bid.offset, raw_size, on_cmpl);
00286 }
00287
00288 static void * operator new (size_t bytes)
00289 {
00290 unsigned_type meta_info_size = bytes % raw_size;
00291 STXXL_VERBOSE1("typed::block operator new: Meta info size: " << meta_info_size);
00292
00293 void * result = aligned_alloc<BLOCK_ALIGN>(bytes - meta_info_size, meta_info_size);
00294 #ifdef STXXL_VALGRIND_TYPED_BLOCK_INITIALIZE_ZERO
00295 memset(result, 0, bytes);
00296 #endif
00297 char * tmp = (char *)result;
00298 tmp += RawSize_;
00299 while (tmp < ((char *)result) + bytes)
00300 {
00301 tmp += RawSize_;
00302 }
00303 return result;
00304 }
00305
00306 static void * operator new[] (size_t bytes)
00307 {
00308 unsigned_type meta_info_size = bytes % raw_size;
00309 STXXL_VERBOSE1("typed::block operator new[]: Meta info size: " << meta_info_size);
00310
00311 void * result = aligned_alloc<BLOCK_ALIGN>(bytes - meta_info_size, meta_info_size);
00312 #ifdef STXXL_VALGRIND_TYPED_BLOCK_INITIALIZE_ZERO
00313 memset(result, 0, bytes);
00314 #endif
00315 char * tmp = (char *)result;
00316 tmp += RawSize_;
00317 while (tmp < ((char *)result) + bytes)
00318 {
00319 tmp += RawSize_;
00320 }
00321 return result;
00322 }
00323
00324 static void * operator new (size_t , void * ptr)
00325 {
00326 return ptr;
00327 }
00328
00329 static void operator delete (void * ptr)
00330 {
00331 aligned_dealloc<BLOCK_ALIGN>(ptr);
00332 }
00333
00334 static void operator delete[] (void * ptr)
00335 {
00336 aligned_dealloc<BLOCK_ALIGN>(ptr);
00337 }
00338
00339 static void operator delete (void *, void *)
00340 { }
00341
00342 #if 1
00343
00344
00345
00346
00347
00348
00349
00350
00351
00352 ~typed_block()
00353 {
00354 STXXL_VERBOSE_TYPED_BLOCK("[" << (void *)this << "] typed_block is destructed");
00355 }
00356 #endif
00357 };
00358
00360
00361 __STXXL_END_NAMESPACE
00362
00363 #endif // !STXXL_TYPED_BLOCK_HEADER
00364