Summary:
According to the C++11 standard [dcl.type.simple]p4:
The type denoted by decltype(e) is defined as follows:
- if e is an unparenthesized id-expression or an unparenthesized
class member access (5.2.5), decltype(e) is the type of the entity
named by e.
Currently Clang handles the 'member access' case incorrectly for
static data members (decltype returns T& instead of T). This patch
fixes the issue.
Reviewers: faisalv, rsmith, rogfer01
Reviewed By: rogfer01
Subscribers: rogfer01, cfe-commits
Differential Revision: https://reviews.llvm.org/D42969
llvm-svn: 325117
if (const ValueDecl *VD = dyn_cast<ValueDecl>(DRE->getDecl()))
return VD->getType();
} else if (const MemberExpr *ME = dyn_cast<MemberExpr>(E)) {
- if (const FieldDecl *FD = dyn_cast<FieldDecl>(ME->getMemberDecl()))
- return FD->getType();
+ if (const ValueDecl *VD = ME->getMemberDecl())
+ if (isa<FieldDecl>(VD) || isa<VarDecl>(VD))
+ return VD->getType();
} else if (const ObjCIvarRefExpr *IR = dyn_cast<ObjCIvarRefExpr>(E)) {
return IR->getDecl()->getType();
} else if (const ObjCPropertyRefExpr *PR = dyn_cast<ObjCPropertyRefExpr>(E)) {
const int&& foo();
int i;
-struct A { double x; };
+struct A {
+ double x;
+ static int y;
+};
const A* a = new A();
static_assert(is_same<decltype(foo()), const int&&>::value, "");
static_assert(is_same<decltype(i), int>::value, "");
static_assert(is_same<decltype(a->x), double>::value, "");
static_assert(is_same<decltype((a->x)), const double&>::value, "");
+static_assert(is_same<decltype(a->y), int>::value, "");
+static_assert(is_same<decltype((a->y)), int&>::value, "");
static_assert(is_same<decltype(static_cast<int&&>(i)), int&&>::value, "");
int f0(int); // expected-note{{possible target}}