00001 #ifndef __INSTANTIO_CACHE_H
00002 #define __INSTANTIO_CACHE_H
00003
00004 #ifdef _MSC_VER
00005 # pragma once
00006 #endif
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #include "InstantIODef.h"
00027 #include "BasicCache.h"
00028 #include "RefCtr.h"
00029 #include <stack>
00030 #include <exception>
00031 #ifdef __sgi
00032 # include <assert.h>
00033 #else
00034 # include <cassert>
00035 #endif
00036
00037
00038 namespace InstantIO
00039 {
00040
00041
00048 template <class T> class Cache: public BasicCache
00049 {
00050 public:
00051
00058 ~Cache()
00059 {
00060 if (cache_.size() != memory_.size())
00061 #if (defined(__GNUC__) || defined(__sgi))
00062 throw std::exception();
00063 #else
00064 throw std::exception("Trying to release a Cache object that has unreleased data objects");
00065 #endif
00066 while (!memory_.empty())
00067 {
00068 delete memory_.top();
00069 memory_.pop();
00070 }
00071 };
00072
00080 inline static Cache<T> &the()
00081 { return the_; }
00082
00095 RefCtr<T> *acquire()
00096 {
00097 RefCtr<T> *value;
00098
00099 lock();
00100 if (cache_.empty())
00101 {
00102 value = new RefCtr<T>;
00103 memory_.push(value);
00104 }
00105 else
00106 {
00107 value = cache_.top();
00108 cache_.pop();
00109 }
00110 unlock();
00111
00112 return value;
00113 };
00114
00125 void release(RefCtr<T> *value)
00126 {
00127 assert(value != 0);
00128 lock();
00129 cache_.push(value);
00130 unlock();
00131 };
00132
00133
00134
00135
00136
00144 inline Cache(): BasicCache() {}
00145
00146 private:
00147
00149 Cache(const Cache<T> &);
00150
00152 const Cache<T> &operator=(const Cache<T> &);
00153
00155 static Cache<T> the_;
00156
00158 std::stack<RefCtr<T>*> memory_;
00159
00161 std::stack<RefCtr<T>*> cache_;
00162 };
00163
00164
00166 template <class T> Cache<T> Cache<T>::the_;
00167
00168
00169 }
00170
00171
00172 #endif // __INSTANTIO_CACHE_H