1 | /* |
---|
2 | ----------------------------------------------------------------------------- |
---|
3 | This source file is part of OGRE |
---|
4 | (Object-oriented Graphics Rendering Engine) |
---|
5 | For the latest info, see http://www.ogre3d.org/ |
---|
6 | |
---|
7 | Copyright (c) 2000-2013 Torus Knot Software Ltd |
---|
8 | |
---|
9 | Permission is hereby granted, free of charge, to any person obtaining a copy |
---|
10 | of this software and associated documentation files (the "Software"), to deal |
---|
11 | in the Software without restriction, including without limitation the rights |
---|
12 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell |
---|
13 | copies of the Software, and to permit persons to whom the Software is |
---|
14 | furnished to do so, subject to the following conditions: |
---|
15 | |
---|
16 | The above copyright notice and this permission notice shall be included in |
---|
17 | all copies or substantial portions of the Software. |
---|
18 | |
---|
19 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
---|
20 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
---|
21 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE |
---|
22 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
---|
23 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
---|
24 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN |
---|
25 | THE SOFTWARE. |
---|
26 | ----------------------------------------------------------------------------- |
---|
27 | */ |
---|
28 | |
---|
29 | #ifndef __MemoryAllocatorConfig_H__ |
---|
30 | #define __MemoryAllocatorConfig_H__ |
---|
31 | |
---|
32 | #include "OgreMemoryAllocatedObject.h" |
---|
33 | #include "OgreHeaderPrefix.h" |
---|
34 | |
---|
35 | /** \addtogroup Core |
---|
36 | * @{ |
---|
37 | */ |
---|
38 | /** \addtogroup Memory |
---|
39 | * @{ |
---|
40 | */ |
---|
41 | /** @file |
---|
42 | |
---|
43 | This file configures Ogre's memory allocators. You can modify this |
---|
44 | file to alter the allocation routines used for Ogre's main objects. |
---|
45 | |
---|
46 | When customising memory allocation, all you need to do is provide one or |
---|
47 | more custom allocation policy classes. These classes need to implement: |
---|
48 | |
---|
49 | @code |
---|
50 | // Allocate bytes - file/line/func information should be optional, |
---|
51 | // will be provided when available but not everywhere (e.g. release mode, STL allocations) |
---|
52 | static inline void* allocateBytes(size_t count, const char* file = 0, int line = 0, const char* func = 0); |
---|
53 | // Free bytes |
---|
54 | static inline void deallocateBytes(void* ptr); |
---|
55 | // Return the max number of bytes available to be allocated in a single allocation |
---|
56 | static inline size_t getMaxAllocationSize(); |
---|
57 | @endcode |
---|
58 | |
---|
59 | Policies are then used as implementations for the wrapper classes and macros |
---|
60 | which call them. AllocatedObject for example provides the hooks to override |
---|
61 | the new and delete operators for a class and redirect the functionality to the |
---|
62 | policy. STLAllocator is a class which is provided to STL containers in order |
---|
63 | to hook up allocation of the containers members to the allocation policy. |
---|
64 | @par |
---|
65 | In addition to linking allocations to policies, this class also defines |
---|
66 | a number of macros to allow debugging information to be passed along with |
---|
67 | allocations, such as the file and line number they originate from. It's |
---|
68 | important to realise that we do not redefine the 'new' and 'delete' symbols |
---|
69 | with macros, because that's very difficult to consistently do when other |
---|
70 | libraries are also trying to do the same thing; instead we use dedicated |
---|
71 | 'OGRE_' prefixed macros. See OGRE_NEW and related items. |
---|
72 | @par |
---|
73 | The base macros you can use are listed below, in order of preference and |
---|
74 | with their conditions stated: |
---|
75 | <ul> |
---|
76 | <li>OGRE_NEW - use to allocate an object which have custom new/delete operators |
---|
77 | to handle custom allocations, usually this means it's derived from Ogre::AllocatedObject. |
---|
78 | Free the memory using OGRE_DELETE. You can in fact use the regular new/delete |
---|
79 | for these classes but you won't get any line number debugging if you do. |
---|
80 | The memory category is automatically derived for these classes; for all other |
---|
81 | allocations you have to specify it. |
---|
82 | </li> |
---|
83 | <li>OGRE_NEW_T - use to allocate a single class / struct that does not have custom |
---|
84 | new/delete operators, either because it is non-virtual (Vector3, Quaternion), |
---|
85 | or because it is from an external library (e.g. STL). You must |
---|
86 | deallocate with OGRE_DELETE_T if you expect the destructor to be called. |
---|
87 | You may free the memory using OGRE_FREE if you are absolutely sure there |
---|
88 | is no destructor to be called. |
---|
89 | These macros ensure that constructors and destructors are called correctly |
---|
90 | even though the memory originates externally (via placement new). Also note |
---|
91 | that you have to specify the type and memory category so that the correct |
---|
92 | allocator can be derived, when both allocating |
---|
93 | and freeing. |
---|
94 | </li> |
---|
95 | <li>OGRE_NEW_ARRAY_T - as OGRE_NEW_T except with an extra parameter to construct |
---|
96 | multiple instances in contiguous memory. Again constructors and destructors |
---|
97 | are called. Free with OGRE_DELETE_ARRAY_T. |
---|
98 | </li> |
---|
99 | <li>OGRE_ALLOC_T - use to allocate a set of primitive types conveniently with type safety. |
---|
100 | This <i>can</i> also be used for classes and structs but it is <b>imperative</b> that |
---|
101 | you understand that neither the constructor nor the destructor will be called. |
---|
102 | Sometimes you want this because it's more efficient just to grab/free a chunk of |
---|
103 | memory without having to iterate over each element constructing / destructing. |
---|
104 | Free the memory with OGRE_FREE. </li> |
---|
105 | <li>OGRE_MALLOC - the most raw form of allocation, just a set of bytes. |
---|
106 | Use OGRE_FREE to release.</li> |
---|
107 | <li>_SIMD and _ALIGN variants - all of the above have variations which allow |
---|
108 | aligned memory allocations. The _SIMD versions align automatically to the |
---|
109 | SIMD requirements of your platform, the _ALIGN variants allow user-defined |
---|
110 | alignment to be specified. </li> |
---|
111 | </ul> |
---|
112 | Here are some examples: |
---|
113 | @code |
---|
114 | /// AllocatedObject subclass, with custom operator new / delete |
---|
115 | AllocatedClass* obj = OGRE_NEW AllocatedClass(); |
---|
116 | OGRE_DELETE obj; |
---|
117 | AllocatedClass* array = OGRE_NEW AllocatedClass[10]; |
---|
118 | OGRE_DELETE [] obj; |
---|
119 | /// Non-virtual or external class, constructors / destructors called |
---|
120 | ExternalClass* obj = OGRE_NEW_T(ExternalClass, MEMCATEGORY_GENERAL)(constructorArgs); |
---|
121 | OGRE_DELETE_T(obj, ExternalClass, MEMCATEGORY_GENERAL); |
---|
122 | ExternalClass* obj = OGRE_NEW_ARRAY_T(ExternalClass, 10, MEMCATEGORY_GENERAL); |
---|
123 | OGRE_DELETE_ARRAY_T(obj, NonVirtualClass, 10, MEMCATEGORY_GENERAL); |
---|
124 | /// Primitive types |
---|
125 | long* pLong = OGRE_ALLOC_T(long, 10, MEMCATEGORY_GENERAL); |
---|
126 | OGRE_FREE(pLong, MEMCATEGORY_GENERAL); |
---|
127 | /// Primitive type with constructor (you can mismatch OGRE_NEW_T and OGRE_FREE because no destructor) |
---|
128 | long* pLong = OGRE_NEW_T(long, MEMCATEGORY_GENERAL)(0); |
---|
129 | OGRE_FREE(pLong, MEMCATEGORY_GENERAL); |
---|
130 | /// Raw memory |
---|
131 | void* pVoid = OGRE_MALLOC(1024, MEMCATEGORY_GENERAL); |
---|
132 | OGRE_FREE(pVoid, MEMCATEGORY_GENERAL); |
---|
133 | @endcode |
---|
134 | OGRE_ALLOC_T is also the route to go for allocating real primitive types like |
---|
135 | int & float. You free the memory using OGRE_FREE, and both variants have SIMD |
---|
136 | and custom alignment variants. |
---|
137 | */ |
---|
138 | /** @} */ |
---|
139 | /** @} */ |
---|
140 | |
---|
141 | namespace Ogre |
---|
142 | { |
---|
143 | /** \addtogroup Core |
---|
144 | * @{ |
---|
145 | */ |
---|
146 | /** \addtogroup Memory |
---|
147 | * @{ |
---|
148 | */ |
---|
149 | |
---|
150 | /** A set of categories that indicate the purpose of a chunk of memory |
---|
151 | being allocated. |
---|
152 | These categories will be provided at allocation time in order to allow |
---|
153 | the allocation policy to vary its behaviour if it wishes. This allows you |
---|
154 | to use a single policy but still have variant behaviour. The level of |
---|
155 | control it gives you is at a higher level than assigning different |
---|
156 | policies to different classes, but is the only control you have over |
---|
157 | general allocations that are primitive types. |
---|
158 | */ |
---|
159 | enum MemoryCategory |
---|
160 | { |
---|
161 | /// General purpose |
---|
162 | MEMCATEGORY_GENERAL = 0, |
---|
163 | /// Geometry held in main memory |
---|
164 | MEMCATEGORY_GEOMETRY = 1, |
---|
165 | /// Animation data like tracks, bone matrices |
---|
166 | MEMCATEGORY_ANIMATION = 2, |
---|
167 | /// Nodes, control data |
---|
168 | MEMCATEGORY_SCENE_CONTROL = 3, |
---|
169 | /// Scene object instances |
---|
170 | MEMCATEGORY_SCENE_OBJECTS = 4, |
---|
171 | /// Other resources |
---|
172 | MEMCATEGORY_RESOURCE = 5, |
---|
173 | /// Scripting |
---|
174 | MEMCATEGORY_SCRIPTING = 6, |
---|
175 | /// Rendersystem structures |
---|
176 | MEMCATEGORY_RENDERSYS = 7, |
---|
177 | |
---|
178 | |
---|
179 | // sentinel value, do not use |
---|
180 | MEMCATEGORY_COUNT = 8 |
---|
181 | }; |
---|
182 | /** @} */ |
---|
183 | /** @} */ |
---|
184 | |
---|
185 | } |
---|
186 | |
---|
187 | #include "OgreMemoryAllocatedObject.h" |
---|
188 | #include "OgreMemorySTLAllocator.h" |
---|
189 | |
---|
190 | #if OGRE_MEMORY_ALLOCATOR == OGRE_MEMORY_ALLOCATOR_NEDPOOLING |
---|
191 | |
---|
192 | # include "OgreMemoryNedPooling.h" |
---|
193 | namespace Ogre |
---|
194 | { |
---|
195 | // configure default allocators based on the options above |
---|
196 | // notice how we're not using the memory categories here but still roughing them out |
---|
197 | // in your allocators you might choose to create different policies per category |
---|
198 | |
---|
199 | // configurable category, for general malloc |
---|
200 | // notice how we ignore the category here, you could specialise |
---|
201 | template <MemoryCategory Cat> class CategorisedAllocPolicy : public NedPoolingPolicy{}; |
---|
202 | template <MemoryCategory Cat, size_t align = 0> class CategorisedAlignAllocPolicy : public NedPoolingAlignedPolicy<align>{}; |
---|
203 | } |
---|
204 | |
---|
205 | #elif OGRE_MEMORY_ALLOCATOR == OGRE_MEMORY_ALLOCATOR_NED |
---|
206 | |
---|
207 | # include "OgreMemoryNedAlloc.h" |
---|
208 | namespace Ogre |
---|
209 | { |
---|
210 | // configure default allocators based on the options above |
---|
211 | // notice how we're not using the memory categories here but still roughing them out |
---|
212 | // in your allocators you might choose to create different policies per category |
---|
213 | |
---|
214 | // configurable category, for general malloc |
---|
215 | // notice how we ignore the category here, you could specialise |
---|
216 | template <MemoryCategory Cat> class CategorisedAllocPolicy : public NedAllocPolicy{}; |
---|
217 | template <MemoryCategory Cat, size_t align = 0> class CategorisedAlignAllocPolicy : public NedAlignedAllocPolicy<align>{}; |
---|
218 | } |
---|
219 | |
---|
220 | #elif OGRE_MEMORY_ALLOCATOR == OGRE_MEMORY_ALLOCATOR_STD |
---|
221 | |
---|
222 | # include "OgreMemoryStdAlloc.h" |
---|
223 | namespace Ogre |
---|
224 | { |
---|
225 | // configure default allocators based on the options above |
---|
226 | // notice how we're not using the memory categories here but still roughing them out |
---|
227 | // in your allocators you might choose to create different policies per category |
---|
228 | |
---|
229 | // configurable category, for general malloc |
---|
230 | // notice how we ignore the category here |
---|
231 | template <MemoryCategory Cat> class CategorisedAllocPolicy : public StdAllocPolicy{}; |
---|
232 | template <MemoryCategory Cat, size_t align = 0> class CategorisedAlignAllocPolicy : public StdAlignedAllocPolicy<align>{}; |
---|
233 | |
---|
234 | // if you wanted to specialise the allocation per category, here's how it might work: |
---|
235 | // template <> class CategorisedAllocPolicy<MEMCATEGORY_SCENE_OBJECTS> : public YourSceneObjectAllocPolicy{}; |
---|
236 | // template <size_t align> class CategorisedAlignAllocPolicy<MEMCATEGORY_SCENE_OBJECTS, align> : public YourSceneObjectAllocPolicy<align>{}; |
---|
237 | |
---|
238 | |
---|
239 | } |
---|
240 | |
---|
241 | #else |
---|
242 | |
---|
243 | // your allocators here? |
---|
244 | |
---|
245 | #endif |
---|
246 | |
---|
247 | namespace Ogre |
---|
248 | { |
---|
249 | // Useful shortcuts |
---|
250 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_GENERAL> GeneralAllocPolicy; |
---|
251 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_GEOMETRY> GeometryAllocPolicy; |
---|
252 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_ANIMATION> AnimationAllocPolicy; |
---|
253 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_SCENE_CONTROL> SceneCtlAllocPolicy; |
---|
254 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_SCENE_OBJECTS> SceneObjAllocPolicy; |
---|
255 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_RESOURCE> ResourceAllocPolicy; |
---|
256 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_SCRIPTING> ScriptingAllocPolicy; |
---|
257 | typedef CategorisedAllocPolicy<Ogre::MEMCATEGORY_RENDERSYS> RenderSysAllocPolicy; |
---|
258 | |
---|
259 | // Now define all the base classes for each allocation |
---|
260 | typedef AllocatedObject<GeneralAllocPolicy> GeneralAllocatedObject; |
---|
261 | typedef AllocatedObject<GeometryAllocPolicy> GeometryAllocatedObject; |
---|
262 | typedef AllocatedObject<AnimationAllocPolicy> AnimationAllocatedObject; |
---|
263 | typedef AllocatedObject<SceneCtlAllocPolicy> SceneCtlAllocatedObject; |
---|
264 | typedef AllocatedObject<SceneObjAllocPolicy> SceneObjAllocatedObject; |
---|
265 | typedef AllocatedObject<ResourceAllocPolicy> ResourceAllocatedObject; |
---|
266 | typedef AllocatedObject<ScriptingAllocPolicy> ScriptingAllocatedObject; |
---|
267 | typedef AllocatedObject<RenderSysAllocPolicy> RenderSysAllocatedObject; |
---|
268 | |
---|
269 | |
---|
270 | // Per-class allocators defined here |
---|
271 | // NOTE: small, non-virtual classes should not subclass an allocator |
---|
272 | // the virtual function table could double their size and make them less efficient |
---|
273 | // use primitive or STL allocators / deallocators for those |
---|
274 | typedef ScriptingAllocatedObject AbstractNodeAlloc; |
---|
275 | typedef AnimationAllocatedObject AnimableAlloc; |
---|
276 | typedef AnimationAllocatedObject AnimationAlloc; |
---|
277 | typedef GeneralAllocatedObject ArchiveAlloc; |
---|
278 | typedef GeometryAllocatedObject BatchedGeometryAlloc; |
---|
279 | typedef RenderSysAllocatedObject BufferAlloc; |
---|
280 | typedef GeneralAllocatedObject CodecAlloc; |
---|
281 | typedef ResourceAllocatedObject CompositorInstAlloc; |
---|
282 | typedef GeneralAllocatedObject ConfigAlloc; |
---|
283 | typedef GeneralAllocatedObject ControllerAlloc; |
---|
284 | typedef GeometryAllocatedObject DebugGeomAlloc; |
---|
285 | typedef GeneralAllocatedObject DynLibAlloc; |
---|
286 | typedef GeometryAllocatedObject EdgeDataAlloc; |
---|
287 | typedef GeneralAllocatedObject FactoryAlloc; |
---|
288 | typedef SceneObjAllocatedObject FXAlloc; |
---|
289 | typedef GeneralAllocatedObject ImageAlloc; |
---|
290 | typedef GeometryAllocatedObject IndexDataAlloc; |
---|
291 | typedef GeneralAllocatedObject LogAlloc; |
---|
292 | typedef SceneObjAllocatedObject MovableAlloc; |
---|
293 | typedef SceneCtlAllocatedObject NodeAlloc; |
---|
294 | typedef SceneObjAllocatedObject OverlayAlloc; |
---|
295 | typedef RenderSysAllocatedObject GpuParamsAlloc; |
---|
296 | typedef ResourceAllocatedObject PassAlloc; |
---|
297 | typedef GeometryAllocatedObject PatchAlloc; |
---|
298 | typedef GeneralAllocatedObject PluginAlloc; |
---|
299 | typedef GeneralAllocatedObject ProfilerAlloc; |
---|
300 | typedef GeometryAllocatedObject ProgMeshAlloc; |
---|
301 | typedef SceneCtlAllocatedObject RenderQueueAlloc; |
---|
302 | typedef RenderSysAllocatedObject RenderSysAlloc; |
---|
303 | typedef GeneralAllocatedObject RootAlloc; |
---|
304 | typedef ResourceAllocatedObject ResourceAlloc; |
---|
305 | typedef GeneralAllocatedObject SerializerAlloc; |
---|
306 | typedef SceneCtlAllocatedObject SceneMgtAlloc; |
---|
307 | typedef ScriptingAllocatedObject ScriptCompilerAlloc; |
---|
308 | typedef ScriptingAllocatedObject ScriptTranslatorAlloc; |
---|
309 | typedef SceneCtlAllocatedObject ShadowDataAlloc; |
---|
310 | typedef GeneralAllocatedObject StreamAlloc; |
---|
311 | typedef SceneObjAllocatedObject SubEntityAlloc; |
---|
312 | typedef ResourceAllocatedObject SubMeshAlloc; |
---|
313 | typedef ResourceAllocatedObject TechniqueAlloc; |
---|
314 | typedef GeneralAllocatedObject TimerAlloc; |
---|
315 | typedef ResourceAllocatedObject TextureUnitStateAlloc; |
---|
316 | typedef GeneralAllocatedObject UtilityAlloc; |
---|
317 | typedef GeometryAllocatedObject VertexDataAlloc; |
---|
318 | typedef RenderSysAllocatedObject ViewportAlloc; |
---|
319 | typedef SceneCtlAllocatedObject LodAlloc; |
---|
320 | typedef GeneralAllocatedObject FileSystemLayerAlloc; |
---|
321 | |
---|
322 | // Containers (by-value only) |
---|
323 | // Will be of the form: |
---|
324 | // typedef STLAllocator<T, DefaultAllocPolicy, Category> TAlloc; |
---|
325 | // for use in vector<T, TAlloc>::type |
---|
326 | |
---|
327 | |
---|
328 | |
---|
329 | } |
---|
330 | |
---|
331 | // Util functions |
---|
332 | namespace Ogre |
---|
333 | { |
---|
334 | /** \addtogroup Core |
---|
335 | * @{ |
---|
336 | */ |
---|
337 | /** \addtogroup Memory |
---|
338 | * @{ |
---|
339 | */ |
---|
340 | |
---|
341 | /** Utility function for constructing an array of objects with placement new, |
---|
342 | without using new[] (which allocates an undocumented amount of extra memory |
---|
343 | and so isn't appropriate for custom allocators). |
---|
344 | */ |
---|
345 | template<typename T> |
---|
346 | T* constructN(T* basePtr, size_t count) |
---|
347 | { |
---|
348 | for (size_t i = 0; i < count; ++i) |
---|
349 | { |
---|
350 | new ((void*)(basePtr+i)) T(); |
---|
351 | } |
---|
352 | return basePtr; |
---|
353 | } |
---|
354 | /** @} */ |
---|
355 | /** @} */ |
---|
356 | |
---|
357 | } |
---|
358 | // define macros |
---|
359 | |
---|
360 | /** \addtogroup Core |
---|
361 | * @{ |
---|
362 | */ |
---|
363 | /** \addtogroup Memory |
---|
364 | * @{ |
---|
365 | */ |
---|
366 | |
---|
367 | #if OGRE_DEBUG_MODE |
---|
368 | |
---|
369 | /// Allocate a block of raw memory, and indicate the category of usage |
---|
370 | # define OGRE_MALLOC(bytes, category) ::Ogre::CategorisedAllocPolicy<category>::allocateBytes(bytes, __FILE__, __LINE__, __FUNCTION__) |
---|
371 | /// Allocate a block of memory for a primitive type, and indicate the category of usage |
---|
372 | # define OGRE_ALLOC_T(T, count, category) static_cast<T*>(::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)) |
---|
373 | /// Free the memory allocated with OGRE_MALLOC or OGRE_ALLOC_T. Category is required to be restated to ensure the matching policy is used |
---|
374 | # define OGRE_FREE(ptr, category) ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr) |
---|
375 | |
---|
376 | /// Allocate space for one primitive type, external type or non-virtual type with constructor parameters |
---|
377 | # define OGRE_NEW_T(T, category) new (::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T), __FILE__, __LINE__, __FUNCTION__)) T |
---|
378 | /// Allocate a block of memory for 'count' primitive types - do not use for classes that inherit from AllocatedObject |
---|
379 | # define OGRE_NEW_ARRAY_T(T, count, category) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)), count) |
---|
380 | /// Free the memory allocated with OGRE_NEW_T. Category is required to be restated to ensure the matching policy is used |
---|
381 | # define OGRE_DELETE_T(ptr, T, category) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
382 | /// Free the memory allocated with OGRE_NEW_ARRAY_T. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
383 | # define OGRE_DELETE_ARRAY_T(ptr, T, count, category) if(ptr){for (size_t b = 0; b < count; ++b) { (ptr)[b].~T();} ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
384 | |
---|
385 | // aligned allocation |
---|
386 | /// Allocate a block of raw memory aligned to SIMD boundaries, and indicate the category of usage |
---|
387 | # define OGRE_MALLOC_SIMD(bytes, category) ::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(bytes, __FILE__, __LINE__, __FUNCTION__) |
---|
388 | /// Allocate a block of raw memory aligned to user defined boundaries, and indicate the category of usage |
---|
389 | # define OGRE_MALLOC_ALIGN(bytes, category, align) ::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(bytes, __FILE__, __LINE__, __FUNCTION__) |
---|
390 | /// Allocate a block of memory for a primitive type aligned to SIMD boundaries, and indicate the category of usage |
---|
391 | # define OGRE_ALLOC_T_SIMD(T, count, category) static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)) |
---|
392 | /// Allocate a block of memory for a primitive type aligned to user defined boundaries, and indicate the category of usage |
---|
393 | # define OGRE_ALLOC_T_ALIGN(T, count, category, align) static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)) |
---|
394 | /// Free the memory allocated with either OGRE_MALLOC_SIMD or OGRE_ALLOC_T_SIMD. Category is required to be restated to ensure the matching policy is used |
---|
395 | # define OGRE_FREE_SIMD(ptr, category) ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes(ptr) |
---|
396 | /// Free the memory allocated with either OGRE_MALLOC_ALIGN or OGRE_ALLOC_T_ALIGN. Category is required to be restated to ensure the matching policy is used |
---|
397 | # define OGRE_FREE_ALIGN(ptr, category, align) ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes(ptr) |
---|
398 | |
---|
399 | /// Allocate space for one primitive type, external type or non-virtual type aligned to SIMD boundaries |
---|
400 | # define OGRE_NEW_T_SIMD(T, category) new (::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T), __FILE__, __LINE__, __FUNCTION__)) T |
---|
401 | /// Allocate a block of memory for 'count' primitive types aligned to SIMD boundaries - do not use for classes that inherit from AllocatedObject |
---|
402 | # define OGRE_NEW_ARRAY_T_SIMD(T, count, category) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)), count) |
---|
403 | /// Free the memory allocated with OGRE_NEW_T_SIMD. Category is required to be restated to ensure the matching policy is used |
---|
404 | # define OGRE_DELETE_T_SIMD(ptr, T, category) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes(ptr);} |
---|
405 | /// Free the memory allocated with OGRE_NEW_ARRAY_T_SIMD. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
406 | # define OGRE_DELETE_ARRAY_T_SIMD(ptr, T, count, category) if(ptr){for (size_t b = 0; b < count; ++b) { (ptr)[b].~T();} ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes(ptr);} |
---|
407 | /// Allocate space for one primitive type, external type or non-virtual type aligned to user defined boundaries |
---|
408 | # define OGRE_NEW_T_ALIGN(T, category, align) new (::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T), __FILE__, __LINE__, __FUNCTION__)) T |
---|
409 | /// Allocate a block of memory for 'count' primitive types aligned to user defined boundaries - do not use for classes that inherit from AllocatedObject |
---|
410 | # define OGRE_NEW_ARRAY_T_ALIGN(T, count, category, align) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T)*(count), __FILE__, __LINE__, __FUNCTION__)), count) |
---|
411 | /// Free the memory allocated with OGRE_NEW_T_ALIGN. Category is required to be restated to ensure the matching policy is used |
---|
412 | # define OGRE_DELETE_T_ALIGN(ptr, T, category, align) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes(ptr);} |
---|
413 | /// Free the memory allocated with OGRE_NEW_ARRAY_T_ALIGN. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
414 | # define OGRE_DELETE_ARRAY_T_ALIGN(ptr, T, count, category, align) if(ptr){for (size_t _b = 0; _b < count; ++_b) { (ptr)[_b].~T();} ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes(ptr);} |
---|
415 | |
---|
416 | // new / delete for classes deriving from AllocatedObject (alignment determined by per-class policy) |
---|
417 | // Also hooks up the file/line/function params |
---|
418 | // Can only be used with classes that derive from AllocatedObject since customised new/delete needed |
---|
419 | # define OGRE_NEW new (__FILE__, __LINE__, __FUNCTION__) |
---|
420 | # define OGRE_DELETE delete |
---|
421 | |
---|
422 | |
---|
423 | #else // !OGRE_DEBUG_MODE |
---|
424 | |
---|
425 | /// Allocate a block of raw memory, and indicate the category of usage |
---|
426 | # define OGRE_MALLOC(bytes, category) ::Ogre::CategorisedAllocPolicy<category>::allocateBytes(bytes) |
---|
427 | /// Allocate a block of memory for a primitive type, and indicate the category of usage |
---|
428 | # define OGRE_ALLOC_T(T, count, category) static_cast<T*>(::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T)*(count))) |
---|
429 | /// Free the memory allocated with OGRE_MALLOC or OGRE_ALLOC_T. Category is required to be restated to ensure the matching policy is used |
---|
430 | # define OGRE_FREE(ptr, category) ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr) |
---|
431 | |
---|
432 | /// Allocate space for one primitive type, external type or non-virtual type with constructor parameters |
---|
433 | # define OGRE_NEW_T(T, category) new (::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T))) T |
---|
434 | /// Allocate a block of memory for 'count' primitive types - do not use for classes that inherit from AllocatedObject |
---|
435 | # define OGRE_NEW_ARRAY_T(T, count, category) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAllocPolicy<category>::allocateBytes(sizeof(T)*(count))), count) |
---|
436 | /// Free the memory allocated with OGRE_NEW_T. Category is required to be restated to ensure the matching policy is used |
---|
437 | # define OGRE_DELETE_T(ptr, T, category) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
438 | /// Free the memory allocated with OGRE_NEW_ARRAY_T. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
439 | # define OGRE_DELETE_ARRAY_T(ptr, T, count, category) if(ptr){for (size_t b = 0; b < count; ++b) { (ptr)[b].~T();} ::Ogre::CategorisedAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
440 | |
---|
441 | // aligned allocation |
---|
442 | /// Allocate a block of raw memory aligned to SIMD boundaries, and indicate the category of usage |
---|
443 | # define OGRE_MALLOC_SIMD(bytes, category) ::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(bytes) |
---|
444 | /// Allocate a block of raw memory aligned to user defined boundaries, and indicate the category of usage |
---|
445 | # define OGRE_MALLOC_ALIGN(bytes, category, align) ::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(bytes) |
---|
446 | /// Allocate a block of memory for a primitive type aligned to SIMD boundaries, and indicate the category of usage |
---|
447 | # define OGRE_ALLOC_T_SIMD(T, count, category) static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T)*(count))) |
---|
448 | /// Allocate a block of memory for a primitive type aligned to user defined boundaries, and indicate the category of usage |
---|
449 | # define OGRE_ALLOC_T_ALIGN(T, count, category, align) static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T)*(count))) |
---|
450 | /// Free the memory allocated with either OGRE_MALLOC_SIMD or OGRE_ALLOC_T_SIMD. Category is required to be restated to ensure the matching policy is used |
---|
451 | # define OGRE_FREE_SIMD(ptr, category) ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes((void*)ptr) |
---|
452 | /// Free the memory allocated with either OGRE_MALLOC_ALIGN or OGRE_ALLOC_T_ALIGN. Category is required to be restated to ensure the matching policy is used |
---|
453 | # define OGRE_FREE_ALIGN(ptr, category, align) ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes((void*)ptr) |
---|
454 | |
---|
455 | /// Allocate space for one primitive type, external type or non-virtual type aligned to SIMD boundaries |
---|
456 | # define OGRE_NEW_T_SIMD(T, category) new (::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T))) T |
---|
457 | /// Allocate a block of memory for 'count' primitive types aligned to SIMD boundaries - do not use for classes that inherit from AllocatedObject |
---|
458 | # define OGRE_NEW_ARRAY_T_SIMD(T, count, category) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category>::allocateBytes(sizeof(T)*(count))), count) |
---|
459 | /// Free the memory allocated with OGRE_NEW_T_SIMD. Category is required to be restated to ensure the matching policy is used |
---|
460 | # define OGRE_DELETE_T_SIMD(ptr, T, category) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
461 | /// Free the memory allocated with OGRE_NEW_ARRAY_T_SIMD. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
462 | # define OGRE_DELETE_ARRAY_T_SIMD(ptr, T, count, category) if(ptr){for (size_t b = 0; b < count; ++b) { (ptr)[b].~T();} ::Ogre::CategorisedAlignAllocPolicy<category>::deallocateBytes((void*)ptr);} |
---|
463 | /// Allocate space for one primitive type, external type or non-virtual type aligned to user defined boundaries |
---|
464 | # define OGRE_NEW_T_ALIGN(T, category, align) new (::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T))) T |
---|
465 | /// Allocate a block of memory for 'count' primitive types aligned to user defined boundaries - do not use for classes that inherit from AllocatedObject |
---|
466 | # define OGRE_NEW_ARRAY_T_ALIGN(T, count, category, align) ::Ogre::constructN(static_cast<T*>(::Ogre::CategorisedAlignAllocPolicy<category, align>::allocateBytes(sizeof(T)*(count))), count) |
---|
467 | /// Free the memory allocated with OGRE_NEW_T_ALIGN. Category is required to be restated to ensure the matching policy is used |
---|
468 | # define OGRE_DELETE_T_ALIGN(ptr, T, category, align) if(ptr){(ptr)->~T(); ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes((void*)ptr);} |
---|
469 | /// Free the memory allocated with OGRE_NEW_ARRAY_T_ALIGN. Category is required to be restated to ensure the matching policy is used, count and type to call destructor |
---|
470 | # define OGRE_DELETE_ARRAY_T_ALIGN(ptr, T, count, category, align) if(ptr){for (size_t _b = 0; _b < count; ++_b) { (ptr)[_b].~T();} ::Ogre::CategorisedAlignAllocPolicy<category, align>::deallocateBytes((void*)ptr);} |
---|
471 | |
---|
472 | // new / delete for classes deriving from AllocatedObject (alignment determined by per-class policy) |
---|
473 | # define OGRE_NEW new |
---|
474 | # define OGRE_DELETE delete |
---|
475 | |
---|
476 | #endif // OGRE_DEBUG_MODE |
---|
477 | |
---|
478 | |
---|
479 | namespace Ogre |
---|
480 | { |
---|
481 | /** Function which invokes OGRE_DELETE on a given pointer. |
---|
482 | @remarks |
---|
483 | Useful to pass custom deletion policies to external libraries (e. g. boost). |
---|
484 | */ |
---|
485 | template<typename T> |
---|
486 | void deletePtr(T* ptr) |
---|
487 | { |
---|
488 | OGRE_DELETE ptr; |
---|
489 | } |
---|
490 | } |
---|
491 | |
---|
492 | /** @} */ |
---|
493 | /** @} */ |
---|
494 | |
---|
495 | |
---|
496 | #include "OgreHeaderSuffix.h" |
---|
497 | |
---|
498 | #endif |
---|