How does free know how much to free?

后端 未结 11 2128
情话喂你
情话喂你 2020-11-22 03:28

In C programming, you can pass any kind of pointer you like as an argument to free, how does it know the size of the allocated memory to free? Whenever I pass a pointer to s

相关标签:
11条回答
  • 2020-11-22 03:45

    to answer the second question, yes you could (kind of) use the same technique as malloc() by simply assigning the first cell inside every array to the size of the array. that lets you send the array without sending an additional size argument.

    0 讨论(0)
  • 2020-11-22 03:47

    This answer is relocated from How does free() know how much memory to deallocate? where I was abrubtly prevented from answering by an apparent duplicate question. This answer then should be relevant to this duplicate:


    For the case of malloc, the heap allocator stores a mapping of the original returned pointer, to relevant details needed for freeing the memory later. This typically involves storing the size of the memory region in whatever form relevant to the allocator in use, for example raw size, or a node in a binary tree used to track allocations, or a count of memory "units" in use.

    free will not fail if you "rename" the pointer, or duplicate it in any way. It is not however reference counted, and only the first free will be correct. Additional frees are "double free" errors.

    Attempting to free any pointer with a value different to those returned by previous mallocs, and as yet unfreed is an error. It is not possible to partially free memory regions returned from malloc.

    0 讨论(0)
  • 2020-11-22 03:49

    Most implementations of C memory allocation functions will store accounting information for each block, either in-line or separately.

    One typical way (in-line) is to actually allocate both a header and the memory you asked for, padded out to some minimum size. So for example, if you asked for 20 bytes, the system may allocate a 48-byte block:

    • 16-byte header containing size, special marker, checksum, pointers to next/previous block and so on.
    • 32 bytes data area (your 20 bytes padded out to a multiple of 16).

    The address then given to you is the address of the data area. Then, when you free the block, free will simply take the address you give it and, assuming you haven't stuffed up that address or the memory around it, check the accounting information immediately before it. Graphically, that would be along the lines of:

     ____ The allocated block ____
    /                             \
    +--------+--------------------+
    | Header | Your data area ... |
    +--------+--------------------+
              ^
              |
              +-- The address you are given
    

    Keep in mind the size of the header and the padding are totally implementation defined (actually, the entire thing is implementation-defined (a) but the in-line accounting option is a common one).

    The checksums and special markers that exist in the accounting information are often the cause of errors like "Memory arena corrupted" or "Double free" if you overwrite them or free them twice.

    The padding (to make allocation more efficient) is why you can sometimes write a little bit beyond the end of your requested space without causing problems (still, don't do that, it's undefined behaviour and, just because it works sometimes, doesn't mean it's okay to do it).


    (a) I've written implementations of malloc in embedded systems where you got 128 bytes no matter what you asked for (that was the size of the largest structure in the system), assuming you asked for 128 bytes or less (requests for more would be met with a NULL return value). A very simple bit-mask (i.e., not in-line) was used to decide whether a 128-byte chunk was allocated or not.

    Others I've developed had different pools for 16-byte chunks, 64-bytes chunks, 256-byte chunks and 1K chunks, again using a bit-mask to decide what blocks were used or available.

    Both these options managed to reduce the overhead of the accounting information and to increase the speed of malloc and free (no need to coalesce adjacent blocks when freeing), particularly important in the environment we were working in.

    0 讨论(0)
  • 2020-11-22 03:53

    The heap manager stored the amount of memory belonging to the allocated block somewhere when you called malloc.

    I never implemented one myself, but I guess the memory right in front of the allocated block might contain the meta information.

    0 讨论(0)
  • 2020-11-22 03:53

    When we call malloc it's simply consume more byte from it's requirement. This more byte consumption contain information like check sum,size and other additional information. When we call free at that time it directly go to that additional information where it's find the address and also find how much block will be free.

    0 讨论(0)
  • 2020-11-22 03:56

    When you call malloc(), you specify the amount of memory to allocate. The amount of memory actually used is slightly more than this, and includes extra information that records (at least) how big the block is. You can't (reliably) access that other information - and nor should you :-).

    When you call free(), it simply looks at the extra information to find out how big the block is.

    0 讨论(0)
提交回复
热议问题