Jump to content

Heap management and aligned allocations


photo

Recommended Posts

Hi,

 

I've got some feature request concerning how memory heap allocations are done in Unigine, and more precisely on how one can switch from the Unigine heap allocator to a different one (such as dlmalloc for instance, or the default Windows allocator which is not so fast but is pretty good at keeping memory fragmentation low).

 

Important thing before going on: I'm using the source-code version of the SDK, and Unigine is linked statically to my project (so not as a separated DLL).

 

So here are the requests:

 

1) At first glance, it seems pretty straightforward to switch from the Unigne allocator to the default system one. The way it's meant to be done is by removing the #USE_MEMORY and everything should be fine. Well it's not, and the reason for that is (obviously) the SSE variables that need to be 16 bytes aligned. So here is the first problem with the memory management in Unigine: the entire code relies on the assumption that new and delete use a default 16 bytes alignement for any allocation. Switching back to an alternative allocator makes the engine crash.

 

An easy way to go around this problem is to override the new/delete operators from the user side, and plug all allocations to a pretty regular _mm_malloc(size, 16) and _mm_free(ptr). Specifying a special alignment for *ALL* allocations is really not the recommanded way to allocate memory... But anyway, that works *almost* fine. There is still one place in the code that is not using the new/delete but uses directly malloc/free instead, which make the engine crash at startup (have a look at Allocator.h line 60 and 67). So the request is pretty simple: could you please remove this direct call to malloc/free and use new/delete instead ? Doing that will ensure that all allocations are redirected to the user-defined new/delete routines.

 

2) As mentionned earlier, requesting a specific 16 bytes alignment for all allocations is really not recommanded. So the second suggestion would be to identify all the engine allocations that really need this alignment, and use a specific allocation/deallocation routine for those. By doing this, the user would be able to know wich allocations need an alignment and redirect to the appropriate alloc/dealloc function.

 

3) Ideally, it would be great if the engine could expose a set of function pointers to the memory allocations methods (ie: one pointer to allocate(), one pointer to alignedAllocate(), one pointer to deallocate() and one pointer to alignedDeallocate()). The user would then be able to replace these functions with custom ones and redirect all unigine allocations to his own heap allocator.

 

That's pretty much it. Thanks a lot for your time !

 

Alessandro Di Meco

Link to comment
  • 2 weeks later...

Hi Alessandro! From France with allocations?)

 

1) At first glance, it seems pretty straightforward to switch from the Unigne allocator to the default system one. The way it's meant to be done is by removing the #USE_MEMORY and everything should be fine. Well it's not, and the reason for that is (obviously) the SSE variables that need to be 16 bytes aligned. So here is the first problem with the memory management in Unigine: the entire code relies on the assumption that new and delete use a default 16 bytes alignement for any allocation. Switching back to an alternative allocator makes the engine crash.

Actually, it is straightforward, but one additional step is required. You need to compile an engine using scons simd=none. After that, removing the #USE_MEMORY define does the trick.

 

So the request is pretty simple: could you please remove this direct call to malloc/free and use new/delete instead ? Doing that will ensure that all allocations are redirected to the user-defined new/delete routines.

Ok, if it's necessary for you, we'll do that.

 

2) As mentionned earlier, requesting a specific 16 bytes alignment for all allocations is really not recommanded. So the second suggestion would be to identify all the engine allocations that really need this alignment, and use a specific allocation/deallocation routine for those. By doing this, the user would be able to know wich allocations need an alignment and redirect to the appropriate alloc/dealloc function.

In the engine 16 byte alignment is always used since it allows for efficient memory optimization (depending on the allocated data size). That's why I'm afraid the policy stays the same.

Link to comment
×
×
  • Create New...