| Re .0:
We're closing SPR HPAQC0VCX with this answer:
"
Symptom:
DEC C++/Alpha/UNIX V5.5 rejects the following program:
typedef struct { int value; } DATA;
typedef struct { DATA var; } MY_DATA;
volatile MY_DATA* ptr1;
MY_DATA* ptr2;
void main()
{
int buffer;
DATA test = { 1 };
ptr1 = (MY_DATA*) &buffer;
ptr2 = (MY_DATA*) &buffer;
ptr1->var = test; // ERROR
ptr2->var = test; // OK
}
Diagnosis:
As DEC C++ reports, the sample program contains an error.
The language definition for DEC C++ is the May-91 printing of Ellis &
Stroustrup's _The Annotated C++ Reference Manual_ ("ARM"). The ARM states on p.
295 of �12.8 (Copying Class Objects):
"
..., if all bases and members of a class X have assignment operators accepting
const arguments, the generated assignment operator for class X will take a
single argument of type const X &, as follows:
X &X::operator = (const X &)
otherwise, it will take a single argument of type X &:
X &X::operator = (X &)
and assignment by copying of const X objects will not be possible. ...
"
In the sample program, struct DATA has no base classes, and a single (non-const)
member of type int. Thus, the generated assignment operator for class DATA has
the signature:
DATA &DATA::operator = (const DATA &)
Note that this operator does not have the ``volatile'' keyword as a
cv-qualifier. That is, ``volatile does not follow the close parenthesis of the
operator's argument list. Such an operator cannot be applied to a left-hand
side with a volatile type.
In the sample expression ``ptr1->var = test'', ptr1->var is of type
``volatile DATA''. Since class DATA has no user-defined assignment operators,
and the generated assignment operator cannot be applied to that type, the
program is justifiably rejected.
Cure:
Fix the sample program.
If you know of a way to safely assign DATA objects to volatile DATA objects, one
can define an appropriate assignment operator:
struct DATA {
int value;
volatile DATA &operator = (const DATA &rhs) volatile
{
value = rhs.value;
return *this;
}
};
Or, if the DATA object is in fact not volatile at the point of the assignment,
one can use a cast to express that fact:
((MY_DATA *)ptr1)->var = test;
"
Re .4:
>compromise and make it a warning?
Hmmm, an error does sound like overkill. I'll log a suggestion to decrease
NONVOLCALL, NONCONSTCALL and NONUNALCALL to warnings. However, it probably
won't get fixed in a release before ANSI C++. (I wouldn't even bet on the
severity being any particular level in the first release).
/AHM
|