ISO/IEC 9899:TC2 (i.e. the C99 standard), §7.20.3 states:
If the size of the space requested is zero, the behavior is implementation-defined: either a null pointer is returned, or the behavior is as if the size were some nonzero value, except that the returned pointer shall not be used to access an object.
In other words, malloc(0) may either return NULL or a valid pointer which I may not dereference.
What is the rationale behind this behavior?
And wouldn't it be easier to just define that malloc(0) leads to UB?
The C99 Rationale (PDF link) discusses the memory management functions (from C99 7.20.3) and explains:
Making
malloc(0)
result in UB would be much worse. As it stands, you don't have to care what happens when the size is zero, as long as you're consistent about callingfree
.The problem is that some existing implementations allocate a pointer for
malloc(0)
, some return null pointers, and almost all of them are adamant about sticking with their behavior because the same people who wrote the implementations wrote lots of bad, non-portable software that makes use of their chosen behavior (GNU being among the worst offenders in this area). Thus the standard got stuck allowing both behaviors to keep them all happy.Because allocating 0 bytes may actually have sense. For example, when you are allocating an array with unknown number of items. UB would allow the program crash, whereas with the current behaviour you can safely allocate
numberOfItems * itemSize
bytes.The logic is following: if you ask for 0 bytes, you get a pointer back. Of course, you must not dereference it, as this would have accessed 0-th byte (which you haven't allocated). But you can safely free the memory afterwards. So you don't need to make 0 a special case.
This was about why not define
malloc(0)
as UB. About the decision not to define the result strictly (NULL
vs. unique pointer to empty space) see James' answer. (In short: both approaches have their advantages and disadvantages. The idea of returning a unique non-null pointer is more compelling, but requires more conceptual work and puts more burden on implementors.)