memarray.hxx
Go to the documentation of this file.00001
00002
00003 #ifndef CH_MATRIX_CLASSES__MEMARRAY_HXX
00004 #define CH_MATRIX_CLASSES__MEMARRAY_HXX
00005
00015 #include <iostream>
00016 #include "matop.hxx"
00017 #if (CONICBUNDLE_DEBUG>=1)
00018 #include <iomanip>
00019 #include <stdlib.h>
00020 #endif
00021
00022
00023 namespace CH_Matrix_Classes {
00024
00029
00046 class Memarray{
00047 private:
00048
00050 class Entry{
00051 public:
00052 Entry *next;
00053 char *addr;
00054 long size;
00055 int index;
00056
00058 Entry(){next=0; addr=0; size=0;}
00060 ~Entry(){delete[] addr;}
00061 };
00062
00063 long max_entries;
00064 long max_sizes;
00065 long max_addr_entr;
00066 unsigned long addr_mask;
00067 unsigned long in_use;
00068 unsigned long memarray_users;
00069
00070 Entry first_empty;
00071 Entry* entry_store;
00072 Entry* first_free;
00073 Entry* first_used;
00074
00076 int size_index(register long size);
00078 long index_size(register int index);
00080 int addr_index(register const char *addr);
00082 int get_more_entries();
00083
00084 public:
00086 Memarray(long number_of_entries,int number_of_sizes,int address_bits);
00088 ~Memarray();
00090 unsigned long get_in_use() const {return in_use;}
00092 unsigned long get_memarray_users() const {return memarray_users;}
00094 unsigned long increment_memarray_users() {return ++memarray_users;}
00096 unsigned long decrement_memarray_users() {return --memarray_users;}
00097
00099 long get(register long size,char *& addr);
00101 long get(long size,double *& addr)
00102 {return get(size*long(sizeof(double)),(char*&)addr)/long(sizeof(double));}
00104 long get(long size,float *& addr)
00105 {return get(size*long(sizeof(float)),(char*&)addr)/long(sizeof(float));}
00107 long get(long size,long *& addr)
00108 {return get(size*long(sizeof(long)),(char*&)addr)/long(sizeof(long));}
00110 long get(long size,int *& addr)
00111 {return get(size*long(sizeof(int)),(char*&)addr)/long(sizeof(int));}
00113 int free(register void *addr);
00114 };
00115
00117 class Memarrayuser
00118 {
00119 protected:
00121 static Memarray* memarray;
00122 public:
00124 Memarrayuser()
00125 {
00126 if (memarray==0) {
00127 memarray=new Memarray(1L,60,10);
00128 }
00129 memarray->increment_memarray_users();
00130 }
00131
00133 virtual ~Memarrayuser()
00134 {
00135 #if (CONICBUNDLE_DEBUG>=1)
00136 if (memarray==0) {
00137 MEmessage(MatrixError(ME_unspec,"*** Error: Memarrayuser::~Memarrayuser(): memory management killed prematurely",MTglobalfun));
00138 }
00139 #endif
00140 if (memarray->decrement_memarray_users()==0) {
00141 delete memarray;
00142 memarray=0;
00143 }
00144 }
00145 };
00146
00148 template<class T>
00149 inline int mem_provide(
00150 Memarray& memarray,
00151 long provide,
00152 long in_use,
00153 long& avail,
00154 T*& store
00155 )
00156 {
00157 if (provide<avail) return 0;
00158 T* tmpstore;
00159 long tmpavail=memarray.get(((provide>2*avail)?provide:2*avail)*long(sizeof(T)),(char *&)tmpstore)/long(sizeof(T));
00160 if ((tmpstore==0)&&(provide<2*avail)){
00161 tmpavail=memarray.get(provide*long(sizeof(T)),(char *&)tmpstore)/long(sizeof(T));
00162 }
00163 if (tmpstore==0) return 1;
00164 long i;
00165 for(i=0;i<in_use;i++){
00166 tmpstore[i]=store[i];
00167 }
00168 memarray.free((void *)store);
00169 store=tmpstore;
00170 avail=tmpavail;
00171 return 0;
00172 }
00173
00175 template<class T>
00176 inline int mem_provide_init0(
00177 Memarray& memarray,
00178 long provide,
00179 long& avail,
00180 T*& store
00181 )
00182 {
00183 if (provide<avail) return 0;
00184 T* tmpstore;
00185 long tmpavail=memarray.get(((provide>2*avail)?provide:2*avail)*long(sizeof(T)),(char *&)tmpstore)/long(sizeof(T));
00186 if ((tmpstore==0)&&(provide<2*avail)){
00187 tmpavail=memarray.get(provide*long(sizeof(T)),(char *&)tmpstore)/long(sizeof(T));
00188 }
00189 if (tmpstore==0) return 1;
00190 long i;
00191 for(i=0;i<avail;i++){
00192 tmpstore[i]=store[i];
00193 }
00194 for(;i<tmpavail;i++){
00195 tmpstore[i]=0;
00196 }
00197 memarray.free((void *)store);
00198 store=tmpstore;
00199 avail=tmpavail;
00200 return 0;
00201 }
00202
00204
00205 }
00206
00207 #endif
00208