Created on 2022-06-04.00:00:00 last changed 18 months ago
Suggested resolution:
Change in 7.6.4 [expr.mptr.oper] paragraph 4 as follows:
Abbreviating pm-expression.*cast-expression as E1.*E2, E1 is called the object expression.If the dynamic type of E1 does not contain the member to which E2 refers,Where the type of E2 is "pointer to member of T", C is the (unique) class of which the member to which E2 refers is a direct member, and B is the object of type T that either is the result of E1 or is the uniquely so-typed base subobject thereof, if B is neither of type C nor a base class subobject of an object of type C, then the behavior is undefined.
Consider:
struct A {}; struct AA : A { int y; }; struct B : A { int x; }; struct C : AA, B {}; constexpr int f(const A &a) { int A::*mp = static_cast<int A::*>(&B::x); return a.*mp; } extern char x[f(static_cast<const AA &>(C{{{}, 13}, {{}, 42}}))]; extern char x[13];
Subclause 7.6.4 [expr.mptr.oper] paragraph 4 specifies:
Abbreviating pm-expression.*cast-expression as E1.*E2, E1 is called the object expression. If the dynamic type of E1 does not contain the member to which E2 refers, the behavior is undefined.
In the example, the dynamic type of a is C, which does contain B::x, and the undefined behavior provision does not trigger. Thus the call to f is required to yield 42; however common implementations produce 13. The behavior for this case ought to be undefined.
History | |||
---|---|---|---|
Date | User | Action | Args |
2023-06-20 19:34:52 | admin | set | status: open -> review |
2022-06-08 07:12:46 | admin | set | messages: + msg6845 |
2022-06-04 00:00:00 | admin | create |