Thread: Using calloc

  1. #1
    Registered User
    Join Date
    Nov 2007
    Location
    Giessen, Germany
    Posts
    2
    <<mod edit - split from thread >>

    Hi there,
    i am also new to c programming and have also a question concerning the malloc/free functions.
    The following code:
    Code:
    double *pAr = (double*)calloc(100, sizeof(*pAr));
    for(i=0;i<101;i++)
           do something
    
    if(pAr)free(pAr);
    The program gives a segmentation fault when calling "free"
    where I would expected to do so when passing over the array boundary
    or to ignore that.
    Last edited by Salem; 11-07-2007 at 09:43 AM. Reason: Split thread

  2. #2
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by giancu View Post
    Hi there,
    i am also new to c programming and have also a question concerning the malloc/free functions.
    The following code:
    Code:
    double *pAr = (double*)calloc(100, sizeof(*pAr));
    for(i=0;i<101;i++)
           do something
    
    if(pAr)free(pAr);
    The program gives a segmentation fault when calling "free"
    where I would expected to do so when passing over the array boundary
    or to ignore that.
    It MAY give a segfault in free if you go outside the array - it is definitely "undefined behaviour" which means "the compiler and system may do whatever it likes at this point" - likely scenario is a crash of some sort, but for all we know, it may cause ANYTHING to happen.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  3. #3
    Registered User
    Join Date
    Nov 2007
    Location
    Giessen, Germany
    Posts
    2

    Talking

    Quote Originally Posted by matsp View Post
    It MAY give a segfault in free if you go outside the array - it is definitely "undefined behaviour" which means "the compiler and system may do whatever it likes at this point" - likely scenario is a crash of some sort, but for all we know, it may cause ANYTHING to happen.

    --
    Mats
    Thanks for your reply!
    In my naivety I thought that malloc/calloc function will allocate memory and somehow
    keep track of the allocated size (it is anyway given as a parameter), so that free
    will look at this size and use it to "deallocate". So that I find somehow surprising that
    passing over the boundary will have an influence on free....
    Well I guess that's "undefined behaviour"

  4. #4
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by giancu View Post
    Thanks for your reply!
    In my naivety I thought that malloc/calloc function will allocate memory and somehow
    keep track of the allocated size (it is anyway given as a parameter), so that free
    will look at this size and use it to "deallocate". So that I find somehow surprising that
    passing over the boundary will have an influence on free....
    Well I guess that's "undefined behaviour"
    Yes, another effect of this "undefined behaviour" might be that some completely different data structure is affected by containing "unknown" data [e.g. an integer data element is suddenly overwritten by a double variable, so the integer is now completely "rubbish"]. This gets much more interesting when writing drivers, were an errant index in allocated memory might change the data being written to disk by the disk-driver - even though your driver is ONLY touching a serial port and never writing to the disk...

    free may well have data stored at the back of your data structure - it's either that or at the beginning. Or it may be that free expects something else to "be" at the end of the allocated block, such as a header for the NEXT block of memory. Of coruse, we could have guards to prevent it from being overwritten, but that would only work for so much overwriting - the data connected to the memory allocations has to be stored somewhere...

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  5. #5
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Do not rely on the zero-filling of calloc to produce meaningful data.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  6. #6
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by giancu View Post
    Thanks for your reply!
    In my naivety I thought that malloc/calloc function will allocate memory and somehow
    keep track of the allocated size (it is anyway given as a parameter), so that free
    will look at this size and use it to "deallocate".
    It does. It obviously keeps this critical piece of information in the chunk of memory you accidentally overwrote!

  7. #7
    Registered User
    Join Date
    Sep 2006
    Posts
    835
    1) You don't need to cast malloc/calloc/realloc: see

    http://faq.cprogramming.com/cgi-bin/...&id=1043284351

    Also make sure to #include <stdlib.h>.

    2) If i is an index into your calloc()'d array, then your loop should read
    Code:
    for(i=0;i<100;i++)
    since the index should go from 0 to 99 only. By the way, you're not changing the value of pAr inside the loop, are you? The pointer you pass to free() needs to be the same one you get from malloc()/calloc()/realloc().
    3) You don't need to check if pAr is NULL before free()'ing it, since the standard guarantees that free(NULL) does nothing. However, you should check if pAr is NULL immediately after calloc()'ing it.

  8. #8
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by robatino View Post
    3) You don't need to check if pAr is NULL before free()'ing it, since the standard guarantees that free(NULL) does nothing. However, you should check if pAr is NULL immediately after calloc()'ing it.
    Empirical testing shows that this is not ALWAYS true (I have certainly worked with systems that DO NOT like free(NULL))- and there's absolutely no benefit with calling free WITH a NULL pointer.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  9. #9
    Registered User
    Join Date
    Sep 2006
    Posts
    835
    Quote Originally Posted by matsp View Post
    Empirical testing shows that this is not ALWAYS true (I have certainly worked with systems that DO NOT like free(NULL))- and there's absolutely no benefit with calling free WITH a NULL pointer.
    Any fairly recent and standards-compliant compiler shouldn't have this problem (although admittedly a lot of posters seem to be using compilers from the last century, so it needs to be mentioned). If the OP is having this problem he needs to get a newer one. The benefit of being able to use free(NULL) is to not have to call it conditionally - the people who wrote the standard evidently thought it was worthwhile enough to guarantee the behavior.

    Edit: I know that internally the compiler just does the equivalent conditional execution of the instruction, but it's such a trivial thing to do that any compiler that doesn't do it properly probably either hasn't been updated in many years, or is maintained by someone who just doesn't care, either of which is a good reason not to use said compiler.
    Last edited by robatino; 11-07-2007 at 01:12 PM.

  10. #10
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by robatino View Post
    Any fairly recent and standards-compliant compiler shouldn't have this problem (although admittedly a lot of posters seem to be using compilers from the last century, so it needs to be mentioned). If the OP is having this problem he needs to get a newer one. The benefit of being able to use free(NULL) is to not have to call it conditionally - the people who wrote the standard evidently thought it was worthwhile enough to guarantee the behavior.

    Edit: I know that internally the compiler just does the equivalent conditional execution of the instruction, but it's such a trivial thing to do that any compiler that doesn't do it properly probably either hasn't been updated in many years, or is maintained by someone who just doesn't care, either of which is a good reason not to use said compiler.
    Yes, I agree with that on hobby projects. However, I have worked on several projects where the compiler is at least afew years old - simply because "replacing the compiler will introduce more risk to the project". Where I work right now, we use gcc 3.4.2, which I'm sure is circa 2002. I can of course get a newer compiler for MY machine, but the code has to work on everyones system, not just mine - there are a few hundred SW engineers in the company, with literally hundreds of thousands of lines of C and C++ code.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  11. #11
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    we use gcc 3.4.2, which I'm sure is circa 2002
    GCC 3.4.2 is from the latter half of 2004, actually. http://archives.free.net.ph/message/...569e46.en.html

    What's the use of a standard if no one uses it? In this case, I think it would be best to rely on the standard's behaviour in allowing free(NULL). If this doesn't work, you could always get away with
    Code:
    #define free(p) if(p) free(p)
    Unless the compiler doesn't support using macros which contain the macro's name. Sigh . . . then you might have to do something like this.
    Code:
    void null_free(void *p) {
        if(p) free(p);
    }
    #define free(p) null_free(p)
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. malloc, calloc from the FAQ
    By salvadoravi in forum C Programming
    Replies: 10
    Last Post: 01-21-2008, 03:29 AM
  2. Help with calloc and pointers to strings.
    By sweetarg in forum C Programming
    Replies: 1
    Last Post: 10-24-2005, 02:28 PM
  3. Malloc and calloc problem!!
    By xxhimanshu in forum C Programming
    Replies: 19
    Last Post: 08-10-2005, 05:37 AM
  4. Why use calloc()?
    By dwks in forum C Programming
    Replies: 8
    Last Post: 07-20-2005, 08:22 AM
  5. difference between calloc and malloc
    By saravanan_ts in forum C Programming
    Replies: 4
    Last Post: 07-28-2003, 06:13 AM