00001 /* 00002 * This file is part of openMask © INRIA, CNRS, Universite de Rennes 1 1993-2002, thereinafter the Software 00003 * 00004 * The Software has been developped within the Siames Project. 00005 * INRIA, the University of Rennes 1 and CNRS jointly hold intellectual property rights 00006 * 00007 * The Software has been registered with the Agence pour la Protection des 00008 * Programmes (APP) under registration number IDDN.FR.001.510008.00.S.P.2001.000.41200 00009 * 00010 * This file may be distributed under the terms of the Q Public License 00011 * version 1.0 as defined by Trolltech AS of Norway and appearing in the file 00012 * LICENSE.QPL included in the packaging of this file. 00013 * 00014 * Licensees holding valid specific licenses issued by INRIA, CNRS or Université de Rennes 1 00015 * for the software may use this file in accordance with that specific license 00016 * 00017 */ 00018 #include <PsnNew.h> 00019 #include <PsnMemoryElementDescriptor.h> 00020 #include <PsnSharedMemoryManager.h> 00021 #include <PsnSystemMemoryManager.h> 00022 #include <iostream> 00023 00024 PsnSystemMemoryManager * HeapStackTop::getSystemMemoryManager() 00025 { 00026 // using new causes an infinite loop, as new needs getSystmeMemoryManager 00027 // 00028 static PsnSystemMemoryManager toto ; 00029 return & toto ; 00030 } 00031 00032 pthread_key_t HeapStackTop::initialiseGlobalMemoryManagerKey () 00033 { 00034 static bool done = false ; 00035 if ( ! done ) 00036 { 00037 pthread_key_t res ; 00038 pthread_key_create(&res, NULL) ; 00039 pthread_setspecific ( res , getSystemMemoryManager() ); 00040 done = true ; 00041 globalMemoryManagerKey = res ; 00042 return res ; 00043 } 00044 else 00045 { 00046 return globalMemoryManagerKey ; 00047 } 00048 } 00049 00050 00051 00052 pthread_key_t HeapStackTop::initialiseFreedKey () 00053 { 00054 static bool done = false ; 00055 if ( ! done ) 00056 { 00057 pthread_key_t res ; 00058 pthread_key_create(&res, NULL) ; 00059 pthread_setspecific ( res , NULL ); 00060 done = true ; 00061 freedKey =res ; 00062 return res ; 00063 } 00064 else 00065 { 00066 return freedKey ; 00067 } 00068 } 00069 00070 pthread_key_t HeapStackTop::globalMemoryManagerKey = HeapStackTop::initialiseGlobalMemoryManagerKey () ; 00071 pthread_key_t HeapStackTop::freedKey = HeapStackTop::initialiseFreedKey () ; 00072 00073 00074 00075 void * HeapStackTop::operator new (size_t size) { 00076 static pthread_key_t bidon = initialiseFreedKey () ; 00077 void * freed = pthread_getspecific(freedKey) ; 00078 00079 if (freed!=NULL) { 00080 return freed; 00081 } 00082 else { 00083 return ::operator new(size); 00084 } 00085 } 00086 00087 void HeapStackTop::operator delete(void* addr, size_t size) { 00088 static pthread_key_t bidon = initialiseFreedKey () ; 00089 void * freed = pthread_getspecific(freedKey) ; 00090 if (freed!=NULL) { 00091 ::operator delete (freed); 00092 } 00093 pthread_setspecific(freedKey, addr); 00094 } 00095 00096 00097 00098 HeapStackTop::HeapStackTop(PsnMemoryManager * newTop) { 00099 static pthread_key_t bidon = HeapStackTop::initialiseGlobalMemoryManagerKey () ; 00100 #ifdef _DEBUGMEMORYMANAGEMENT 00101 cerr<<"HeapStackTop::HeapStackTop"<<endl; 00102 #endif 00103 _oldMemoryManager = pthread_getspecific( globalMemoryManagerKey ) ; 00104 pthread_setspecific ( globalMemoryManagerKey , newTop ); 00105 } 00106 00107 00108 00109 HeapStackTop::~HeapStackTop() { 00110 static pthread_key_t bidon = HeapStackTop::initialiseGlobalMemoryManagerKey () ; 00111 #ifdef _DEBUGMEMORYMANAGEMENT 00112 cerr<<"HeapStackTop::~HeapStackTop"<<endl; 00113 #endif 00114 pthread_setspecific ( globalMemoryManagerKey , _oldMemoryManager ); 00115 } 00116 00117 #ifndef _SGI 00118 00119 void *operator new (size_t size) throw (bad_alloc) 00120 { 00121 /* because new could be used during static allocations, and that order of static initialisation 00122 * cannot be controlled, the first time new is called it's possible that HeapStackTop::globalMemoryManagerKey 00123 * has not yet been initialised. Therefore, a correct initialisation of 00124 * HeapStackTop::globalMemoryManagerKey has to be generated on the first call to the redefined new*/ 00125 00126 static pthread_key_t bidon = HeapStackTop::initialiseGlobalMemoryManagerKey () ; 00127 00128 #ifdef _DEBUGMEMORYMANAGEMENT 00129 assert ( bidon == HeapStackTop::globalMemoryManagerKey ) ; 00130 #endif 00131 00132 void * resul; 00133 #ifdef _DEBUGMEMORYMANAGEMENT 00134 cerr<<"Utilisation de new "<<endl; 00135 #endif 00136 void * currentMemoryManager = (PsnMemoryManager *) pthread_getspecific( HeapStackTop::globalMemoryManagerKey ) ; 00137 00138 #ifdef _DEBUGMEMORYMANAGEMENT 00139 assert ( currentMemoryManager != NULL ) ; 00140 #endif 00141 00142 resul = ( (PsnMemoryManager *)currentMemoryManager)->allocateSizeRemembered(size); 00143 00144 #ifdef _DEBUGMEMORYMANAGEMENT 00145 cerr<<"Utilisation de new fin "<<resul<<endl; 00146 #endif 00147 return resul; 00148 } 00149 00150 00151 00152 void *operator new[] (size_t size) throw (bad_alloc) 00153 { 00154 void * resul = operator new(size) ; 00155 if (resul != NULL) 00156 { 00157 return resul ; 00158 } 00159 else 00160 { 00161 throw bad_alloc() ; 00162 } 00163 } 00164 00165 00166 00167 void *operator new (size_t size, const nothrow_t&) throw() 00168 { 00169 return operator new(size); 00170 } 00171 00172 void *operator new[] (size_t size, const nothrow_t&) throw() { 00173 return operator new(size); 00174 } 00175 00176 void operator delete (void * ptr) throw() { 00177 #ifdef _DEBUGMEMORYMANAGEMENT 00178 cerr<<"Utilisation de delete "<<ptr<<endl; 00179 #endif 00180 if ( ptr != 0 ) 00181 { 00182 PsnMemoryManager * currentMemoryManager = (PsnMemoryManager *) (pthread_getspecific( HeapStackTop::globalMemoryManagerKey ) ); 00183 00184 if ( currentMemoryManager != NULL ) 00185 { 00186 // heuristic: the correct memory manager to use is probably the current memory manager 00187 // this heuristic enables to avoid global search (and look) for the correct memory manager in the good cases 00188 currentMemoryManager->freeSizeRemembered( ptr ); 00189 } 00190 } 00191 #ifdef _DEBUGMEMORYMANAGEMENT 00192 cerr<<"Utilisation de delete fin"<<endl; 00193 #endif 00194 } 00195 00196 void operator delete[] (void * ptr) throw() { 00197 #ifdef _DEBUGMEMORYMANAGEMENT 00198 cerr<<"operator delete[] (void * ptr) throw()"<<endl; 00199 #endif 00200 operator delete ( ptr ) ; 00201 // operator delete(ptr); 00202 } 00203 00204 void operator delete (void * ptr , const nothrow_t&) throw() 00205 { 00206 operator delete(ptr) ; 00207 //operator delete(ptr); 00208 } 00209 00210 void operator delete[] (void * ptr , const nothrow_t&) throw() 00211 { 00212 operator delete(ptr); 00213 //operator delete(ptr); 00214 } 00215 00216 #endif 00217 00218 00219 00220 00221 00222
| Documentation generated on Mon Nov 25 15:25:01 2002 |
Generated with doxygen 1.2.12 by Dimitri van Heesch , 1997-2001 |