3 ms·
I wish these kind of articles targeted to higher-level programmers would start teaching to use 'calloc' before 'malloc'. New C users will have a bad time catchi
by thepumpkin1979 13y ago
I wish these kind of articles targeted to higher-level programmers would start teaching to use 'calloc' before 'malloc'. New C users will have a bad time catching random bugs when they allocate a struct via malloc and immediately check members using de-referencing in 'if' conditions which will be randomly evaluated as true because malloc doesn't initialize the memory to zero and therefore all the members of the struct through the pointer returned by malloc are full of garbage. My rules are: either use malloc if you intent to immediately initialize the memory or use calloc and pass the pointer around.
- Nursie 13y agoIIRC while this is true and good practice, many modern OS/libc implementations will zero stuff anyway.
- KMag 13y agoDon't count on it. Modern OSes will zero out pages when your process brk()/ mmap()/etc. them into your address space, to avoid security problems. However, unless you're using a debugging version of libc/LD_PRELOAD'ing malloc/free implementations, etc., I don't believe most malloc/free implementations will necessarily hand you memory containing a known pattern. Certainly the main selling point of non-default malloc/free implementations is performance. Zeroing out memory between uses by the same process has some overhead, and the benefits are more of a mixed bag than the case of accidentally leaking sensitive data a programmer has forgotten to zero out (or doesn't think is sensitive) between processes. Your free() implementation can't return partial pages[0], and in general will only return multi-page contiguous blocks to the OS, due to memory fragmentation, anticipation of soon needing to malloc() again, and a desire to keep system call overhead down. The consequence is that if you do a lot of malloc()ing and free()ing, you're likely to sometimes get zero'd out pages, and sometimes get garbage that your process has previously written to memory, but you should never get garbage that another process has written to memory. (Unless, of course, it's shared memory or copy-on-write shared with a parent process.) [0] Well, if your CPU/MMU supports segment registers or you're willing to do unsafe things that can't be enforced by the MMU, then your OS could support returning partial pages to the OS. However, modern desktop/tablet/smartphone OSes don't work this way. EDIT: Too lazy to read how to get asterisks to show up consistently. I changed *aloc to "malloc".
- enjoy-your-stay 13y ago... or initialize you freshly malloc'd memory to DEADBEEF for you. Just to helpfully let you know when you're reading a bit of uninitialized RAM.
- pcwalton 13y agoOn the other hand, if it's available, Valgrind will do a better job of catching uninitialized memory use if you use malloc instead of calloc. (IMO, explicit initialization is better than just zeroing stuff out, because there's no guarantee that zeroed memory is valid. Especially when pointers are involved—dereferencing a null pointer in C is undefined behavior, so compilers are free to wreak havoc on any code that it can prove attempts to do that...)
- thepumpkin1979 13y agoThat's true. I usually initialize the struct in the stack and then assign it to the pointer, then pass the pointer around.