Given that scanf has (const char *) in the documentation from Microsoft and the answer to this question what the heck is going when I do the same for (char **) promotion to
The first example of yours works, because you're converting rvalues of char*
to const char*
, which is OK (basically because you cannot assign to rvalues). The second doesn't, because the target of a (non-const) pointer is always a lvalue.
Just try (maybe with the aid of the compiler) which operations you can do with char**
, which work with const char**
, and think if and what types are interchangeable.
Check if this clarifies for you:
char * a_mutable = /*...*/;
const char * a_constant = /*...*/;
char **pointer_to_mutable = &a_mutable; /* ok */
const char **pointer_to_constant = &a_constant; /* ok */
pointer_to_constant = pointer_to_mutable; /* oops, are you sure? */
*pointer_to_constant = a_mutable; /* valid, but will screw things around */
The last line is valid, since pointer_to_constant
is a mutable pointer to a mutable pointer to a constant character, but it would break things since you are making a_constant
point to a_mutable
. That is why you are not allowed to make pointer_to_constant
receive the contents of pointer_to_mutable
.
char** -> const char **
is dangerous, since you might end up accidentally modifying the underlying const
object.
The correct way to write what you want is:
void processargs(const char * const *p)
{
}
You're allowed to increase access restriction, you just can't decrease it. Going from a normal pointer to a const pointer is fine, going from a const pointer to a normal pointer is not.
The second example doesn't compile because you're not converting a pointer to a const pointer, you're converting from a pointer to one type (char*
) to another (const char*
). For example, you can change a char**
to a char* const*
, but not a const char**
.