printf("%p") and casting to (void *)
The %p
conversion specifier requires an argument of type void *
. If you don't pass an argument of type void *
, the function call invokes undefined behavior.
From the C Standard (C11, 7.21.6.1p8 Formatted input/output functions):
"p - The argument shall be a pointer to void."
Pointer types in C are not required to have the same size or the same representation.
An example of an implementation with different pointer types representation is Cray PVP where the representation of pointer types is 64-bit for void *
and char *
but 32-bit for the other pointer types.
See "Cray C/C++ Reference Manual", Table 3. in "9.1.2.2" http://docs.cray.com/books/004-2179-003/004-2179-003-manual.pdf
In C language all pointer types potentially differ in their representations. So, yes, int *
is different from void *
. A real-life platform that would illustrate this difference might be difficult (or impossible) to find, but at the conceptual level the difference is still there.
In other words, in general case different pointer types have different representations. int *
is different from void *
and different from double *
. The fact that your platform uses the same representation for void *
and int *
is nothing more than a coincidence, as far as C language is concerned.
The language states that some pointer types are required to have identical representations, which includes void *
vs. char *
, pointers to different struct types or, say, int *
and const int *
. But these are just exceptions from the general rule.