const char * and char * are compatible pointer types?

M

max

Dear all,

I did the following analysis to conclude that the following pointer
types are not compatible. Please let me know If my analysis and
interpretation of the C standard are correct:

const char * : "pointer to const-qualified char".
char *: "pointer to char".

Are these pointed-to types compatibles?

--------------------------
C89
--------------------------
6.5.4.1
Pointer declarators
....
For two pointer types to be compatible, both shall be identically
qualified
and both shall be pointers to compatible types.
....
--------------------------

Well, using definition in 6.5.4.1 we can see that we comply with the
first part
("both shall be identically qualified").
Both are identically qualified (no qualifiers, both are unqualified
types).

Let us see now about the second part of definition in 6.5.4.1
("and both shall be pointers to compatible types").

So do these pointers:

1) const char *; /* pointer to const-qualified char */
2) char *; /* pointer to char */

point to compatible types?

In the case of pointer 1) const char *;
this pointer points to a 'const-qualified char'.
In the case of pointer 2) char *;
this pointer points to a 'char'.

Is a 'const-qualified char' compatible with a
'char'?

--------------------------
C89
--------------------------
6.1.2.5
Types
.....
The qualified or unqualified versions of a type are distinct types that
belong to the same type category and have the same representation and
alignment requirements.
....
--------------------------

As we can see according to 6.1.2.5 and
6.1.2.6 ("Two types have compatible type if their types are the same").
A 'const-qualified char' is NOT compatible with a 'char'
because their types are different.

And as we can see:

1) const char *; /* pointer to const-qualified char */
2) char *; /* pointer to char */

cannot satisfy second part of definition in
6.5.4.1 ("and both shall be pointers to compatible types"). Because
they do not point to compatible types.

Therefore 1) and 2) are NOT compatible pointers.

Thank you very much to everybody in advance,

Max
 
M

Malcolm

max said:
const char * : "pointer to const-qualified char".
char *: "pointer to char".

Are these pointed-to types compatibles?
The technical answer is no. A const char * cannot be converted to a plain
char *, whilst a char * can be converted to a const char *.
The reason is that const char * points to strings that may not be modified.
You can treat a mutable string as immodifiable, but not a string in
read-only memory as modifiable.

Unfortunately const was a late addition to the language. As a result, a lot
of C code uses plain char *s where const char * would have been more
appropriate. To avoid breaking old code, the conversion between char * and
const char *was made rather loose.

(There are also problems with functions like strchr(). It returns a pointer
to the first instance of a character in a string. So if you pass it a
mutable string you want a char *, if you pass it a read-only string you want
a const char * back. However there is no easy way of doing this in the
language as it stands. Hence the function returns a char *.)
 
K

Keith Thompson

Malcolm said:
The technical answer is no. A const char * cannot be converted to a plain
char *, whilst a char * can be converted to a const char *.
The reason is that const char * points to strings that may not be modified.
You can treat a mutable string as immodifiable, but not a string in
read-only memory as modifiable.

A char* or const char* doesn't necessarily point to a string. If it's
valid and non-null, it points to a character; that character may or
may not be the first element of an array (or, arguably, it's always
the first element of an array, possibly of length 1), and the array
may or may not be a string.

I think you're thinking of the issue of string literals (for which the
corresponding character array isn't const, but trying to modify it
invokes undefined behavior) -- but the original question didn't
mention string literals. Strings and string literals certainly
motivate the rules, but they aren't necessary to describing them.
 
J

Jordan Abel

The technical answer is no. A const char * cannot be converted to a plain
char *, whilst a char * can be converted to a const char *.

However, a const char * can be _cast_ to a plain char *, and will not
break unexpectedly. That is, if the const char * value was originally
converted from a modifiable char * in the first place, of if the object
pointed to by the resulting char * pointer is not in fact modified,
there is no undefined behavior invoked.
The reason is that const char * points to strings that may not be modified.
You can treat a mutable string as immodifiable, but not a string in
read-only memory as modifiable.

Unfortunately const was a late addition to the language. As a result, a lot
of C code uses plain char *s where const char * would have been more
appropriate. To avoid breaking old code, the conversion between char * and
const char *was made rather loose.

Actually, the only concession made to such issues was that string
literals, though immutable, are of type char *. This can be changed in
some modern compilers, and there is some debate as to whether this
actually causes such implementations to be non-conforming.
 
D

Douglas A. Gwyn

Jordan said:
Actually, the only concession made to such issues was that string
literals, though immutable, are of type char *. This can be changed in
some modern compilers, and there is some debate as to whether this
actually causes such implementations to be non-conforming.

There shouldn't be any question about it:
char *s; // not const-qualified
s = "Am I const?"; // must be allowed
If the compiler supports the operation, but also issues a
diagnostic, then technically it might be conforming but in
practice it will be a pain.
 
M

Malcolm

Jordan Abel said:
Actually, the only concession made to such issues was that string
literals, though immutable, are of type char *. This can be changed in
some modern compilers, and there is some debate as to whether this
actually causes such implementations to be non-conforming.
Also strchr(). Also the fact that a cast from a const char * to a char * is
legal, which ideally it shouldn't be.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,581
Members
45,056
Latest member
GlycogenSupporthealth

Latest Threads

Top