Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

calloc(): Do the individual values matter for performance?

I'm currently writing an embedded application in C where performance is critical.

Currently, I'm allocating lots of empty memory like this: calloc(1, num_bytes) - however, I simply calculate num_bytes as the product of a number of items and the size of each item earlier in the code as it's code that used to call malloc.

calloc seems unique in that it is the only memory allocation function of the -alloc family which takes two arguments for the size. Is there a good reason for doing this? Are there performance implications for specifying different arguments? What was the rationale in choosing this argument layout?

like image 862
Thomas O Avatar asked Oct 06 '22 19:10

Thomas O


1 Answers

One advantage of having the separate arguments is that it automatically guards against integer overflow:

// On a 32-bit system, the calloc will almost certainly fail, but the malloc
// will succeed to overflow, likely leading to crashes and/or security holes
// (e.g. if the number of items to allocate came from an untrusted source)
void *a = calloc(64, 67108865);  // 2^32/64 + 1
void *b = malloc(64 * 67108865);  // will allocate 64 bytes on 32-bit systems

For large allocations, there can also be a performance advantage of doing a calloc instead of a malloc and memset combination, since the calloc implementation can use its internal knowledge of the heap to avoid unnecessary work or have improved cache performance.

For example, if the allocator decides to use an OS function such as mmap(2) or VirtualAlloc to acquire more virtual address space, that memory will come pre-zeroed for security reasons. See this question for a detailed explanation. For small allocations, you're unlikely to notice much of a difference.

Some calloc implementations just call malloc and memset internally, so there's no advantage other than a potential overflow check.

like image 66
Adam Rosenfield Avatar answered Oct 10 '22 02:10

Adam Rosenfield