summaryrefslogtreecommitdiffstats
path: root/include/clang/AST/ExprCXX.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/clang/AST/ExprCXX.h')
-rw-r--r--include/clang/AST/ExprCXX.h1061
1 files changed, 791 insertions, 270 deletions
diff --git a/include/clang/AST/ExprCXX.h b/include/clang/AST/ExprCXX.h
index 0a94354..85ce962 100644
--- a/include/clang/AST/ExprCXX.h
+++ b/include/clang/AST/ExprCXX.h
@@ -21,11 +21,11 @@
namespace clang {
- class CXXConstructorDecl;
- class CXXDestructorDecl;
- class CXXMethodDecl;
- class CXXTemporary;
- class TemplateArgumentListInfo;
+class CXXConstructorDecl;
+class CXXDestructorDecl;
+class CXXMethodDecl;
+class CXXTemporary;
+class TemplateArgumentListInfo;
//===--------------------------------------------------------------------===//
// C++ Expressions.
@@ -51,8 +51,9 @@ class CXXOperatorCallExpr : public CallExpr {
public:
CXXOperatorCallExpr(ASTContext& C, OverloadedOperatorKind Op, Expr *fn,
Expr **args, unsigned numargs, QualType t,
- SourceLocation operatorloc)
- : CallExpr(C, CXXOperatorCallExprClass, fn, args, numargs, t, operatorloc),
+ ExprValueKind VK, SourceLocation operatorloc)
+ : CallExpr(C, CXXOperatorCallExprClass, fn, 0, args, numargs, t, VK,
+ operatorloc),
Operator(Op) {}
explicit CXXOperatorCallExpr(ASTContext& C, EmptyShell Empty) :
CallExpr(C, CXXOperatorCallExprClass, Empty) { }
@@ -70,7 +71,7 @@ public:
/// bracket.
SourceLocation getOperatorLoc() const { return getRParenLoc(); }
- virtual SourceRange getSourceRange() const;
+ SourceRange getSourceRange() const;
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXOperatorCallExprClass;
@@ -89,8 +90,8 @@ public:
class CXXMemberCallExpr : public CallExpr {
public:
CXXMemberCallExpr(ASTContext &C, Expr *fn, Expr **args, unsigned numargs,
- QualType t, SourceLocation rparenloc)
- : CallExpr(C, CXXMemberCallExprClass, fn, args, numargs, t, rparenloc) {}
+ QualType t, ExprValueKind VK, SourceLocation RP)
+ : CallExpr(C, CXXMemberCallExprClass, fn, 0, args, numargs, t, VK, RP) {}
CXXMemberCallExpr(ASTContext &C, EmptyShell Empty)
: CallExpr(C, CXXMemberCallExprClass, Empty) { }
@@ -100,7 +101,14 @@ public:
/// operation would return "x".
Expr *getImplicitObjectArgument();
- virtual SourceRange getSourceRange() const;
+ /// getRecordDecl - Retrieves the CXXRecordDecl for the underlying type of
+ /// the implicit object argument. Note that this is may not be the same
+ /// declaration as that of the class context of the CXXMethodDecl which this
+ /// function is calling.
+ /// FIXME: Returns 0 for member pointer call exprs.
+ CXXRecordDecl *getRecordDecl();
+
+ SourceRange getSourceRange() const;
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXMemberCallExprClass;
@@ -108,6 +116,35 @@ public:
static bool classof(const CXXMemberCallExpr *) { return true; }
};
+/// CUDAKernelCallExpr - Represents a call to a CUDA kernel function.
+class CUDAKernelCallExpr : public CallExpr {
+private:
+ enum { CONFIG, END_PREARG };
+
+public:
+ CUDAKernelCallExpr(ASTContext &C, Expr *fn, CallExpr *Config,
+ Expr **args, unsigned numargs, QualType t,
+ ExprValueKind VK, SourceLocation RP)
+ : CallExpr(C, CUDAKernelCallExprClass, fn, END_PREARG, args, numargs, t, VK,
+ RP) {
+ setConfig(Config);
+ }
+
+ CUDAKernelCallExpr(ASTContext &C, EmptyShell Empty)
+ : CallExpr(C, CUDAKernelCallExprClass, END_PREARG, Empty) { }
+
+ const CallExpr *getConfig() const {
+ return cast_or_null<CallExpr>(getPreArg(CONFIG));
+ }
+ CallExpr *getConfig() { return cast_or_null<CallExpr>(getPreArg(CONFIG)); }
+ void setConfig(CallExpr *E) { setPreArg(CONFIG, E); }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == CUDAKernelCallExprClass;
+ }
+ static bool classof(const CUDAKernelCallExpr *) { return true; }
+};
+
/// CXXNamedCastExpr - Abstract class common to all of the C++ "named"
/// casts, @c static_cast, @c dynamic_cast, @c reinterpret_cast, or @c
/// const_cast.
@@ -118,26 +155,33 @@ public:
class CXXNamedCastExpr : public ExplicitCastExpr {
private:
SourceLocation Loc; // the location of the casting op
-
+ SourceLocation RParenLoc; // the location of the right parenthesis
+
protected:
- CXXNamedCastExpr(StmtClass SC, QualType ty, CastKind kind, Expr *op,
- unsigned PathSize, TypeSourceInfo *writtenTy,
- SourceLocation l)
- : ExplicitCastExpr(SC, ty, kind, op, PathSize, writtenTy), Loc(l) {}
+ CXXNamedCastExpr(StmtClass SC, QualType ty, ExprValueKind VK,
+ CastKind kind, Expr *op, unsigned PathSize,
+ TypeSourceInfo *writtenTy, SourceLocation l,
+ SourceLocation RParenLoc)
+ : ExplicitCastExpr(SC, ty, VK, kind, op, PathSize, writtenTy), Loc(l),
+ RParenLoc(RParenLoc) {}
explicit CXXNamedCastExpr(StmtClass SC, EmptyShell Shell, unsigned PathSize)
: ExplicitCastExpr(SC, Shell, PathSize) { }
+ friend class ASTStmtReader;
+
public:
const char *getCastName() const;
/// \brief Retrieve the location of the cast operator keyword, e.g.,
/// "static_cast".
SourceLocation getOperatorLoc() const { return Loc; }
- void setOperatorLoc(SourceLocation L) { Loc = L; }
- virtual SourceRange getSourceRange() const {
- return SourceRange(Loc, getSubExpr()->getSourceRange().getEnd());
+ /// \brief Retrieve the location of the closing parenthesis.
+ SourceLocation getRParenLoc() const { return RParenLoc; }
+
+ SourceRange getSourceRange() const {
+ return SourceRange(Loc, RParenLoc);
}
static bool classof(const Stmt *T) {
switch (T->getStmtClass()) {
@@ -158,20 +202,21 @@ public:
/// This expression node represents a C++ static cast, e.g.,
/// @c static_cast<int>(1.0).
class CXXStaticCastExpr : public CXXNamedCastExpr {
- CXXStaticCastExpr(QualType ty, CastKind kind, Expr *op,
+ CXXStaticCastExpr(QualType ty, ExprValueKind vk, CastKind kind, Expr *op,
unsigned pathSize, TypeSourceInfo *writtenTy,
- SourceLocation l)
- : CXXNamedCastExpr(CXXStaticCastExprClass, ty, kind, op, pathSize,
- writtenTy, l) {}
+ SourceLocation l, SourceLocation RParenLoc)
+ : CXXNamedCastExpr(CXXStaticCastExprClass, ty, vk, kind, op, pathSize,
+ writtenTy, l, RParenLoc) {}
explicit CXXStaticCastExpr(EmptyShell Empty, unsigned PathSize)
: CXXNamedCastExpr(CXXStaticCastExprClass, Empty, PathSize) { }
public:
static CXXStaticCastExpr *Create(ASTContext &Context, QualType T,
- CastKind K, Expr *Op,
+ ExprValueKind VK, CastKind K, Expr *Op,
const CXXCastPath *Path,
- TypeSourceInfo *Written, SourceLocation L);
+ TypeSourceInfo *Written, SourceLocation L,
+ SourceLocation RParenLoc);
static CXXStaticCastExpr *CreateEmpty(ASTContext &Context,
unsigned PathSize);
@@ -188,20 +233,21 @@ public:
/// This expression node represents a dynamic cast, e.g.,
/// @c dynamic_cast<Derived*>(BasePtr).
class CXXDynamicCastExpr : public CXXNamedCastExpr {
- CXXDynamicCastExpr(QualType ty, CastKind kind, Expr *op,
- unsigned pathSize, TypeSourceInfo *writtenTy,
- SourceLocation l)
- : CXXNamedCastExpr(CXXDynamicCastExprClass, ty, kind, op, pathSize,
- writtenTy, l) {}
+ CXXDynamicCastExpr(QualType ty, ExprValueKind VK, CastKind kind,
+ Expr *op, unsigned pathSize, TypeSourceInfo *writtenTy,
+ SourceLocation l, SourceLocation RParenLoc)
+ : CXXNamedCastExpr(CXXDynamicCastExprClass, ty, VK, kind, op, pathSize,
+ writtenTy, l, RParenLoc) {}
explicit CXXDynamicCastExpr(EmptyShell Empty, unsigned pathSize)
: CXXNamedCastExpr(CXXDynamicCastExprClass, Empty, pathSize) { }
public:
static CXXDynamicCastExpr *Create(ASTContext &Context, QualType T,
- CastKind Kind, Expr *Op,
+ ExprValueKind VK, CastKind Kind, Expr *Op,
const CXXCastPath *Path,
- TypeSourceInfo *Written, SourceLocation L);
+ TypeSourceInfo *Written, SourceLocation L,
+ SourceLocation RParenLoc);
static CXXDynamicCastExpr *CreateEmpty(ASTContext &Context,
unsigned pathSize);
@@ -219,20 +265,22 @@ public:
/// This expression node represents a reinterpret cast, e.g.,
/// @c reinterpret_cast<int>(VoidPtr).
class CXXReinterpretCastExpr : public CXXNamedCastExpr {
- CXXReinterpretCastExpr(QualType ty, CastKind kind, Expr *op,
- unsigned pathSize,
- TypeSourceInfo *writtenTy, SourceLocation l)
- : CXXNamedCastExpr(CXXReinterpretCastExprClass, ty, kind, op, pathSize,
- writtenTy, l) {}
+ CXXReinterpretCastExpr(QualType ty, ExprValueKind vk, CastKind kind,
+ Expr *op, unsigned pathSize,
+ TypeSourceInfo *writtenTy, SourceLocation l,
+ SourceLocation RParenLoc)
+ : CXXNamedCastExpr(CXXReinterpretCastExprClass, ty, vk, kind, op,
+ pathSize, writtenTy, l, RParenLoc) {}
CXXReinterpretCastExpr(EmptyShell Empty, unsigned pathSize)
: CXXNamedCastExpr(CXXReinterpretCastExprClass, Empty, pathSize) { }
public:
static CXXReinterpretCastExpr *Create(ASTContext &Context, QualType T,
- CastKind Kind, Expr *Op,
- const CXXCastPath *Path,
- TypeSourceInfo *WrittenTy, SourceLocation L);
+ ExprValueKind VK, CastKind Kind,
+ Expr *Op, const CXXCastPath *Path,
+ TypeSourceInfo *WrittenTy, SourceLocation L,
+ SourceLocation RParenLoc);
static CXXReinterpretCastExpr *CreateEmpty(ASTContext &Context,
unsigned pathSize);
@@ -248,17 +296,20 @@ public:
/// This expression node represents a const cast, e.g.,
/// @c const_cast<char*>(PtrToConstChar).
class CXXConstCastExpr : public CXXNamedCastExpr {
- CXXConstCastExpr(QualType ty, Expr *op, TypeSourceInfo *writtenTy,
- SourceLocation l)
- : CXXNamedCastExpr(CXXConstCastExprClass, ty, CK_NoOp, op,
- 0, writtenTy, l) {}
+ CXXConstCastExpr(QualType ty, ExprValueKind VK, Expr *op,
+ TypeSourceInfo *writtenTy, SourceLocation l,
+ SourceLocation RParenLoc)
+ : CXXNamedCastExpr(CXXConstCastExprClass, ty, VK, CK_NoOp, op,
+ 0, writtenTy, l, RParenLoc) {}
explicit CXXConstCastExpr(EmptyShell Empty)
: CXXNamedCastExpr(CXXConstCastExprClass, Empty, 0) { }
public:
- static CXXConstCastExpr *Create(ASTContext &Context, QualType T, Expr *Op,
- TypeSourceInfo *WrittenTy, SourceLocation L);
+ static CXXConstCastExpr *Create(ASTContext &Context, QualType T,
+ ExprValueKind VK, Expr *Op,
+ TypeSourceInfo *WrittenTy, SourceLocation L,
+ SourceLocation RParenLoc);
static CXXConstCastExpr *CreateEmpty(ASTContext &Context);
static bool classof(const Stmt *T) {
@@ -274,7 +325,9 @@ class CXXBoolLiteralExpr : public Expr {
SourceLocation Loc;
public:
CXXBoolLiteralExpr(bool val, QualType Ty, SourceLocation l) :
- Expr(CXXBoolLiteralExprClass, Ty, false, false), Value(val), Loc(l) {}
+ Expr(CXXBoolLiteralExprClass, Ty, VK_RValue, OK_Ordinary, false, false,
+ false),
+ Value(val), Loc(l) {}
explicit CXXBoolLiteralExpr(EmptyShell Empty)
: Expr(CXXBoolLiteralExprClass, Empty) { }
@@ -282,7 +335,7 @@ public:
bool getValue() const { return Value; }
void setValue(bool V) { Value = V; }
- virtual SourceRange getSourceRange() const { return SourceRange(Loc); }
+ SourceRange getSourceRange() const { return SourceRange(Loc); }
SourceLocation getLocation() const { return Loc; }
void setLocation(SourceLocation L) { Loc = L; }
@@ -293,8 +346,7 @@ public:
static bool classof(const CXXBoolLiteralExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
};
/// CXXNullPtrLiteralExpr - [C++0x 2.14.7] C++ Pointer Literal
@@ -302,12 +354,14 @@ class CXXNullPtrLiteralExpr : public Expr {
SourceLocation Loc;
public:
CXXNullPtrLiteralExpr(QualType Ty, SourceLocation l) :
- Expr(CXXNullPtrLiteralExprClass, Ty, false, false), Loc(l) {}
+ Expr(CXXNullPtrLiteralExprClass, Ty, VK_RValue, OK_Ordinary, false, false,
+ false),
+ Loc(l) {}
explicit CXXNullPtrLiteralExpr(EmptyShell Empty)
: Expr(CXXNullPtrLiteralExprClass, Empty) { }
- virtual SourceRange getSourceRange() const { return SourceRange(Loc); }
+ SourceRange getSourceRange() const { return SourceRange(Loc); }
SourceLocation getLocation() const { return Loc; }
void setLocation(SourceLocation L) { Loc = L; }
@@ -317,8 +371,7 @@ public:
}
static bool classof(const CXXNullPtrLiteralExpr *) { return true; }
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
};
/// CXXTypeidExpr - A C++ @c typeid expression (C++ [expr.typeid]), which gets
@@ -333,19 +386,21 @@ private:
public:
CXXTypeidExpr(QualType Ty, TypeSourceInfo *Operand, SourceRange R)
- : Expr(CXXTypeidExprClass, Ty,
+ : Expr(CXXTypeidExprClass, Ty, VK_LValue, OK_Ordinary,
// typeid is never type-dependent (C++ [temp.dep.expr]p4)
false,
// typeid is value-dependent if the type or expression are dependent
- Operand->getType()->isDependentType()),
+ Operand->getType()->isDependentType(),
+ Operand->getType()->containsUnexpandedParameterPack()),
Operand(Operand), Range(R) { }
CXXTypeidExpr(QualType Ty, Expr *Operand, SourceRange R)
- : Expr(CXXTypeidExprClass, Ty,
+ : Expr(CXXTypeidExprClass, Ty, VK_LValue, OK_Ordinary,
// typeid is never type-dependent (C++ [temp.dep.expr]p4)
- false,
+ false,
// typeid is value-dependent if the type or expression are dependent
- Operand->isTypeDependent() || Operand->isValueDependent()),
+ Operand->isTypeDependent() || Operand->isValueDependent(),
+ Operand->containsUnexpandedParameterPack()),
Operand(Operand), Range(R) { }
CXXTypeidExpr(EmptyShell Empty, bool isExpr)
@@ -383,7 +438,7 @@ public:
Operand = E;
}
- virtual SourceRange getSourceRange() const { return Range; }
+ SourceRange getSourceRange() const { return Range; }
void setSourceRange(SourceRange R) { Range = R; }
static bool classof(const Stmt *T) {
@@ -392,8 +447,84 @@ public:
static bool classof(const CXXTypeidExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ if (isTypeOperand()) return child_range();
+ Stmt **begin = reinterpret_cast<Stmt**>(&Operand);
+ return child_range(begin, begin + 1);
+ }
+};
+
+/// CXXUuidofExpr - A microsoft C++ @c __uuidof expression, which gets
+/// the _GUID that corresponds to the supplied type or expression.
+///
+/// This represents code like @c __uuidof(COMTYPE) or @c __uuidof(*comPtr)
+class CXXUuidofExpr : public Expr {
+private:
+ llvm::PointerUnion<Stmt *, TypeSourceInfo *> Operand;
+ SourceRange Range;
+
+public:
+ CXXUuidofExpr(QualType Ty, TypeSourceInfo *Operand, SourceRange R)
+ : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary,
+ false, Operand->getType()->isDependentType(),
+ Operand->getType()->containsUnexpandedParameterPack()),
+ Operand(Operand), Range(R) { }
+
+ CXXUuidofExpr(QualType Ty, Expr *Operand, SourceRange R)
+ : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary,
+ false, Operand->isTypeDependent(),
+ Operand->containsUnexpandedParameterPack()),
+ Operand(Operand), Range(R) { }
+
+ CXXUuidofExpr(EmptyShell Empty, bool isExpr)
+ : Expr(CXXUuidofExprClass, Empty) {
+ if (isExpr)
+ Operand = (Expr*)0;
+ else
+ Operand = (TypeSourceInfo*)0;
+ }
+
+ bool isTypeOperand() const { return Operand.is<TypeSourceInfo *>(); }
+
+ /// \brief Retrieves the type operand of this __uuidof() expression after
+ /// various required adjustments (removing reference types, cv-qualifiers).
+ QualType getTypeOperand() const;
+
+ /// \brief Retrieve source information for the type operand.
+ TypeSourceInfo *getTypeOperandSourceInfo() const {
+ assert(isTypeOperand() && "Cannot call getTypeOperand for __uuidof(expr)");
+ return Operand.get<TypeSourceInfo *>();
+ }
+
+ void setTypeOperandSourceInfo(TypeSourceInfo *TSI) {
+ assert(isTypeOperand() && "Cannot call getTypeOperand for __uuidof(expr)");
+ Operand = TSI;
+ }
+
+ Expr *getExprOperand() const {
+ assert(!isTypeOperand() && "Cannot call getExprOperand for __uuidof(type)");
+ return static_cast<Expr*>(Operand.get<Stmt *>());
+ }
+
+ void setExprOperand(Expr *E) {
+ assert(!isTypeOperand() && "Cannot call getExprOperand for __uuidof(type)");
+ Operand = E;
+ }
+
+ SourceRange getSourceRange() const { return Range; }
+ void setSourceRange(SourceRange R) { Range = R; }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == CXXUuidofExprClass;
+ }
+ static bool classof(const CXXUuidofExpr *) { return true; }
+
+ // Iterators
+ child_range children() {
+ if (isTypeOperand()) return child_range();
+ Stmt **begin = reinterpret_cast<Stmt**>(&Operand);
+ return child_range(begin, begin + 1);
+ }
};
/// CXXThisExpr - Represents the "this" expression in C++, which is a
@@ -413,10 +544,11 @@ class CXXThisExpr : public Expr {
public:
CXXThisExpr(SourceLocation L, QualType Type, bool isImplicit)
- : Expr(CXXThisExprClass, Type,
+ : Expr(CXXThisExprClass, Type, VK_RValue, OK_Ordinary,
// 'this' is type-dependent if the class type of the enclosing
// member function is dependent (C++ [temp.dep.expr]p2)
- Type->isDependentType(), Type->isDependentType()),
+ Type->isDependentType(), Type->isDependentType(),
+ /*ContainsUnexpandedParameterPack=*/false),
Loc(L), Implicit(isImplicit) { }
CXXThisExpr(EmptyShell Empty) : Expr(CXXThisExprClass, Empty) {}
@@ -424,7 +556,7 @@ public:
SourceLocation getLocation() const { return Loc; }
void setLocation(SourceLocation L) { Loc = L; }
- virtual SourceRange getSourceRange() const { return SourceRange(Loc); }
+ SourceRange getSourceRange() const { return SourceRange(Loc); }
bool isImplicit() const { return Implicit; }
void setImplicit(bool I) { Implicit = I; }
@@ -435,8 +567,7 @@ public:
static bool classof(const CXXThisExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
};
/// CXXThrowExpr - [C++ 15] C++ Throw Expression. This handles
@@ -451,7 +582,9 @@ public:
// exepression. The l is the location of the throw keyword. expr
// can by null, if the optional expression to throw isn't present.
CXXThrowExpr(Expr *expr, QualType Ty, SourceLocation l) :
- Expr(CXXThrowExprClass, Ty, false, false), Op(expr), ThrowLoc(l) {}
+ Expr(CXXThrowExprClass, Ty, VK_RValue, OK_Ordinary, false, false,
+ expr && expr->containsUnexpandedParameterPack()),
+ Op(expr), ThrowLoc(l) {}
CXXThrowExpr(EmptyShell Empty) : Expr(CXXThrowExprClass, Empty) {}
const Expr *getSubExpr() const { return cast_or_null<Expr>(Op); }
@@ -461,7 +594,7 @@ public:
SourceLocation getThrowLoc() const { return ThrowLoc; }
void setThrowLoc(SourceLocation L) { ThrowLoc = L; }
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
if (getSubExpr() == 0)
return SourceRange(ThrowLoc, ThrowLoc);
return SourceRange(ThrowLoc, getSubExpr()->getSourceRange().getEnd());
@@ -473,8 +606,9 @@ public:
static bool classof(const CXXThrowExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ return child_range(&Op, Op ? &Op+1 : &Op);
+ }
};
/// CXXDefaultArgExpr - C++ [dcl.fct.default]. This wraps up a
@@ -497,12 +631,16 @@ class CXXDefaultArgExpr : public Expr {
param->hasUnparsedDefaultArg()
? param->getType().getNonReferenceType()
: param->getDefaultArg()->getType(),
- false, false),
+ param->getDefaultArg()->getValueKind(),
+ param->getDefaultArg()->getObjectKind(), false, false, false),
Param(param, false), Loc(Loc) { }
CXXDefaultArgExpr(StmtClass SC, SourceLocation Loc, ParmVarDecl *param,
Expr *SubExpr)
- : Expr(SC, SubExpr->getType(), false, false), Param(param, true), Loc(Loc) {
+ : Expr(SC, SubExpr->getType(),
+ SubExpr->getValueKind(), SubExpr->getObjectKind(),
+ false, false, false),
+ Param(param, true), Loc(Loc) {
*reinterpret_cast<Expr **>(this + 1) = SubExpr;
}
@@ -544,7 +682,7 @@ public:
/// used.
SourceLocation getUsedLocation() const { return Loc; }
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
// Default argument expressions have no representation in the
// source, so they have an empty source range.
return SourceRange();
@@ -556,8 +694,7 @@ public:
static bool classof(const CXXDefaultArgExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
friend class ASTStmtReader;
friend class ASTStmtWriter;
@@ -597,9 +734,12 @@ class CXXBindTemporaryExpr : public Expr {
Stmt *SubExpr;
- CXXBindTemporaryExpr(CXXTemporary *temp, Expr* subexpr)
- : Expr(CXXBindTemporaryExprClass, subexpr->getType(), false, false),
- Temp(temp), SubExpr(subexpr) { }
+ CXXBindTemporaryExpr(CXXTemporary *temp, Expr* SubExpr)
+ : Expr(CXXBindTemporaryExprClass, SubExpr->getType(),
+ VK_RValue, OK_Ordinary, SubExpr->isTypeDependent(),
+ SubExpr->isValueDependent(),
+ SubExpr->containsUnexpandedParameterPack()),
+ Temp(temp), SubExpr(SubExpr) { }
public:
CXXBindTemporaryExpr(EmptyShell Empty)
@@ -616,7 +756,7 @@ public:
Expr *getSubExpr() { return cast<Expr>(SubExpr); }
void setSubExpr(Expr *E) { SubExpr = E; }
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
return SubExpr->getSourceRange();
}
@@ -627,8 +767,7 @@ public:
static bool classof(const CXXBindTemporaryExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(&SubExpr, &SubExpr + 1); }
};
/// CXXConstructExpr - Represents a call to a C++ constructor.
@@ -644,6 +783,7 @@ private:
CXXConstructorDecl *Constructor;
SourceLocation Loc;
+ SourceRange ParenRange;
bool Elidable : 1;
bool ZeroInitialization : 1;
unsigned ConstructKind : 2;
@@ -656,7 +796,8 @@ protected:
CXXConstructorDecl *d, bool elidable,
Expr **args, unsigned numargs,
bool ZeroInitialization = false,
- ConstructionKind ConstructKind = CK_Complete);
+ ConstructionKind ConstructKind = CK_Complete,
+ SourceRange ParenRange = SourceRange());
/// \brief Construct an empty C++ construction expression.
CXXConstructExpr(StmtClass SC, EmptyShell Empty)
@@ -675,7 +816,8 @@ public:
CXXConstructorDecl *D, bool Elidable,
Expr **Args, unsigned NumArgs,
bool ZeroInitialization = false,
- ConstructionKind ConstructKind = CK_Complete);
+ ConstructionKind ConstructKind = CK_Complete,
+ SourceRange ParenRange = SourceRange());
CXXConstructorDecl* getConstructor() const { return Constructor; }
@@ -731,7 +873,8 @@ public:
Args[Arg] = ArgExpr;
}
- virtual SourceRange getSourceRange() const;
+ SourceRange getSourceRange() const;
+ SourceRange getParenRange() const { return ParenRange; }
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXConstructExprClass ||
@@ -740,8 +883,9 @@ public:
static bool classof(const CXXConstructExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ return child_range(&Args[0], &Args[0]+NumArgs);
+ }
friend class ASTStmtReader;
};
@@ -753,12 +897,13 @@ class CXXFunctionalCastExpr : public ExplicitCastExpr {
SourceLocation TyBeginLoc;
SourceLocation RParenLoc;
- CXXFunctionalCastExpr(QualType ty, TypeSourceInfo *writtenTy,
+ CXXFunctionalCastExpr(QualType ty, ExprValueKind VK,
+ TypeSourceInfo *writtenTy,
SourceLocation tyBeginLoc, CastKind kind,
Expr *castExpr, unsigned pathSize,
SourceLocation rParenLoc)
- : ExplicitCastExpr(CXXFunctionalCastExprClass, ty, kind, castExpr,
- pathSize, writtenTy),
+ : ExplicitCastExpr(CXXFunctionalCastExprClass, ty, VK, kind,
+ castExpr, pathSize, writtenTy),
TyBeginLoc(tyBeginLoc), RParenLoc(rParenLoc) {}
explicit CXXFunctionalCastExpr(EmptyShell Shell, unsigned PathSize)
@@ -766,6 +911,7 @@ class CXXFunctionalCastExpr : public ExplicitCastExpr {
public:
static CXXFunctionalCastExpr *Create(ASTContext &Context, QualType T,
+ ExprValueKind VK,
TypeSourceInfo *Written,
SourceLocation TyBeginLoc,
CastKind Kind, Expr *Op,
@@ -779,7 +925,7 @@ public:
SourceLocation getRParenLoc() const { return RParenLoc; }
void setRParenLoc(SourceLocation L) { RParenLoc = L; }
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
return SourceRange(TyBeginLoc, RParenLoc);
}
static bool classof(const Stmt *T) {
@@ -804,24 +950,21 @@ public:
/// };
/// @endcode
class CXXTemporaryObjectExpr : public CXXConstructExpr {
- SourceLocation TyBeginLoc;
- SourceLocation RParenLoc;
+ TypeSourceInfo *Type;
public:
CXXTemporaryObjectExpr(ASTContext &C, CXXConstructorDecl *Cons,
- QualType writtenTy, SourceLocation tyBeginLoc,
+ TypeSourceInfo *Type,
Expr **Args,unsigned NumArgs,
- SourceLocation rParenLoc,
+ SourceRange parenRange,
bool ZeroInitialization = false);
explicit CXXTemporaryObjectExpr(EmptyShell Empty)
- : CXXConstructExpr(CXXTemporaryObjectExprClass, Empty) { }
+ : CXXConstructExpr(CXXTemporaryObjectExprClass, Empty), Type() { }
- SourceLocation getTypeBeginLoc() const { return TyBeginLoc; }
- SourceLocation getRParenLoc() const { return RParenLoc; }
+ TypeSourceInfo *getTypeSourceInfo() const { return Type; }
- virtual SourceRange getSourceRange() const {
- return SourceRange(TyBeginLoc, RParenLoc);
- }
+ SourceRange getSourceRange() const;
+
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXTemporaryObjectExprClass;
}
@@ -835,32 +978,31 @@ public:
/// T, which is a non-class type.
///
class CXXScalarValueInitExpr : public Expr {
- SourceLocation TyBeginLoc;
SourceLocation RParenLoc;
+ TypeSourceInfo *TypeInfo;
+ friend class ASTStmtReader;
+
public:
- CXXScalarValueInitExpr(QualType ty, SourceLocation tyBeginLoc,
- SourceLocation rParenLoc ) :
- Expr(CXXScalarValueInitExprClass, ty, false, false),
- TyBeginLoc(tyBeginLoc), RParenLoc(rParenLoc) {}
+ /// \brief Create an explicitly-written scalar-value initialization
+ /// expression.
+ CXXScalarValueInitExpr(QualType Type,
+ TypeSourceInfo *TypeInfo,
+ SourceLocation rParenLoc ) :
+ Expr(CXXScalarValueInitExprClass, Type, VK_RValue, OK_Ordinary,
+ false, false, false),
+ RParenLoc(rParenLoc), TypeInfo(TypeInfo) {}
+
explicit CXXScalarValueInitExpr(EmptyShell Shell)
: Expr(CXXScalarValueInitExprClass, Shell) { }
- SourceLocation getTypeBeginLoc() const { return TyBeginLoc; }
- SourceLocation getRParenLoc() const { return RParenLoc; }
-
- void setTypeBeginLoc(SourceLocation L) { TyBeginLoc = L; }
- void setRParenLoc(SourceLocation L) { RParenLoc = L; }
-
- /// @brief Whether this initialization expression was
- /// implicitly-generated.
- bool isImplicit() const {
- return TyBeginLoc.isInvalid() && RParenLoc.isInvalid();
+ TypeSourceInfo *getTypeSourceInfo() const {
+ return TypeInfo;
}
+
+ SourceLocation getRParenLoc() const { return RParenLoc; }
- virtual SourceRange getSourceRange() const {
- return SourceRange(TyBeginLoc, RParenLoc);
- }
+ SourceRange getSourceRange() const;
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXScalarValueInitExprClass;
@@ -868,8 +1010,7 @@ public:
static bool classof(const CXXScalarValueInitExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
};
/// CXXNewExpr - A new expression for memory allocation and constructor calls,
@@ -882,8 +1023,11 @@ class CXXNewExpr : public Expr {
bool Initializer : 1;
// Do we allocate an array? If so, the first SubExpr is the size expression.
bool Array : 1;
+ // If this is an array allocation, does the usual deallocation
+ // function for the allocated type want to know the allocated size?
+ bool UsualArrayDeleteWantsSize : 1;
// The number of placement new arguments.
- unsigned NumPlacementArgs : 15;
+ unsigned NumPlacementArgs : 14;
// The number of constructor arguments. This may be 1 even for non-class
// types; use the pseudo copy constructor.
unsigned NumConstructorArgs : 14;
@@ -900,12 +1044,17 @@ class CXXNewExpr : public Expr {
// Must be null for all other types.
CXXConstructorDecl *Constructor;
+ /// \brief The allocated type-source information, as written in the source.
+ TypeSourceInfo *AllocatedTypeInfo;
+
/// \brief If the allocated type was expressed as a parenthesized type-id,
/// the source range covering the parenthesized type-id.
SourceRange TypeIdParens;
SourceLocation StartLoc;
SourceLocation EndLoc;
+ SourceLocation ConstructorLParen;
+ SourceLocation ConstructorRParen;
friend class ASTStmtReader;
public:
@@ -914,8 +1063,11 @@ public:
SourceRange TypeIdParens,
Expr *arraySize, CXXConstructorDecl *constructor, bool initializer,
Expr **constructorArgs, unsigned numConsArgs,
- FunctionDecl *operatorDelete, QualType ty,
- SourceLocation startLoc, SourceLocation endLoc);
+ FunctionDecl *operatorDelete, bool usualArrayDeleteWantsSize,
+ QualType ty, TypeSourceInfo *AllocatedTypeInfo,
+ SourceLocation startLoc, SourceLocation endLoc,
+ SourceLocation constructorLParen,
+ SourceLocation constructorRParen);
explicit CXXNewExpr(EmptyShell Shell)
: Expr(CXXNewExprClass, Shell), SubExprs(0) { }
@@ -927,6 +1079,10 @@ public:
return getType()->getAs<PointerType>()->getPointeeType();
}
+ TypeSourceInfo *getAllocatedTypeSourceInfo() const {
+ return AllocatedTypeInfo;
+ }
+
FunctionDecl *getOperatorNew() const { return OperatorNew; }
void setOperatorNew(FunctionDecl *D) { OperatorNew = D; }
FunctionDecl *getOperatorDelete() const { return OperatorDelete; }
@@ -943,6 +1099,10 @@ public:
}
unsigned getNumPlacementArgs() const { return NumPlacementArgs; }
+ Expr **getPlacementArgs() {
+ return reinterpret_cast<Expr **>(SubExprs + Array);
+ }
+
Expr *getPlacementArg(unsigned i) {
assert(i < NumPlacementArgs && "Index out of range");
return cast<Expr>(SubExprs[Array + i]);
@@ -956,11 +1116,21 @@ public:
SourceRange getTypeIdParens() const { return TypeIdParens; }
bool isGlobalNew() const { return GlobalNew; }
- void setGlobalNew(bool V) { GlobalNew = V; }
bool hasInitializer() const { return Initializer; }
- void setHasInitializer(bool V) { Initializer = V; }
+
+ /// Answers whether the usual array deallocation function for the
+ /// allocated type expects the size of the allocation as a
+ /// parameter.
+ bool doesUsualArrayDeleteWantSize() const {
+ return UsualArrayDeleteWantsSize;
+ }
unsigned getNumConstructorArgs() const { return NumConstructorArgs; }
+
+ Expr **getConstructorArgs() {
+ return reinterpret_cast<Expr **>(SubExprs + Array + NumPlacementArgs);
+ }
+
Expr *getConstructorArg(unsigned i) {
assert(i < NumConstructorArgs && "Index out of range");
return cast<Expr>(SubExprs[Array + NumPlacementArgs + i]);
@@ -1007,13 +1177,13 @@ public:
const_arg_iterator raw_arg_begin() const { return SubExprs; }
const_arg_iterator raw_arg_end() const { return constructor_arg_end(); }
-
SourceLocation getStartLoc() const { return StartLoc; }
- void setStartLoc(SourceLocation L) { StartLoc = L; }
SourceLocation getEndLoc() const { return EndLoc; }
- void setEndLoc(SourceLocation L) { EndLoc = L; }
-
- virtual SourceRange getSourceRange() const {
+
+ SourceLocation getConstructorLParen() const { return ConstructorLParen; }
+ SourceLocation getConstructorRParen() const { return ConstructorRParen; }
+
+ SourceRange getSourceRange() const {
return SourceRange(StartLoc, EndLoc);
}
@@ -1023,8 +1193,11 @@ public:
static bool classof(const CXXNewExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ return child_range(&SubExprs[0],
+ &SubExprs[0] + Array + getNumPlacementArgs()
+ + getNumConstructorArgs());
+ }
};
/// CXXDeleteExpr - A delete expression for memory deallocation and destructor
@@ -1034,6 +1207,13 @@ class CXXDeleteExpr : public Expr {
bool GlobalDelete : 1;
// Is this the array form of delete, i.e. "delete[]"?
bool ArrayForm : 1;
+ // ArrayFormAsWritten can be different from ArrayForm if 'delete' is applied
+ // to pointer-to-array type (ArrayFormAsWritten will be false while ArrayForm
+ // will be true).
+ bool ArrayFormAsWritten : 1;
+ // Does the usual deallocation function for the element type require
+ // a size_t argument?
+ bool UsualArrayDeleteWantsSize : 1;
// Points to the operator delete overload that is used. Could be a member.
FunctionDecl *OperatorDelete;
// The pointer expression to be deleted.
@@ -1042,30 +1222,42 @@ class CXXDeleteExpr : public Expr {
SourceLocation Loc;
public:
CXXDeleteExpr(QualType ty, bool globalDelete, bool arrayForm,
+ bool arrayFormAsWritten, bool usualArrayDeleteWantsSize,
FunctionDecl *operatorDelete, Expr *arg, SourceLocation loc)
- : Expr(CXXDeleteExprClass, ty, false, false), GlobalDelete(globalDelete),
- ArrayForm(arrayForm), OperatorDelete(operatorDelete), Argument(arg),
- Loc(loc) { }
+ : Expr(CXXDeleteExprClass, ty, VK_RValue, OK_Ordinary, false, false,
+ arg->containsUnexpandedParameterPack()),
+ GlobalDelete(globalDelete),
+ ArrayForm(arrayForm), ArrayFormAsWritten(arrayFormAsWritten),
+ UsualArrayDeleteWantsSize(usualArrayDeleteWantsSize),
+ OperatorDelete(operatorDelete), Argument(arg), Loc(loc) { }
explicit CXXDeleteExpr(EmptyShell Shell)
: Expr(CXXDeleteExprClass, Shell), OperatorDelete(0), Argument(0) { }
bool isGlobalDelete() const { return GlobalDelete; }
bool isArrayForm() const { return ArrayForm; }
-
- void setGlobalDelete(bool V) { GlobalDelete = V; }
- void setArrayForm(bool V) { ArrayForm = V; }
+ bool isArrayFormAsWritten() const { return ArrayFormAsWritten; }
+
+ /// Answers whether the usual array deallocation function for the
+ /// allocated type expects the size of the allocation as a
+ /// parameter. This can be true even if the actual deallocation
+ /// function that we're using doesn't want a size.
+ bool doesUsualArrayDeleteWantSize() const {
+ return UsualArrayDeleteWantsSize;
+ }
FunctionDecl *getOperatorDelete() const { return OperatorDelete; }
- void setOperatorDelete(FunctionDecl *D) { OperatorDelete = D; }
Expr *getArgument() { return cast<Expr>(Argument); }
const Expr *getArgument() const { return cast<Expr>(Argument); }
- void setArgument(Expr *E) { Argument = E; }
- virtual SourceRange getSourceRange() const {
+ /// \brief Retrieve the type being destroyed. If the type being
+ /// destroyed is a dependent type which may or may not be a pointer,
+ /// return an invalid type.
+ QualType getDestroyedType() const;
+
+ SourceRange getSourceRange() const {
return SourceRange(Loc, Argument->getLocEnd());
}
- void setStartLoc(SourceLocation L) { Loc = L; }
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXDeleteExprClass;
@@ -1073,8 +1265,9 @@ public:
static bool classof(const CXXDeleteExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(&Argument, &Argument+1); }
+
+ friend class ASTStmtReader;
};
/// \brief Structure used to store the type being destroyed by a
@@ -1171,21 +1364,7 @@ public:
TypeSourceInfo *ScopeType,
SourceLocation ColonColonLoc,
SourceLocation TildeLoc,
- PseudoDestructorTypeStorage DestroyedType)
- : Expr(CXXPseudoDestructorExprClass,
- Context.getPointerType(Context.getFunctionType(Context.VoidTy, 0, 0,
- false, 0, false,
- false, 0, 0,
- FunctionType::ExtInfo())),
- /*isTypeDependent=*/(Base->isTypeDependent() ||
- (DestroyedType.getTypeSourceInfo() &&
- DestroyedType.getTypeSourceInfo()->getType()->isDependentType())),
- /*isValueDependent=*/Base->isValueDependent()),
- Base(static_cast<Stmt *>(Base)), IsArrow(isArrow),
- OperatorLoc(OperatorLoc), Qualifier(Qualifier),
- QualifierRange(QualifierRange),
- ScopeType(ScopeType), ColonColonLoc(ColonColonLoc), TildeLoc(TildeLoc),
- DestroyedType(DestroyedType) { }
+ PseudoDestructorTypeStorage DestroyedType);
explicit CXXPseudoDestructorExpr(EmptyShell Shell)
: Expr(CXXPseudoDestructorExprClass, Shell),
@@ -1278,7 +1457,7 @@ public:
DestroyedType = PseudoDestructorTypeStorage(Info);
}
- virtual SourceRange getSourceRange() const;
+ SourceRange getSourceRange() const;
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXPseudoDestructorExprClass;
@@ -1286,8 +1465,7 @@ public:
static bool classof(const CXXPseudoDestructorExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(&Base, &Base + 1); }
};
/// UnaryTypeTraitExpr - A GCC or MS unary type trait, as used in the
@@ -1296,8 +1474,10 @@ public:
/// __is_pod(int) == true
/// __is_enum(std::string) == false
class UnaryTypeTraitExpr : public Expr {
- /// UTT - The trait.
- UnaryTypeTrait UTT;
+ /// UTT - The trait. A UnaryTypeTrait enum in MSVC compat unsigned.
+ unsigned UTT : 31;
+ /// The value of the type trait. Unspecified if dependent.
+ bool Value : 1;
/// Loc - The location of the type trait keyword.
SourceLocation Loc;
@@ -1305,25 +1485,31 @@ class UnaryTypeTraitExpr : public Expr {
/// RParen - The location of the closing paren.
SourceLocation RParen;
- /// QueriedType - The type we're testing.
- QualType QueriedType;
+ /// The type being queried.
+ TypeSourceInfo *QueriedType;
public:
- UnaryTypeTraitExpr(SourceLocation loc, UnaryTypeTrait utt, QualType queried,
+ UnaryTypeTraitExpr(SourceLocation loc, UnaryTypeTrait utt,
+ TypeSourceInfo *queried, bool value,
SourceLocation rparen, QualType ty)
- : Expr(UnaryTypeTraitExprClass, ty, false, queried->isDependentType()),
- UTT(utt), Loc(loc), RParen(rparen), QueriedType(queried) { }
+ : Expr(UnaryTypeTraitExprClass, ty, VK_RValue, OK_Ordinary,
+ false, queried->getType()->isDependentType(),
+ queried->getType()->containsUnexpandedParameterPack()),
+ UTT(utt), Value(value), Loc(loc), RParen(rparen), QueriedType(queried) { }
explicit UnaryTypeTraitExpr(EmptyShell Empty)
- : Expr(UnaryTypeTraitExprClass, Empty), UTT((UnaryTypeTrait)0) { }
+ : Expr(UnaryTypeTraitExprClass, Empty), UTT(0), Value(false),
+ QueriedType() { }
- virtual SourceRange getSourceRange() const { return SourceRange(Loc, RParen);}
+ SourceRange getSourceRange() const { return SourceRange(Loc, RParen);}
- UnaryTypeTrait getTrait() const { return UTT; }
+ UnaryTypeTrait getTrait() const { return static_cast<UnaryTypeTrait>(UTT); }
- QualType getQueriedType() const { return QueriedType; }
+ QualType getQueriedType() const { return QueriedType->getType(); }
- bool EvaluateTrait(ASTContext&) const;
+ TypeSourceInfo *getQueriedTypeSourceInfo() const { return QueriedType; }
+
+ bool getValue() const { return Value; }
static bool classof(const Stmt *T) {
return T->getStmtClass() == UnaryTypeTraitExprClass;
@@ -1331,8 +1517,74 @@ public:
static bool classof(const UnaryTypeTraitExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(); }
+
+ friend class ASTStmtReader;
+};
+
+/// BinaryTypeTraitExpr - A GCC or MS binary type trait, as used in the
+/// implementation of TR1/C++0x type trait templates.
+/// Example:
+/// __is_base_of(Base, Derived) == true
+class BinaryTypeTraitExpr : public Expr {
+ /// BTT - The trait. A BinaryTypeTrait enum in MSVC compat unsigned.
+ unsigned BTT : 8;
+
+ /// The value of the type trait. Unspecified if dependent.
+ bool Value : 1;
+
+ /// Loc - The location of the type trait keyword.
+ SourceLocation Loc;
+
+ /// RParen - The location of the closing paren.
+ SourceLocation RParen;
+
+ /// The lhs type being queried.
+ TypeSourceInfo *LhsType;
+
+ /// The rhs type being queried.
+ TypeSourceInfo *RhsType;
+
+public:
+ BinaryTypeTraitExpr(SourceLocation loc, BinaryTypeTrait btt,
+ TypeSourceInfo *lhsType, TypeSourceInfo *rhsType,
+ bool value, SourceLocation rparen, QualType ty)
+ : Expr(BinaryTypeTraitExprClass, ty, VK_RValue, OK_Ordinary, false,
+ lhsType->getType()->isDependentType() ||
+ rhsType->getType()->isDependentType(),
+ (lhsType->getType()->containsUnexpandedParameterPack() ||
+ rhsType->getType()->containsUnexpandedParameterPack())),
+ BTT(btt), Value(value), Loc(loc), RParen(rparen),
+ LhsType(lhsType), RhsType(rhsType) { }
+
+
+ explicit BinaryTypeTraitExpr(EmptyShell Empty)
+ : Expr(BinaryTypeTraitExprClass, Empty), BTT(0), Value(false),
+ LhsType(), RhsType() { }
+
+ SourceRange getSourceRange() const {
+ return SourceRange(Loc, RParen);
+ }
+
+ BinaryTypeTrait getTrait() const {
+ return static_cast<BinaryTypeTrait>(BTT);
+ }
+
+ QualType getLhsType() const { return LhsType->getType(); }
+ QualType getRhsType() const { return RhsType->getType(); }
+
+ TypeSourceInfo *getLhsTypeSourceInfo() const { return LhsType; }
+ TypeSourceInfo *getRhsTypeSourceInfo() const { return RhsType; }
+
+ bool getValue() const { assert(!isTypeDependent()); return Value; }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == BinaryTypeTraitExprClass;
+ }
+ static bool classof(const BinaryTypeTraitExpr *) { return true; }
+
+ // Iterators
+ child_range children() { return child_range(); }
friend class ASTStmtReader;
};
@@ -1360,23 +1612,23 @@ protected:
/// True if the name was a template-id.
bool HasExplicitTemplateArgs;
- OverloadExpr(StmtClass K, ASTContext &C, QualType T, bool Dependent,
+ OverloadExpr(StmtClass K, ASTContext &C,
NestedNameSpecifier *Qualifier, SourceRange QRange,
const DeclarationNameInfo &NameInfo,
- bool HasTemplateArgs,
- UnresolvedSetIterator Begin, UnresolvedSetIterator End);
+ const TemplateArgumentListInfo *TemplateArgs,
+ UnresolvedSetIterator Begin, UnresolvedSetIterator End,
+ bool KnownDependent = false,
+ bool KnownContainsUnexpandedParameterPack = false);
OverloadExpr(StmtClass K, EmptyShell Empty)
: Expr(K, Empty), Results(0), NumResults(0),
Qualifier(0), HasExplicitTemplateArgs(false) { }
-public:
- /// Computes whether an unresolved lookup on the given declarations
- /// and optional template arguments is type- and value-dependent.
- static bool ComputeDependence(UnresolvedSetIterator Begin,
- UnresolvedSetIterator End,
- const TemplateArgumentListInfo *Args);
+ void initializeResults(ASTContext &C,
+ UnresolvedSetIterator Begin,
+ UnresolvedSetIterator End);
+public:
struct FindResult {
OverloadExpr *Expression;
bool IsAddressOfOperand;
@@ -1420,9 +1672,6 @@ public:
return UnresolvedSetIterator(Results + NumResults);
}
- void initializeResults(ASTContext &C,
- UnresolvedSetIterator Begin,UnresolvedSetIterator End);
-
/// Gets the number of declarations in the unresolved set.
unsigned getNumDecls() const { return NumResults; }
@@ -1469,6 +1718,9 @@ public:
T->getStmtClass() == UnresolvedMemberExprClass;
}
static bool classof(const OverloadExpr *) { return true; }
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
};
/// \brief A reference to a name which we were able to look up during
@@ -1498,14 +1750,15 @@ class UnresolvedLookupExpr : public OverloadExpr {
/// against the qualified-lookup bits.
CXXRecordDecl *NamingClass;
- UnresolvedLookupExpr(ASTContext &C, QualType T, bool Dependent,
+ UnresolvedLookupExpr(ASTContext &C,
CXXRecordDecl *NamingClass,
NestedNameSpecifier *Qualifier, SourceRange QRange,
const DeclarationNameInfo &NameInfo,
- bool RequiresADL, bool Overloaded, bool HasTemplateArgs,
+ bool RequiresADL, bool Overloaded,
+ const TemplateArgumentListInfo *TemplateArgs,
UnresolvedSetIterator Begin, UnresolvedSetIterator End)
- : OverloadExpr(UnresolvedLookupExprClass, C, T, Dependent, Qualifier,
- QRange, NameInfo, HasTemplateArgs, Begin, End),
+ : OverloadExpr(UnresolvedLookupExprClass, C, Qualifier, QRange, NameInfo,
+ TemplateArgs, Begin, End),
RequiresADL(RequiresADL), Overloaded(Overloaded), NamingClass(NamingClass)
{}
@@ -1516,7 +1769,6 @@ class UnresolvedLookupExpr : public OverloadExpr {
public:
static UnresolvedLookupExpr *Create(ASTContext &C,
- bool Dependent,
CXXRecordDecl *NamingClass,
NestedNameSpecifier *Qualifier,
SourceRange QualifierRange,
@@ -1524,16 +1776,12 @@ public:
bool ADL, bool Overloaded,
UnresolvedSetIterator Begin,
UnresolvedSetIterator End) {
- return new(C) UnresolvedLookupExpr(C,
- Dependent ? C.DependentTy : C.OverloadTy,
- Dependent, NamingClass,
- Qualifier, QualifierRange, NameInfo,
- ADL, Overloaded, false,
- Begin, End);
+ return new(C) UnresolvedLookupExpr(C, NamingClass, Qualifier,
+ QualifierRange, NameInfo, ADL,
+ Overloaded, 0, Begin, End);
}
static UnresolvedLookupExpr *Create(ASTContext &C,
- bool Dependent,
CXXRecordDecl *NamingClass,
NestedNameSpecifier *Qualifier,
SourceRange QualifierRange,
@@ -1544,6 +1792,7 @@ public:
UnresolvedSetIterator End);
static UnresolvedLookupExpr *CreateEmpty(ASTContext &C,
+ bool HasExplicitTemplateArgs,
unsigned NumTemplateArgs);
/// True if this declaration should be extended by
@@ -1606,15 +1855,14 @@ public:
return getExplicitTemplateArgs().NumTemplateArgs;
}
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
SourceRange Range(getNameInfo().getSourceRange());
if (getQualifier()) Range.setBegin(getQualifierRange().getBegin());
if (hasExplicitTemplateArgs()) Range.setEnd(getRAngleLoc());
return Range;
}
- virtual StmtIterator child_begin();
- virtual StmtIterator child_end();
+ child_range children() { return child_range(); }
static bool classof(const Stmt *T) {
return T->getStmtClass() == UnresolvedLookupExprClass;
@@ -1655,11 +1903,7 @@ class DependentScopeDeclRefExpr : public Expr {
NestedNameSpecifier *Qualifier,
SourceRange QualifierRange,
const DeclarationNameInfo &NameInfo,
- bool HasExplicitTemplateArgs)
- : Expr(DependentScopeDeclRefExprClass, T, true, true),
- NameInfo(NameInfo), QualifierRange(QualifierRange), Qualifier(Qualifier),
- HasExplicitTemplateArgs(HasExplicitTemplateArgs)
- {}
+ const TemplateArgumentListInfo *Args);
public:
static DependentScopeDeclRefExpr *Create(ASTContext &C,
@@ -1669,6 +1913,7 @@ public:
const TemplateArgumentListInfo *TemplateArgs = 0);
static DependentScopeDeclRefExpr *CreateEmpty(ASTContext &C,
+ bool HasExplicitTemplateArgs,
unsigned NumTemplateArgs);
/// \brief Retrieve the name that this expression refers to.
@@ -1740,7 +1985,7 @@ public:
return getExplicitTemplateArgs().NumTemplateArgs;
}
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
SourceRange Range(QualifierRange.getBegin(), getLocation());
if (hasExplicitTemplateArgs())
Range.setEnd(getRAngleLoc());
@@ -1752,25 +1997,32 @@ public:
}
static bool classof(const DependentScopeDeclRefExpr *) { return true; }
- virtual StmtIterator child_begin();
- virtual StmtIterator child_end();
+ child_range children() { return child_range(); }
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
};
-class CXXExprWithTemporaries : public Expr {
+/// Represents an expression --- generally a full-expression --- which
+/// introduces cleanups to be run at the end of the sub-expression's
+/// evaluation. The most common source of expression-introduced
+/// cleanups is temporary objects in C++, but several other C++
+/// expressions can create cleanups.
+class ExprWithCleanups : public Expr {
Stmt *SubExpr;
CXXTemporary **Temps;
unsigned NumTemps;
- CXXExprWithTemporaries(ASTContext &C, Expr *SubExpr, CXXTemporary **Temps,
- unsigned NumTemps);
-
+ ExprWithCleanups(ASTContext &C, Expr *SubExpr,
+ CXXTemporary **Temps, unsigned NumTemps);
+
public:
- CXXExprWithTemporaries(EmptyShell Empty)
- : Expr(CXXExprWithTemporariesClass, Empty),
+ ExprWithCleanups(EmptyShell Empty)
+ : Expr(ExprWithCleanupsClass, Empty),
SubExpr(0), Temps(0), NumTemps(0) {}
- static CXXExprWithTemporaries *Create(ASTContext &C, Expr *SubExpr,
+ static ExprWithCleanups *Create(ASTContext &C, Expr *SubExpr,
CXXTemporary **Temps,
unsigned NumTemps);
@@ -1782,7 +2034,7 @@ public:
return Temps[i];
}
const CXXTemporary *getTemporary(unsigned i) const {
- return const_cast<CXXExprWithTemporaries*>(this)->getTemporary(i);
+ return const_cast<ExprWithCleanups*>(this)->getTemporary(i);
}
void setTemporary(unsigned i, CXXTemporary *T) {
assert(i < NumTemps && "Index out of range");
@@ -1793,19 +2045,18 @@ public:
const Expr *getSubExpr() const { return cast<Expr>(SubExpr); }
void setSubExpr(Expr *E) { SubExpr = E; }
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
return SubExpr->getSourceRange();
}
// Implement isa/cast/dyncast/etc.
static bool classof(const Stmt *T) {
- return T->getStmtClass() == CXXExprWithTemporariesClass;
+ return T->getStmtClass() == ExprWithCleanupsClass;
}
- static bool classof(const CXXExprWithTemporaries *) { return true; }
+ static bool classof(const ExprWithCleanups *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() { return child_range(&SubExpr, &SubExpr + 1); }
};
/// \brief Describes an explicit type conversion that uses functional
@@ -1830,12 +2081,9 @@ public:
/// constructor call, conversion function call, or some kind of type
/// conversion.
class CXXUnresolvedConstructExpr : public Expr {
- /// \brief The starting location of the type
- SourceLocation TyBeginLoc;
-
/// \brief The type being constructed.
- QualType Type;
-
+ TypeSourceInfo *Type;
+
/// \brief The location of the left parentheses ('(').
SourceLocation LParenLoc;
@@ -1845,20 +2093,20 @@ class CXXUnresolvedConstructExpr : public Expr {
/// \brief The number of arguments used to construct the type.
unsigned NumArgs;
- CXXUnresolvedConstructExpr(SourceLocation TyBegin,
- QualType T,
+ CXXUnresolvedConstructExpr(TypeSourceInfo *Type,
SourceLocation LParenLoc,
Expr **Args,
unsigned NumArgs,
SourceLocation RParenLoc);
CXXUnresolvedConstructExpr(EmptyShell Empty, unsigned NumArgs)
- : Expr(CXXUnresolvedConstructExprClass, Empty), NumArgs(NumArgs) { }
+ : Expr(CXXUnresolvedConstructExprClass, Empty), Type(), NumArgs(NumArgs) { }
+ friend class ASTStmtReader;
+
public:
static CXXUnresolvedConstructExpr *Create(ASTContext &C,
- SourceLocation TyBegin,
- QualType T,
+ TypeSourceInfo *Type,
SourceLocation LParenLoc,
Expr **Args,
unsigned NumArgs,
@@ -1867,15 +2115,14 @@ public:
static CXXUnresolvedConstructExpr *CreateEmpty(ASTContext &C,
unsigned NumArgs);
- /// \brief Retrieve the source location where the type begins.
- SourceLocation getTypeBeginLoc() const { return TyBeginLoc; }
- void setTypeBeginLoc(SourceLocation L) { TyBeginLoc = L; }
-
/// \brief Retrieve the type that is being constructed, as specified
/// in the source code.
- QualType getTypeAsWritten() const { return Type; }
- void setTypeAsWritten(QualType T) { Type = T; }
+ QualType getTypeAsWritten() const { return Type->getType(); }
+ /// \brief Retrieve the type source information for the type being
+ /// constructed.
+ TypeSourceInfo *getTypeSourceInfo() const { return Type; }
+
/// \brief Retrieve the location of the left parentheses ('(') that
/// precedes the argument list.
SourceLocation getLParenLoc() const { return LParenLoc; }
@@ -1916,17 +2163,18 @@ public:
*(arg_begin() + I) = E;
}
- virtual SourceRange getSourceRange() const {
- return SourceRange(TyBeginLoc, RParenLoc);
- }
+ SourceRange getSourceRange() const;
+
static bool classof(const Stmt *T) {
return T->getStmtClass() == CXXUnresolvedConstructExprClass;
}
static bool classof(const CXXUnresolvedConstructExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ Stmt **begin = reinterpret_cast<Stmt**>(this+1);
+ return child_range(begin, begin + NumArgs);
+ }
};
/// \brief Represents a C++ member access expression where the actual
@@ -1987,19 +2235,13 @@ class CXXDependentScopeMemberExpr : public Expr {
public:
CXXDependentScopeMemberExpr(ASTContext &C,
- Expr *Base, QualType BaseType,
- bool IsArrow,
- SourceLocation OperatorLoc,
- NestedNameSpecifier *Qualifier,
- SourceRange QualifierRange,
- NamedDecl *FirstQualifierFoundInScope,
- DeclarationNameInfo MemberNameInfo)
- : Expr(CXXDependentScopeMemberExprClass, C.DependentTy, true, true),
- Base(Base), BaseType(BaseType), IsArrow(IsArrow),
- HasExplicitTemplateArgs(false), OperatorLoc(OperatorLoc),
- Qualifier(Qualifier), QualifierRange(QualifierRange),
- FirstQualifierFoundInScope(FirstQualifierFoundInScope),
- MemberNameInfo(MemberNameInfo) { }
+ Expr *Base, QualType BaseType,
+ bool IsArrow,
+ SourceLocation OperatorLoc,
+ NestedNameSpecifier *Qualifier,
+ SourceRange QualifierRange,
+ NamedDecl *FirstQualifierFoundInScope,
+ DeclarationNameInfo MemberNameInfo);
static CXXDependentScopeMemberExpr *
Create(ASTContext &C,
@@ -2012,7 +2254,8 @@ public:
const TemplateArgumentListInfo *TemplateArgs);
static CXXDependentScopeMemberExpr *
- CreateEmpty(ASTContext &C, unsigned NumTemplateArgs);
+ CreateEmpty(ASTContext &C, bool HasExplicitTemplateArgs,
+ unsigned NumTemplateArgs);
/// \brief True if this is an implicit access, i.e. one in which the
/// member being accessed was not written in the source. The source
@@ -2147,7 +2390,7 @@ public:
return getExplicitTemplateArgs().RAngleLoc;
}
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
SourceRange Range;
if (!isImplicitAccess())
Range.setBegin(Base->getSourceRange().getBegin());
@@ -2169,8 +2412,13 @@ public:
static bool classof(const CXXDependentScopeMemberExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ if (isImplicitAccess()) return child_range();
+ return child_range(&Base, &Base + 1);
+ }
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
};
/// \brief Represents a C++ member access expression for which lookup
@@ -2206,8 +2454,7 @@ class UnresolvedMemberExpr : public OverloadExpr {
/// \brief The location of the '->' or '.' operator.
SourceLocation OperatorLoc;
- UnresolvedMemberExpr(ASTContext &C, QualType T, bool Dependent,
- bool HasUnresolvedUsing,
+ UnresolvedMemberExpr(ASTContext &C, bool HasUnresolvedUsing,
Expr *Base, QualType BaseType, bool IsArrow,
SourceLocation OperatorLoc,
NestedNameSpecifier *Qualifier,
@@ -2222,7 +2469,7 @@ class UnresolvedMemberExpr : public OverloadExpr {
public:
static UnresolvedMemberExpr *
- Create(ASTContext &C, bool Dependent, bool HasUnresolvedUsing,
+ Create(ASTContext &C, bool HasUnresolvedUsing,
Expr *Base, QualType BaseType, bool IsArrow,
SourceLocation OperatorLoc,
NestedNameSpecifier *Qualifier,
@@ -2232,7 +2479,8 @@ public:
UnresolvedSetIterator Begin, UnresolvedSetIterator End);
static UnresolvedMemberExpr *
- CreateEmpty(ASTContext &C, unsigned NumTemplateArgs);
+ CreateEmpty(ASTContext &C, bool HasExplicitTemplateArgs,
+ unsigned NumTemplateArgs);
/// \brief True if this is an implicit access, i.e. one in which the
/// member being accessed was not written in the source. The source
@@ -2337,7 +2585,7 @@ public:
return getExplicitTemplateArgs().RAngleLoc;
}
- virtual SourceRange getSourceRange() const {
+ SourceRange getSourceRange() const {
SourceRange Range = getMemberNameInfo().getSourceRange();
if (!isImplicitAccess())
Range.setBegin(Base->getSourceRange().getBegin());
@@ -2355,10 +2603,130 @@ public:
static bool classof(const UnresolvedMemberExpr *) { return true; }
// Iterators
- virtual child_iterator child_begin();
- virtual child_iterator child_end();
+ child_range children() {
+ if (isImplicitAccess()) return child_range();
+ return child_range(&Base, &Base + 1);
+ }
+};
+
+/// \brief Represents a C++0x noexcept expression (C++ [expr.unary.noexcept]).
+///
+/// The noexcept expression tests whether a given expression might throw. Its
+/// result is a boolean constant.
+class CXXNoexceptExpr : public Expr {
+ bool Value : 1;
+ Stmt *Operand;
+ SourceRange Range;
+
+ friend class ASTStmtReader;
+
+public:
+ CXXNoexceptExpr(QualType Ty, Expr *Operand, CanThrowResult Val,
+ SourceLocation Keyword, SourceLocation RParen)
+ : Expr(CXXNoexceptExprClass, Ty, VK_RValue, OK_Ordinary,
+ /*TypeDependent*/false,
+ /*ValueDependent*/Val == CT_Dependent,
+ Operand->containsUnexpandedParameterPack()),
+ Value(Val == CT_Cannot), Operand(Operand), Range(Keyword, RParen)
+ { }
+
+ CXXNoexceptExpr(EmptyShell Empty)
+ : Expr(CXXNoexceptExprClass, Empty)
+ { }
+
+ Expr *getOperand() const { return static_cast<Expr*>(Operand); }
+
+ SourceRange getSourceRange() const { return Range; }
+
+ bool getValue() const { return Value; }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == CXXNoexceptExprClass;
+ }
+ static bool classof(const CXXNoexceptExpr *) { return true; }
+
+ // Iterators
+ child_range children() { return child_range(&Operand, &Operand + 1); }
};
+/// \brief Represents a C++0x pack expansion that produces a sequence of
+/// expressions.
+///
+/// A pack expansion expression contains a pattern (which itself is an
+/// expression) followed by an ellipsis. For example:
+///
+/// \code
+/// template<typename F, typename ...Types>
+/// void forward(F f, Types &&...args) {
+/// f(static_cast<Types&&>(args)...);
+/// }
+/// \endcode
+///
+/// Here, the argument to the function object \c f is a pack expansion whose
+/// pattern is \c static_cast<Types&&>(args). When the \c forward function
+/// template is instantiated, the pack expansion will instantiate to zero or
+/// or more function arguments to the function object \c f.
+class PackExpansionExpr : public Expr {
+ SourceLocation EllipsisLoc;
+
+ /// \brief The number of expansions that will be produced by this pack
+ /// expansion expression, if known.
+ ///
+ /// When zero, the number of expansions is not known. Otherwise, this value
+ /// is the number of expansions + 1.
+ unsigned NumExpansions;
+
+ Stmt *Pattern;
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
+
+public:
+ PackExpansionExpr(QualType T, Expr *Pattern, SourceLocation EllipsisLoc,
+ llvm::Optional<unsigned> NumExpansions)
+ : Expr(PackExpansionExprClass, T, Pattern->getValueKind(),
+ Pattern->getObjectKind(), /*TypeDependent=*/true,
+ /*ValueDependent=*/true, /*ContainsUnexpandedParameterPack=*/false),
+ EllipsisLoc(EllipsisLoc),
+ NumExpansions(NumExpansions? *NumExpansions + 1 : 0),
+ Pattern(Pattern) { }
+
+ PackExpansionExpr(EmptyShell Empty) : Expr(PackExpansionExprClass, Empty) { }
+
+ /// \brief Retrieve the pattern of the pack expansion.
+ Expr *getPattern() { return reinterpret_cast<Expr *>(Pattern); }
+
+ /// \brief Retrieve the pattern of the pack expansion.
+ const Expr *getPattern() const { return reinterpret_cast<Expr *>(Pattern); }
+
+ /// \brief Retrieve the location of the ellipsis that describes this pack
+ /// expansion.
+ SourceLocation getEllipsisLoc() const { return EllipsisLoc; }
+
+ /// \brief Determine the number of expansions that will be produced when
+ /// this pack expansion is instantiated, if already known.
+ llvm::Optional<unsigned> getNumExpansions() const {
+ if (NumExpansions)
+ return NumExpansions - 1;
+
+ return llvm::Optional<unsigned>();
+ }
+
+ SourceRange getSourceRange() const {
+ return SourceRange(Pattern->getLocStart(), EllipsisLoc);
+ }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == PackExpansionExprClass;
+ }
+ static bool classof(const PackExpansionExpr *) { return true; }
+
+ // Iterators
+ child_range children() {
+ return child_range(&Pattern, &Pattern + 1);
+ }
+};
+
inline ExplicitTemplateArgumentList &OverloadExpr::getExplicitTemplateArgs() {
if (isa<UnresolvedLookupExpr>(this))
return cast<UnresolvedLookupExpr>(this)->getExplicitTemplateArgs();
@@ -2366,6 +2734,159 @@ inline ExplicitTemplateArgumentList &OverloadExpr::getExplicitTemplateArgs() {
return cast<UnresolvedMemberExpr>(this)->getExplicitTemplateArgs();
}
+/// \brief Represents an expression that computes the length of a parameter
+/// pack.
+///
+/// \code
+/// template<typename ...Types>
+/// struct count {
+/// static const unsigned value = sizeof...(Types);
+/// };
+/// \endcode
+class SizeOfPackExpr : public Expr {
+ /// \brief The location of the 'sizeof' keyword.
+ SourceLocation OperatorLoc;
+
+ /// \brief The location of the name of the parameter pack.
+ SourceLocation PackLoc;
+
+ /// \brief The location of the closing parenthesis.
+ SourceLocation RParenLoc;
+
+ /// \brief The length of the parameter pack, if known.
+ ///
+ /// When this expression is value-dependent, the length of the parameter pack
+ /// is unknown. When this expression is not value-dependent, the length is
+ /// known.
+ unsigned Length;
+
+ /// \brief The parameter pack itself.
+ NamedDecl *Pack;
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
+
+public:
+ /// \brief Creates a value-dependent expression that computes the length of
+ /// the given parameter pack.
+ SizeOfPackExpr(QualType SizeType, SourceLocation OperatorLoc, NamedDecl *Pack,
+ SourceLocation PackLoc, SourceLocation RParenLoc)
+ : Expr(SizeOfPackExprClass, SizeType, VK_RValue, OK_Ordinary,
+ /*TypeDependent=*/false, /*ValueDependent=*/true,
+ /*ContainsUnexpandedParameterPack=*/false),
+ OperatorLoc(OperatorLoc), PackLoc(PackLoc), RParenLoc(RParenLoc),
+ Length(0), Pack(Pack) { }
+
+ /// \brief Creates an expression that computes the length of
+ /// the given parameter pack, which is already known.
+ SizeOfPackExpr(QualType SizeType, SourceLocation OperatorLoc, NamedDecl *Pack,
+ SourceLocation PackLoc, SourceLocation RParenLoc,
+ unsigned Length)
+ : Expr(SizeOfPackExprClass, SizeType, VK_RValue, OK_Ordinary,
+ /*TypeDependent=*/false, /*ValueDependent=*/false,
+ /*ContainsUnexpandedParameterPack=*/false),
+ OperatorLoc(OperatorLoc), PackLoc(PackLoc), RParenLoc(RParenLoc),
+ Length(Length), Pack(Pack) { }
+
+ /// \brief Create an empty expression.
+ SizeOfPackExpr(EmptyShell Empty) : Expr(SizeOfPackExprClass, Empty) { }
+
+ /// \brief Determine the location of the 'sizeof' keyword.
+ SourceLocation getOperatorLoc() const { return OperatorLoc; }
+
+ /// \brief Determine the location of the parameter pack.
+ SourceLocation getPackLoc() const { return PackLoc; }
+
+ /// \brief Determine the location of the right parenthesis.
+ SourceLocation getRParenLoc() const { return RParenLoc; }
+
+ /// \brief Retrieve the parameter pack.
+ NamedDecl *getPack() const { return Pack; }
+
+ /// \brief Retrieve the length of the parameter pack.
+ ///
+ /// This routine may only be invoked when the expression is not
+ /// value-dependent.
+ unsigned getPackLength() const {
+ assert(!isValueDependent() &&
+ "Cannot get the length of a value-dependent pack size expression");
+ return Length;
+ }
+
+ SourceRange getSourceRange() const {
+ return SourceRange(OperatorLoc, RParenLoc);
+ }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == SizeOfPackExprClass;
+ }
+ static bool classof(const SizeOfPackExpr *) { return true; }
+
+ // Iterators
+ child_range children() { return child_range(); }
+};
+
+/// \brief Represents a reference to a non-type template parameter pack that
+/// has been substituted with a non-template argument pack.
+///
+/// When a pack expansion in the source code contains multiple parameter packs
+/// and those parameter packs correspond to different levels of template
+/// parameter lists, this node node is used to represent a non-type template
+/// parameter pack from an outer level, which has already had its argument pack
+/// substituted but that still lives within a pack expansion that itself
+/// could not be instantiated. When actually performing a substitution into
+/// that pack expansion (e.g., when all template parameters have corresponding
+/// arguments), this type will be replaced with the appropriate underlying
+/// expression at the current pack substitution index.
+class SubstNonTypeTemplateParmPackExpr : public Expr {
+ /// \brief The non-type template parameter pack itself.
+ NonTypeTemplateParmDecl *Param;
+
+ /// \brief A pointer to the set of template arguments that this
+ /// parameter pack is instantiated with.
+ const TemplateArgument *Arguments;
+
+ /// \brief The number of template arguments in \c Arguments.
+ unsigned NumArguments;
+
+ /// \brief The location of the non-type template parameter pack reference.
+ SourceLocation NameLoc;
+
+ friend class ASTStmtReader;
+ friend class ASTStmtWriter;
+
+public:
+ SubstNonTypeTemplateParmPackExpr(QualType T,
+ NonTypeTemplateParmDecl *Param,
+ SourceLocation NameLoc,
+ const TemplateArgument &ArgPack);
+
+ SubstNonTypeTemplateParmPackExpr(EmptyShell Empty)
+ : Expr(SubstNonTypeTemplateParmPackExprClass, Empty) { }
+
+ /// \brief Retrieve the non-type template parameter pack being substituted.
+ NonTypeTemplateParmDecl *getParameterPack() const { return Param; }
+
+ /// \brief Retrieve the location of the parameter pack name.
+ SourceLocation getParameterPackLocation() const { return NameLoc; }
+
+ /// \brief Retrieve the template argument pack containing the substituted
+ /// template arguments.
+ TemplateArgument getArgumentPack() const;
+
+ SourceRange getSourceRange() const { return NameLoc; }
+
+ static bool classof(const Stmt *T) {
+ return T->getStmtClass() == SubstNonTypeTemplateParmPackExprClass;
+ }
+ static bool classof(const SubstNonTypeTemplateParmPackExpr *) {
+ return true;
+ }
+
+ // Iterators
+ child_range children() { return child_range(); }
+};
+
} // end namespace clang
#endif
OpenPOWER on IntegriCloud