[comp.lang.c++] const vs. void

ajw@watson.hf.intel.com (Alan Waldock) (03/21/91)

This is a kind of repost, on account of our mail servers are up
the creek.

If, to protect data, I point to it with a 'char const *', the
compiler prevents me from using that pointer as the first (destination)
argument to 'strncpy()', which requires a 'char *'.

However, I'm free to pass it (as destination) to 'memcpy()', which
specifies a 'void *' as its first argument.

It's as if a 'void *' will accept any pointer, const or no.
Is this right?

-- Alan Waldock, from but not on behalf of Intel Corporation
   ajw@watson.hf.intel.com       ...uunet!intelhf!watson!ajw

steve@taumet.com (Stephen Clamage) (03/22/91)

ajw@watson.hf.intel.com (Alan Waldock) writes:

>If, to protect data, I point to it with a 'char const *', the
>compiler prevents me from using that pointer as the first (destination)
>argument to 'strncpy()', which requires a 'char *'.

>However, I'm free to pass it (as destination) to 'memcpy()', which
>specifies a 'void *' as its first argument.

>It's as if a 'void *' will accept any pointer, const or no.  Is this right?

Until recently, any pointer could be implicitly converted to void*,
including a pointer to const.

The ARM now specifies that the conversion will not occur, and the call
to memcpy() will fail without an explicit cast.  I believe cfront 2.1
enforces this new restriction.
-- 

Steve Clamage, TauMetric Corp, steve@taumet.com

garnett@savage.bellcore.com (Michael Garnett) (03/22/91)

In article <1991Mar20.164518.19928@intelhf.hf.intel.com>, ajw@watson.hf.intel.com (Alan Waldock) writes:
|> This is a kind of repost, on account of our mail servers are up
|> the creek.
|> 
|> If, to protect data, I point to it with a 'char const *', the
|> compiler prevents me from using that pointer as the first (destination)
|> argument to 'strncpy()', which requires a 'char *'.
|> 
|> However, I'm free to pass it (as destination) to 'memcpy()', which
|> specifies a 'void *' as its first argument.
|> 
|> It's as if a 'void *' will accept any pointer, const or no.
|> Is this right?
|> 
|> -- Alan Waldock, from but not on behalf of Intel Corporation
|>    ajw@watson.hf.intel.com       ...uunet!intelhf!watson!ajw
---------
]]]]] I never use "char const *", but I tested it and it seems to behave like
]]]]] "const char *".  I assume that this is correct.  Can anyone verify this?

You compiler is right to complain about the call to strncpy.  If that 
pointer is passed into strncpy, strncpy can change your pointed-to data
(that is what strncpy is supposed to do to its first argument).
However, allowing you to pass it into a "void *" is WRONG.  You CAN
pass it into a "const void *" ("void const *"?).

The gist is... you can't "protect" your pointed-to data..
and still expect functions like strncpy to be able to change the data
for you.  You can cast away the constness as in
	strncpy ((char*)foo, bar, 5)
BUT this is strongly NOT advised.
------------------------------------------------------------------------
    *********                  Michael S. Garnett 
  **    o    **                Information Networks Research
 **   _- -_   **               Ph: 201-829-4591
**   /     \   **              Internet: garnett@thumper.bellcore.com
*   |       |   *              UUCP: ...!bellcore!thumper!garnett
**  |       |  **
 ** /_______\ ** // I speak for only myself, and NOT any company or	
  **    o    **  // organization directly or indirectly associated with
    *********    // Bell Communications Research

jimad@microsoft.UUCP (Jim ADCOCK) (03/26/91)

In article <1991Mar20.164518.19928@intelhf.hf.intel.com> ajw@watson.hf.intel.com writes:

>It's as if a 'void *' will accept any pointer, const or no.
>Is this right?

ARM page 36 says:

"A pointer to any non-const and non-volatile object type may be converted
to a void*."

Many people would interpret this as a prohibition from compilers accepting
an implicit conversion of a pointer to a const or volatile to a void*.
I do not consider it such a prohibition,  but rather a statement of 
permission.  If the ANSI-C++ committee defines such a conversion to be a 
constrained error [a error compilers are required to detect] then such 
is truly "illegal."  Until if-and-when the ANSI-C++ committee defined 
this [and any other thing] as a constrained error, all we can say is that 
it is "implementation dependent."

This is a general problem with the ARM.  Since it is a reference manual,
not a specification, it tends to state those things that a C++ programmer
is allowed to do, and tends not to state those things that a C++
compiler is required to reject.  Hopefully, the ANSI-C++ committee will
make it "clear" what compilers are required to reject, in a manner 
similar to the ANSI-C specification's "constraints."

PS:

Even if there is a specification stating what compilers are required
to accept, and what they are required to reject, there still remains
a gray area of "implementation dependent" code where compilers are allowed
to accept or reject the code, and generate something sensible or not in the 
process.