17

When using realloc is the memory automatically freed? Or is it necessary to use free with realloc? Which of the following is correct?

//Situation A
ptr1 = realloc(ptr1, 3 * sizeof(int));

//Situation B
ptr1 = realloc(ptr2, 3 * sizeof(int));
free(ptr1);
ptr1 = ptr2;
Cory
  • 235
  • 1
  • 3
  • 10

5 Answers5

42

Neither is correct. realloc() can return a pointer to newly allocated memory or NULL on error. What you should do is check the return value:

ptr1 = realloc(ptr2, 3 * sizeof(int));
if (!ptr1) {
    /* Do something here to handle the failure */
    /* ptr2 is still pointing to allocated memory, so you may need to free(ptr2) here */
}

/* Success! ptr1 is now pointing to allocated memory and ptr2 was deallocated already */
free(ptr1);
Scorpions4ever
  • 444
  • 4
  • 2
13

After ptr1 = realloc(ptr2, 3 * sizeof(int)); ptr2 is invalid and should not be used. You need to free ptr1 only. In some cases the return value of realloc will be the same value you passed in though.

You can safely consider ptr1=realloc(ptr2, ... as equivalent to this:

ptr1 = malloc(...);
memcpy(ptr1, ptr2, ...);
free(ptr2);

This is what happens in most cases, unless the new size still fits in the old memory block - then realloc could return the original memory block.

As other allocation functions, realloc returns NULL if it fails - you may want to check for that.

Erik
  • 88,732
  • 13
  • 198
  • 189
  • 3
    "ptr2 is invalid and should not be used" - unless a null pointer is returned, in which case ptr2 is still valid and still needs freeing eventually. So in the equivalent code, the second and third lines are both only `if (ptr1)`. – Steve Jessop Mar 24 '11 at 23:55
5

realloc() automatically frees the original memory, or returns it unchanged (aside from metadata) if you realloc() to a smaller size or there is unallocated memory available to simply expand the original allocation in place.

geekosaur
  • 59,309
  • 11
  • 123
  • 114
1

According to http://www.cplusplus.com/reference/clibrary/cstdlib/realloc/, realloc returns the new memory block if the reallocation is successful, keeps the original memory block if not. Standard usage would look like this:

ptr2 = realloc(ptr1, new_size);
if (ptr2 == NULL) {
   //ptr1 still contains pointer to original array
} else {
   //ptr2 contains new array, ptr1 is invalid
}
Adam Trhon
  • 2,915
  • 1
  • 20
  • 51
  • The description you provide is not in accordance with the behaviour the Standard mandates: `realloc` returns NULL when it fails. – pmg Mar 24 '11 at 23:24
  • I tried to fix it with the edit, didn't want to delete what was written. Do you know how to strikethrough the unwanted text here? – Adam Trhon Mar 24 '11 at 23:26
  • 1
    just remove the error. The point of editing is to improve the answer. If anyone thinks pmg's comment looks out of place in light of the answer as they see it, they can check the revision history. – Steve Jessop Mar 24 '11 at 23:58
0

In both situations, ptr1 must be freed.

Situation B is more complex because ptr2 potentially points to freed space. Or not. It depends on whether it could be reallocated. ptr2 should not be used after the realloc in B.

wallyk
  • 56,922
  • 16
  • 83
  • 148