|
Sierra Toolkit
Version of the Day
|
00001 /* 00002 Copyright (C) 2009-2010 Electronic Arts, Inc. All rights reserved. 00003 00004 Redistribution and use in source and binary forms, with or without 00005 modification, are permitted provided that the following conditions 00006 are met: 00007 00008 1. Redistributions of source code must retain the above copyright 00009 notice, this list of conditions and the following disclaimer. 00010 2. Redistributions in binary form must reproduce the above copyright 00011 notice, this list of conditions and the following disclaimer in the 00012 documentation and/or other materials provided with the distribution. 00013 3. Neither the name of Electronic Arts, Inc. ("EA") nor the names of 00014 its contributors may be used to endorse or promote products derived 00015 from this software without specific prior written permission. 00016 00017 THIS SOFTWARE IS PROVIDED BY ELECTRONIC ARTS AND ITS CONTRIBUTORS "AS IS" AND ANY 00018 EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 00019 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 00020 DISCLAIMED. IN NO EVENT SHALL ELECTRONIC ARTS OR ITS CONTRIBUTORS BE LIABLE FOR ANY 00021 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 00022 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00023 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 00024 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00025 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 00026 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00027 */ 00028 00030 // EASTL/allocator.h 00031 // 00032 // Copyright (c) 2005, Electronic Arts. All rights reserved. 00033 // Written and maintained by Paul Pedriana. 00035 00036 00037 #ifndef EASTL_ALLOCATOR_H 00038 #define EASTL_ALLOCATOR_H 00039 00040 00041 #include <stk_util/util/config_eastl.h> 00042 #include <stddef.h> 00043 00044 00045 #ifdef _MSC_VER 00046 #pragma warning(push) 00047 #pragma warning(disable: 4189) // local variable is initialized but not referenced 00048 #endif 00049 00050 00051 namespace eastl 00052 { 00053 00058 #ifndef EASTL_ALLOCATOR_DEFAULT_NAME 00059 #define EASTL_ALLOCATOR_DEFAULT_NAME EASTL_DEFAULT_NAME_PREFIX // Unless the user overrides something, this is "EASTL". 00060 #endif 00061 00062 00067 enum alloc_flags 00068 { 00069 MEM_TEMP = 0, // Low memory, not necessarily actually temporary. 00070 MEM_PERM = 1 // High memory, for things that won't be unloaded. 00071 }; 00072 00073 00081 class EASTL_API allocator 00082 { 00083 public: 00084 EASTL_ALLOCATOR_EXPLICIT allocator(const char* pName = EASTL_NAME_VAL(EASTL_ALLOCATOR_DEFAULT_NAME)); 00085 allocator(const allocator& x); 00086 allocator(const allocator& x, const char* pName); 00087 00088 allocator& operator=(const allocator& x); 00089 00090 void* allocate(size_t n, int flags = 0); 00091 void* allocate(size_t n, size_t alignment, size_t offset, int flags = 0); 00092 void deallocate(void* p, size_t n); 00093 00094 const char* get_name() const; 00095 void set_name(const char* pName); 00096 00097 protected: 00098 #if EASTL_NAME_ENABLED 00099 const char* mpName; // Debug name, used to track memory. 00100 #endif 00101 }; 00102 00103 bool operator==(const allocator& a, const allocator& b); 00104 bool operator!=(const allocator& a, const allocator& b); 00105 00106 EASTL_API allocator* GetDefaultAllocator(); 00107 EASTL_API allocator* SetDefaultAllocator(allocator* pAllocator); 00108 00109 00110 00128 template <typename Allocator> 00129 inline Allocator* get_default_allocator(const Allocator*) 00130 { 00131 return NULL; // By default we return NULL; the user must make specialization of this function in order to provide their own implementation. 00132 } 00133 00134 inline EASTLAllocatorType* get_default_allocator(const EASTLAllocatorType*) 00135 { 00136 return EASTLAllocatorDefault(); // For the built-in allocator EASTLAllocatorType, we happen to already have a function for returning the default allocator instance, so we provide it. 00137 } 00138 00139 00145 inline void* default_allocfreemethod(size_t n, void* pBuffer, void* /*pContext*/) 00146 { 00147 EASTLAllocatorType* const pAllocator = EASTLAllocatorDefault(); 00148 00149 if(pBuffer) // If freeing... 00150 { 00151 EASTLFree(*pAllocator, pBuffer, n); 00152 return NULL; // The return value is meaningless for the free. 00153 } 00154 else // allocating 00155 return EASTLAlloc(*pAllocator, n); 00156 } 00157 00158 00166 template <typename Allocator> 00167 void* allocate_memory(Allocator& a, size_t n, size_t alignment, size_t alignmentOffset) 00168 { 00169 if(alignment <= 8) 00170 return EASTLAlloc(a, n); 00171 return EASTLAllocAligned(a, n, alignment, alignmentOffset); 00172 } 00173 00174 } // namespace eastl 00175 00176 00177 00178 00179 00180 #ifndef EASTL_USER_DEFINED_ALLOCATOR // If the user hasn't declared that he has defined a different allocator implementation elsewhere... 00181 00182 #ifdef _MSC_VER 00183 #pragma warning(push, 0) 00184 #include <new> 00185 #pragma warning(pop) 00186 #else 00187 #include <new> 00188 #endif 00189 00190 #if !EASTL_DLL // If building a regular library and not building EASTL as a DLL... 00191 // It is expected that the application define the following 00192 // versions of operator new for the application. Either that or the 00193 // user needs to override the implementation of the allocator class. 00194 void* operator new[](size_t size, const char* pName, int flags, unsigned debugFlags, const char* file, int line); 00195 void* operator new[](size_t size, size_t alignment, size_t alignmentOffset, const char* pName, int flags, unsigned debugFlags, const char* file, int line); 00196 #endif 00197 00198 namespace eastl 00199 { 00200 inline allocator::allocator(const char* EASTL_NAME(pName)) 00201 { 00202 #if EASTL_NAME_ENABLED 00203 mpName = pName ? pName : EASTL_ALLOCATOR_DEFAULT_NAME; 00204 #endif 00205 } 00206 00207 00208 inline allocator::allocator(const allocator& EASTL_NAME(alloc)) 00209 { 00210 #if EASTL_NAME_ENABLED 00211 mpName = alloc.mpName; 00212 #endif 00213 } 00214 00215 00216 inline allocator::allocator(const allocator&, const char* EASTL_NAME(pName)) 00217 { 00218 #if EASTL_NAME_ENABLED 00219 mpName = pName ? pName : EASTL_ALLOCATOR_DEFAULT_NAME; 00220 #endif 00221 } 00222 00223 00224 inline allocator& allocator::operator=(const allocator& EASTL_NAME(alloc)) 00225 { 00226 #if EASTL_NAME_ENABLED 00227 mpName = alloc.mpName; 00228 #endif 00229 return *this; 00230 } 00231 00232 00233 inline const char* allocator::get_name() const 00234 { 00235 #if EASTL_NAME_ENABLED 00236 return mpName; 00237 #else 00238 return EASTL_ALLOCATOR_DEFAULT_NAME; 00239 #endif 00240 } 00241 00242 00243 inline void allocator::set_name(const char* EASTL_NAME(pName)) 00244 { 00245 #if EASTL_NAME_ENABLED 00246 mpName = pName; 00247 #endif 00248 } 00249 00250 00251 inline void* allocator::allocate(size_t n, int flags) 00252 { 00253 #if EASTL_NAME_ENABLED 00254 #define pName mpName 00255 #else 00256 #define pName EASTL_ALLOCATOR_DEFAULT_NAME 00257 #endif 00258 00259 #if EASTL_DLL 00260 // We currently have no support for implementing flags when 00261 // using the C runtime library operator new function. The user 00262 // can use SetDefaultAllocator to override the default allocator. 00263 (void)flags; 00264 return ::new char[n]; 00265 #elif (EASTL_DEBUGPARAMS_LEVEL <= 0) 00266 return ::new((char*)0, flags, 0, (char*)0, 0) char[n]; 00267 #elif (EASTL_DEBUGPARAMS_LEVEL == 1) 00268 return ::new( pName, flags, 0, (char*)0, 0) char[n]; 00269 #else 00270 return ::new( pName, flags, 0, __FILE__, __LINE__) char[n]; 00271 #endif 00272 } 00273 00274 00275 inline void* allocator::allocate(size_t n, size_t alignment, size_t offset, int flags) 00276 { 00277 #if EASTL_DLL 00278 // We have a problem here. We cannot support alignment, as we don't have access 00279 // to a memory allocator that can provide aligned memory. The C++ standard doesn't 00280 // recognize such a thing. The user will need to call SetDefaultAllocator to 00281 // provide an alloator which supports alignment. 00282 EASTL_ASSERT(alignment <= 8); // 8 (sizeof(double)) is the standard alignment returned by operator new. 00283 (void)alignment; (void)offset; (void)flags; 00284 return new char[n]; 00285 #elif (EASTL_DEBUGPARAMS_LEVEL <= 0) 00286 return ::new(alignment, offset, (char*)0, flags, 0, (char*)0, 0) char[n]; 00287 #elif (EASTL_DEBUGPARAMS_LEVEL == 1) 00288 return ::new(alignment, offset, pName, flags, 0, (char*)0, 0) char[n]; 00289 #else 00290 return ::new(alignment, offset, pName, flags, 0, __FILE__, __LINE__) char[n]; 00291 #endif 00292 00293 #undef pName // See above for the definition of this. 00294 } 00295 00296 00297 inline void allocator::deallocate(void* p, size_t) 00298 { 00299 delete[] (char*)p; 00300 } 00301 00302 00303 inline bool operator==(const allocator&, const allocator&) 00304 { 00305 return true; // All allocators are considered equal, as they merely use global new/delete. 00306 } 00307 00308 00309 inline bool operator!=(const allocator&, const allocator&) 00310 { 00311 return false; // All allocators are considered equal, as they merely use global new/delete. 00312 } 00313 00314 00315 } // namespace eastl 00316 00317 00318 #endif // EASTL_USER_DEFINED_ALLOCATOR 00319 00320 00321 #ifdef _MSC_VER 00322 #pragma warning(pop) 00323 #endif 00324 00325 00326 #endif // Header include guard