While debugging a crash, I came across this issue in some code:
int func()
{
char *p1 = malloc(...);
if (p1 == NULL)
goto err_exit;
char *p2 = malloc(...);
if (p2 == NULL)
goto err_exit;
...
err_exit:
free(p2);
free(p1);
return -1;
}
The problem occurs when the first malloc fails. Because we jump across the initialization of p2, it contains random data and the call to free(p2) can crash.
I would expect/hope that this would be treated the same way as in C++ where the compiler does not allow a goto to jump across an initialization.
My question: is jumping across an initialization allowed by the standard or is this a bug in gcc’s implementation of c99?
You can ask gcc to warn you when you jump over a variable definition by using
-Wjump-misses-initand then you can use-Werror(or, more precisely,-Werror=jump-misses-init) to force the users to deal with it. This warning is included in-Wc++-compatso the gcc developers are aware that the code behaves differently in C versus C++.You could also change the code slightly:
… and just keep pairing labels with initialized variables. You’ll have the same problem with calling many other functions with unitialized variables, free just happens to be a more obvious one.