The behaviour of malloc(0)
in the C11 standard quotes the following*:
void* malloc( size_t size );
If size is zero, the behavior is implementation defined (null pointer may be returned, or some non-null pointer may be returned that may not be used to access storage, but has to be passed to free).
*(Quoted from cppreference.com rather than the official ISO/IEC 9899:2011 standard, as the former needs to be purchased.)
With this definition I would not have expected the following to work (compiled with icc
18.0.0):
#include <stdlib.h>
#include <stdio.h>
int main(int argc, char **argv)
{
double *u = malloc(0);
u[0] = 3.0;
printf("The value of u[0] is %lf", u[0]);
free(u);
return 0;
}
Surprisingly it worked and gave the output:
The value of u[0] is 3.000000
Process finished with exit code 0
It appears u[0] = 3.0;
accesses storage. Had malloc
returned NULL
instead, then this would cause a segmentation fault.
Have I misunderstood the notion of accessing storage, or is there something else happening?
Update / Clarification
It seems the crux of my question was in the wording "may not be used to access storage", and whether "may not" meant should not or cannot. I had read this as meaning that whatever pointer was returned could not be dereferenced (unless realloc
'd).
I have since found the answers to I can use more memory than how much I've allocated with malloc(), why? very applicable to this question. The main point being that writing outside of allocated memory is undefined behaviour, and while this is undoubtedly wrong, it is not guaranteed to throw and error.
The question what's the point in malloc(0)
? has several answers mentioning the pointer returned.