Home > Net >  Find if allocation is trivially resizable?
Find if allocation is trivially resizable?

Time:11-22

realloc may simply update bookkeeping info here and there to increase your allocation size, or it may actually malloc a new one and memcpy the previous allocation (or may fail).

I want to be able to query the memory manager if an allocation is trivially resizable (either because it reserved more than I mallocd or because it was able coalesce adjacent blocks , etc...) and if yes, then I'll ask it to go ahead and do so, else I'd want to malloc and memcpy an arbitrary subset of the original allocation in an arbitrary order myself.

Other StackOverflow answers seem to do one of these four :

  • Suggest realloc anyways. This can be quite inefficient for large quantities of data, where the double-copy can have serious effect. Usually, it is the fastest portable route.
  • Suggest manual malloc memcpy free. This is worse, because now instead of some double copying when allocation may not be resized, everything is double copied every time the allocation fills up. Performs terribly.
  • Suggest a platform specific extension. This is not practical, as my code, like a lot of C code, requires portability.
  • Suggest it's impossible. C already assumes the presence of a memory manager with ability to either resize allocations in place or create a new one. So, why can't I have one more level of control on it? We can have aligned malloc; why not this ?

NOTE : This question is posted under both C and C tags because solutions from either language are acceptable and relevant.

EDIT 1:

In the words of FB vector :

But wait, there's more. Many memory allocators do not support in- place reallocation, although most of them could. This comes from the now notorious design of realloc() to opaquely perform either in-place reallocation or an allocate-memcpy-deallocate cycle. Such lack of control subsequently forced all clib-based allocator designs to avoid in-place reallocation, and that includes C 's new and std::allocator. This is a major loss of efficiency because an in-place reallocation, being very cheap, may mean a much less aggressive growth strategy. In turn that means less slack memory and faster reallocations.

See this.

CodePudding user response:

Suggest realloc anyways. This can be quite inefficient for large quantities of data, where the double-copy can have serious effect.

Due to reasons why realloc can sometimes avoid copying and allocation, this is an irrelevant point because in practical implementations, that condition doesn't exist with large quantities of data. If you know that the allocation is large, then it's fairly safe to assume that realloc will have to copy and allocate. Hence, you can make the choice without having to make the "impossible" check.

If reallocation is optional and you cannot afford the copy, then unconditionally choose the option to not reallocate. If reallocation isn't optional, then whether realloc would copy and allocate or not doesn't have an effect on what you have to do.

Suggest a platform specific extension. This is not practical, as my code, like a lot of C code, requires portability.

This is the only way to achieve what you're asking for because there is no standard way to query whether realloc will copy and allocate.

However, keep in mind that it is possible to port such code by conditionally disabling this feature using pre-defined macros.

Suggest it's impossible.

This is true if you choose to rely on standard C .

is there a way to do this that I have not come across in my search ?

No, the list is exhaustive.

CodePudding user response:

The standard memory interface is well documented. If you want some feature that isn't part of that interface, your solution is going to be custom, third party, or platform-specific.

  • Suggest it's impossible. C already assumes the presence of a memory manager with ability to either resize allocations in place or create a new one. So, why can't I have one more level of control on it?

Because it isn't part of the standard interface. The fact that it could have been made part of the standard interface does not mean that is is part of the standard interface.

... We can have aligned malloc; why not this ?

If you want it to be in the standard, propose a change to the working group. It's not going to arrive quickly.

If you want something to work now, you need to write your own allocator or find a third-party one that meets your requirements.

Note that

  • Suggest a platform specific extension. This is not practical, as my code, like a lot of C code, requires portability.

isn't a real problem (or at least, is one that people often cope with just fine). You may have to write a different implementation for each platform you want to support (and fall back on realloc where nothing better is available), but this isn't uncommon for cross-platform code.

CodePudding user response:

I suppose that what you wanna get is the size of spare space following your malloc'ed memory block. It is possible, memory manager reserves a header before each block, you can get information you want from the block header, but obviously it is not portable due to different implementation of various memory manager. I think a better way is to use a memory pool to manage heap memory yourself, it will be more efficient and portable.

  • Related