开发者

C free and struct

My question is about C free() function for deallocating memory blocks previously allocat开发者_如何学Pythoned with malloc().

If i have a struct data type compose of several pointers, each of them pointing to different memory locations, what would happen to those memory locations if i apply free() on the struct? will that locations be free too? or just the memory block that allocate the pointer?


No. They won't be freed. You have to free them "manually". The malloc knows nothing about the content of your struct (it does not know it is a struct at all, it is just a "piece of memory" from its point of view).


If you only free the struct, memory pointed to by pointers inside the struct won't be freed (assuming it was mallocd). You should free them first.

You can use valgrind (if available) to see for yourself:

#include <stdlib.h>

struct resources{
   int * aint;
   double * adouble;
};                                                                              
int main(){

   int* someint = malloc(sizeof(int) * 1024);
   double* somedouble = malloc(sizeof(double)* 1024);

   struct resources *r  = malloc(sizeof(struct resources));

   r->aint = someint;
   r->adouble = somedouble;

   free (r);
   return 0;

}

$ gcc test_struct.c -o test
$ valgrind ./test
==9192== Memcheck, a memory error detector
==9192== Copyright (C) 2002-2009, and GNU GPL'd, by Julian Seward et al.
==9192== Using Valgrind-3.6.0.SVN-Debian and LibVEX; rerun with -h for copyright info
==9192== Command: ./test
==9192== 
==9192== 
==9192== HEAP SUMMARY:
==9192==     in use at exit: 12,288 bytes in 2 blocks
==9192==   total heap usage: 3 allocs, 1 frees, 12,296 bytes allocated
==9192== 
==9192== LEAK SUMMARY:
==9192==    definitely lost: 12,288 bytes in 2 blocks
==9192==    indirectly lost: 0 bytes in 0 blocks
==9192==      possibly lost: 0 bytes in 0 blocks
==9192==    still reachable: 0 bytes in 0 blocks
==9192==         suppressed: 0 bytes in 0 blocks
==9192== Rerun with --leak-check=full to see details of leaked memory
==9192== 
==9192== For counts of detected and suppressed errors, rerun with: -v
==9192== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 12 from 7)


struct Node
{
  struct Node *nextSibling;
  struct Node *prevSibling;
  struct Node *parentNode;
  ...
};
...
struct Node *rootNode;
/* Initialize `rootNode' and fill in its various fields;
   do the same with more nodes.  */

If you use free(rootNode), it will only free the memory of that single node. In other words, you'll have a bunch of memory allocated that you won't be able to free unless you free it before freeing the memory used by the node you actually want to delete.


Just to clarify on @Chrono Kitsune's answer, it'd still be possible to free the pointers inside of the struct, but it's risky.

What free(rootNode) does is actually tell the memory management unit that the memory space that was being used by rootNode is not being used anymore and is fair game for anything else that needs it. Though, rootNode still points to the same location, it's now considered an invalid pointer, and its contents may by corrupted because its location can now be overwritten by other things.

If you try to access rootNode right after freeing it, it might work, but there's no guarantee, so it's safest to free its contents (that have been malloc'd) before deleteing rootNode itself.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜