blob: 872b3c0189b26af75816833ee4652c54b6e0557a [file] [log] [blame]
John McCall550e0c22009-10-21 00:40:46 +00001//===------- TreeTransform.h - Semantic Tree Transformation -----*- C++ -*-===/
Douglas Gregord6ff3322009-08-04 16:50:30 +00002//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//===----------------------------------------------------------------------===/
8//
9// This file implements a semantic tree transformation that takes a given
10// AST and rebuilds it, possibly transforming some nodes in the process.
11//
12//===----------------------------------------------------------------------===/
13#ifndef LLVM_CLANG_SEMA_TREETRANSFORM_H
14#define LLVM_CLANG_SEMA_TREETRANSFORM_H
15
16#include "Sema.h"
Douglas Gregor1135c352009-08-06 05:28:30 +000017#include "clang/Sema/SemaDiagnostic.h"
Douglas Gregor2b6ca462009-09-03 21:38:09 +000018#include "clang/AST/Decl.h"
Douglas Gregor766b0bb2009-08-06 22:17:10 +000019#include "clang/AST/Expr.h"
Douglas Gregora16548e2009-08-11 05:31:07 +000020#include "clang/AST/ExprCXX.h"
21#include "clang/AST/ExprObjC.h"
Douglas Gregorebe10102009-08-20 07:17:43 +000022#include "clang/AST/Stmt.h"
23#include "clang/AST/StmtCXX.h"
24#include "clang/AST/StmtObjC.h"
John McCall550e0c22009-10-21 00:40:46 +000025#include "clang/AST/TypeLocBuilder.h"
Douglas Gregora16548e2009-08-11 05:31:07 +000026#include "clang/Parse/Ownership.h"
27#include "clang/Parse/Designator.h"
28#include "clang/Lex/Preprocessor.h"
John McCall550e0c22009-10-21 00:40:46 +000029#include "llvm/Support/ErrorHandling.h"
Douglas Gregord6ff3322009-08-04 16:50:30 +000030#include <algorithm>
31
32namespace clang {
Mike Stump11289f42009-09-09 15:08:12 +000033
Douglas Gregord6ff3322009-08-04 16:50:30 +000034/// \brief A semantic tree transformation that allows one to transform one
35/// abstract syntax tree into another.
36///
Mike Stump11289f42009-09-09 15:08:12 +000037/// A new tree transformation is defined by creating a new subclass \c X of
38/// \c TreeTransform<X> and then overriding certain operations to provide
39/// behavior specific to that transformation. For example, template
Douglas Gregord6ff3322009-08-04 16:50:30 +000040/// instantiation is implemented as a tree transformation where the
41/// transformation of TemplateTypeParmType nodes involves substituting the
42/// template arguments for their corresponding template parameters; a similar
43/// transformation is performed for non-type template parameters and
44/// template template parameters.
45///
46/// This tree-transformation template uses static polymorphism to allow
Mike Stump11289f42009-09-09 15:08:12 +000047/// subclasses to customize any of its operations. Thus, a subclass can
Douglas Gregord6ff3322009-08-04 16:50:30 +000048/// override any of the transformation or rebuild operators by providing an
49/// operation with the same signature as the default implementation. The
50/// overridding function should not be virtual.
51///
52/// Semantic tree transformations are split into two stages, either of which
53/// can be replaced by a subclass. The "transform" step transforms an AST node
54/// or the parts of an AST node using the various transformation functions,
55/// then passes the pieces on to the "rebuild" step, which constructs a new AST
56/// node of the appropriate kind from the pieces. The default transformation
57/// routines recursively transform the operands to composite AST nodes (e.g.,
58/// the pointee type of a PointerType node) and, if any of those operand nodes
59/// were changed by the transformation, invokes the rebuild operation to create
60/// a new AST node.
61///
Mike Stump11289f42009-09-09 15:08:12 +000062/// Subclasses can customize the transformation at various levels. The
Douglas Gregore922c772009-08-04 22:27:00 +000063/// most coarse-grained transformations involve replacing TransformType(),
Douglas Gregord6ff3322009-08-04 16:50:30 +000064/// TransformExpr(), TransformDecl(), TransformNestedNameSpecifier(),
65/// TransformTemplateName(), or TransformTemplateArgument() with entirely
66/// new implementations.
67///
68/// For more fine-grained transformations, subclasses can replace any of the
69/// \c TransformXXX functions (where XXX is the name of an AST node, e.g.,
Douglas Gregorebe10102009-08-20 07:17:43 +000070/// PointerType, StmtExpr) to alter the transformation. As mentioned previously,
Douglas Gregord6ff3322009-08-04 16:50:30 +000071/// replacing TransformTemplateTypeParmType() allows template instantiation
Mike Stump11289f42009-09-09 15:08:12 +000072/// to substitute template arguments for their corresponding template
Douglas Gregord6ff3322009-08-04 16:50:30 +000073/// parameters. Additionally, subclasses can override the \c RebuildXXX
74/// functions to control how AST nodes are rebuilt when their operands change.
75/// By default, \c TreeTransform will invoke semantic analysis to rebuild
76/// AST nodes. However, certain other tree transformations (e.g, cloning) may
77/// be able to use more efficient rebuild steps.
78///
79/// There are a handful of other functions that can be overridden, allowing one
Mike Stump11289f42009-09-09 15:08:12 +000080/// to avoid traversing nodes that don't need any transformation
Douglas Gregord6ff3322009-08-04 16:50:30 +000081/// (\c AlreadyTransformed()), force rebuilding AST nodes even when their
82/// operands have not changed (\c AlwaysRebuild()), and customize the
83/// default locations and entity names used for type-checking
84/// (\c getBaseLocation(), \c getBaseEntity()).
Douglas Gregord6ff3322009-08-04 16:50:30 +000085template<typename Derived>
86class TreeTransform {
87protected:
88 Sema &SemaRef;
Mike Stump11289f42009-09-09 15:08:12 +000089
90public:
Douglas Gregora16548e2009-08-11 05:31:07 +000091 typedef Sema::OwningStmtResult OwningStmtResult;
92 typedef Sema::OwningExprResult OwningExprResult;
93 typedef Sema::StmtArg StmtArg;
94 typedef Sema::ExprArg ExprArg;
95 typedef Sema::MultiExprArg MultiExprArg;
Douglas Gregorebe10102009-08-20 07:17:43 +000096 typedef Sema::MultiStmtArg MultiStmtArg;
Mike Stump11289f42009-09-09 15:08:12 +000097
Douglas Gregord6ff3322009-08-04 16:50:30 +000098 /// \brief Initializes a new tree transformer.
99 TreeTransform(Sema &SemaRef) : SemaRef(SemaRef) { }
Mike Stump11289f42009-09-09 15:08:12 +0000100
Douglas Gregord6ff3322009-08-04 16:50:30 +0000101 /// \brief Retrieves a reference to the derived class.
102 Derived &getDerived() { return static_cast<Derived&>(*this); }
103
104 /// \brief Retrieves a reference to the derived class.
Mike Stump11289f42009-09-09 15:08:12 +0000105 const Derived &getDerived() const {
106 return static_cast<const Derived&>(*this);
Douglas Gregord6ff3322009-08-04 16:50:30 +0000107 }
108
109 /// \brief Retrieves a reference to the semantic analysis object used for
110 /// this tree transform.
111 Sema &getSema() const { return SemaRef; }
Mike Stump11289f42009-09-09 15:08:12 +0000112
Douglas Gregord6ff3322009-08-04 16:50:30 +0000113 /// \brief Whether the transformation should always rebuild AST nodes, even
114 /// if none of the children have changed.
115 ///
116 /// Subclasses may override this function to specify when the transformation
117 /// should rebuild all AST nodes.
118 bool AlwaysRebuild() { return false; }
Mike Stump11289f42009-09-09 15:08:12 +0000119
Douglas Gregord6ff3322009-08-04 16:50:30 +0000120 /// \brief Returns the location of the entity being transformed, if that
121 /// information was not available elsewhere in the AST.
122 ///
Mike Stump11289f42009-09-09 15:08:12 +0000123 /// By default, returns no source-location information. Subclasses can
Douglas Gregord6ff3322009-08-04 16:50:30 +0000124 /// provide an alternative implementation that provides better location
125 /// information.
126 SourceLocation getBaseLocation() { return SourceLocation(); }
Mike Stump11289f42009-09-09 15:08:12 +0000127
Douglas Gregord6ff3322009-08-04 16:50:30 +0000128 /// \brief Returns the name of the entity being transformed, if that
129 /// information was not available elsewhere in the AST.
130 ///
131 /// By default, returns an empty name. Subclasses can provide an alternative
132 /// implementation with a more precise name.
133 DeclarationName getBaseEntity() { return DeclarationName(); }
134
Douglas Gregora16548e2009-08-11 05:31:07 +0000135 /// \brief Sets the "base" location and entity when that
136 /// information is known based on another transformation.
137 ///
138 /// By default, the source location and entity are ignored. Subclasses can
139 /// override this function to provide a customized implementation.
140 void setBase(SourceLocation Loc, DeclarationName Entity) { }
Mike Stump11289f42009-09-09 15:08:12 +0000141
Douglas Gregora16548e2009-08-11 05:31:07 +0000142 /// \brief RAII object that temporarily sets the base location and entity
143 /// used for reporting diagnostics in types.
144 class TemporaryBase {
145 TreeTransform &Self;
146 SourceLocation OldLocation;
147 DeclarationName OldEntity;
Mike Stump11289f42009-09-09 15:08:12 +0000148
Douglas Gregora16548e2009-08-11 05:31:07 +0000149 public:
150 TemporaryBase(TreeTransform &Self, SourceLocation Location,
Mike Stump11289f42009-09-09 15:08:12 +0000151 DeclarationName Entity) : Self(Self) {
Douglas Gregora16548e2009-08-11 05:31:07 +0000152 OldLocation = Self.getDerived().getBaseLocation();
153 OldEntity = Self.getDerived().getBaseEntity();
154 Self.getDerived().setBase(Location, Entity);
155 }
Mike Stump11289f42009-09-09 15:08:12 +0000156
Douglas Gregora16548e2009-08-11 05:31:07 +0000157 ~TemporaryBase() {
158 Self.getDerived().setBase(OldLocation, OldEntity);
159 }
160 };
Mike Stump11289f42009-09-09 15:08:12 +0000161
162 /// \brief Determine whether the given type \p T has already been
Douglas Gregord6ff3322009-08-04 16:50:30 +0000163 /// transformed.
164 ///
165 /// Subclasses can provide an alternative implementation of this routine
Mike Stump11289f42009-09-09 15:08:12 +0000166 /// to short-circuit evaluation when it is known that a given type will
Douglas Gregord6ff3322009-08-04 16:50:30 +0000167 /// not change. For example, template instantiation need not traverse
168 /// non-dependent types.
169 bool AlreadyTransformed(QualType T) {
170 return T.isNull();
171 }
172
173 /// \brief Transforms the given type into another type.
174 ///
John McCall550e0c22009-10-21 00:40:46 +0000175 /// By default, this routine transforms a type by creating a
176 /// DeclaratorInfo for it and delegating to the appropriate
177 /// function. This is expensive, but we don't mind, because
178 /// this method is deprecated anyway; all users should be
179 /// switched to storing DeclaratorInfos.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000180 ///
181 /// \returns the transformed type.
182 QualType TransformType(QualType T);
Mike Stump11289f42009-09-09 15:08:12 +0000183
John McCall550e0c22009-10-21 00:40:46 +0000184 /// \brief Transforms the given type-with-location into a new
185 /// type-with-location.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000186 ///
John McCall550e0c22009-10-21 00:40:46 +0000187 /// By default, this routine transforms a type by delegating to the
188 /// appropriate TransformXXXType to build a new type. Subclasses
189 /// may override this function (to take over all type
190 /// transformations) or some set of the TransformXXXType functions
191 /// to alter the transformation.
192 DeclaratorInfo *TransformType(DeclaratorInfo *DI);
193
194 /// \brief Transform the given type-with-location into a new
195 /// type, collecting location information in the given builder
196 /// as necessary.
197 ///
198 QualType TransformType(TypeLocBuilder &TLB, TypeLoc TL);
Mike Stump11289f42009-09-09 15:08:12 +0000199
Douglas Gregor766b0bb2009-08-06 22:17:10 +0000200 /// \brief Transform the given statement.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000201 ///
Mike Stump11289f42009-09-09 15:08:12 +0000202 /// By default, this routine transforms a statement by delegating to the
Douglas Gregorebe10102009-08-20 07:17:43 +0000203 /// appropriate TransformXXXStmt function to transform a specific kind of
204 /// statement or the TransformExpr() function to transform an expression.
205 /// Subclasses may override this function to transform statements using some
206 /// other mechanism.
207 ///
208 /// \returns the transformed statement.
Douglas Gregora16548e2009-08-11 05:31:07 +0000209 OwningStmtResult TransformStmt(Stmt *S);
Mike Stump11289f42009-09-09 15:08:12 +0000210
Douglas Gregor766b0bb2009-08-06 22:17:10 +0000211 /// \brief Transform the given expression.
212 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000213 /// By default, this routine transforms an expression by delegating to the
214 /// appropriate TransformXXXExpr function to build a new expression.
215 /// Subclasses may override this function to transform expressions using some
216 /// other mechanism.
217 ///
218 /// \returns the transformed expression.
219 OwningExprResult TransformExpr(Expr *E) {
220 return getDerived().TransformExpr(E, /*isAddressOfOperand=*/false);
221 }
222
223 /// \brief Transform the given expression.
224 ///
225 /// By default, this routine transforms an expression by delegating to the
226 /// appropriate TransformXXXExpr function to build a new expression.
227 /// Subclasses may override this function to transform expressions using some
228 /// other mechanism.
229 ///
230 /// \returns the transformed expression.
231 OwningExprResult TransformExpr(Expr *E, bool isAddressOfOperand);
Mike Stump11289f42009-09-09 15:08:12 +0000232
Douglas Gregord6ff3322009-08-04 16:50:30 +0000233 /// \brief Transform the given declaration, which is referenced from a type
234 /// or expression.
235 ///
Douglas Gregor1135c352009-08-06 05:28:30 +0000236 /// By default, acts as the identity function on declarations. Subclasses
237 /// may override this function to provide alternate behavior.
238 Decl *TransformDecl(Decl *D) { return D; }
Douglas Gregorebe10102009-08-20 07:17:43 +0000239
240 /// \brief Transform the definition of the given declaration.
241 ///
Mike Stump11289f42009-09-09 15:08:12 +0000242 /// By default, invokes TransformDecl() to transform the declaration.
Douglas Gregorebe10102009-08-20 07:17:43 +0000243 /// Subclasses may override this function to provide alternate behavior.
244 Decl *TransformDefinition(Decl *D) { return getDerived().TransformDecl(D); }
Mike Stump11289f42009-09-09 15:08:12 +0000245
Douglas Gregora5cb6da2009-10-20 05:58:46 +0000246 /// \brief Transform the given declaration, which was the first part of a
247 /// nested-name-specifier in a member access expression.
248 ///
249 /// This specific declaration transformation only applies to the first
250 /// identifier in a nested-name-specifier of a member access expression, e.g.,
251 /// the \c T in \c x->T::member
252 ///
253 /// By default, invokes TransformDecl() to transform the declaration.
254 /// Subclasses may override this function to provide alternate behavior.
255 NamedDecl *TransformFirstQualifierInScope(NamedDecl *D, SourceLocation Loc) {
256 return cast_or_null<NamedDecl>(getDerived().TransformDecl(D));
257 }
258
Douglas Gregord6ff3322009-08-04 16:50:30 +0000259 /// \brief Transform the given nested-name-specifier.
260 ///
Mike Stump11289f42009-09-09 15:08:12 +0000261 /// By default, transforms all of the types and declarations within the
Douglas Gregor1135c352009-08-06 05:28:30 +0000262 /// nested-name-specifier. Subclasses may override this function to provide
263 /// alternate behavior.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000264 NestedNameSpecifier *TransformNestedNameSpecifier(NestedNameSpecifier *NNS,
Douglas Gregorc26e0f62009-09-03 16:14:30 +0000265 SourceRange Range,
Douglas Gregor2b6ca462009-09-03 21:38:09 +0000266 QualType ObjectType = QualType(),
267 NamedDecl *FirstQualifierInScope = 0);
Mike Stump11289f42009-09-09 15:08:12 +0000268
Douglas Gregorf816bd72009-09-03 22:13:48 +0000269 /// \brief Transform the given declaration name.
270 ///
271 /// By default, transforms the types of conversion function, constructor,
272 /// and destructor names and then (if needed) rebuilds the declaration name.
273 /// Identifiers and selectors are returned unmodified. Sublcasses may
274 /// override this function to provide alternate behavior.
275 DeclarationName TransformDeclarationName(DeclarationName Name,
Douglas Gregorc59e5612009-10-19 22:04:39 +0000276 SourceLocation Loc,
277 QualType ObjectType = QualType());
Mike Stump11289f42009-09-09 15:08:12 +0000278
Douglas Gregord6ff3322009-08-04 16:50:30 +0000279 /// \brief Transform the given template name.
Mike Stump11289f42009-09-09 15:08:12 +0000280 ///
Douglas Gregor71dc5092009-08-06 06:41:21 +0000281 /// By default, transforms the template name by transforming the declarations
Mike Stump11289f42009-09-09 15:08:12 +0000282 /// and nested-name-specifiers that occur within the template name.
Douglas Gregor71dc5092009-08-06 06:41:21 +0000283 /// Subclasses may override this function to provide alternate behavior.
Douglas Gregor308047d2009-09-09 00:23:06 +0000284 TemplateName TransformTemplateName(TemplateName Name,
285 QualType ObjectType = QualType());
Mike Stump11289f42009-09-09 15:08:12 +0000286
Douglas Gregord6ff3322009-08-04 16:50:30 +0000287 /// \brief Transform the given template argument.
288 ///
Mike Stump11289f42009-09-09 15:08:12 +0000289 /// By default, this operation transforms the type, expression, or
290 /// declaration stored within the template argument and constructs a
Douglas Gregore922c772009-08-04 22:27:00 +0000291 /// new template argument from the transformed result. Subclasses may
292 /// override this function to provide alternate behavior.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000293 TemplateArgument TransformTemplateArgument(const TemplateArgument &Arg);
Mike Stump11289f42009-09-09 15:08:12 +0000294
John McCall550e0c22009-10-21 00:40:46 +0000295#define ABSTRACT_TYPELOC(CLASS, PARENT)
296#define TYPELOC(CLASS, PARENT) \
297 QualType Transform##CLASS##Type(TypeLocBuilder &TLB, CLASS##TypeLoc T);
298#include "clang/AST/TypeLocNodes.def"
Douglas Gregord6ff3322009-08-04 16:50:30 +0000299
Douglas Gregorc59e5612009-10-19 22:04:39 +0000300 QualType
301 TransformTemplateSpecializationType(const TemplateSpecializationType *T,
302 QualType ObjectType);
303
Douglas Gregorebe10102009-08-20 07:17:43 +0000304 OwningStmtResult TransformCompoundStmt(CompoundStmt *S, bool IsStmtExpr);
Mike Stump11289f42009-09-09 15:08:12 +0000305
Douglas Gregorebe10102009-08-20 07:17:43 +0000306#define STMT(Node, Parent) \
307 OwningStmtResult Transform##Node(Node *S);
Douglas Gregora16548e2009-08-11 05:31:07 +0000308#define EXPR(Node, Parent) \
309 OwningExprResult Transform##Node(Node *E);
310#define ABSTRACT_EXPR(Node, Parent)
311#include "clang/AST/StmtNodes.def"
Mike Stump11289f42009-09-09 15:08:12 +0000312
Douglas Gregord6ff3322009-08-04 16:50:30 +0000313 /// \brief Build a new pointer type given its pointee type.
314 ///
315 /// By default, performs semantic analysis when building the pointer type.
316 /// Subclasses may override this routine to provide different behavior.
317 QualType RebuildPointerType(QualType PointeeType);
318
319 /// \brief Build a new block pointer type given its pointee type.
320 ///
Mike Stump11289f42009-09-09 15:08:12 +0000321 /// By default, performs semantic analysis when building the block pointer
Douglas Gregord6ff3322009-08-04 16:50:30 +0000322 /// type. Subclasses may override this routine to provide different behavior.
323 QualType RebuildBlockPointerType(QualType PointeeType);
324
325 /// \brief Build a new lvalue reference type given the type it references.
326 ///
327 /// By default, performs semantic analysis when building the lvalue reference
328 /// type. Subclasses may override this routine to provide different behavior.
329 QualType RebuildLValueReferenceType(QualType ReferentType);
330
331 /// \brief Build a new rvalue reference type given the type it references.
332 ///
333 /// By default, performs semantic analysis when building the rvalue reference
334 /// type. Subclasses may override this routine to provide different behavior.
335 QualType RebuildRValueReferenceType(QualType ReferentType);
Mike Stump11289f42009-09-09 15:08:12 +0000336
Douglas Gregord6ff3322009-08-04 16:50:30 +0000337 /// \brief Build a new member pointer type given the pointee type and the
338 /// class type it refers into.
339 ///
340 /// By default, performs semantic analysis when building the member pointer
341 /// type. Subclasses may override this routine to provide different behavior.
342 QualType RebuildMemberPointerType(QualType PointeeType, QualType ClassType);
Mike Stump11289f42009-09-09 15:08:12 +0000343
John McCall550e0c22009-10-21 00:40:46 +0000344 /// \brief Build a new Objective C object pointer type.
345 QualType RebuildObjCObjectPointerType(QualType PointeeType);
346
Douglas Gregord6ff3322009-08-04 16:50:30 +0000347 /// \brief Build a new array type given the element type, size
348 /// modifier, size of the array (if known), size expression, and index type
349 /// qualifiers.
350 ///
351 /// By default, performs semantic analysis when building the array type.
352 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000353 /// Also by default, all of the other Rebuild*Array
Douglas Gregord6ff3322009-08-04 16:50:30 +0000354 QualType RebuildArrayType(QualType ElementType,
355 ArrayType::ArraySizeModifier SizeMod,
356 const llvm::APInt *Size,
357 Expr *SizeExpr,
358 unsigned IndexTypeQuals,
359 SourceRange BracketsRange);
Mike Stump11289f42009-09-09 15:08:12 +0000360
Douglas Gregord6ff3322009-08-04 16:50:30 +0000361 /// \brief Build a new constant array type given the element type, size
362 /// modifier, (known) size of the array, and index type qualifiers.
363 ///
364 /// By default, performs semantic analysis when building the array type.
365 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000366 QualType RebuildConstantArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000367 ArrayType::ArraySizeModifier SizeMod,
368 const llvm::APInt &Size,
369 unsigned IndexTypeQuals);
370
Douglas Gregord6ff3322009-08-04 16:50:30 +0000371 /// \brief Build a new incomplete array type given the element type, size
372 /// modifier, and index type qualifiers.
373 ///
374 /// By default, performs semantic analysis when building the array type.
375 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000376 QualType RebuildIncompleteArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000377 ArrayType::ArraySizeModifier SizeMod,
378 unsigned IndexTypeQuals);
379
Mike Stump11289f42009-09-09 15:08:12 +0000380 /// \brief Build a new variable-length array type given the element type,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000381 /// size modifier, size expression, and index type qualifiers.
382 ///
383 /// By default, performs semantic analysis when building the array type.
384 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000385 QualType RebuildVariableArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000386 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +0000387 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000388 unsigned IndexTypeQuals,
389 SourceRange BracketsRange);
390
Mike Stump11289f42009-09-09 15:08:12 +0000391 /// \brief Build a new dependent-sized array type given the element type,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000392 /// size modifier, size expression, and index type qualifiers.
393 ///
394 /// By default, performs semantic analysis when building the array type.
395 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000396 QualType RebuildDependentSizedArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000397 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +0000398 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000399 unsigned IndexTypeQuals,
400 SourceRange BracketsRange);
401
402 /// \brief Build a new vector type given the element type and
403 /// number of elements.
404 ///
405 /// By default, performs semantic analysis when building the vector type.
406 /// Subclasses may override this routine to provide different behavior.
407 QualType RebuildVectorType(QualType ElementType, unsigned NumElements);
Mike Stump11289f42009-09-09 15:08:12 +0000408
Douglas Gregord6ff3322009-08-04 16:50:30 +0000409 /// \brief Build a new extended vector type given the element type and
410 /// number of elements.
411 ///
412 /// By default, performs semantic analysis when building the vector type.
413 /// Subclasses may override this routine to provide different behavior.
414 QualType RebuildExtVectorType(QualType ElementType, unsigned NumElements,
415 SourceLocation AttributeLoc);
Mike Stump11289f42009-09-09 15:08:12 +0000416
417 /// \brief Build a new potentially dependently-sized extended vector type
Douglas Gregord6ff3322009-08-04 16:50:30 +0000418 /// given the element type and number of elements.
419 ///
420 /// By default, performs semantic analysis when building the vector type.
421 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000422 QualType RebuildDependentSizedExtVectorType(QualType ElementType,
Douglas Gregora16548e2009-08-11 05:31:07 +0000423 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000424 SourceLocation AttributeLoc);
Mike Stump11289f42009-09-09 15:08:12 +0000425
Douglas Gregord6ff3322009-08-04 16:50:30 +0000426 /// \brief Build a new function type.
427 ///
428 /// By default, performs semantic analysis when building the function type.
429 /// Subclasses may override this routine to provide different behavior.
430 QualType RebuildFunctionProtoType(QualType T,
Mike Stump11289f42009-09-09 15:08:12 +0000431 QualType *ParamTypes,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000432 unsigned NumParamTypes,
433 bool Variadic, unsigned Quals);
Mike Stump11289f42009-09-09 15:08:12 +0000434
John McCall550e0c22009-10-21 00:40:46 +0000435 /// \brief Build a new unprototyped function type.
436 QualType RebuildFunctionNoProtoType(QualType ResultType);
437
Douglas Gregord6ff3322009-08-04 16:50:30 +0000438 /// \brief Build a new typedef type.
439 QualType RebuildTypedefType(TypedefDecl *Typedef) {
440 return SemaRef.Context.getTypeDeclType(Typedef);
441 }
442
443 /// \brief Build a new class/struct/union type.
444 QualType RebuildRecordType(RecordDecl *Record) {
445 return SemaRef.Context.getTypeDeclType(Record);
446 }
447
448 /// \brief Build a new Enum type.
449 QualType RebuildEnumType(EnumDecl *Enum) {
450 return SemaRef.Context.getTypeDeclType(Enum);
451 }
John McCallfcc33b02009-09-05 00:15:47 +0000452
453 /// \brief Build a new elaborated type.
454 QualType RebuildElaboratedType(QualType T, ElaboratedType::TagKind Tag) {
455 return SemaRef.Context.getElaboratedType(T, Tag);
456 }
Mike Stump11289f42009-09-09 15:08:12 +0000457
458 /// \brief Build a new typeof(expr) type.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000459 ///
460 /// By default, performs semantic analysis when building the typeof type.
461 /// Subclasses may override this routine to provide different behavior.
Douglas Gregora16548e2009-08-11 05:31:07 +0000462 QualType RebuildTypeOfExprType(ExprArg Underlying);
Douglas Gregord6ff3322009-08-04 16:50:30 +0000463
Mike Stump11289f42009-09-09 15:08:12 +0000464 /// \brief Build a new typeof(type) type.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000465 ///
466 /// By default, builds a new TypeOfType with the given underlying type.
467 QualType RebuildTypeOfType(QualType Underlying);
468
Mike Stump11289f42009-09-09 15:08:12 +0000469 /// \brief Build a new C++0x decltype type.
Douglas Gregord6ff3322009-08-04 16:50:30 +0000470 ///
471 /// By default, performs semantic analysis when building the decltype type.
472 /// Subclasses may override this routine to provide different behavior.
Douglas Gregora16548e2009-08-11 05:31:07 +0000473 QualType RebuildDecltypeType(ExprArg Underlying);
Mike Stump11289f42009-09-09 15:08:12 +0000474
Douglas Gregord6ff3322009-08-04 16:50:30 +0000475 /// \brief Build a new template specialization type.
476 ///
477 /// By default, performs semantic analysis when building the template
478 /// specialization type. Subclasses may override this routine to provide
479 /// different behavior.
480 QualType RebuildTemplateSpecializationType(TemplateName Template,
481 const TemplateArgument *Args,
482 unsigned NumArgs);
Mike Stump11289f42009-09-09 15:08:12 +0000483
Douglas Gregord6ff3322009-08-04 16:50:30 +0000484 /// \brief Build a new qualified name type.
485 ///
Mike Stump11289f42009-09-09 15:08:12 +0000486 /// By default, builds a new QualifiedNameType type from the
487 /// nested-name-specifier and the named type. Subclasses may override
Douglas Gregord6ff3322009-08-04 16:50:30 +0000488 /// this routine to provide different behavior.
489 QualType RebuildQualifiedNameType(NestedNameSpecifier *NNS, QualType Named) {
490 return SemaRef.Context.getQualifiedNameType(NNS, Named);
Mike Stump11289f42009-09-09 15:08:12 +0000491 }
Douglas Gregord6ff3322009-08-04 16:50:30 +0000492
493 /// \brief Build a new typename type that refers to a template-id.
494 ///
495 /// By default, builds a new TypenameType type from the nested-name-specifier
Mike Stump11289f42009-09-09 15:08:12 +0000496 /// and the given type. Subclasses may override this routine to provide
Douglas Gregord6ff3322009-08-04 16:50:30 +0000497 /// different behavior.
498 QualType RebuildTypenameType(NestedNameSpecifier *NNS, QualType T) {
499 if (NNS->isDependent())
Mike Stump11289f42009-09-09 15:08:12 +0000500 return SemaRef.Context.getTypenameType(NNS,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000501 cast<TemplateSpecializationType>(T));
Mike Stump11289f42009-09-09 15:08:12 +0000502
Douglas Gregord6ff3322009-08-04 16:50:30 +0000503 return SemaRef.Context.getQualifiedNameType(NNS, T);
Mike Stump11289f42009-09-09 15:08:12 +0000504 }
Douglas Gregord6ff3322009-08-04 16:50:30 +0000505
506 /// \brief Build a new typename type that refers to an identifier.
507 ///
508 /// By default, performs semantic analysis when building the typename type
Mike Stump11289f42009-09-09 15:08:12 +0000509 /// (or qualified name type). Subclasses may override this routine to provide
Douglas Gregord6ff3322009-08-04 16:50:30 +0000510 /// different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000511 QualType RebuildTypenameType(NestedNameSpecifier *NNS,
Douglas Gregord6ff3322009-08-04 16:50:30 +0000512 const IdentifierInfo *Id) {
513 return SemaRef.CheckTypenameType(NNS, *Id,
514 SourceRange(getDerived().getBaseLocation()));
Douglas Gregor1135c352009-08-06 05:28:30 +0000515 }
Mike Stump11289f42009-09-09 15:08:12 +0000516
Douglas Gregor1135c352009-08-06 05:28:30 +0000517 /// \brief Build a new nested-name-specifier given the prefix and an
518 /// identifier that names the next step in the nested-name-specifier.
519 ///
520 /// By default, performs semantic analysis when building the new
521 /// nested-name-specifier. Subclasses may override this routine to provide
522 /// different behavior.
523 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
524 SourceRange Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +0000525 IdentifierInfo &II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +0000526 QualType ObjectType,
527 NamedDecl *FirstQualifierInScope);
Douglas Gregor1135c352009-08-06 05:28:30 +0000528
529 /// \brief Build a new nested-name-specifier given the prefix and the
530 /// namespace named in the next step in the nested-name-specifier.
531 ///
532 /// By default, performs semantic analysis when building the new
533 /// nested-name-specifier. Subclasses may override this routine to provide
534 /// different behavior.
535 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
536 SourceRange Range,
537 NamespaceDecl *NS);
538
539 /// \brief Build a new nested-name-specifier given the prefix and the
540 /// type named in the next step in the nested-name-specifier.
541 ///
542 /// By default, performs semantic analysis when building the new
543 /// nested-name-specifier. Subclasses may override this routine to provide
544 /// different behavior.
545 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
546 SourceRange Range,
547 bool TemplateKW,
548 QualType T);
Douglas Gregor71dc5092009-08-06 06:41:21 +0000549
550 /// \brief Build a new template name given a nested name specifier, a flag
551 /// indicating whether the "template" keyword was provided, and the template
552 /// that the template name refers to.
553 ///
554 /// By default, builds the new template name directly. Subclasses may override
555 /// this routine to provide different behavior.
556 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
557 bool TemplateKW,
558 TemplateDecl *Template);
559
560 /// \brief Build a new template name given a nested name specifier, a flag
561 /// indicating whether the "template" keyword was provided, and a set of
562 /// overloaded function templates.
563 ///
564 /// By default, builds the new template name directly. Subclasses may override
565 /// this routine to provide different behavior.
566 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
567 bool TemplateKW,
568 OverloadedFunctionDecl *Ovl);
Mike Stump11289f42009-09-09 15:08:12 +0000569
Douglas Gregor71dc5092009-08-06 06:41:21 +0000570 /// \brief Build a new template name given a nested name specifier and the
571 /// name that is referred to as a template.
572 ///
573 /// By default, performs semantic analysis to determine whether the name can
574 /// be resolved to a specific template, then builds the appropriate kind of
575 /// template name. Subclasses may override this routine to provide different
576 /// behavior.
577 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
Douglas Gregor308047d2009-09-09 00:23:06 +0000578 const IdentifierInfo &II,
579 QualType ObjectType);
Mike Stump11289f42009-09-09 15:08:12 +0000580
581
Douglas Gregorebe10102009-08-20 07:17:43 +0000582 /// \brief Build a new compound statement.
583 ///
584 /// By default, performs semantic analysis to build the new statement.
585 /// Subclasses may override this routine to provide different behavior.
586 OwningStmtResult RebuildCompoundStmt(SourceLocation LBraceLoc,
587 MultiStmtArg Statements,
588 SourceLocation RBraceLoc,
589 bool IsStmtExpr) {
590 return getSema().ActOnCompoundStmt(LBraceLoc, RBraceLoc, move(Statements),
591 IsStmtExpr);
592 }
593
594 /// \brief Build a new case statement.
595 ///
596 /// By default, performs semantic analysis to build the new statement.
597 /// Subclasses may override this routine to provide different behavior.
598 OwningStmtResult RebuildCaseStmt(SourceLocation CaseLoc,
599 ExprArg LHS,
600 SourceLocation EllipsisLoc,
601 ExprArg RHS,
602 SourceLocation ColonLoc) {
Mike Stump11289f42009-09-09 15:08:12 +0000603 return getSema().ActOnCaseStmt(CaseLoc, move(LHS), EllipsisLoc, move(RHS),
Douglas Gregorebe10102009-08-20 07:17:43 +0000604 ColonLoc);
605 }
Mike Stump11289f42009-09-09 15:08:12 +0000606
Douglas Gregorebe10102009-08-20 07:17:43 +0000607 /// \brief Attach the body to a new case statement.
608 ///
609 /// By default, performs semantic analysis to build the new statement.
610 /// Subclasses may override this routine to provide different behavior.
611 OwningStmtResult RebuildCaseStmtBody(StmtArg S, StmtArg Body) {
612 getSema().ActOnCaseStmtBody(S.get(), move(Body));
613 return move(S);
614 }
Mike Stump11289f42009-09-09 15:08:12 +0000615
Douglas Gregorebe10102009-08-20 07:17:43 +0000616 /// \brief Build a new default statement.
617 ///
618 /// By default, performs semantic analysis to build the new statement.
619 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000620 OwningStmtResult RebuildDefaultStmt(SourceLocation DefaultLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000621 SourceLocation ColonLoc,
622 StmtArg SubStmt) {
Mike Stump11289f42009-09-09 15:08:12 +0000623 return getSema().ActOnDefaultStmt(DefaultLoc, ColonLoc, move(SubStmt),
Douglas Gregorebe10102009-08-20 07:17:43 +0000624 /*CurScope=*/0);
625 }
Mike Stump11289f42009-09-09 15:08:12 +0000626
Douglas Gregorebe10102009-08-20 07:17:43 +0000627 /// \brief Build a new label statement.
628 ///
629 /// By default, performs semantic analysis to build the new statement.
630 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000631 OwningStmtResult RebuildLabelStmt(SourceLocation IdentLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000632 IdentifierInfo *Id,
633 SourceLocation ColonLoc,
634 StmtArg SubStmt) {
635 return SemaRef.ActOnLabelStmt(IdentLoc, Id, ColonLoc, move(SubStmt));
636 }
Mike Stump11289f42009-09-09 15:08:12 +0000637
Douglas Gregorebe10102009-08-20 07:17:43 +0000638 /// \brief Build a new "if" statement.
639 ///
640 /// By default, performs semantic analysis to build the new statement.
641 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000642 OwningStmtResult RebuildIfStmt(SourceLocation IfLoc, Sema::FullExprArg Cond,
643 StmtArg Then, SourceLocation ElseLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000644 StmtArg Else) {
645 return getSema().ActOnIfStmt(IfLoc, Cond, move(Then), ElseLoc, move(Else));
646 }
Mike Stump11289f42009-09-09 15:08:12 +0000647
Douglas Gregorebe10102009-08-20 07:17:43 +0000648 /// \brief Start building a new switch statement.
649 ///
650 /// By default, performs semantic analysis to build the new statement.
651 /// Subclasses may override this routine to provide different behavior.
652 OwningStmtResult RebuildSwitchStmtStart(ExprArg Cond) {
653 return getSema().ActOnStartOfSwitchStmt(move(Cond));
654 }
Mike Stump11289f42009-09-09 15:08:12 +0000655
Douglas Gregorebe10102009-08-20 07:17:43 +0000656 /// \brief Attach the body to the switch statement.
657 ///
658 /// By default, performs semantic analysis to build the new statement.
659 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000660 OwningStmtResult RebuildSwitchStmtBody(SourceLocation SwitchLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000661 StmtArg Switch, StmtArg Body) {
662 return getSema().ActOnFinishSwitchStmt(SwitchLoc, move(Switch),
663 move(Body));
664 }
665
666 /// \brief Build a new while statement.
667 ///
668 /// By default, performs semantic analysis to build the new statement.
669 /// Subclasses may override this routine to provide different behavior.
670 OwningStmtResult RebuildWhileStmt(SourceLocation WhileLoc,
671 Sema::FullExprArg Cond,
672 StmtArg Body) {
673 return getSema().ActOnWhileStmt(WhileLoc, Cond, move(Body));
674 }
Mike Stump11289f42009-09-09 15:08:12 +0000675
Douglas Gregorebe10102009-08-20 07:17:43 +0000676 /// \brief Build a new do-while statement.
677 ///
678 /// By default, performs semantic analysis to build the new statement.
679 /// Subclasses may override this routine to provide different behavior.
680 OwningStmtResult RebuildDoStmt(SourceLocation DoLoc, StmtArg Body,
681 SourceLocation WhileLoc,
682 SourceLocation LParenLoc,
683 ExprArg Cond,
684 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +0000685 return getSema().ActOnDoStmt(DoLoc, move(Body), WhileLoc, LParenLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000686 move(Cond), RParenLoc);
687 }
688
689 /// \brief Build a new for statement.
690 ///
691 /// By default, performs semantic analysis to build the new statement.
692 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000693 OwningStmtResult RebuildForStmt(SourceLocation ForLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000694 SourceLocation LParenLoc,
695 StmtArg Init, ExprArg Cond, ExprArg Inc,
696 SourceLocation RParenLoc, StmtArg Body) {
Mike Stump11289f42009-09-09 15:08:12 +0000697 return getSema().ActOnForStmt(ForLoc, LParenLoc, move(Init), move(Cond),
Douglas Gregorebe10102009-08-20 07:17:43 +0000698 move(Inc), RParenLoc, move(Body));
699 }
Mike Stump11289f42009-09-09 15:08:12 +0000700
Douglas Gregorebe10102009-08-20 07:17:43 +0000701 /// \brief Build a new goto statement.
702 ///
703 /// By default, performs semantic analysis to build the new statement.
704 /// Subclasses may override this routine to provide different behavior.
705 OwningStmtResult RebuildGotoStmt(SourceLocation GotoLoc,
706 SourceLocation LabelLoc,
707 LabelStmt *Label) {
708 return getSema().ActOnGotoStmt(GotoLoc, LabelLoc, Label->getID());
709 }
710
711 /// \brief Build a new indirect goto statement.
712 ///
713 /// By default, performs semantic analysis to build the new statement.
714 /// Subclasses may override this routine to provide different behavior.
715 OwningStmtResult RebuildIndirectGotoStmt(SourceLocation GotoLoc,
716 SourceLocation StarLoc,
717 ExprArg Target) {
718 return getSema().ActOnIndirectGotoStmt(GotoLoc, StarLoc, move(Target));
719 }
Mike Stump11289f42009-09-09 15:08:12 +0000720
Douglas Gregorebe10102009-08-20 07:17:43 +0000721 /// \brief Build a new return statement.
722 ///
723 /// By default, performs semantic analysis to build the new statement.
724 /// Subclasses may override this routine to provide different behavior.
725 OwningStmtResult RebuildReturnStmt(SourceLocation ReturnLoc,
726 ExprArg Result) {
Mike Stump11289f42009-09-09 15:08:12 +0000727
Douglas Gregorebe10102009-08-20 07:17:43 +0000728 return getSema().ActOnReturnStmt(ReturnLoc, move(Result));
729 }
Mike Stump11289f42009-09-09 15:08:12 +0000730
Douglas Gregorebe10102009-08-20 07:17:43 +0000731 /// \brief Build a new declaration statement.
732 ///
733 /// By default, performs semantic analysis to build the new statement.
734 /// Subclasses may override this routine to provide different behavior.
735 OwningStmtResult RebuildDeclStmt(Decl **Decls, unsigned NumDecls,
Mike Stump11289f42009-09-09 15:08:12 +0000736 SourceLocation StartLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000737 SourceLocation EndLoc) {
738 return getSema().Owned(
739 new (getSema().Context) DeclStmt(
740 DeclGroupRef::Create(getSema().Context,
741 Decls, NumDecls),
742 StartLoc, EndLoc));
743 }
Mike Stump11289f42009-09-09 15:08:12 +0000744
Douglas Gregorebe10102009-08-20 07:17:43 +0000745 /// \brief Build a new C++ exception declaration.
746 ///
747 /// By default, performs semantic analysis to build the new decaration.
748 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000749 VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl, QualType T,
Douglas Gregorebe10102009-08-20 07:17:43 +0000750 DeclaratorInfo *Declarator,
751 IdentifierInfo *Name,
752 SourceLocation Loc,
753 SourceRange TypeRange) {
Mike Stump11289f42009-09-09 15:08:12 +0000754 return getSema().BuildExceptionDeclaration(0, T, Declarator, Name, Loc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000755 TypeRange);
756 }
757
758 /// \brief Build a new C++ catch statement.
759 ///
760 /// By default, performs semantic analysis to build the new statement.
761 /// Subclasses may override this routine to provide different behavior.
762 OwningStmtResult RebuildCXXCatchStmt(SourceLocation CatchLoc,
763 VarDecl *ExceptionDecl,
764 StmtArg Handler) {
765 return getSema().Owned(
Mike Stump11289f42009-09-09 15:08:12 +0000766 new (getSema().Context) CXXCatchStmt(CatchLoc, ExceptionDecl,
Douglas Gregorebe10102009-08-20 07:17:43 +0000767 Handler.takeAs<Stmt>()));
768 }
Mike Stump11289f42009-09-09 15:08:12 +0000769
Douglas Gregorebe10102009-08-20 07:17:43 +0000770 /// \brief Build a new C++ try statement.
771 ///
772 /// By default, performs semantic analysis to build the new statement.
773 /// Subclasses may override this routine to provide different behavior.
774 OwningStmtResult RebuildCXXTryStmt(SourceLocation TryLoc,
775 StmtArg TryBlock,
776 MultiStmtArg Handlers) {
777 return getSema().ActOnCXXTryBlock(TryLoc, move(TryBlock), move(Handlers));
778 }
Mike Stump11289f42009-09-09 15:08:12 +0000779
Douglas Gregora16548e2009-08-11 05:31:07 +0000780 /// \brief Build a new expression that references a declaration.
781 ///
782 /// By default, performs semantic analysis to build the new expression.
783 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor4bd90e52009-10-23 18:54:35 +0000784 OwningExprResult RebuildDeclRefExpr(NestedNameSpecifier *Qualifier,
785 SourceRange QualifierRange,
786 NamedDecl *ND, SourceLocation Loc) {
787 CXXScopeSpec SS;
788 SS.setScopeRep(Qualifier);
789 SS.setRange(QualifierRange);
Douglas Gregora16548e2009-08-11 05:31:07 +0000790 return getSema().BuildDeclarationNameExpr(Loc, ND,
791 /*FIXME:*/false,
Douglas Gregor4bd90e52009-10-23 18:54:35 +0000792 &SS,
Douglas Gregora16548e2009-08-11 05:31:07 +0000793 /*FIXME:*/false);
794 }
Mike Stump11289f42009-09-09 15:08:12 +0000795
Douglas Gregora16548e2009-08-11 05:31:07 +0000796 /// \brief Build a new expression in parentheses.
Mike Stump11289f42009-09-09 15:08:12 +0000797 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000798 /// By default, performs semantic analysis to build the new expression.
799 /// Subclasses may override this routine to provide different behavior.
800 OwningExprResult RebuildParenExpr(ExprArg SubExpr, SourceLocation LParen,
801 SourceLocation RParen) {
802 return getSema().ActOnParenExpr(LParen, RParen, move(SubExpr));
803 }
804
Douglas Gregorad8a3362009-09-04 17:36:40 +0000805 /// \brief Build a new pseudo-destructor expression.
Mike Stump11289f42009-09-09 15:08:12 +0000806 ///
Douglas Gregorad8a3362009-09-04 17:36:40 +0000807 /// By default, performs semantic analysis to build the new expression.
808 /// Subclasses may override this routine to provide different behavior.
809 OwningExprResult RebuildCXXPseudoDestructorExpr(ExprArg Base,
810 SourceLocation OperatorLoc,
811 bool isArrow,
812 SourceLocation DestroyedTypeLoc,
813 QualType DestroyedType,
814 NestedNameSpecifier *Qualifier,
815 SourceRange QualifierRange) {
816 CXXScopeSpec SS;
817 if (Qualifier) {
818 SS.setRange(QualifierRange);
819 SS.setScopeRep(Qualifier);
820 }
821
Mike Stump11289f42009-09-09 15:08:12 +0000822 DeclarationName Name
Douglas Gregorad8a3362009-09-04 17:36:40 +0000823 = SemaRef.Context.DeclarationNames.getCXXDestructorName(
824 SemaRef.Context.getCanonicalType(DestroyedType));
Mike Stump11289f42009-09-09 15:08:12 +0000825
826 return getSema().BuildMemberReferenceExpr(/*Scope=*/0, move(Base),
Douglas Gregorad8a3362009-09-04 17:36:40 +0000827 OperatorLoc,
828 isArrow? tok::arrow : tok::period,
829 DestroyedTypeLoc,
830 Name,
831 Sema::DeclPtrTy::make((Decl *)0),
832 &SS);
Mike Stump11289f42009-09-09 15:08:12 +0000833 }
834
Douglas Gregora16548e2009-08-11 05:31:07 +0000835 /// \brief Build a new unary operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000836 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000837 /// By default, performs semantic analysis to build the new expression.
838 /// Subclasses may override this routine to provide different behavior.
839 OwningExprResult RebuildUnaryOperator(SourceLocation OpLoc,
840 UnaryOperator::Opcode Opc,
841 ExprArg SubExpr) {
842 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(SubExpr));
843 }
Mike Stump11289f42009-09-09 15:08:12 +0000844
Douglas Gregora16548e2009-08-11 05:31:07 +0000845 /// \brief Build a new sizeof or alignof expression with a type argument.
Mike Stump11289f42009-09-09 15:08:12 +0000846 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000847 /// By default, performs semantic analysis to build the new expression.
848 /// Subclasses may override this routine to provide different behavior.
849 OwningExprResult RebuildSizeOfAlignOf(QualType T, SourceLocation OpLoc,
850 bool isSizeOf, SourceRange R) {
851 return getSema().CreateSizeOfAlignOfExpr(T, OpLoc, isSizeOf, R);
852 }
853
Mike Stump11289f42009-09-09 15:08:12 +0000854 /// \brief Build a new sizeof or alignof expression with an expression
Douglas Gregora16548e2009-08-11 05:31:07 +0000855 /// argument.
Mike Stump11289f42009-09-09 15:08:12 +0000856 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000857 /// By default, performs semantic analysis to build the new expression.
858 /// Subclasses may override this routine to provide different behavior.
859 OwningExprResult RebuildSizeOfAlignOf(ExprArg SubExpr, SourceLocation OpLoc,
860 bool isSizeOf, SourceRange R) {
Mike Stump11289f42009-09-09 15:08:12 +0000861 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +0000862 = getSema().CreateSizeOfAlignOfExpr((Expr *)SubExpr.get(),
863 OpLoc, isSizeOf, R);
864 if (Result.isInvalid())
865 return getSema().ExprError();
Mike Stump11289f42009-09-09 15:08:12 +0000866
Douglas Gregora16548e2009-08-11 05:31:07 +0000867 SubExpr.release();
868 return move(Result);
869 }
Mike Stump11289f42009-09-09 15:08:12 +0000870
Douglas Gregora16548e2009-08-11 05:31:07 +0000871 /// \brief Build a new array subscript expression.
Mike Stump11289f42009-09-09 15:08:12 +0000872 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000873 /// By default, performs semantic analysis to build the new expression.
874 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000875 OwningExprResult RebuildArraySubscriptExpr(ExprArg LHS,
Douglas Gregora16548e2009-08-11 05:31:07 +0000876 SourceLocation LBracketLoc,
877 ExprArg RHS,
878 SourceLocation RBracketLoc) {
879 return getSema().ActOnArraySubscriptExpr(/*Scope=*/0, move(LHS),
Mike Stump11289f42009-09-09 15:08:12 +0000880 LBracketLoc, move(RHS),
Douglas Gregora16548e2009-08-11 05:31:07 +0000881 RBracketLoc);
882 }
883
884 /// \brief Build a new call expression.
Mike Stump11289f42009-09-09 15:08:12 +0000885 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000886 /// By default, performs semantic analysis to build the new expression.
887 /// Subclasses may override this routine to provide different behavior.
888 OwningExprResult RebuildCallExpr(ExprArg Callee, SourceLocation LParenLoc,
889 MultiExprArg Args,
890 SourceLocation *CommaLocs,
891 SourceLocation RParenLoc) {
892 return getSema().ActOnCallExpr(/*Scope=*/0, move(Callee), LParenLoc,
893 move(Args), CommaLocs, RParenLoc);
894 }
895
896 /// \brief Build a new member access expression.
Mike Stump11289f42009-09-09 15:08:12 +0000897 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000898 /// By default, performs semantic analysis to build the new expression.
899 /// Subclasses may override this routine to provide different behavior.
900 OwningExprResult RebuildMemberExpr(ExprArg Base, SourceLocation OpLoc,
Mike Stump11289f42009-09-09 15:08:12 +0000901 bool isArrow,
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000902 NestedNameSpecifier *Qualifier,
903 SourceRange QualifierRange,
904 SourceLocation MemberLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +0000905 NamedDecl *Member) {
Anders Carlsson5da84842009-09-01 04:26:58 +0000906 if (!Member->getDeclName()) {
907 // We have a reference to an unnamed field.
908 assert(!Qualifier && "Can't have an unnamed field with a qualifier!");
Mike Stump11289f42009-09-09 15:08:12 +0000909
910 MemberExpr *ME =
Anders Carlsson5da84842009-09-01 04:26:58 +0000911 new (getSema().Context) MemberExpr(Base.takeAs<Expr>(), isArrow,
912 Member, MemberLoc,
913 cast<FieldDecl>(Member)->getType());
914 return getSema().Owned(ME);
915 }
Mike Stump11289f42009-09-09 15:08:12 +0000916
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000917 CXXScopeSpec SS;
918 if (Qualifier) {
919 SS.setRange(QualifierRange);
920 SS.setScopeRep(Qualifier);
921 }
922
Douglas Gregorf14b46f2009-08-31 20:00:26 +0000923 return getSema().BuildMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +0000924 isArrow? tok::arrow : tok::period,
925 MemberLoc,
Douglas Gregorf14b46f2009-08-31 20:00:26 +0000926 Member->getDeclName(),
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000927 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
928 &SS);
Douglas Gregora16548e2009-08-11 05:31:07 +0000929 }
Mike Stump11289f42009-09-09 15:08:12 +0000930
Douglas Gregora16548e2009-08-11 05:31:07 +0000931 /// \brief Build a new binary operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000932 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000933 /// By default, performs semantic analysis to build the new expression.
934 /// Subclasses may override this routine to provide different behavior.
935 OwningExprResult RebuildBinaryOperator(SourceLocation OpLoc,
936 BinaryOperator::Opcode Opc,
937 ExprArg LHS, ExprArg RHS) {
938 OwningExprResult Result
Mike Stump11289f42009-09-09 15:08:12 +0000939 = getSema().CreateBuiltinBinOp(OpLoc, Opc, (Expr *)LHS.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +0000940 (Expr *)RHS.get());
941 if (Result.isInvalid())
942 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +0000943
Douglas Gregora16548e2009-08-11 05:31:07 +0000944 LHS.release();
945 RHS.release();
946 return move(Result);
947 }
948
949 /// \brief Build a new conditional operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000950 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000951 /// By default, performs semantic analysis to build the new expression.
952 /// Subclasses may override this routine to provide different behavior.
953 OwningExprResult RebuildConditionalOperator(ExprArg Cond,
954 SourceLocation QuestionLoc,
955 ExprArg LHS,
956 SourceLocation ColonLoc,
957 ExprArg RHS) {
Mike Stump11289f42009-09-09 15:08:12 +0000958 return getSema().ActOnConditionalOp(QuestionLoc, ColonLoc, move(Cond),
Douglas Gregora16548e2009-08-11 05:31:07 +0000959 move(LHS), move(RHS));
960 }
961
962 /// \brief Build a new implicit cast expression.
Mike Stump11289f42009-09-09 15:08:12 +0000963 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000964 /// By default, builds a new implicit cast without any semantic analysis.
965 /// Subclasses may override this routine to provide different behavior.
966 OwningExprResult RebuildImplicitCastExpr(QualType T, CastExpr::CastKind Kind,
967 ExprArg SubExpr, bool isLvalue) {
968 ImplicitCastExpr *ICE
Mike Stump11289f42009-09-09 15:08:12 +0000969 = new (getSema().Context) ImplicitCastExpr(T, Kind,
Douglas Gregora16548e2009-08-11 05:31:07 +0000970 (Expr *)SubExpr.release(),
971 isLvalue);
972 return getSema().Owned(ICE);
973 }
974
975 /// \brief Build a new C-style cast expression.
Mike Stump11289f42009-09-09 15:08:12 +0000976 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000977 /// By default, performs semantic analysis to build the new expression.
978 /// Subclasses may override this routine to provide different behavior.
979 OwningExprResult RebuildCStyleCaseExpr(SourceLocation LParenLoc,
980 QualType ExplicitTy,
981 SourceLocation RParenLoc,
982 ExprArg SubExpr) {
983 return getSema().ActOnCastExpr(/*Scope=*/0,
984 LParenLoc,
985 ExplicitTy.getAsOpaquePtr(),
986 RParenLoc,
987 move(SubExpr));
988 }
Mike Stump11289f42009-09-09 15:08:12 +0000989
Douglas Gregora16548e2009-08-11 05:31:07 +0000990 /// \brief Build a new compound literal expression.
Mike Stump11289f42009-09-09 15:08:12 +0000991 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000992 /// By default, performs semantic analysis to build the new expression.
993 /// Subclasses may override this routine to provide different behavior.
994 OwningExprResult RebuildCompoundLiteralExpr(SourceLocation LParenLoc,
995 QualType T,
996 SourceLocation RParenLoc,
997 ExprArg Init) {
998 return getSema().ActOnCompoundLiteral(LParenLoc, T.getAsOpaquePtr(),
999 RParenLoc, move(Init));
1000 }
Mike Stump11289f42009-09-09 15:08:12 +00001001
Douglas Gregora16548e2009-08-11 05:31:07 +00001002 /// \brief Build a new extended vector element access expression.
Mike Stump11289f42009-09-09 15:08:12 +00001003 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001004 /// By default, performs semantic analysis to build the new expression.
1005 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001006 OwningExprResult RebuildExtVectorElementExpr(ExprArg Base,
Douglas Gregora16548e2009-08-11 05:31:07 +00001007 SourceLocation OpLoc,
1008 SourceLocation AccessorLoc,
1009 IdentifierInfo &Accessor) {
1010 return getSema().ActOnMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
1011 tok::period, AccessorLoc,
1012 Accessor,
1013 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0));
1014 }
Mike Stump11289f42009-09-09 15:08:12 +00001015
Douglas Gregora16548e2009-08-11 05:31:07 +00001016 /// \brief Build a new initializer list expression.
Mike Stump11289f42009-09-09 15:08:12 +00001017 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001018 /// By default, performs semantic analysis to build the new expression.
1019 /// Subclasses may override this routine to provide different behavior.
1020 OwningExprResult RebuildInitList(SourceLocation LBraceLoc,
1021 MultiExprArg Inits,
1022 SourceLocation RBraceLoc) {
1023 return SemaRef.ActOnInitList(LBraceLoc, move(Inits), RBraceLoc);
1024 }
Mike Stump11289f42009-09-09 15:08:12 +00001025
Douglas Gregora16548e2009-08-11 05:31:07 +00001026 /// \brief Build a new designated initializer expression.
Mike Stump11289f42009-09-09 15:08:12 +00001027 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001028 /// By default, performs semantic analysis to build the new expression.
1029 /// Subclasses may override this routine to provide different behavior.
1030 OwningExprResult RebuildDesignatedInitExpr(Designation &Desig,
1031 MultiExprArg ArrayExprs,
1032 SourceLocation EqualOrColonLoc,
1033 bool GNUSyntax,
1034 ExprArg Init) {
1035 OwningExprResult Result
1036 = SemaRef.ActOnDesignatedInitializer(Desig, EqualOrColonLoc, GNUSyntax,
1037 move(Init));
1038 if (Result.isInvalid())
1039 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001040
Douglas Gregora16548e2009-08-11 05:31:07 +00001041 ArrayExprs.release();
1042 return move(Result);
1043 }
Mike Stump11289f42009-09-09 15:08:12 +00001044
Douglas Gregora16548e2009-08-11 05:31:07 +00001045 /// \brief Build a new value-initialized expression.
Mike Stump11289f42009-09-09 15:08:12 +00001046 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001047 /// By default, builds the implicit value initialization without performing
1048 /// any semantic analysis. Subclasses may override this routine to provide
1049 /// different behavior.
1050 OwningExprResult RebuildImplicitValueInitExpr(QualType T) {
1051 return SemaRef.Owned(new (SemaRef.Context) ImplicitValueInitExpr(T));
1052 }
Mike Stump11289f42009-09-09 15:08:12 +00001053
Douglas Gregora16548e2009-08-11 05:31:07 +00001054 /// \brief Build a new \c va_arg expression.
Mike Stump11289f42009-09-09 15:08:12 +00001055 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001056 /// By default, performs semantic analysis to build the new expression.
1057 /// Subclasses may override this routine to provide different behavior.
1058 OwningExprResult RebuildVAArgExpr(SourceLocation BuiltinLoc, ExprArg SubExpr,
1059 QualType T, SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001060 return getSema().ActOnVAArg(BuiltinLoc, move(SubExpr), T.getAsOpaquePtr(),
Douglas Gregora16548e2009-08-11 05:31:07 +00001061 RParenLoc);
1062 }
1063
1064 /// \brief Build a new expression list in parentheses.
Mike Stump11289f42009-09-09 15:08:12 +00001065 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001066 /// By default, performs semantic analysis to build the new expression.
1067 /// Subclasses may override this routine to provide different behavior.
1068 OwningExprResult RebuildParenListExpr(SourceLocation LParenLoc,
1069 MultiExprArg SubExprs,
1070 SourceLocation RParenLoc) {
1071 return getSema().ActOnParenListExpr(LParenLoc, RParenLoc, move(SubExprs));
1072 }
Mike Stump11289f42009-09-09 15:08:12 +00001073
Douglas Gregora16548e2009-08-11 05:31:07 +00001074 /// \brief Build a new address-of-label expression.
Mike Stump11289f42009-09-09 15:08:12 +00001075 ///
1076 /// By default, performs semantic analysis, using the name of the label
Douglas Gregora16548e2009-08-11 05:31:07 +00001077 /// rather than attempting to map the label statement itself.
1078 /// Subclasses may override this routine to provide different behavior.
1079 OwningExprResult RebuildAddrLabelExpr(SourceLocation AmpAmpLoc,
1080 SourceLocation LabelLoc,
1081 LabelStmt *Label) {
1082 return getSema().ActOnAddrLabel(AmpAmpLoc, LabelLoc, Label->getID());
1083 }
Mike Stump11289f42009-09-09 15:08:12 +00001084
Douglas Gregora16548e2009-08-11 05:31:07 +00001085 /// \brief Build a new GNU statement expression.
Mike Stump11289f42009-09-09 15:08:12 +00001086 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001087 /// By default, performs semantic analysis to build the new expression.
1088 /// Subclasses may override this routine to provide different behavior.
1089 OwningExprResult RebuildStmtExpr(SourceLocation LParenLoc,
1090 StmtArg SubStmt,
1091 SourceLocation RParenLoc) {
1092 return getSema().ActOnStmtExpr(LParenLoc, move(SubStmt), RParenLoc);
1093 }
Mike Stump11289f42009-09-09 15:08:12 +00001094
Douglas Gregora16548e2009-08-11 05:31:07 +00001095 /// \brief Build a new __builtin_types_compatible_p expression.
1096 ///
1097 /// By default, performs semantic analysis to build the new expression.
1098 /// Subclasses may override this routine to provide different behavior.
1099 OwningExprResult RebuildTypesCompatibleExpr(SourceLocation BuiltinLoc,
1100 QualType T1, QualType T2,
1101 SourceLocation RParenLoc) {
1102 return getSema().ActOnTypesCompatibleExpr(BuiltinLoc,
1103 T1.getAsOpaquePtr(),
1104 T2.getAsOpaquePtr(),
1105 RParenLoc);
1106 }
Mike Stump11289f42009-09-09 15:08:12 +00001107
Douglas Gregora16548e2009-08-11 05:31:07 +00001108 /// \brief Build a new __builtin_choose_expr expression.
1109 ///
1110 /// By default, performs semantic analysis to build the new expression.
1111 /// Subclasses may override this routine to provide different behavior.
1112 OwningExprResult RebuildChooseExpr(SourceLocation BuiltinLoc,
1113 ExprArg Cond, ExprArg LHS, ExprArg RHS,
1114 SourceLocation RParenLoc) {
1115 return SemaRef.ActOnChooseExpr(BuiltinLoc,
1116 move(Cond), move(LHS), move(RHS),
1117 RParenLoc);
1118 }
Mike Stump11289f42009-09-09 15:08:12 +00001119
Douglas Gregora16548e2009-08-11 05:31:07 +00001120 /// \brief Build a new overloaded operator call expression.
1121 ///
1122 /// By default, performs semantic analysis to build the new expression.
1123 /// The semantic analysis provides the behavior of template instantiation,
1124 /// copying with transformations that turn what looks like an overloaded
Mike Stump11289f42009-09-09 15:08:12 +00001125 /// operator call into a use of a builtin operator, performing
Douglas Gregora16548e2009-08-11 05:31:07 +00001126 /// argument-dependent lookup, etc. Subclasses may override this routine to
1127 /// provide different behavior.
1128 OwningExprResult RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
1129 SourceLocation OpLoc,
1130 ExprArg Callee,
1131 ExprArg First,
1132 ExprArg Second);
Mike Stump11289f42009-09-09 15:08:12 +00001133
1134 /// \brief Build a new C++ "named" cast expression, such as static_cast or
Douglas Gregora16548e2009-08-11 05:31:07 +00001135 /// reinterpret_cast.
1136 ///
1137 /// By default, this routine dispatches to one of the more-specific routines
Mike Stump11289f42009-09-09 15:08:12 +00001138 /// for a particular named case, e.g., RebuildCXXStaticCastExpr().
Douglas Gregora16548e2009-08-11 05:31:07 +00001139 /// Subclasses may override this routine to provide different behavior.
1140 OwningExprResult RebuildCXXNamedCastExpr(SourceLocation OpLoc,
1141 Stmt::StmtClass Class,
1142 SourceLocation LAngleLoc,
1143 QualType T,
1144 SourceLocation RAngleLoc,
1145 SourceLocation LParenLoc,
1146 ExprArg SubExpr,
1147 SourceLocation RParenLoc) {
1148 switch (Class) {
1149 case Stmt::CXXStaticCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001150 return getDerived().RebuildCXXStaticCastExpr(OpLoc, LAngleLoc, T,
1151 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001152 move(SubExpr), RParenLoc);
1153
1154 case Stmt::CXXDynamicCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001155 return getDerived().RebuildCXXDynamicCastExpr(OpLoc, LAngleLoc, T,
1156 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001157 move(SubExpr), RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001158
Douglas Gregora16548e2009-08-11 05:31:07 +00001159 case Stmt::CXXReinterpretCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001160 return getDerived().RebuildCXXReinterpretCastExpr(OpLoc, LAngleLoc, T,
1161 RAngleLoc, LParenLoc,
1162 move(SubExpr),
Douglas Gregora16548e2009-08-11 05:31:07 +00001163 RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001164
Douglas Gregora16548e2009-08-11 05:31:07 +00001165 case Stmt::CXXConstCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001166 return getDerived().RebuildCXXConstCastExpr(OpLoc, LAngleLoc, T,
1167 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001168 move(SubExpr), RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001169
Douglas Gregora16548e2009-08-11 05:31:07 +00001170 default:
1171 assert(false && "Invalid C++ named cast");
1172 break;
1173 }
Mike Stump11289f42009-09-09 15:08:12 +00001174
Douglas Gregora16548e2009-08-11 05:31:07 +00001175 return getSema().ExprError();
1176 }
Mike Stump11289f42009-09-09 15:08:12 +00001177
Douglas Gregora16548e2009-08-11 05:31:07 +00001178 /// \brief Build a new C++ static_cast expression.
1179 ///
1180 /// By default, performs semantic analysis to build the new expression.
1181 /// Subclasses may override this routine to provide different behavior.
1182 OwningExprResult RebuildCXXStaticCastExpr(SourceLocation OpLoc,
1183 SourceLocation LAngleLoc,
1184 QualType T,
1185 SourceLocation RAngleLoc,
1186 SourceLocation LParenLoc,
1187 ExprArg SubExpr,
1188 SourceLocation RParenLoc) {
1189 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_static_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001190 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001191 LParenLoc, move(SubExpr), RParenLoc);
1192 }
1193
1194 /// \brief Build a new C++ dynamic_cast expression.
1195 ///
1196 /// By default, performs semantic analysis to build the new expression.
1197 /// Subclasses may override this routine to provide different behavior.
1198 OwningExprResult RebuildCXXDynamicCastExpr(SourceLocation OpLoc,
1199 SourceLocation LAngleLoc,
1200 QualType T,
1201 SourceLocation RAngleLoc,
1202 SourceLocation LParenLoc,
1203 ExprArg SubExpr,
1204 SourceLocation RParenLoc) {
1205 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_dynamic_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001206 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001207 LParenLoc, move(SubExpr), RParenLoc);
1208 }
1209
1210 /// \brief Build a new C++ reinterpret_cast expression.
1211 ///
1212 /// By default, performs semantic analysis to build the new expression.
1213 /// Subclasses may override this routine to provide different behavior.
1214 OwningExprResult RebuildCXXReinterpretCastExpr(SourceLocation OpLoc,
1215 SourceLocation LAngleLoc,
1216 QualType T,
1217 SourceLocation RAngleLoc,
1218 SourceLocation LParenLoc,
1219 ExprArg SubExpr,
1220 SourceLocation RParenLoc) {
1221 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_reinterpret_cast,
1222 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1223 LParenLoc, move(SubExpr), RParenLoc);
1224 }
1225
1226 /// \brief Build a new C++ const_cast expression.
1227 ///
1228 /// By default, performs semantic analysis to build the new expression.
1229 /// Subclasses may override this routine to provide different behavior.
1230 OwningExprResult RebuildCXXConstCastExpr(SourceLocation OpLoc,
1231 SourceLocation LAngleLoc,
1232 QualType T,
1233 SourceLocation RAngleLoc,
1234 SourceLocation LParenLoc,
1235 ExprArg SubExpr,
1236 SourceLocation RParenLoc) {
1237 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_const_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001238 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001239 LParenLoc, move(SubExpr), RParenLoc);
1240 }
Mike Stump11289f42009-09-09 15:08:12 +00001241
Douglas Gregora16548e2009-08-11 05:31:07 +00001242 /// \brief Build a new C++ functional-style cast expression.
1243 ///
1244 /// By default, performs semantic analysis to build the new expression.
1245 /// Subclasses may override this routine to provide different behavior.
1246 OwningExprResult RebuildCXXFunctionalCastExpr(SourceRange TypeRange,
1247 QualType T,
1248 SourceLocation LParenLoc,
1249 ExprArg SubExpr,
1250 SourceLocation RParenLoc) {
Chris Lattnerdca19592009-08-24 05:19:01 +00001251 void *Sub = SubExpr.takeAs<Expr>();
Douglas Gregora16548e2009-08-11 05:31:07 +00001252 return getSema().ActOnCXXTypeConstructExpr(TypeRange,
1253 T.getAsOpaquePtr(),
1254 LParenLoc,
Chris Lattnerdca19592009-08-24 05:19:01 +00001255 Sema::MultiExprArg(getSema(), &Sub, 1),
Mike Stump11289f42009-09-09 15:08:12 +00001256 /*CommaLocs=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001257 RParenLoc);
1258 }
Mike Stump11289f42009-09-09 15:08:12 +00001259
Douglas Gregora16548e2009-08-11 05:31:07 +00001260 /// \brief Build a new C++ typeid(type) expression.
1261 ///
1262 /// By default, performs semantic analysis to build the new expression.
1263 /// Subclasses may override this routine to provide different behavior.
1264 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1265 SourceLocation LParenLoc,
1266 QualType T,
1267 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001268 return getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, true,
Douglas Gregora16548e2009-08-11 05:31:07 +00001269 T.getAsOpaquePtr(), RParenLoc);
1270 }
Mike Stump11289f42009-09-09 15:08:12 +00001271
Douglas Gregora16548e2009-08-11 05:31:07 +00001272 /// \brief Build a new C++ typeid(expr) expression.
1273 ///
1274 /// By default, performs semantic analysis to build the new expression.
1275 /// Subclasses may override this routine to provide different behavior.
1276 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1277 SourceLocation LParenLoc,
1278 ExprArg Operand,
1279 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001280 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00001281 = getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, false, Operand.get(),
1282 RParenLoc);
1283 if (Result.isInvalid())
1284 return getSema().ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001285
Douglas Gregora16548e2009-08-11 05:31:07 +00001286 Operand.release(); // FIXME: since ActOnCXXTypeid silently took ownership
1287 return move(Result);
Mike Stump11289f42009-09-09 15:08:12 +00001288 }
1289
Douglas Gregora16548e2009-08-11 05:31:07 +00001290 /// \brief Build a new C++ "this" expression.
1291 ///
1292 /// By default, builds a new "this" expression without performing any
Mike Stump11289f42009-09-09 15:08:12 +00001293 /// semantic analysis. Subclasses may override this routine to provide
Douglas Gregora16548e2009-08-11 05:31:07 +00001294 /// different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001295 OwningExprResult RebuildCXXThisExpr(SourceLocation ThisLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001296 QualType ThisType) {
1297 return getSema().Owned(
1298 new (getSema().Context) CXXThisExpr(ThisLoc, ThisType));
1299 }
1300
1301 /// \brief Build a new C++ throw expression.
1302 ///
1303 /// By default, performs semantic analysis to build the new expression.
1304 /// Subclasses may override this routine to provide different behavior.
1305 OwningExprResult RebuildCXXThrowExpr(SourceLocation ThrowLoc, ExprArg Sub) {
1306 return getSema().ActOnCXXThrow(ThrowLoc, move(Sub));
1307 }
1308
1309 /// \brief Build a new C++ default-argument expression.
1310 ///
1311 /// By default, builds a new default-argument expression, which does not
1312 /// require any semantic analysis. Subclasses may override this routine to
1313 /// provide different behavior.
1314 OwningExprResult RebuildCXXDefaultArgExpr(ParmVarDecl *Param) {
Anders Carlssone8271232009-08-14 18:30:22 +00001315 return getSema().Owned(CXXDefaultArgExpr::Create(getSema().Context, Param));
Douglas Gregora16548e2009-08-11 05:31:07 +00001316 }
1317
1318 /// \brief Build a new C++ zero-initialization expression.
1319 ///
1320 /// By default, performs semantic analysis to build the new expression.
1321 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001322 OwningExprResult RebuildCXXZeroInitValueExpr(SourceLocation TypeStartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001323 SourceLocation LParenLoc,
1324 QualType T,
1325 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001326 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeStartLoc),
1327 T.getAsOpaquePtr(), LParenLoc,
1328 MultiExprArg(getSema(), 0, 0),
Douglas Gregora16548e2009-08-11 05:31:07 +00001329 0, RParenLoc);
1330 }
Mike Stump11289f42009-09-09 15:08:12 +00001331
Douglas Gregora16548e2009-08-11 05:31:07 +00001332 /// \brief Build a new C++ conditional declaration expression.
1333 ///
1334 /// By default, performs semantic analysis to build the new expression.
1335 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001336 OwningExprResult RebuildCXXConditionDeclExpr(SourceLocation StartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001337 SourceLocation EqLoc,
1338 VarDecl *Var) {
1339 return SemaRef.Owned(new (SemaRef.Context) CXXConditionDeclExpr(StartLoc,
1340 EqLoc,
1341 Var));
1342 }
Mike Stump11289f42009-09-09 15:08:12 +00001343
Douglas Gregora16548e2009-08-11 05:31:07 +00001344 /// \brief Build a new C++ "new" expression.
1345 ///
1346 /// By default, performs semantic analysis to build the new expression.
1347 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001348 OwningExprResult RebuildCXXNewExpr(SourceLocation StartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001349 bool UseGlobal,
1350 SourceLocation PlacementLParen,
1351 MultiExprArg PlacementArgs,
1352 SourceLocation PlacementRParen,
Mike Stump11289f42009-09-09 15:08:12 +00001353 bool ParenTypeId,
Douglas Gregora16548e2009-08-11 05:31:07 +00001354 QualType AllocType,
1355 SourceLocation TypeLoc,
1356 SourceRange TypeRange,
1357 ExprArg ArraySize,
1358 SourceLocation ConstructorLParen,
1359 MultiExprArg ConstructorArgs,
1360 SourceLocation ConstructorRParen) {
Mike Stump11289f42009-09-09 15:08:12 +00001361 return getSema().BuildCXXNew(StartLoc, UseGlobal,
Douglas Gregora16548e2009-08-11 05:31:07 +00001362 PlacementLParen,
1363 move(PlacementArgs),
1364 PlacementRParen,
1365 ParenTypeId,
1366 AllocType,
1367 TypeLoc,
1368 TypeRange,
1369 move(ArraySize),
1370 ConstructorLParen,
1371 move(ConstructorArgs),
1372 ConstructorRParen);
1373 }
Mike Stump11289f42009-09-09 15:08:12 +00001374
Douglas Gregora16548e2009-08-11 05:31:07 +00001375 /// \brief Build a new C++ "delete" expression.
1376 ///
1377 /// By default, performs semantic analysis to build the new expression.
1378 /// Subclasses may override this routine to provide different behavior.
1379 OwningExprResult RebuildCXXDeleteExpr(SourceLocation StartLoc,
1380 bool IsGlobalDelete,
1381 bool IsArrayForm,
1382 ExprArg Operand) {
1383 return getSema().ActOnCXXDelete(StartLoc, IsGlobalDelete, IsArrayForm,
1384 move(Operand));
1385 }
Mike Stump11289f42009-09-09 15:08:12 +00001386
Douglas Gregora16548e2009-08-11 05:31:07 +00001387 /// \brief Build a new unary type trait expression.
1388 ///
1389 /// By default, performs semantic analysis to build the new expression.
1390 /// Subclasses may override this routine to provide different behavior.
1391 OwningExprResult RebuildUnaryTypeTrait(UnaryTypeTrait Trait,
1392 SourceLocation StartLoc,
1393 SourceLocation LParenLoc,
1394 QualType T,
1395 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001396 return getSema().ActOnUnaryTypeTrait(Trait, StartLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001397 T.getAsOpaquePtr(), RParenLoc);
1398 }
1399
Mike Stump11289f42009-09-09 15:08:12 +00001400 /// \brief Build a new (previously unresolved) declaration reference
Douglas Gregora16548e2009-08-11 05:31:07 +00001401 /// expression.
1402 ///
1403 /// By default, performs semantic analysis to build the new expression.
1404 /// Subclasses may override this routine to provide different behavior.
1405 OwningExprResult RebuildUnresolvedDeclRefExpr(NestedNameSpecifier *NNS,
1406 SourceRange QualifierRange,
1407 DeclarationName Name,
1408 SourceLocation Location,
1409 bool IsAddressOfOperand) {
1410 CXXScopeSpec SS;
1411 SS.setRange(QualifierRange);
1412 SS.setScopeRep(NNS);
Mike Stump11289f42009-09-09 15:08:12 +00001413 return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001414 Location,
1415 Name,
1416 /*Trailing lparen=*/false,
1417 &SS,
1418 IsAddressOfOperand);
1419 }
1420
1421 /// \brief Build a new template-id expression.
1422 ///
1423 /// By default, performs semantic analysis to build the new expression.
1424 /// Subclasses may override this routine to provide different behavior.
Douglas Gregord019ff62009-10-22 17:20:55 +00001425 OwningExprResult RebuildTemplateIdExpr(NestedNameSpecifier *Qualifier,
1426 SourceRange QualifierRange,
1427 TemplateName Template,
Douglas Gregora16548e2009-08-11 05:31:07 +00001428 SourceLocation TemplateLoc,
1429 SourceLocation LAngleLoc,
1430 TemplateArgument *TemplateArgs,
1431 unsigned NumTemplateArgs,
1432 SourceLocation RAngleLoc) {
Douglas Gregord019ff62009-10-22 17:20:55 +00001433 return getSema().BuildTemplateIdExpr(Qualifier, QualifierRange,
1434 Template, TemplateLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001435 LAngleLoc,
1436 TemplateArgs, NumTemplateArgs,
1437 RAngleLoc);
1438 }
1439
1440 /// \brief Build a new object-construction expression.
1441 ///
1442 /// By default, performs semantic analysis to build the new expression.
1443 /// Subclasses may override this routine to provide different behavior.
1444 OwningExprResult RebuildCXXConstructExpr(QualType T,
1445 CXXConstructorDecl *Constructor,
1446 bool IsElidable,
1447 MultiExprArg Args) {
Anders Carlsson1b4ebfa2009-09-05 07:40:38 +00001448 return getSema().BuildCXXConstructExpr(/*FIXME:ConstructLoc*/
1449 SourceLocation(),
1450 T, Constructor, IsElidable,
Anders Carlsson5995a3e2009-09-07 22:23:31 +00001451 move(Args));
Douglas Gregora16548e2009-08-11 05:31:07 +00001452 }
1453
1454 /// \brief Build a new object-construction expression.
1455 ///
1456 /// By default, performs semantic analysis to build the new expression.
1457 /// Subclasses may override this routine to provide different behavior.
1458 OwningExprResult RebuildCXXTemporaryObjectExpr(SourceLocation TypeBeginLoc,
1459 QualType T,
1460 SourceLocation LParenLoc,
1461 MultiExprArg Args,
1462 SourceLocation *Commas,
1463 SourceLocation RParenLoc) {
1464 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc),
1465 T.getAsOpaquePtr(),
1466 LParenLoc,
1467 move(Args),
1468 Commas,
1469 RParenLoc);
1470 }
1471
1472 /// \brief Build a new object-construction expression.
1473 ///
1474 /// By default, performs semantic analysis to build the new expression.
1475 /// Subclasses may override this routine to provide different behavior.
1476 OwningExprResult RebuildCXXUnresolvedConstructExpr(SourceLocation TypeBeginLoc,
1477 QualType T,
1478 SourceLocation LParenLoc,
1479 MultiExprArg Args,
1480 SourceLocation *Commas,
1481 SourceLocation RParenLoc) {
1482 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc,
1483 /*FIXME*/LParenLoc),
1484 T.getAsOpaquePtr(),
1485 LParenLoc,
1486 move(Args),
1487 Commas,
1488 RParenLoc);
1489 }
Mike Stump11289f42009-09-09 15:08:12 +00001490
Douglas Gregora16548e2009-08-11 05:31:07 +00001491 /// \brief Build a new member reference expression.
1492 ///
1493 /// By default, performs semantic analysis to build the new expression.
1494 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor2168a9f2009-08-11 15:56:57 +00001495 OwningExprResult RebuildCXXUnresolvedMemberExpr(ExprArg BaseE,
Douglas Gregora16548e2009-08-11 05:31:07 +00001496 bool IsArrow,
1497 SourceLocation OperatorLoc,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001498 NestedNameSpecifier *Qualifier,
1499 SourceRange QualifierRange,
Douglas Gregora16548e2009-08-11 05:31:07 +00001500 DeclarationName Name,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001501 SourceLocation MemberLoc,
1502 NamedDecl *FirstQualifierInScope) {
Douglas Gregor2168a9f2009-08-11 15:56:57 +00001503 OwningExprResult Base = move(BaseE);
Douglas Gregora16548e2009-08-11 05:31:07 +00001504 tok::TokenKind OpKind = IsArrow? tok::arrow : tok::period;
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001505
Douglas Gregora16548e2009-08-11 05:31:07 +00001506 CXXScopeSpec SS;
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001507 SS.setRange(QualifierRange);
1508 SS.setScopeRep(Qualifier);
Mike Stump11289f42009-09-09 15:08:12 +00001509
Douglas Gregor308047d2009-09-09 00:23:06 +00001510 return SemaRef.BuildMemberReferenceExpr(/*Scope=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001511 move(Base), OperatorLoc, OpKind,
Douglas Gregorf14b46f2009-08-31 20:00:26 +00001512 MemberLoc,
1513 Name,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001514 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001515 &SS,
1516 FirstQualifierInScope);
Douglas Gregora16548e2009-08-11 05:31:07 +00001517 }
1518
Douglas Gregor308047d2009-09-09 00:23:06 +00001519 /// \brief Build a new member reference expression with explicit template
1520 /// arguments.
1521 ///
1522 /// By default, performs semantic analysis to build the new expression.
1523 /// Subclasses may override this routine to provide different behavior.
1524 OwningExprResult RebuildCXXUnresolvedMemberExpr(ExprArg BaseE,
1525 bool IsArrow,
1526 SourceLocation OperatorLoc,
1527 NestedNameSpecifier *Qualifier,
1528 SourceRange QualifierRange,
1529 TemplateName Template,
1530 SourceLocation TemplateNameLoc,
1531 NamedDecl *FirstQualifierInScope,
1532 SourceLocation LAngleLoc,
1533 const TemplateArgument *TemplateArgs,
1534 unsigned NumTemplateArgs,
1535 SourceLocation RAngleLoc) {
1536 OwningExprResult Base = move(BaseE);
1537 tok::TokenKind OpKind = IsArrow? tok::arrow : tok::period;
Mike Stump11289f42009-09-09 15:08:12 +00001538
Douglas Gregor308047d2009-09-09 00:23:06 +00001539 CXXScopeSpec SS;
1540 SS.setRange(QualifierRange);
1541 SS.setScopeRep(Qualifier);
Mike Stump11289f42009-09-09 15:08:12 +00001542
Douglas Gregor308047d2009-09-09 00:23:06 +00001543 // FIXME: We're going to end up looking up the template based on its name,
1544 // twice! Also, duplicates part of Sema::ActOnMemberTemplateIdReferenceExpr.
1545 DeclarationName Name;
1546 if (TemplateDecl *ActualTemplate = Template.getAsTemplateDecl())
1547 Name = ActualTemplate->getDeclName();
Mike Stump11289f42009-09-09 15:08:12 +00001548 else if (OverloadedFunctionDecl *Ovl
Douglas Gregor308047d2009-09-09 00:23:06 +00001549 = Template.getAsOverloadedFunctionDecl())
1550 Name = Ovl->getDeclName();
1551 else
1552 Name = Template.getAsDependentTemplateName()->getName();
Mike Stump11289f42009-09-09 15:08:12 +00001553
1554 return SemaRef.BuildMemberReferenceExpr(/*Scope=*/0, move(Base),
Douglas Gregor308047d2009-09-09 00:23:06 +00001555 OperatorLoc, OpKind,
1556 TemplateNameLoc, Name, true,
1557 LAngleLoc, TemplateArgs,
1558 NumTemplateArgs, RAngleLoc,
1559 Sema::DeclPtrTy(), &SS);
1560 }
Mike Stump11289f42009-09-09 15:08:12 +00001561
Douglas Gregora16548e2009-08-11 05:31:07 +00001562 /// \brief Build a new Objective-C @encode expression.
1563 ///
1564 /// By default, performs semantic analysis to build the new expression.
1565 /// Subclasses may override this routine to provide different behavior.
1566 OwningExprResult RebuildObjCEncodeExpr(SourceLocation AtLoc,
1567 QualType T,
1568 SourceLocation RParenLoc) {
1569 return SemaRef.Owned(SemaRef.BuildObjCEncodeExpression(AtLoc, T,
1570 RParenLoc));
Mike Stump11289f42009-09-09 15:08:12 +00001571 }
Douglas Gregora16548e2009-08-11 05:31:07 +00001572
1573 /// \brief Build a new Objective-C protocol expression.
1574 ///
1575 /// By default, performs semantic analysis to build the new expression.
1576 /// Subclasses may override this routine to provide different behavior.
1577 OwningExprResult RebuildObjCProtocolExpr(ObjCProtocolDecl *Protocol,
1578 SourceLocation AtLoc,
1579 SourceLocation ProtoLoc,
1580 SourceLocation LParenLoc,
1581 SourceLocation RParenLoc) {
1582 return SemaRef.Owned(SemaRef.ParseObjCProtocolExpression(
1583 Protocol->getIdentifier(),
1584 AtLoc,
1585 ProtoLoc,
1586 LParenLoc,
Mike Stump11289f42009-09-09 15:08:12 +00001587 RParenLoc));
Douglas Gregora16548e2009-08-11 05:31:07 +00001588 }
Mike Stump11289f42009-09-09 15:08:12 +00001589
Douglas Gregora16548e2009-08-11 05:31:07 +00001590 /// \brief Build a new shuffle vector expression.
1591 ///
1592 /// By default, performs semantic analysis to build the new expression.
1593 /// Subclasses may override this routine to provide different behavior.
1594 OwningExprResult RebuildShuffleVectorExpr(SourceLocation BuiltinLoc,
1595 MultiExprArg SubExprs,
1596 SourceLocation RParenLoc) {
1597 // Find the declaration for __builtin_shufflevector
Mike Stump11289f42009-09-09 15:08:12 +00001598 const IdentifierInfo &Name
Douglas Gregora16548e2009-08-11 05:31:07 +00001599 = SemaRef.Context.Idents.get("__builtin_shufflevector");
1600 TranslationUnitDecl *TUDecl = SemaRef.Context.getTranslationUnitDecl();
1601 DeclContext::lookup_result Lookup = TUDecl->lookup(DeclarationName(&Name));
1602 assert(Lookup.first != Lookup.second && "No __builtin_shufflevector?");
Mike Stump11289f42009-09-09 15:08:12 +00001603
Douglas Gregora16548e2009-08-11 05:31:07 +00001604 // Build a reference to the __builtin_shufflevector builtin
1605 FunctionDecl *Builtin = cast<FunctionDecl>(*Lookup.first);
Mike Stump11289f42009-09-09 15:08:12 +00001606 Expr *Callee
Douglas Gregora16548e2009-08-11 05:31:07 +00001607 = new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(),
1608 BuiltinLoc, false, false);
1609 SemaRef.UsualUnaryConversions(Callee);
Mike Stump11289f42009-09-09 15:08:12 +00001610
1611 // Build the CallExpr
Douglas Gregora16548e2009-08-11 05:31:07 +00001612 unsigned NumSubExprs = SubExprs.size();
1613 Expr **Subs = (Expr **)SubExprs.release();
1614 CallExpr *TheCall = new (SemaRef.Context) CallExpr(SemaRef.Context, Callee,
1615 Subs, NumSubExprs,
1616 Builtin->getResultType(),
1617 RParenLoc);
1618 OwningExprResult OwnedCall(SemaRef.Owned(TheCall));
Mike Stump11289f42009-09-09 15:08:12 +00001619
Douglas Gregora16548e2009-08-11 05:31:07 +00001620 // Type-check the __builtin_shufflevector expression.
1621 OwningExprResult Result = SemaRef.SemaBuiltinShuffleVector(TheCall);
1622 if (Result.isInvalid())
1623 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001624
Douglas Gregora16548e2009-08-11 05:31:07 +00001625 OwnedCall.release();
Mike Stump11289f42009-09-09 15:08:12 +00001626 return move(Result);
Douglas Gregora16548e2009-08-11 05:31:07 +00001627 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00001628};
Douglas Gregora16548e2009-08-11 05:31:07 +00001629
Douglas Gregorebe10102009-08-20 07:17:43 +00001630template<typename Derived>
1631Sema::OwningStmtResult TreeTransform<Derived>::TransformStmt(Stmt *S) {
1632 if (!S)
1633 return SemaRef.Owned(S);
Mike Stump11289f42009-09-09 15:08:12 +00001634
Douglas Gregorebe10102009-08-20 07:17:43 +00001635 switch (S->getStmtClass()) {
1636 case Stmt::NoStmtClass: break;
Mike Stump11289f42009-09-09 15:08:12 +00001637
Douglas Gregorebe10102009-08-20 07:17:43 +00001638 // Transform individual statement nodes
1639#define STMT(Node, Parent) \
1640 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S));
1641#define EXPR(Node, Parent)
1642#include "clang/AST/StmtNodes.def"
Mike Stump11289f42009-09-09 15:08:12 +00001643
Douglas Gregorebe10102009-08-20 07:17:43 +00001644 // Transform expressions by calling TransformExpr.
1645#define STMT(Node, Parent)
1646#define EXPR(Node, Parent) case Stmt::Node##Class:
1647#include "clang/AST/StmtNodes.def"
1648 {
1649 Sema::OwningExprResult E = getDerived().TransformExpr(cast<Expr>(S));
1650 if (E.isInvalid())
1651 return getSema().StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00001652
Douglas Gregorebe10102009-08-20 07:17:43 +00001653 return getSema().Owned(E.takeAs<Stmt>());
1654 }
Mike Stump11289f42009-09-09 15:08:12 +00001655 }
1656
Douglas Gregorebe10102009-08-20 07:17:43 +00001657 return SemaRef.Owned(S->Retain());
1658}
Mike Stump11289f42009-09-09 15:08:12 +00001659
1660
Douglas Gregore922c772009-08-04 22:27:00 +00001661template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00001662Sema::OwningExprResult TreeTransform<Derived>::TransformExpr(Expr *E,
1663 bool isAddressOfOperand) {
1664 if (!E)
1665 return SemaRef.Owned(E);
1666
1667 switch (E->getStmtClass()) {
1668 case Stmt::NoStmtClass: break;
1669#define STMT(Node, Parent) case Stmt::Node##Class: break;
1670#define EXPR(Node, Parent) \
1671 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E));
1672#include "clang/AST/StmtNodes.def"
Mike Stump11289f42009-09-09 15:08:12 +00001673 }
1674
Douglas Gregora16548e2009-08-11 05:31:07 +00001675 return SemaRef.Owned(E->Retain());
Douglas Gregor766b0bb2009-08-06 22:17:10 +00001676}
1677
1678template<typename Derived>
Douglas Gregor1135c352009-08-06 05:28:30 +00001679NestedNameSpecifier *
1680TreeTransform<Derived>::TransformNestedNameSpecifier(NestedNameSpecifier *NNS,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001681 SourceRange Range,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001682 QualType ObjectType,
1683 NamedDecl *FirstQualifierInScope) {
Douglas Gregor96ee7892009-08-31 21:41:48 +00001684 if (!NNS)
1685 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001686
Douglas Gregorebe10102009-08-20 07:17:43 +00001687 // Transform the prefix of this nested name specifier.
Douglas Gregor1135c352009-08-06 05:28:30 +00001688 NestedNameSpecifier *Prefix = NNS->getPrefix();
1689 if (Prefix) {
Mike Stump11289f42009-09-09 15:08:12 +00001690 Prefix = getDerived().TransformNestedNameSpecifier(Prefix, Range,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001691 ObjectType,
1692 FirstQualifierInScope);
Douglas Gregor1135c352009-08-06 05:28:30 +00001693 if (!Prefix)
1694 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001695
1696 // Clear out the object type and the first qualifier in scope; they only
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001697 // apply to the first element in the nested-name-specifier.
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001698 ObjectType = QualType();
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001699 FirstQualifierInScope = 0;
Douglas Gregor1135c352009-08-06 05:28:30 +00001700 }
Mike Stump11289f42009-09-09 15:08:12 +00001701
Douglas Gregor1135c352009-08-06 05:28:30 +00001702 switch (NNS->getKind()) {
1703 case NestedNameSpecifier::Identifier:
Mike Stump11289f42009-09-09 15:08:12 +00001704 assert((Prefix || !ObjectType.isNull()) &&
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001705 "Identifier nested-name-specifier with no prefix or object type");
1706 if (!getDerived().AlwaysRebuild() && Prefix == NNS->getPrefix() &&
1707 ObjectType.isNull())
Douglas Gregor1135c352009-08-06 05:28:30 +00001708 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001709
1710 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001711 *NNS->getAsIdentifier(),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001712 ObjectType,
1713 FirstQualifierInScope);
Mike Stump11289f42009-09-09 15:08:12 +00001714
Douglas Gregor1135c352009-08-06 05:28:30 +00001715 case NestedNameSpecifier::Namespace: {
Mike Stump11289f42009-09-09 15:08:12 +00001716 NamespaceDecl *NS
Douglas Gregor1135c352009-08-06 05:28:30 +00001717 = cast_or_null<NamespaceDecl>(
1718 getDerived().TransformDecl(NNS->getAsNamespace()));
Mike Stump11289f42009-09-09 15:08:12 +00001719 if (!getDerived().AlwaysRebuild() &&
Douglas Gregor1135c352009-08-06 05:28:30 +00001720 Prefix == NNS->getPrefix() &&
1721 NS == NNS->getAsNamespace())
1722 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001723
Douglas Gregor1135c352009-08-06 05:28:30 +00001724 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, NS);
1725 }
Mike Stump11289f42009-09-09 15:08:12 +00001726
Douglas Gregor1135c352009-08-06 05:28:30 +00001727 case NestedNameSpecifier::Global:
1728 // There is no meaningful transformation that one could perform on the
1729 // global scope.
1730 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001731
Douglas Gregor1135c352009-08-06 05:28:30 +00001732 case NestedNameSpecifier::TypeSpecWithTemplate:
1733 case NestedNameSpecifier::TypeSpec: {
1734 QualType T = getDerived().TransformType(QualType(NNS->getAsType(), 0));
Douglas Gregor71dc5092009-08-06 06:41:21 +00001735 if (T.isNull())
1736 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001737
Douglas Gregor1135c352009-08-06 05:28:30 +00001738 if (!getDerived().AlwaysRebuild() &&
1739 Prefix == NNS->getPrefix() &&
1740 T == QualType(NNS->getAsType(), 0))
1741 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001742
1743 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
1744 NNS->getKind() == NestedNameSpecifier::TypeSpecWithTemplate,
Douglas Gregor1135c352009-08-06 05:28:30 +00001745 T);
1746 }
1747 }
Mike Stump11289f42009-09-09 15:08:12 +00001748
Douglas Gregor1135c352009-08-06 05:28:30 +00001749 // Required to silence a GCC warning
Mike Stump11289f42009-09-09 15:08:12 +00001750 return 0;
Douglas Gregor1135c352009-08-06 05:28:30 +00001751}
1752
1753template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001754DeclarationName
Douglas Gregorf816bd72009-09-03 22:13:48 +00001755TreeTransform<Derived>::TransformDeclarationName(DeclarationName Name,
Douglas Gregorc59e5612009-10-19 22:04:39 +00001756 SourceLocation Loc,
1757 QualType ObjectType) {
Douglas Gregorf816bd72009-09-03 22:13:48 +00001758 if (!Name)
1759 return Name;
1760
1761 switch (Name.getNameKind()) {
1762 case DeclarationName::Identifier:
1763 case DeclarationName::ObjCZeroArgSelector:
1764 case DeclarationName::ObjCOneArgSelector:
1765 case DeclarationName::ObjCMultiArgSelector:
1766 case DeclarationName::CXXOperatorName:
1767 case DeclarationName::CXXUsingDirective:
1768 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001769
Douglas Gregorf816bd72009-09-03 22:13:48 +00001770 case DeclarationName::CXXConstructorName:
1771 case DeclarationName::CXXDestructorName:
1772 case DeclarationName::CXXConversionFunctionName: {
1773 TemporaryBase Rebase(*this, Loc, Name);
Douglas Gregorc59e5612009-10-19 22:04:39 +00001774 QualType T;
1775 if (!ObjectType.isNull() &&
1776 isa<TemplateSpecializationType>(Name.getCXXNameType())) {
1777 TemplateSpecializationType *SpecType
1778 = cast<TemplateSpecializationType>(Name.getCXXNameType());
1779 T = TransformTemplateSpecializationType(SpecType, ObjectType);
1780 } else
1781 T = getDerived().TransformType(Name.getCXXNameType());
Douglas Gregorf816bd72009-09-03 22:13:48 +00001782 if (T.isNull())
1783 return DeclarationName();
Mike Stump11289f42009-09-09 15:08:12 +00001784
Douglas Gregorf816bd72009-09-03 22:13:48 +00001785 return SemaRef.Context.DeclarationNames.getCXXSpecialName(
Mike Stump11289f42009-09-09 15:08:12 +00001786 Name.getNameKind(),
Douglas Gregorf816bd72009-09-03 22:13:48 +00001787 SemaRef.Context.getCanonicalType(T));
Douglas Gregorf816bd72009-09-03 22:13:48 +00001788 }
Mike Stump11289f42009-09-09 15:08:12 +00001789 }
1790
Douglas Gregorf816bd72009-09-03 22:13:48 +00001791 return DeclarationName();
1792}
1793
1794template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001795TemplateName
Douglas Gregor308047d2009-09-09 00:23:06 +00001796TreeTransform<Derived>::TransformTemplateName(TemplateName Name,
1797 QualType ObjectType) {
Douglas Gregor71dc5092009-08-06 06:41:21 +00001798 if (QualifiedTemplateName *QTN = Name.getAsQualifiedTemplateName()) {
Mike Stump11289f42009-09-09 15:08:12 +00001799 NestedNameSpecifier *NNS
Douglas Gregor71dc5092009-08-06 06:41:21 +00001800 = getDerived().TransformNestedNameSpecifier(QTN->getQualifier(),
1801 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
1802 if (!NNS)
1803 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001804
Douglas Gregor71dc5092009-08-06 06:41:21 +00001805 if (TemplateDecl *Template = QTN->getTemplateDecl()) {
Mike Stump11289f42009-09-09 15:08:12 +00001806 TemplateDecl *TransTemplate
Douglas Gregor71dc5092009-08-06 06:41:21 +00001807 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1808 if (!TransTemplate)
1809 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001810
Douglas Gregor71dc5092009-08-06 06:41:21 +00001811 if (!getDerived().AlwaysRebuild() &&
1812 NNS == QTN->getQualifier() &&
1813 TransTemplate == Template)
1814 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001815
Douglas Gregor71dc5092009-08-06 06:41:21 +00001816 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1817 TransTemplate);
1818 }
Mike Stump11289f42009-09-09 15:08:12 +00001819
Douglas Gregor71dc5092009-08-06 06:41:21 +00001820 OverloadedFunctionDecl *Ovl = QTN->getOverloadedFunctionDecl();
1821 assert(Ovl && "Not a template name or an overload set?");
Mike Stump11289f42009-09-09 15:08:12 +00001822 OverloadedFunctionDecl *TransOvl
Douglas Gregor71dc5092009-08-06 06:41:21 +00001823 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1824 if (!TransOvl)
1825 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001826
Douglas Gregor71dc5092009-08-06 06:41:21 +00001827 if (!getDerived().AlwaysRebuild() &&
1828 NNS == QTN->getQualifier() &&
1829 TransOvl == Ovl)
1830 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001831
Douglas Gregor71dc5092009-08-06 06:41:21 +00001832 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1833 TransOvl);
1834 }
Mike Stump11289f42009-09-09 15:08:12 +00001835
Douglas Gregor71dc5092009-08-06 06:41:21 +00001836 if (DependentTemplateName *DTN = Name.getAsDependentTemplateName()) {
Mike Stump11289f42009-09-09 15:08:12 +00001837 NestedNameSpecifier *NNS
Douglas Gregor71dc5092009-08-06 06:41:21 +00001838 = getDerived().TransformNestedNameSpecifier(DTN->getQualifier(),
1839 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
Douglas Gregor308047d2009-09-09 00:23:06 +00001840 if (!NNS && DTN->getQualifier())
Douglas Gregor71dc5092009-08-06 06:41:21 +00001841 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001842
Douglas Gregor71dc5092009-08-06 06:41:21 +00001843 if (!getDerived().AlwaysRebuild() &&
Douglas Gregorc59e5612009-10-19 22:04:39 +00001844 NNS == DTN->getQualifier() &&
1845 ObjectType.isNull())
Douglas Gregor71dc5092009-08-06 06:41:21 +00001846 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001847
Douglas Gregor308047d2009-09-09 00:23:06 +00001848 return getDerived().RebuildTemplateName(NNS, *DTN->getName(), ObjectType);
Douglas Gregor71dc5092009-08-06 06:41:21 +00001849 }
Mike Stump11289f42009-09-09 15:08:12 +00001850
Douglas Gregor71dc5092009-08-06 06:41:21 +00001851 if (TemplateDecl *Template = Name.getAsTemplateDecl()) {
Mike Stump11289f42009-09-09 15:08:12 +00001852 TemplateDecl *TransTemplate
Douglas Gregor71dc5092009-08-06 06:41:21 +00001853 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1854 if (!TransTemplate)
1855 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001856
Douglas Gregor71dc5092009-08-06 06:41:21 +00001857 if (!getDerived().AlwaysRebuild() &&
1858 TransTemplate == Template)
1859 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001860
Douglas Gregor71dc5092009-08-06 06:41:21 +00001861 return TemplateName(TransTemplate);
1862 }
Mike Stump11289f42009-09-09 15:08:12 +00001863
Douglas Gregor71dc5092009-08-06 06:41:21 +00001864 OverloadedFunctionDecl *Ovl = Name.getAsOverloadedFunctionDecl();
1865 assert(Ovl && "Not a template name or an overload set?");
Mike Stump11289f42009-09-09 15:08:12 +00001866 OverloadedFunctionDecl *TransOvl
Douglas Gregor71dc5092009-08-06 06:41:21 +00001867 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1868 if (!TransOvl)
1869 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001870
Douglas Gregor71dc5092009-08-06 06:41:21 +00001871 if (!getDerived().AlwaysRebuild() &&
1872 TransOvl == Ovl)
1873 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001874
Douglas Gregor71dc5092009-08-06 06:41:21 +00001875 return TemplateName(TransOvl);
1876}
1877
1878template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001879TemplateArgument
Douglas Gregore922c772009-08-04 22:27:00 +00001880TreeTransform<Derived>::TransformTemplateArgument(const TemplateArgument &Arg) {
1881 switch (Arg.getKind()) {
1882 case TemplateArgument::Null:
1883 case TemplateArgument::Integral:
1884 return Arg;
Mike Stump11289f42009-09-09 15:08:12 +00001885
Douglas Gregore922c772009-08-04 22:27:00 +00001886 case TemplateArgument::Type: {
1887 QualType T = getDerived().TransformType(Arg.getAsType());
1888 if (T.isNull())
1889 return TemplateArgument();
1890 return TemplateArgument(Arg.getLocation(), T);
1891 }
Mike Stump11289f42009-09-09 15:08:12 +00001892
Douglas Gregore922c772009-08-04 22:27:00 +00001893 case TemplateArgument::Declaration: {
1894 Decl *D = getDerived().TransformDecl(Arg.getAsDecl());
1895 if (!D)
1896 return TemplateArgument();
1897 return TemplateArgument(Arg.getLocation(), D);
1898 }
Mike Stump11289f42009-09-09 15:08:12 +00001899
Douglas Gregore922c772009-08-04 22:27:00 +00001900 case TemplateArgument::Expression: {
1901 // Template argument expressions are not potentially evaluated.
Mike Stump11289f42009-09-09 15:08:12 +00001902 EnterExpressionEvaluationContext Unevaluated(getSema(),
Douglas Gregore922c772009-08-04 22:27:00 +00001903 Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00001904
Douglas Gregore922c772009-08-04 22:27:00 +00001905 Sema::OwningExprResult E = getDerived().TransformExpr(Arg.getAsExpr());
1906 if (E.isInvalid())
1907 return TemplateArgument();
1908 return TemplateArgument(E.takeAs<Expr>());
1909 }
Mike Stump11289f42009-09-09 15:08:12 +00001910
Douglas Gregore922c772009-08-04 22:27:00 +00001911 case TemplateArgument::Pack: {
1912 llvm::SmallVector<TemplateArgument, 4> TransformedArgs;
1913 TransformedArgs.reserve(Arg.pack_size());
Mike Stump11289f42009-09-09 15:08:12 +00001914 for (TemplateArgument::pack_iterator A = Arg.pack_begin(),
Douglas Gregore922c772009-08-04 22:27:00 +00001915 AEnd = Arg.pack_end();
1916 A != AEnd; ++A) {
1917 TemplateArgument TA = getDerived().TransformTemplateArgument(*A);
1918 if (TA.isNull())
1919 return TA;
Mike Stump11289f42009-09-09 15:08:12 +00001920
Douglas Gregore922c772009-08-04 22:27:00 +00001921 TransformedArgs.push_back(TA);
1922 }
1923 TemplateArgument Result;
Mike Stump11289f42009-09-09 15:08:12 +00001924 Result.setArgumentPack(TransformedArgs.data(), TransformedArgs.size(),
Douglas Gregore922c772009-08-04 22:27:00 +00001925 true);
1926 return Result;
1927 }
1928 }
Mike Stump11289f42009-09-09 15:08:12 +00001929
Douglas Gregore922c772009-08-04 22:27:00 +00001930 // Work around bogus GCC warning
1931 return TemplateArgument();
1932}
1933
Douglas Gregord6ff3322009-08-04 16:50:30 +00001934//===----------------------------------------------------------------------===//
1935// Type transformation
1936//===----------------------------------------------------------------------===//
1937
1938template<typename Derived>
1939QualType TreeTransform<Derived>::TransformType(QualType T) {
1940 if (getDerived().AlreadyTransformed(T))
1941 return T;
Mike Stump11289f42009-09-09 15:08:12 +00001942
John McCall550e0c22009-10-21 00:40:46 +00001943 // Temporary workaround. All of these transformations should
1944 // eventually turn into transformations on TypeLocs.
1945 DeclaratorInfo *DI = getSema().Context.CreateDeclaratorInfo(T);
John McCallde889892009-10-21 00:44:26 +00001946 DI->getTypeLoc().initialize(getDerived().getBaseLocation());
John McCall550e0c22009-10-21 00:40:46 +00001947
1948 DeclaratorInfo *NewDI = getDerived().TransformType(DI);
John McCall8ccfcb52009-09-24 19:53:00 +00001949
John McCall550e0c22009-10-21 00:40:46 +00001950 if (!NewDI)
1951 return QualType();
1952
1953 return NewDI->getType();
1954}
1955
1956template<typename Derived>
1957DeclaratorInfo *TreeTransform<Derived>::TransformType(DeclaratorInfo *DI) {
1958 if (getDerived().AlreadyTransformed(DI->getType()))
1959 return DI;
1960
1961 TypeLocBuilder TLB;
1962
1963 TypeLoc TL = DI->getTypeLoc();
1964 TLB.reserve(TL.getFullDataSize());
1965
1966 QualType Result = getDerived().TransformType(TLB, TL);
1967 if (Result.isNull())
1968 return 0;
1969
1970 return TLB.getDeclaratorInfo(SemaRef.Context, Result);
1971}
1972
1973template<typename Derived>
1974QualType
1975TreeTransform<Derived>::TransformType(TypeLocBuilder &TLB, TypeLoc T) {
1976 switch (T.getTypeLocClass()) {
1977#define ABSTRACT_TYPELOC(CLASS, PARENT)
1978#define TYPELOC(CLASS, PARENT) \
1979 case TypeLoc::CLASS: \
1980 return getDerived().Transform##CLASS##Type(TLB, cast<CLASS##TypeLoc>(T));
1981#include "clang/AST/TypeLocNodes.def"
Douglas Gregord6ff3322009-08-04 16:50:30 +00001982 }
Mike Stump11289f42009-09-09 15:08:12 +00001983
John McCall550e0c22009-10-21 00:40:46 +00001984 llvm::llvm_unreachable("unhandled type loc!");
1985 return QualType();
1986}
1987
1988/// FIXME: By default, this routine adds type qualifiers only to types
1989/// that can have qualifiers, and silently suppresses those qualifiers
1990/// that are not permitted (e.g., qualifiers on reference or function
1991/// types). This is the right thing for template instantiation, but
1992/// probably not for other clients.
1993template<typename Derived>
1994QualType
1995TreeTransform<Derived>::TransformQualifiedType(TypeLocBuilder &TLB,
1996 QualifiedTypeLoc T) {
1997 Qualifiers Quals = T.getType().getQualifiers();
1998
1999 QualType Result = getDerived().TransformType(TLB, T.getUnqualifiedLoc());
2000 if (Result.isNull())
2001 return QualType();
2002
2003 // Silently suppress qualifiers if the result type can't be qualified.
2004 // FIXME: this is the right thing for template instantiation, but
2005 // probably not for other clients.
2006 if (Result->isFunctionType() || Result->isReferenceType())
Douglas Gregord6ff3322009-08-04 16:50:30 +00002007 return Result;
Mike Stump11289f42009-09-09 15:08:12 +00002008
John McCall550e0c22009-10-21 00:40:46 +00002009 Result = SemaRef.Context.getQualifiedType(Result, Quals);
2010
2011 TLB.push<QualifiedTypeLoc>(Result);
2012
2013 // No location information to preserve.
2014
2015 return Result;
2016}
2017
2018template <class TyLoc> static inline
2019QualType TransformTypeSpecType(TypeLocBuilder &TLB, TyLoc T) {
2020 TyLoc NewT = TLB.push<TyLoc>(T.getType());
2021 NewT.setNameLoc(T.getNameLoc());
2022 return T.getType();
2023}
2024
2025// Ugly metaprogramming macros because I couldn't be bothered to make
2026// the equivalent template version work.
2027#define TransformPointerLikeType(TypeClass) do { \
2028 QualType PointeeType \
2029 = getDerived().TransformType(TLB, TL.getPointeeLoc()); \
2030 if (PointeeType.isNull()) \
2031 return QualType(); \
2032 \
2033 QualType Result = TL.getType(); \
2034 if (getDerived().AlwaysRebuild() || \
2035 PointeeType != TL.getPointeeLoc().getType()) { \
2036 Result = getDerived().Rebuild##TypeClass(PointeeType); \
2037 if (Result.isNull()) \
2038 return QualType(); \
2039 } \
2040 \
2041 TypeClass##Loc NewT = TLB.push<TypeClass##Loc>(Result); \
2042 NewT.setSigilLoc(TL.getSigilLoc()); \
2043 \
2044 return Result; \
2045} while(0)
2046
2047// Reference collapsing forces us to transform reference types
2048// differently from the other pointer-like types.
2049#define TransformReferenceType(TypeClass) do { \
2050 QualType PointeeType \
2051 = getDerived().TransformType(TLB, TL.getPointeeLoc()); \
2052 if (PointeeType.isNull()) \
2053 return QualType(); \
2054 \
2055 QualType Result = TL.getType(); \
2056 if (getDerived().AlwaysRebuild() || \
2057 PointeeType != TL.getPointeeLoc().getType()) { \
2058 Result = getDerived().Rebuild##TypeClass(PointeeType); \
2059 if (Result.isNull()) \
2060 return QualType(); \
2061 } \
2062 \
2063 /* Workaround: rebuild doesn't always change the type */ \
2064 /* FIXME: avoid losing this location information. */ \
2065 if (Result == PointeeType) \
2066 return Result; \
2067 ReferenceTypeLoc NewTL; \
2068 if (isa<LValueReferenceType>(Result)) \
2069 NewTL = TLB.push<LValueReferenceTypeLoc>(Result); \
2070 else \
2071 NewTL = TLB.push<RValueReferenceTypeLoc>(Result); \
2072 NewTL.setSigilLoc(TL.getSigilLoc()); \
2073 return Result; \
2074} while (0)
2075
2076template<typename Derived>
2077QualType TreeTransform<Derived>::TransformBuiltinType(TypeLocBuilder &TLB,
2078 BuiltinTypeLoc T) {
2079 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002080}
Mike Stump11289f42009-09-09 15:08:12 +00002081
Douglas Gregord6ff3322009-08-04 16:50:30 +00002082template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002083QualType
John McCall550e0c22009-10-21 00:40:46 +00002084TreeTransform<Derived>::TransformFixedWidthIntType(TypeLocBuilder &TLB,
2085 FixedWidthIntTypeLoc T) {
2086 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002087}
Argyrios Kyrtzidise9189262009-08-19 01:28:17 +00002088
Douglas Gregord6ff3322009-08-04 16:50:30 +00002089template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002090QualType TreeTransform<Derived>::TransformComplexType(TypeLocBuilder &TLB,
2091 ComplexTypeLoc T) {
2092 // FIXME: recurse?
2093 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002094}
Mike Stump11289f42009-09-09 15:08:12 +00002095
Douglas Gregord6ff3322009-08-04 16:50:30 +00002096template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002097QualType TreeTransform<Derived>::TransformPointerType(TypeLocBuilder &TLB,
2098 PointerTypeLoc TL) {
2099 TransformPointerLikeType(PointerType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002100}
Mike Stump11289f42009-09-09 15:08:12 +00002101
2102template<typename Derived>
2103QualType
John McCall550e0c22009-10-21 00:40:46 +00002104TreeTransform<Derived>::TransformBlockPointerType(TypeLocBuilder &TLB,
2105 BlockPointerTypeLoc TL) {
2106 TransformPointerLikeType(BlockPointerType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002107}
2108
Mike Stump11289f42009-09-09 15:08:12 +00002109template<typename Derived>
2110QualType
John McCall550e0c22009-10-21 00:40:46 +00002111TreeTransform<Derived>::TransformLValueReferenceType(TypeLocBuilder &TLB,
2112 LValueReferenceTypeLoc TL) {
2113 TransformReferenceType(LValueReferenceType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002114}
2115
Mike Stump11289f42009-09-09 15:08:12 +00002116template<typename Derived>
2117QualType
John McCall550e0c22009-10-21 00:40:46 +00002118TreeTransform<Derived>::TransformRValueReferenceType(TypeLocBuilder &TLB,
2119 RValueReferenceTypeLoc TL) {
2120 TransformReferenceType(RValueReferenceType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002121}
Mike Stump11289f42009-09-09 15:08:12 +00002122
Douglas Gregord6ff3322009-08-04 16:50:30 +00002123template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002124QualType
John McCall550e0c22009-10-21 00:40:46 +00002125TreeTransform<Derived>::TransformMemberPointerType(TypeLocBuilder &TLB,
2126 MemberPointerTypeLoc TL) {
2127 MemberPointerType *T = TL.getTypePtr();
2128
2129 QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002130 if (PointeeType.isNull())
2131 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002132
John McCall550e0c22009-10-21 00:40:46 +00002133 // TODO: preserve source information for this.
2134 QualType ClassType
2135 = getDerived().TransformType(QualType(T->getClass(), 0));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002136 if (ClassType.isNull())
2137 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002138
John McCall550e0c22009-10-21 00:40:46 +00002139 QualType Result = TL.getType();
2140 if (getDerived().AlwaysRebuild() ||
2141 PointeeType != T->getPointeeType() ||
2142 ClassType != QualType(T->getClass(), 0)) {
2143 Result = getDerived().RebuildMemberPointerType(PointeeType, ClassType);
2144 if (Result.isNull())
2145 return QualType();
2146 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00002147
John McCall550e0c22009-10-21 00:40:46 +00002148 MemberPointerTypeLoc NewTL = TLB.push<MemberPointerTypeLoc>(Result);
2149 NewTL.setSigilLoc(TL.getSigilLoc());
2150
2151 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002152}
2153
Mike Stump11289f42009-09-09 15:08:12 +00002154template<typename Derived>
2155QualType
John McCall550e0c22009-10-21 00:40:46 +00002156TreeTransform<Derived>::TransformConstantArrayType(TypeLocBuilder &TLB,
2157 ConstantArrayTypeLoc TL) {
2158 ConstantArrayType *T = TL.getTypePtr();
2159 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002160 if (ElementType.isNull())
2161 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002162
John McCall550e0c22009-10-21 00:40:46 +00002163 QualType Result = TL.getType();
2164 if (getDerived().AlwaysRebuild() ||
2165 ElementType != T->getElementType()) {
2166 Result = getDerived().RebuildConstantArrayType(ElementType,
2167 T->getSizeModifier(),
2168 T->getSize(),
2169 T->getIndexTypeCVRQualifiers());
2170 if (Result.isNull())
2171 return QualType();
2172 }
2173
2174 ConstantArrayTypeLoc NewTL = TLB.push<ConstantArrayTypeLoc>(Result);
2175 NewTL.setLBracketLoc(TL.getLBracketLoc());
2176 NewTL.setRBracketLoc(TL.getRBracketLoc());
Mike Stump11289f42009-09-09 15:08:12 +00002177
John McCall550e0c22009-10-21 00:40:46 +00002178 Expr *Size = TL.getSizeExpr();
2179 if (Size) {
2180 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2181 Size = getDerived().TransformExpr(Size).template takeAs<Expr>();
2182 }
2183 NewTL.setSizeExpr(Size);
2184
2185 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002186}
Mike Stump11289f42009-09-09 15:08:12 +00002187
Douglas Gregord6ff3322009-08-04 16:50:30 +00002188template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002189QualType TreeTransform<Derived>::TransformIncompleteArrayType(
John McCall550e0c22009-10-21 00:40:46 +00002190 TypeLocBuilder &TLB,
2191 IncompleteArrayTypeLoc TL) {
2192 IncompleteArrayType *T = TL.getTypePtr();
2193 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002194 if (ElementType.isNull())
2195 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002196
John McCall550e0c22009-10-21 00:40:46 +00002197 QualType Result = TL.getType();
2198 if (getDerived().AlwaysRebuild() ||
2199 ElementType != T->getElementType()) {
2200 Result = getDerived().RebuildIncompleteArrayType(ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00002201 T->getSizeModifier(),
John McCall550e0c22009-10-21 00:40:46 +00002202 T->getIndexTypeCVRQualifiers());
2203 if (Result.isNull())
2204 return QualType();
2205 }
2206
2207 IncompleteArrayTypeLoc NewTL = TLB.push<IncompleteArrayTypeLoc>(Result);
2208 NewTL.setLBracketLoc(TL.getLBracketLoc());
2209 NewTL.setRBracketLoc(TL.getRBracketLoc());
2210 NewTL.setSizeExpr(0);
2211
2212 return Result;
2213}
2214
2215template<typename Derived>
2216QualType
2217TreeTransform<Derived>::TransformVariableArrayType(TypeLocBuilder &TLB,
2218 VariableArrayTypeLoc TL) {
2219 VariableArrayType *T = TL.getTypePtr();
2220 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
2221 if (ElementType.isNull())
2222 return QualType();
2223
2224 // Array bounds are not potentially evaluated contexts
2225 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2226
2227 Sema::OwningExprResult SizeResult
2228 = getDerived().TransformExpr(T->getSizeExpr());
2229 if (SizeResult.isInvalid())
2230 return QualType();
2231
2232 Expr *Size = static_cast<Expr*>(SizeResult.get());
2233
2234 QualType Result = TL.getType();
2235 if (getDerived().AlwaysRebuild() ||
2236 ElementType != T->getElementType() ||
2237 Size != T->getSizeExpr()) {
2238 Result = getDerived().RebuildVariableArrayType(ElementType,
2239 T->getSizeModifier(),
2240 move(SizeResult),
2241 T->getIndexTypeCVRQualifiers(),
2242 T->getBracketsRange());
2243 if (Result.isNull())
2244 return QualType();
2245 }
2246 else SizeResult.take();
2247
2248 VariableArrayTypeLoc NewTL = TLB.push<VariableArrayTypeLoc>(Result);
2249 NewTL.setLBracketLoc(TL.getLBracketLoc());
2250 NewTL.setRBracketLoc(TL.getRBracketLoc());
2251 NewTL.setSizeExpr(Size);
2252
2253 return Result;
2254}
2255
2256template<typename Derived>
2257QualType
2258TreeTransform<Derived>::TransformDependentSizedArrayType(TypeLocBuilder &TLB,
2259 DependentSizedArrayTypeLoc TL) {
2260 DependentSizedArrayType *T = TL.getTypePtr();
2261 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
2262 if (ElementType.isNull())
2263 return QualType();
2264
2265 // Array bounds are not potentially evaluated contexts
2266 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2267
2268 Sema::OwningExprResult SizeResult
2269 = getDerived().TransformExpr(T->getSizeExpr());
2270 if (SizeResult.isInvalid())
2271 return QualType();
2272
2273 Expr *Size = static_cast<Expr*>(SizeResult.get());
2274
2275 QualType Result = TL.getType();
2276 if (getDerived().AlwaysRebuild() ||
2277 ElementType != T->getElementType() ||
2278 Size != T->getSizeExpr()) {
2279 Result = getDerived().RebuildDependentSizedArrayType(ElementType,
2280 T->getSizeModifier(),
2281 move(SizeResult),
2282 T->getIndexTypeCVRQualifiers(),
2283 T->getBracketsRange());
2284 if (Result.isNull())
2285 return QualType();
2286 }
2287 else SizeResult.take();
2288
2289 // We might have any sort of array type now, but fortunately they
2290 // all have the same location layout.
2291 ArrayTypeLoc NewTL = TLB.push<ArrayTypeLoc>(Result);
2292 NewTL.setLBracketLoc(TL.getLBracketLoc());
2293 NewTL.setRBracketLoc(TL.getRBracketLoc());
2294 NewTL.setSizeExpr(Size);
2295
2296 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002297}
Mike Stump11289f42009-09-09 15:08:12 +00002298
2299template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002300QualType TreeTransform<Derived>::TransformDependentSizedExtVectorType(
John McCall550e0c22009-10-21 00:40:46 +00002301 TypeLocBuilder &TLB,
2302 DependentSizedExtVectorTypeLoc TL) {
2303 DependentSizedExtVectorType *T = TL.getTypePtr();
2304
2305 // FIXME: ext vector locs should be nested
Douglas Gregord6ff3322009-08-04 16:50:30 +00002306 QualType ElementType = getDerived().TransformType(T->getElementType());
2307 if (ElementType.isNull())
2308 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002309
Douglas Gregore922c772009-08-04 22:27:00 +00002310 // Vector sizes are not potentially evaluated contexts
2311 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2312
Douglas Gregord6ff3322009-08-04 16:50:30 +00002313 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
2314 if (Size.isInvalid())
2315 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002316
John McCall550e0c22009-10-21 00:40:46 +00002317 QualType Result = TL.getType();
2318 if (getDerived().AlwaysRebuild() ||
John McCall24e7cb62009-10-23 17:55:45 +00002319 ElementType != T->getElementType() ||
2320 Size.get() != T->getSizeExpr()) {
John McCall550e0c22009-10-21 00:40:46 +00002321 Result = getDerived().RebuildDependentSizedExtVectorType(ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00002322 move(Size),
2323 T->getAttributeLoc());
John McCall550e0c22009-10-21 00:40:46 +00002324 if (Result.isNull())
2325 return QualType();
2326 }
2327 else Size.take();
2328
2329 // Result might be dependent or not.
2330 if (isa<DependentSizedExtVectorType>(Result)) {
2331 DependentSizedExtVectorTypeLoc NewTL
2332 = TLB.push<DependentSizedExtVectorTypeLoc>(Result);
2333 NewTL.setNameLoc(TL.getNameLoc());
2334 } else {
2335 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result);
2336 NewTL.setNameLoc(TL.getNameLoc());
2337 }
2338
2339 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002340}
Mike Stump11289f42009-09-09 15:08:12 +00002341
2342template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002343QualType TreeTransform<Derived>::TransformVectorType(TypeLocBuilder &TLB,
2344 VectorTypeLoc TL) {
2345 VectorType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002346 QualType ElementType = getDerived().TransformType(T->getElementType());
2347 if (ElementType.isNull())
2348 return QualType();
2349
John McCall550e0c22009-10-21 00:40:46 +00002350 QualType Result = TL.getType();
2351 if (getDerived().AlwaysRebuild() ||
2352 ElementType != T->getElementType()) {
2353 Result = getDerived().RebuildVectorType(ElementType, T->getNumElements());
2354 if (Result.isNull())
2355 return QualType();
2356 }
2357
2358 VectorTypeLoc NewTL = TLB.push<VectorTypeLoc>(Result);
2359 NewTL.setNameLoc(TL.getNameLoc());
Mike Stump11289f42009-09-09 15:08:12 +00002360
John McCall550e0c22009-10-21 00:40:46 +00002361 return Result;
2362}
2363
2364template<typename Derived>
2365QualType TreeTransform<Derived>::TransformExtVectorType(TypeLocBuilder &TLB,
2366 ExtVectorTypeLoc TL) {
2367 VectorType *T = TL.getTypePtr();
2368 QualType ElementType = getDerived().TransformType(T->getElementType());
2369 if (ElementType.isNull())
2370 return QualType();
2371
2372 QualType Result = TL.getType();
2373 if (getDerived().AlwaysRebuild() ||
2374 ElementType != T->getElementType()) {
2375 Result = getDerived().RebuildExtVectorType(ElementType,
2376 T->getNumElements(),
2377 /*FIXME*/ SourceLocation());
2378 if (Result.isNull())
2379 return QualType();
2380 }
2381
2382 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result);
2383 NewTL.setNameLoc(TL.getNameLoc());
2384
2385 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002386}
Mike Stump11289f42009-09-09 15:08:12 +00002387
2388template<typename Derived>
2389QualType
John McCall550e0c22009-10-21 00:40:46 +00002390TreeTransform<Derived>::TransformFunctionProtoType(TypeLocBuilder &TLB,
2391 FunctionProtoTypeLoc TL) {
2392 FunctionProtoType *T = TL.getTypePtr();
2393 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002394 if (ResultType.isNull())
2395 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002396
John McCall550e0c22009-10-21 00:40:46 +00002397 // Transform the parameters.
Douglas Gregord6ff3322009-08-04 16:50:30 +00002398 llvm::SmallVector<QualType, 4> ParamTypes;
John McCall550e0c22009-10-21 00:40:46 +00002399 llvm::SmallVector<ParmVarDecl*, 4> ParamDecls;
2400 for (unsigned i = 0, e = TL.getNumArgs(); i != e; ++i) {
2401 ParmVarDecl *OldParm = TL.getArg(i);
Mike Stump11289f42009-09-09 15:08:12 +00002402
John McCall550e0c22009-10-21 00:40:46 +00002403 QualType NewType;
2404 ParmVarDecl *NewParm;
2405
2406 if (OldParm) {
2407 DeclaratorInfo *OldDI = OldParm->getDeclaratorInfo();
2408 assert(OldDI->getType() == T->getArgType(i));
2409
2410 DeclaratorInfo *NewDI = getDerived().TransformType(OldDI);
2411 if (!NewDI)
2412 return QualType();
2413
2414 if (NewDI == OldDI)
2415 NewParm = OldParm;
2416 else
2417 NewParm = ParmVarDecl::Create(SemaRef.Context,
2418 OldParm->getDeclContext(),
2419 OldParm->getLocation(),
2420 OldParm->getIdentifier(),
2421 NewDI->getType(),
2422 NewDI,
2423 OldParm->getStorageClass(),
2424 /* DefArg */ NULL);
2425 NewType = NewParm->getType();
2426
2427 // Deal with the possibility that we don't have a parameter
2428 // declaration for this parameter.
2429 } else {
2430 NewParm = 0;
2431
2432 QualType OldType = T->getArgType(i);
2433 NewType = getDerived().TransformType(OldType);
2434 if (NewType.isNull())
2435 return QualType();
2436 }
2437
2438 ParamTypes.push_back(NewType);
2439 ParamDecls.push_back(NewParm);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002440 }
Mike Stump11289f42009-09-09 15:08:12 +00002441
John McCall550e0c22009-10-21 00:40:46 +00002442 QualType Result = TL.getType();
2443 if (getDerived().AlwaysRebuild() ||
2444 ResultType != T->getResultType() ||
2445 !std::equal(T->arg_type_begin(), T->arg_type_end(), ParamTypes.begin())) {
2446 Result = getDerived().RebuildFunctionProtoType(ResultType,
2447 ParamTypes.data(),
2448 ParamTypes.size(),
2449 T->isVariadic(),
2450 T->getTypeQuals());
2451 if (Result.isNull())
2452 return QualType();
2453 }
Mike Stump11289f42009-09-09 15:08:12 +00002454
John McCall550e0c22009-10-21 00:40:46 +00002455 FunctionProtoTypeLoc NewTL = TLB.push<FunctionProtoTypeLoc>(Result);
2456 NewTL.setLParenLoc(TL.getLParenLoc());
2457 NewTL.setRParenLoc(TL.getRParenLoc());
2458 for (unsigned i = 0, e = NewTL.getNumArgs(); i != e; ++i)
2459 NewTL.setArg(i, ParamDecls[i]);
2460
2461 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002462}
Mike Stump11289f42009-09-09 15:08:12 +00002463
Douglas Gregord6ff3322009-08-04 16:50:30 +00002464template<typename Derived>
2465QualType TreeTransform<Derived>::TransformFunctionNoProtoType(
John McCall550e0c22009-10-21 00:40:46 +00002466 TypeLocBuilder &TLB,
2467 FunctionNoProtoTypeLoc TL) {
2468 FunctionNoProtoType *T = TL.getTypePtr();
2469 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc());
2470 if (ResultType.isNull())
2471 return QualType();
2472
2473 QualType Result = TL.getType();
2474 if (getDerived().AlwaysRebuild() ||
2475 ResultType != T->getResultType())
2476 Result = getDerived().RebuildFunctionNoProtoType(ResultType);
2477
2478 FunctionNoProtoTypeLoc NewTL = TLB.push<FunctionNoProtoTypeLoc>(Result);
2479 NewTL.setLParenLoc(TL.getLParenLoc());
2480 NewTL.setRParenLoc(TL.getRParenLoc());
2481
2482 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002483}
Mike Stump11289f42009-09-09 15:08:12 +00002484
Douglas Gregord6ff3322009-08-04 16:50:30 +00002485template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002486QualType TreeTransform<Derived>::TransformTypedefType(TypeLocBuilder &TLB,
2487 TypedefTypeLoc TL) {
2488 TypedefType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002489 TypedefDecl *Typedef
2490 = cast_or_null<TypedefDecl>(getDerived().TransformDecl(T->getDecl()));
2491 if (!Typedef)
2492 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002493
John McCall550e0c22009-10-21 00:40:46 +00002494 QualType Result = TL.getType();
2495 if (getDerived().AlwaysRebuild() ||
2496 Typedef != T->getDecl()) {
2497 Result = getDerived().RebuildTypedefType(Typedef);
2498 if (Result.isNull())
2499 return QualType();
2500 }
Mike Stump11289f42009-09-09 15:08:12 +00002501
John McCall550e0c22009-10-21 00:40:46 +00002502 TypedefTypeLoc NewTL = TLB.push<TypedefTypeLoc>(Result);
2503 NewTL.setNameLoc(TL.getNameLoc());
2504
2505 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002506}
Mike Stump11289f42009-09-09 15:08:12 +00002507
Douglas Gregord6ff3322009-08-04 16:50:30 +00002508template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002509QualType TreeTransform<Derived>::TransformTypeOfExprType(TypeLocBuilder &TLB,
2510 TypeOfExprTypeLoc TL) {
2511 TypeOfExprType *T = TL.getTypePtr();
2512
Douglas Gregore922c772009-08-04 22:27:00 +00002513 // typeof expressions are not potentially evaluated contexts
2514 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002515
Douglas Gregord6ff3322009-08-04 16:50:30 +00002516 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2517 if (E.isInvalid())
2518 return QualType();
2519
John McCall550e0c22009-10-21 00:40:46 +00002520 QualType Result = TL.getType();
2521 if (getDerived().AlwaysRebuild() ||
2522 E.get() != T->getUnderlyingExpr()) {
2523 Result = getDerived().RebuildTypeOfExprType(move(E));
2524 if (Result.isNull())
2525 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002526 }
John McCall550e0c22009-10-21 00:40:46 +00002527 else E.take();
Mike Stump11289f42009-09-09 15:08:12 +00002528
John McCall550e0c22009-10-21 00:40:46 +00002529 TypeOfExprTypeLoc NewTL = TLB.push<TypeOfExprTypeLoc>(Result);
2530 NewTL.setNameLoc(TL.getNameLoc());
2531
2532 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002533}
Mike Stump11289f42009-09-09 15:08:12 +00002534
2535template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002536QualType TreeTransform<Derived>::TransformTypeOfType(TypeLocBuilder &TLB,
2537 TypeOfTypeLoc TL) {
2538 TypeOfType *T = TL.getTypePtr();
2539
2540 // FIXME: should be an inner type, or at least have a DeclaratorInfo.
Douglas Gregord6ff3322009-08-04 16:50:30 +00002541 QualType Underlying = getDerived().TransformType(T->getUnderlyingType());
2542 if (Underlying.isNull())
2543 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002544
John McCall550e0c22009-10-21 00:40:46 +00002545 QualType Result = TL.getType();
2546 if (getDerived().AlwaysRebuild() ||
2547 Underlying != T->getUnderlyingType()) {
2548 Result = getDerived().RebuildTypeOfType(Underlying);
2549 if (Result.isNull())
2550 return QualType();
2551 }
Mike Stump11289f42009-09-09 15:08:12 +00002552
John McCall550e0c22009-10-21 00:40:46 +00002553 TypeOfTypeLoc NewTL = TLB.push<TypeOfTypeLoc>(Result);
2554 NewTL.setNameLoc(TL.getNameLoc());
2555
2556 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002557}
Mike Stump11289f42009-09-09 15:08:12 +00002558
2559template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002560QualType TreeTransform<Derived>::TransformDecltypeType(TypeLocBuilder &TLB,
2561 DecltypeTypeLoc TL) {
2562 DecltypeType *T = TL.getTypePtr();
2563
Douglas Gregore922c772009-08-04 22:27:00 +00002564 // decltype expressions are not potentially evaluated contexts
2565 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002566
Douglas Gregord6ff3322009-08-04 16:50:30 +00002567 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2568 if (E.isInvalid())
2569 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002570
John McCall550e0c22009-10-21 00:40:46 +00002571 QualType Result = TL.getType();
2572 if (getDerived().AlwaysRebuild() ||
2573 E.get() != T->getUnderlyingExpr()) {
2574 Result = getDerived().RebuildDecltypeType(move(E));
2575 if (Result.isNull())
2576 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002577 }
John McCall550e0c22009-10-21 00:40:46 +00002578 else E.take();
Mike Stump11289f42009-09-09 15:08:12 +00002579
John McCall550e0c22009-10-21 00:40:46 +00002580 DecltypeTypeLoc NewTL = TLB.push<DecltypeTypeLoc>(Result);
2581 NewTL.setNameLoc(TL.getNameLoc());
2582
2583 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002584}
2585
2586template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002587QualType TreeTransform<Derived>::TransformRecordType(TypeLocBuilder &TLB,
2588 RecordTypeLoc TL) {
2589 RecordType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002590 RecordDecl *Record
John McCall550e0c22009-10-21 00:40:46 +00002591 = cast_or_null<RecordDecl>(getDerived().TransformDecl(T->getDecl()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002592 if (!Record)
2593 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002594
John McCall550e0c22009-10-21 00:40:46 +00002595 QualType Result = TL.getType();
2596 if (getDerived().AlwaysRebuild() ||
2597 Record != T->getDecl()) {
2598 Result = getDerived().RebuildRecordType(Record);
2599 if (Result.isNull())
2600 return QualType();
2601 }
Mike Stump11289f42009-09-09 15:08:12 +00002602
John McCall550e0c22009-10-21 00:40:46 +00002603 RecordTypeLoc NewTL = TLB.push<RecordTypeLoc>(Result);
2604 NewTL.setNameLoc(TL.getNameLoc());
2605
2606 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002607}
Mike Stump11289f42009-09-09 15:08:12 +00002608
2609template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002610QualType TreeTransform<Derived>::TransformEnumType(TypeLocBuilder &TLB,
2611 EnumTypeLoc TL) {
2612 EnumType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002613 EnumDecl *Enum
John McCall550e0c22009-10-21 00:40:46 +00002614 = cast_or_null<EnumDecl>(getDerived().TransformDecl(T->getDecl()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002615 if (!Enum)
2616 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002617
John McCall550e0c22009-10-21 00:40:46 +00002618 QualType Result = TL.getType();
2619 if (getDerived().AlwaysRebuild() ||
2620 Enum != T->getDecl()) {
2621 Result = getDerived().RebuildEnumType(Enum);
2622 if (Result.isNull())
2623 return QualType();
2624 }
Mike Stump11289f42009-09-09 15:08:12 +00002625
John McCall550e0c22009-10-21 00:40:46 +00002626 EnumTypeLoc NewTL = TLB.push<EnumTypeLoc>(Result);
2627 NewTL.setNameLoc(TL.getNameLoc());
2628
2629 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002630}
John McCallfcc33b02009-09-05 00:15:47 +00002631
2632template <typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002633QualType TreeTransform<Derived>::TransformElaboratedType(TypeLocBuilder &TLB,
2634 ElaboratedTypeLoc TL) {
2635 ElaboratedType *T = TL.getTypePtr();
2636
2637 // FIXME: this should be a nested type.
John McCallfcc33b02009-09-05 00:15:47 +00002638 QualType Underlying = getDerived().TransformType(T->getUnderlyingType());
2639 if (Underlying.isNull())
2640 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002641
John McCall550e0c22009-10-21 00:40:46 +00002642 QualType Result = TL.getType();
2643 if (getDerived().AlwaysRebuild() ||
2644 Underlying != T->getUnderlyingType()) {
2645 Result = getDerived().RebuildElaboratedType(Underlying, T->getTagKind());
2646 if (Result.isNull())
2647 return QualType();
2648 }
Mike Stump11289f42009-09-09 15:08:12 +00002649
John McCall550e0c22009-10-21 00:40:46 +00002650 ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result);
2651 NewTL.setNameLoc(TL.getNameLoc());
2652
2653 return Result;
John McCallfcc33b02009-09-05 00:15:47 +00002654}
Mike Stump11289f42009-09-09 15:08:12 +00002655
2656
Douglas Gregord6ff3322009-08-04 16:50:30 +00002657template<typename Derived>
2658QualType TreeTransform<Derived>::TransformTemplateTypeParmType(
John McCall550e0c22009-10-21 00:40:46 +00002659 TypeLocBuilder &TLB,
2660 TemplateTypeParmTypeLoc TL) {
2661 return TransformTypeSpecType(TLB, TL);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002662}
2663
Mike Stump11289f42009-09-09 15:08:12 +00002664template<typename Derived>
John McCallcebee162009-10-18 09:09:24 +00002665QualType TreeTransform<Derived>::TransformSubstTemplateTypeParmType(
John McCall550e0c22009-10-21 00:40:46 +00002666 TypeLocBuilder &TLB,
2667 SubstTemplateTypeParmTypeLoc TL) {
2668 return TransformTypeSpecType(TLB, TL);
John McCallcebee162009-10-18 09:09:24 +00002669}
2670
2671template<typename Derived>
Douglas Gregorc59e5612009-10-19 22:04:39 +00002672inline QualType
2673TreeTransform<Derived>::TransformTemplateSpecializationType(
John McCall550e0c22009-10-21 00:40:46 +00002674 TypeLocBuilder &TLB,
2675 TemplateSpecializationTypeLoc TL) {
2676 // TODO: figure out how make this work with an ObjectType.
2677 QualType Result
2678 = TransformTemplateSpecializationType(TL.getTypePtr(), QualType());
2679 if (Result.isNull())
2680 return QualType();
2681
2682 TemplateSpecializationTypeLoc NewTL
2683 = TLB.push<TemplateSpecializationTypeLoc>(Result);
2684 NewTL.setNameLoc(TL.getNameLoc());
2685
2686 return Result;
Douglas Gregorc59e5612009-10-19 22:04:39 +00002687}
2688
2689template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002690QualType TreeTransform<Derived>::TransformTemplateSpecializationType(
Douglas Gregorc59e5612009-10-19 22:04:39 +00002691 const TemplateSpecializationType *T,
2692 QualType ObjectType) {
Mike Stump11289f42009-09-09 15:08:12 +00002693 TemplateName Template
Douglas Gregorc59e5612009-10-19 22:04:39 +00002694 = getDerived().TransformTemplateName(T->getTemplateName(), ObjectType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002695 if (Template.isNull())
2696 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002697
Douglas Gregord6ff3322009-08-04 16:50:30 +00002698 llvm::SmallVector<TemplateArgument, 4> NewTemplateArgs;
2699 NewTemplateArgs.reserve(T->getNumArgs());
2700 for (TemplateSpecializationType::iterator Arg = T->begin(), ArgEnd = T->end();
2701 Arg != ArgEnd; ++Arg) {
2702 TemplateArgument NewArg = getDerived().TransformTemplateArgument(*Arg);
2703 if (NewArg.isNull())
2704 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002705
Douglas Gregord6ff3322009-08-04 16:50:30 +00002706 NewTemplateArgs.push_back(NewArg);
2707 }
Mike Stump11289f42009-09-09 15:08:12 +00002708
Douglas Gregord6ff3322009-08-04 16:50:30 +00002709 // FIXME: early abort if all of the template arguments and such are the
2710 // same.
Mike Stump11289f42009-09-09 15:08:12 +00002711
Douglas Gregord6ff3322009-08-04 16:50:30 +00002712 // FIXME: We're missing the locations of the template name, '<', and '>'.
2713 return getDerived().RebuildTemplateSpecializationType(Template,
2714 NewTemplateArgs.data(),
2715 NewTemplateArgs.size());
2716}
Mike Stump11289f42009-09-09 15:08:12 +00002717
2718template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002719QualType
2720TreeTransform<Derived>::TransformQualifiedNameType(TypeLocBuilder &TLB,
2721 QualifiedNameTypeLoc TL) {
2722 QualifiedNameType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002723 NestedNameSpecifier *NNS
2724 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
2725 SourceRange());
2726 if (!NNS)
2727 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002728
Douglas Gregord6ff3322009-08-04 16:50:30 +00002729 QualType Named = getDerived().TransformType(T->getNamedType());
2730 if (Named.isNull())
2731 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002732
John McCall550e0c22009-10-21 00:40:46 +00002733 QualType Result = TL.getType();
2734 if (getDerived().AlwaysRebuild() ||
2735 NNS != T->getQualifier() ||
2736 Named != T->getNamedType()) {
2737 Result = getDerived().RebuildQualifiedNameType(NNS, Named);
2738 if (Result.isNull())
2739 return QualType();
2740 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00002741
John McCall550e0c22009-10-21 00:40:46 +00002742 QualifiedNameTypeLoc NewTL = TLB.push<QualifiedNameTypeLoc>(Result);
2743 NewTL.setNameLoc(TL.getNameLoc());
2744
2745 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002746}
Mike Stump11289f42009-09-09 15:08:12 +00002747
2748template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002749QualType TreeTransform<Derived>::TransformTypenameType(TypeLocBuilder &TLB,
2750 TypenameTypeLoc TL) {
2751 TypenameType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002752 NestedNameSpecifier *NNS
2753 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
Douglas Gregor15acfb92009-08-06 16:20:37 +00002754 SourceRange(/*FIXME:*/getDerived().getBaseLocation()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002755 if (!NNS)
2756 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002757
John McCall550e0c22009-10-21 00:40:46 +00002758 QualType Result;
2759
Douglas Gregord6ff3322009-08-04 16:50:30 +00002760 if (const TemplateSpecializationType *TemplateId = T->getTemplateId()) {
Mike Stump11289f42009-09-09 15:08:12 +00002761 QualType NewTemplateId
Douglas Gregord6ff3322009-08-04 16:50:30 +00002762 = getDerived().TransformType(QualType(TemplateId, 0));
2763 if (NewTemplateId.isNull())
2764 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002765
Douglas Gregord6ff3322009-08-04 16:50:30 +00002766 if (!getDerived().AlwaysRebuild() &&
2767 NNS == T->getQualifier() &&
2768 NewTemplateId == QualType(TemplateId, 0))
2769 return QualType(T, 0);
Mike Stump11289f42009-09-09 15:08:12 +00002770
John McCall550e0c22009-10-21 00:40:46 +00002771 Result = getDerived().RebuildTypenameType(NNS, NewTemplateId);
2772 } else {
2773 Result = getDerived().RebuildTypenameType(NNS, T->getIdentifier());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002774 }
John McCall550e0c22009-10-21 00:40:46 +00002775 if (Result.isNull())
2776 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002777
John McCall550e0c22009-10-21 00:40:46 +00002778 TypenameTypeLoc NewTL = TLB.push<TypenameTypeLoc>(Result);
2779 NewTL.setNameLoc(TL.getNameLoc());
2780
2781 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002782}
Mike Stump11289f42009-09-09 15:08:12 +00002783
Douglas Gregord6ff3322009-08-04 16:50:30 +00002784template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002785QualType
2786TreeTransform<Derived>::TransformObjCInterfaceType(TypeLocBuilder &TLB,
2787 ObjCInterfaceTypeLoc TL) {
John McCallfc93cf92009-10-22 22:37:11 +00002788 assert(false && "TransformObjCInterfaceType unimplemented");
2789 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002790}
Mike Stump11289f42009-09-09 15:08:12 +00002791
2792template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002793QualType
2794TreeTransform<Derived>::TransformObjCObjectPointerType(TypeLocBuilder &TLB,
2795 ObjCObjectPointerTypeLoc TL) {
John McCallfc93cf92009-10-22 22:37:11 +00002796 assert(false && "TransformObjCObjectPointerType unimplemented");
2797 return QualType();
Argyrios Kyrtzidisa7a36df2009-09-29 19:42:55 +00002798}
2799
Douglas Gregord6ff3322009-08-04 16:50:30 +00002800//===----------------------------------------------------------------------===//
Douglas Gregorebe10102009-08-20 07:17:43 +00002801// Statement transformation
2802//===----------------------------------------------------------------------===//
2803template<typename Derived>
2804Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002805TreeTransform<Derived>::TransformNullStmt(NullStmt *S) {
2806 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00002807}
2808
2809template<typename Derived>
2810Sema::OwningStmtResult
2811TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S) {
2812 return getDerived().TransformCompoundStmt(S, false);
2813}
2814
2815template<typename Derived>
2816Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002817TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S,
Douglas Gregorebe10102009-08-20 07:17:43 +00002818 bool IsStmtExpr) {
2819 bool SubStmtChanged = false;
2820 ASTOwningVector<&ActionBase::DeleteStmt> Statements(getSema());
2821 for (CompoundStmt::body_iterator B = S->body_begin(), BEnd = S->body_end();
2822 B != BEnd; ++B) {
2823 OwningStmtResult Result = getDerived().TransformStmt(*B);
2824 if (Result.isInvalid())
2825 return getSema().StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002826
Douglas Gregorebe10102009-08-20 07:17:43 +00002827 SubStmtChanged = SubStmtChanged || Result.get() != *B;
2828 Statements.push_back(Result.takeAs<Stmt>());
2829 }
Mike Stump11289f42009-09-09 15:08:12 +00002830
Douglas Gregorebe10102009-08-20 07:17:43 +00002831 if (!getDerived().AlwaysRebuild() &&
2832 !SubStmtChanged)
Mike Stump11289f42009-09-09 15:08:12 +00002833 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00002834
2835 return getDerived().RebuildCompoundStmt(S->getLBracLoc(),
2836 move_arg(Statements),
2837 S->getRBracLoc(),
2838 IsStmtExpr);
2839}
Mike Stump11289f42009-09-09 15:08:12 +00002840
Douglas Gregorebe10102009-08-20 07:17:43 +00002841template<typename Derived>
2842Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002843TreeTransform<Derived>::TransformCaseStmt(CaseStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002844 // The case value expressions are not potentially evaluated.
2845 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002846
Douglas Gregorebe10102009-08-20 07:17:43 +00002847 // Transform the left-hand case value.
2848 OwningExprResult LHS = getDerived().TransformExpr(S->getLHS());
2849 if (LHS.isInvalid())
2850 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002851
Douglas Gregorebe10102009-08-20 07:17:43 +00002852 // Transform the right-hand case value (for the GNU case-range extension).
2853 OwningExprResult RHS = getDerived().TransformExpr(S->getRHS());
2854 if (RHS.isInvalid())
2855 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002856
Douglas Gregorebe10102009-08-20 07:17:43 +00002857 // Build the case statement.
2858 // Case statements are always rebuilt so that they will attached to their
2859 // transformed switch statement.
2860 OwningStmtResult Case = getDerived().RebuildCaseStmt(S->getCaseLoc(),
2861 move(LHS),
2862 S->getEllipsisLoc(),
2863 move(RHS),
2864 S->getColonLoc());
2865 if (Case.isInvalid())
2866 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002867
Douglas Gregorebe10102009-08-20 07:17:43 +00002868 // Transform the statement following the case
2869 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2870 if (SubStmt.isInvalid())
2871 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002872
Douglas Gregorebe10102009-08-20 07:17:43 +00002873 // Attach the body to the case statement
2874 return getDerived().RebuildCaseStmtBody(move(Case), move(SubStmt));
2875}
2876
2877template<typename Derived>
2878Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002879TreeTransform<Derived>::TransformDefaultStmt(DefaultStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002880 // Transform the statement following the default case
2881 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2882 if (SubStmt.isInvalid())
2883 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002884
Douglas Gregorebe10102009-08-20 07:17:43 +00002885 // Default statements are always rebuilt
2886 return getDerived().RebuildDefaultStmt(S->getDefaultLoc(), S->getColonLoc(),
2887 move(SubStmt));
2888}
Mike Stump11289f42009-09-09 15:08:12 +00002889
Douglas Gregorebe10102009-08-20 07:17:43 +00002890template<typename Derived>
2891Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002892TreeTransform<Derived>::TransformLabelStmt(LabelStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002893 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2894 if (SubStmt.isInvalid())
2895 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002896
Douglas Gregorebe10102009-08-20 07:17:43 +00002897 // FIXME: Pass the real colon location in.
2898 SourceLocation ColonLoc = SemaRef.PP.getLocForEndOfToken(S->getIdentLoc());
2899 return getDerived().RebuildLabelStmt(S->getIdentLoc(), S->getID(), ColonLoc,
2900 move(SubStmt));
2901}
Mike Stump11289f42009-09-09 15:08:12 +00002902
Douglas Gregorebe10102009-08-20 07:17:43 +00002903template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002904Sema::OwningStmtResult
2905TreeTransform<Derived>::TransformIfStmt(IfStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002906 // Transform the condition
2907 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2908 if (Cond.isInvalid())
2909 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002910
Douglas Gregorebe10102009-08-20 07:17:43 +00002911 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
Mike Stump11289f42009-09-09 15:08:12 +00002912
Douglas Gregorebe10102009-08-20 07:17:43 +00002913 // Transform the "then" branch.
2914 OwningStmtResult Then = getDerived().TransformStmt(S->getThen());
2915 if (Then.isInvalid())
2916 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002917
Douglas Gregorebe10102009-08-20 07:17:43 +00002918 // Transform the "else" branch.
2919 OwningStmtResult Else = getDerived().TransformStmt(S->getElse());
2920 if (Else.isInvalid())
2921 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002922
Douglas Gregorebe10102009-08-20 07:17:43 +00002923 if (!getDerived().AlwaysRebuild() &&
2924 FullCond->get() == S->getCond() &&
2925 Then.get() == S->getThen() &&
2926 Else.get() == S->getElse())
Mike Stump11289f42009-09-09 15:08:12 +00002927 return SemaRef.Owned(S->Retain());
2928
Douglas Gregorebe10102009-08-20 07:17:43 +00002929 return getDerived().RebuildIfStmt(S->getIfLoc(), FullCond, move(Then),
Mike Stump11289f42009-09-09 15:08:12 +00002930 S->getElseLoc(), move(Else));
Douglas Gregorebe10102009-08-20 07:17:43 +00002931}
2932
2933template<typename Derived>
2934Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002935TreeTransform<Derived>::TransformSwitchStmt(SwitchStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002936 // Transform the condition.
2937 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2938 if (Cond.isInvalid())
2939 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002940
Douglas Gregorebe10102009-08-20 07:17:43 +00002941 // Rebuild the switch statement.
2942 OwningStmtResult Switch = getDerived().RebuildSwitchStmtStart(move(Cond));
2943 if (Switch.isInvalid())
2944 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002945
Douglas Gregorebe10102009-08-20 07:17:43 +00002946 // Transform the body of the switch statement.
2947 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2948 if (Body.isInvalid())
2949 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002950
Douglas Gregorebe10102009-08-20 07:17:43 +00002951 // Complete the switch statement.
2952 return getDerived().RebuildSwitchStmtBody(S->getSwitchLoc(), move(Switch),
2953 move(Body));
2954}
Mike Stump11289f42009-09-09 15:08:12 +00002955
Douglas Gregorebe10102009-08-20 07:17:43 +00002956template<typename Derived>
2957Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002958TreeTransform<Derived>::TransformWhileStmt(WhileStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002959 // Transform the condition
2960 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2961 if (Cond.isInvalid())
2962 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002963
Douglas Gregorebe10102009-08-20 07:17:43 +00002964 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
Mike Stump11289f42009-09-09 15:08:12 +00002965
Douglas Gregorebe10102009-08-20 07:17:43 +00002966 // Transform the body
2967 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2968 if (Body.isInvalid())
2969 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002970
Douglas Gregorebe10102009-08-20 07:17:43 +00002971 if (!getDerived().AlwaysRebuild() &&
2972 FullCond->get() == S->getCond() &&
2973 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00002974 return SemaRef.Owned(S->Retain());
2975
Douglas Gregorebe10102009-08-20 07:17:43 +00002976 return getDerived().RebuildWhileStmt(S->getWhileLoc(), FullCond, move(Body));
2977}
Mike Stump11289f42009-09-09 15:08:12 +00002978
Douglas Gregorebe10102009-08-20 07:17:43 +00002979template<typename Derived>
2980Sema::OwningStmtResult
2981TreeTransform<Derived>::TransformDoStmt(DoStmt *S) {
2982 // Transform the condition
2983 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2984 if (Cond.isInvalid())
2985 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002986
Douglas Gregorebe10102009-08-20 07:17:43 +00002987 // Transform the body
2988 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2989 if (Body.isInvalid())
2990 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002991
Douglas Gregorebe10102009-08-20 07:17:43 +00002992 if (!getDerived().AlwaysRebuild() &&
2993 Cond.get() == S->getCond() &&
2994 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00002995 return SemaRef.Owned(S->Retain());
2996
Douglas Gregorebe10102009-08-20 07:17:43 +00002997 return getDerived().RebuildDoStmt(S->getDoLoc(), move(Body), S->getWhileLoc(),
2998 /*FIXME:*/S->getWhileLoc(), move(Cond),
2999 S->getRParenLoc());
3000}
Mike Stump11289f42009-09-09 15:08:12 +00003001
Douglas Gregorebe10102009-08-20 07:17:43 +00003002template<typename Derived>
3003Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003004TreeTransform<Derived>::TransformForStmt(ForStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003005 // Transform the initialization statement
3006 OwningStmtResult Init = getDerived().TransformStmt(S->getInit());
3007 if (Init.isInvalid())
3008 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003009
Douglas Gregorebe10102009-08-20 07:17:43 +00003010 // Transform the condition
3011 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
3012 if (Cond.isInvalid())
3013 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003014
Douglas Gregorebe10102009-08-20 07:17:43 +00003015 // Transform the increment
3016 OwningExprResult Inc = getDerived().TransformExpr(S->getInc());
3017 if (Inc.isInvalid())
3018 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003019
Douglas Gregorebe10102009-08-20 07:17:43 +00003020 // Transform the body
3021 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
3022 if (Body.isInvalid())
3023 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003024
Douglas Gregorebe10102009-08-20 07:17:43 +00003025 if (!getDerived().AlwaysRebuild() &&
3026 Init.get() == S->getInit() &&
3027 Cond.get() == S->getCond() &&
3028 Inc.get() == S->getInc() &&
3029 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00003030 return SemaRef.Owned(S->Retain());
3031
Douglas Gregorebe10102009-08-20 07:17:43 +00003032 return getDerived().RebuildForStmt(S->getForLoc(), S->getLParenLoc(),
3033 move(Init), move(Cond), move(Inc),
3034 S->getRParenLoc(), move(Body));
3035}
3036
3037template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003038Sema::OwningStmtResult
3039TreeTransform<Derived>::TransformGotoStmt(GotoStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003040 // Goto statements must always be rebuilt, to resolve the label.
Mike Stump11289f42009-09-09 15:08:12 +00003041 return getDerived().RebuildGotoStmt(S->getGotoLoc(), S->getLabelLoc(),
Douglas Gregorebe10102009-08-20 07:17:43 +00003042 S->getLabel());
3043}
3044
3045template<typename Derived>
3046Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003047TreeTransform<Derived>::TransformIndirectGotoStmt(IndirectGotoStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003048 OwningExprResult Target = getDerived().TransformExpr(S->getTarget());
3049 if (Target.isInvalid())
3050 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003051
Douglas Gregorebe10102009-08-20 07:17:43 +00003052 if (!getDerived().AlwaysRebuild() &&
3053 Target.get() == S->getTarget())
Mike Stump11289f42009-09-09 15:08:12 +00003054 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003055
3056 return getDerived().RebuildIndirectGotoStmt(S->getGotoLoc(), S->getStarLoc(),
3057 move(Target));
3058}
3059
3060template<typename Derived>
3061Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003062TreeTransform<Derived>::TransformContinueStmt(ContinueStmt *S) {
3063 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003064}
Mike Stump11289f42009-09-09 15:08:12 +00003065
Douglas Gregorebe10102009-08-20 07:17:43 +00003066template<typename Derived>
3067Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003068TreeTransform<Derived>::TransformBreakStmt(BreakStmt *S) {
3069 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003070}
Mike Stump11289f42009-09-09 15:08:12 +00003071
Douglas Gregorebe10102009-08-20 07:17:43 +00003072template<typename Derived>
3073Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003074TreeTransform<Derived>::TransformReturnStmt(ReturnStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003075 Sema::OwningExprResult Result = getDerived().TransformExpr(S->getRetValue());
3076 if (Result.isInvalid())
3077 return SemaRef.StmtError();
3078
Mike Stump11289f42009-09-09 15:08:12 +00003079 // FIXME: We always rebuild the return statement because there is no way
Douglas Gregorebe10102009-08-20 07:17:43 +00003080 // to tell whether the return type of the function has changed.
3081 return getDerived().RebuildReturnStmt(S->getReturnLoc(), move(Result));
3082}
Mike Stump11289f42009-09-09 15:08:12 +00003083
Douglas Gregorebe10102009-08-20 07:17:43 +00003084template<typename Derived>
3085Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003086TreeTransform<Derived>::TransformDeclStmt(DeclStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003087 bool DeclChanged = false;
3088 llvm::SmallVector<Decl *, 4> Decls;
3089 for (DeclStmt::decl_iterator D = S->decl_begin(), DEnd = S->decl_end();
3090 D != DEnd; ++D) {
3091 Decl *Transformed = getDerived().TransformDefinition(*D);
3092 if (!Transformed)
3093 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003094
Douglas Gregorebe10102009-08-20 07:17:43 +00003095 if (Transformed != *D)
3096 DeclChanged = true;
Mike Stump11289f42009-09-09 15:08:12 +00003097
Douglas Gregorebe10102009-08-20 07:17:43 +00003098 Decls.push_back(Transformed);
3099 }
Mike Stump11289f42009-09-09 15:08:12 +00003100
Douglas Gregorebe10102009-08-20 07:17:43 +00003101 if (!getDerived().AlwaysRebuild() && !DeclChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003102 return SemaRef.Owned(S->Retain());
3103
3104 return getDerived().RebuildDeclStmt(Decls.data(), Decls.size(),
Douglas Gregorebe10102009-08-20 07:17:43 +00003105 S->getStartLoc(), S->getEndLoc());
3106}
Mike Stump11289f42009-09-09 15:08:12 +00003107
Douglas Gregorebe10102009-08-20 07:17:43 +00003108template<typename Derived>
3109Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003110TreeTransform<Derived>::TransformSwitchCase(SwitchCase *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003111 assert(false && "SwitchCase is abstract and cannot be transformed");
Mike Stump11289f42009-09-09 15:08:12 +00003112 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003113}
3114
3115template<typename Derived>
3116Sema::OwningStmtResult
3117TreeTransform<Derived>::TransformAsmStmt(AsmStmt *S) {
3118 // FIXME: Implement!
3119 assert(false && "Inline assembly cannot be transformed");
Mike Stump11289f42009-09-09 15:08:12 +00003120 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003121}
3122
3123
3124template<typename Derived>
3125Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003126TreeTransform<Derived>::TransformObjCAtTryStmt(ObjCAtTryStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003127 // FIXME: Implement this
3128 assert(false && "Cannot transform an Objective-C @try statement");
Mike Stump11289f42009-09-09 15:08:12 +00003129 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003130}
Mike Stump11289f42009-09-09 15:08:12 +00003131
Douglas Gregorebe10102009-08-20 07:17:43 +00003132template<typename Derived>
3133Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003134TreeTransform<Derived>::TransformObjCAtCatchStmt(ObjCAtCatchStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003135 // FIXME: Implement this
3136 assert(false && "Cannot transform an Objective-C @catch statement");
3137 return SemaRef.Owned(S->Retain());
3138}
Mike Stump11289f42009-09-09 15:08:12 +00003139
Douglas Gregorebe10102009-08-20 07:17:43 +00003140template<typename Derived>
3141Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003142TreeTransform<Derived>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003143 // FIXME: Implement this
3144 assert(false && "Cannot transform an Objective-C @finally statement");
Mike Stump11289f42009-09-09 15:08:12 +00003145 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003146}
Mike Stump11289f42009-09-09 15:08:12 +00003147
Douglas Gregorebe10102009-08-20 07:17:43 +00003148template<typename Derived>
3149Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003150TreeTransform<Derived>::TransformObjCAtThrowStmt(ObjCAtThrowStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003151 // FIXME: Implement this
3152 assert(false && "Cannot transform an Objective-C @throw statement");
Mike Stump11289f42009-09-09 15:08:12 +00003153 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003154}
Mike Stump11289f42009-09-09 15:08:12 +00003155
Douglas Gregorebe10102009-08-20 07:17:43 +00003156template<typename Derived>
3157Sema::OwningStmtResult
3158TreeTransform<Derived>::TransformObjCAtSynchronizedStmt(
Mike Stump11289f42009-09-09 15:08:12 +00003159 ObjCAtSynchronizedStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003160 // FIXME: Implement this
3161 assert(false && "Cannot transform an Objective-C @synchronized statement");
Mike Stump11289f42009-09-09 15:08:12 +00003162 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003163}
3164
3165template<typename Derived>
3166Sema::OwningStmtResult
3167TreeTransform<Derived>::TransformObjCForCollectionStmt(
Mike Stump11289f42009-09-09 15:08:12 +00003168 ObjCForCollectionStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003169 // FIXME: Implement this
3170 assert(false && "Cannot transform an Objective-C for-each statement");
Mike Stump11289f42009-09-09 15:08:12 +00003171 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003172}
3173
3174
3175template<typename Derived>
3176Sema::OwningStmtResult
3177TreeTransform<Derived>::TransformCXXCatchStmt(CXXCatchStmt *S) {
3178 // Transform the exception declaration, if any.
3179 VarDecl *Var = 0;
3180 if (S->getExceptionDecl()) {
3181 VarDecl *ExceptionDecl = S->getExceptionDecl();
3182 TemporaryBase Rebase(*this, ExceptionDecl->getLocation(),
3183 ExceptionDecl->getDeclName());
3184
3185 QualType T = getDerived().TransformType(ExceptionDecl->getType());
3186 if (T.isNull())
3187 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003188
Douglas Gregorebe10102009-08-20 07:17:43 +00003189 Var = getDerived().RebuildExceptionDecl(ExceptionDecl,
3190 T,
3191 ExceptionDecl->getDeclaratorInfo(),
3192 ExceptionDecl->getIdentifier(),
3193 ExceptionDecl->getLocation(),
3194 /*FIXME: Inaccurate*/
3195 SourceRange(ExceptionDecl->getLocation()));
3196 if (!Var || Var->isInvalidDecl()) {
3197 if (Var)
3198 Var->Destroy(SemaRef.Context);
3199 return SemaRef.StmtError();
3200 }
3201 }
Mike Stump11289f42009-09-09 15:08:12 +00003202
Douglas Gregorebe10102009-08-20 07:17:43 +00003203 // Transform the actual exception handler.
3204 OwningStmtResult Handler = getDerived().TransformStmt(S->getHandlerBlock());
3205 if (Handler.isInvalid()) {
3206 if (Var)
3207 Var->Destroy(SemaRef.Context);
3208 return SemaRef.StmtError();
3209 }
Mike Stump11289f42009-09-09 15:08:12 +00003210
Douglas Gregorebe10102009-08-20 07:17:43 +00003211 if (!getDerived().AlwaysRebuild() &&
3212 !Var &&
3213 Handler.get() == S->getHandlerBlock())
Mike Stump11289f42009-09-09 15:08:12 +00003214 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003215
3216 return getDerived().RebuildCXXCatchStmt(S->getCatchLoc(),
3217 Var,
3218 move(Handler));
3219}
Mike Stump11289f42009-09-09 15:08:12 +00003220
Douglas Gregorebe10102009-08-20 07:17:43 +00003221template<typename Derived>
3222Sema::OwningStmtResult
3223TreeTransform<Derived>::TransformCXXTryStmt(CXXTryStmt *S) {
3224 // Transform the try block itself.
Mike Stump11289f42009-09-09 15:08:12 +00003225 OwningStmtResult TryBlock
Douglas Gregorebe10102009-08-20 07:17:43 +00003226 = getDerived().TransformCompoundStmt(S->getTryBlock());
3227 if (TryBlock.isInvalid())
3228 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003229
Douglas Gregorebe10102009-08-20 07:17:43 +00003230 // Transform the handlers.
3231 bool HandlerChanged = false;
3232 ASTOwningVector<&ActionBase::DeleteStmt> Handlers(SemaRef);
3233 for (unsigned I = 0, N = S->getNumHandlers(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00003234 OwningStmtResult Handler
Douglas Gregorebe10102009-08-20 07:17:43 +00003235 = getDerived().TransformCXXCatchStmt(S->getHandler(I));
3236 if (Handler.isInvalid())
3237 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003238
Douglas Gregorebe10102009-08-20 07:17:43 +00003239 HandlerChanged = HandlerChanged || Handler.get() != S->getHandler(I);
3240 Handlers.push_back(Handler.takeAs<Stmt>());
3241 }
Mike Stump11289f42009-09-09 15:08:12 +00003242
Douglas Gregorebe10102009-08-20 07:17:43 +00003243 if (!getDerived().AlwaysRebuild() &&
3244 TryBlock.get() == S->getTryBlock() &&
3245 !HandlerChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003246 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003247
3248 return getDerived().RebuildCXXTryStmt(S->getTryLoc(), move(TryBlock),
Mike Stump11289f42009-09-09 15:08:12 +00003249 move_arg(Handlers));
Douglas Gregorebe10102009-08-20 07:17:43 +00003250}
Mike Stump11289f42009-09-09 15:08:12 +00003251
Douglas Gregorebe10102009-08-20 07:17:43 +00003252//===----------------------------------------------------------------------===//
Douglas Gregora16548e2009-08-11 05:31:07 +00003253// Expression transformation
3254//===----------------------------------------------------------------------===//
Mike Stump11289f42009-09-09 15:08:12 +00003255template<typename Derived>
3256Sema::OwningExprResult
3257TreeTransform<Derived>::TransformPredefinedExpr(PredefinedExpr *E) {
3258 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003259}
Mike Stump11289f42009-09-09 15:08:12 +00003260
3261template<typename Derived>
3262Sema::OwningExprResult
3263TreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) {
Douglas Gregor4bd90e52009-10-23 18:54:35 +00003264 NestedNameSpecifier *Qualifier = 0;
3265 if (E->getQualifier()) {
3266 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
3267 E->getQualifierRange());
3268 if (!Qualifier)
3269 return SemaRef.ExprError();
3270 }
3271
Mike Stump11289f42009-09-09 15:08:12 +00003272 NamedDecl *ND
Douglas Gregora16548e2009-08-11 05:31:07 +00003273 = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
3274 if (!ND)
3275 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003276
Douglas Gregor4bd90e52009-10-23 18:54:35 +00003277 if (!getDerived().AlwaysRebuild() &&
3278 Qualifier == E->getQualifier() &&
3279 ND == E->getDecl() &&
3280 !E->hasExplicitTemplateArgumentList())
Mike Stump11289f42009-09-09 15:08:12 +00003281 return SemaRef.Owned(E->Retain());
3282
Douglas Gregor4bd90e52009-10-23 18:54:35 +00003283 // FIXME: We're losing the explicit template arguments in this transformation.
3284
3285 llvm::SmallVector<TemplateArgument, 4> TransArgs;
3286 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
3287 TemplateArgument TransArg
3288 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
3289 if (TransArg.isNull())
3290 return SemaRef.ExprError();
3291
3292 TransArgs.push_back(TransArg);
3293 }
3294
3295 // FIXME: Pass the qualifier/qualifier range along.
3296 return getDerived().RebuildDeclRefExpr(Qualifier, E->getQualifierRange(),
3297 ND, E->getLocation());
Douglas Gregora16548e2009-08-11 05:31:07 +00003298}
Mike Stump11289f42009-09-09 15:08:12 +00003299
Douglas Gregora16548e2009-08-11 05:31:07 +00003300template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003301Sema::OwningExprResult
3302TreeTransform<Derived>::TransformIntegerLiteral(IntegerLiteral *E) {
3303 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003304}
Mike Stump11289f42009-09-09 15:08:12 +00003305
Douglas Gregora16548e2009-08-11 05:31:07 +00003306template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003307Sema::OwningExprResult
3308TreeTransform<Derived>::TransformFloatingLiteral(FloatingLiteral *E) {
3309 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003310}
Mike Stump11289f42009-09-09 15:08:12 +00003311
Douglas Gregora16548e2009-08-11 05:31:07 +00003312template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003313Sema::OwningExprResult
3314TreeTransform<Derived>::TransformImaginaryLiteral(ImaginaryLiteral *E) {
3315 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003316}
Mike Stump11289f42009-09-09 15:08:12 +00003317
Douglas Gregora16548e2009-08-11 05:31:07 +00003318template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003319Sema::OwningExprResult
3320TreeTransform<Derived>::TransformStringLiteral(StringLiteral *E) {
3321 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003322}
Mike Stump11289f42009-09-09 15:08:12 +00003323
Douglas Gregora16548e2009-08-11 05:31:07 +00003324template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003325Sema::OwningExprResult
3326TreeTransform<Derived>::TransformCharacterLiteral(CharacterLiteral *E) {
3327 return SemaRef.Owned(E->Retain());
3328}
3329
3330template<typename Derived>
3331Sema::OwningExprResult
3332TreeTransform<Derived>::TransformParenExpr(ParenExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003333 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3334 if (SubExpr.isInvalid())
3335 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003336
Douglas Gregora16548e2009-08-11 05:31:07 +00003337 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003338 return SemaRef.Owned(E->Retain());
3339
3340 return getDerived().RebuildParenExpr(move(SubExpr), E->getLParen(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003341 E->getRParen());
3342}
3343
Mike Stump11289f42009-09-09 15:08:12 +00003344template<typename Derived>
3345Sema::OwningExprResult
3346TreeTransform<Derived>::TransformUnaryOperator(UnaryOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003347 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3348 if (SubExpr.isInvalid())
3349 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003350
Douglas Gregora16548e2009-08-11 05:31:07 +00003351 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003352 return SemaRef.Owned(E->Retain());
3353
Douglas Gregora16548e2009-08-11 05:31:07 +00003354 return getDerived().RebuildUnaryOperator(E->getOperatorLoc(),
3355 E->getOpcode(),
3356 move(SubExpr));
3357}
Mike Stump11289f42009-09-09 15:08:12 +00003358
Douglas Gregora16548e2009-08-11 05:31:07 +00003359template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003360Sema::OwningExprResult
3361TreeTransform<Derived>::TransformSizeOfAlignOfExpr(SizeOfAlignOfExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003362 if (E->isArgumentType()) {
3363 QualType T = getDerived().TransformType(E->getArgumentType());
3364 if (T.isNull())
3365 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003366
Douglas Gregora16548e2009-08-11 05:31:07 +00003367 if (!getDerived().AlwaysRebuild() && T == E->getArgumentType())
3368 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003369
3370 return getDerived().RebuildSizeOfAlignOf(T, E->getOperatorLoc(),
3371 E->isSizeOf(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003372 E->getSourceRange());
3373 }
Mike Stump11289f42009-09-09 15:08:12 +00003374
Douglas Gregora16548e2009-08-11 05:31:07 +00003375 Sema::OwningExprResult SubExpr(SemaRef);
Mike Stump11289f42009-09-09 15:08:12 +00003376 {
Douglas Gregora16548e2009-08-11 05:31:07 +00003377 // C++0x [expr.sizeof]p1:
3378 // The operand is either an expression, which is an unevaluated operand
3379 // [...]
3380 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00003381
Douglas Gregora16548e2009-08-11 05:31:07 +00003382 SubExpr = getDerived().TransformExpr(E->getArgumentExpr());
3383 if (SubExpr.isInvalid())
3384 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003385
Douglas Gregora16548e2009-08-11 05:31:07 +00003386 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr())
3387 return SemaRef.Owned(E->Retain());
3388 }
Mike Stump11289f42009-09-09 15:08:12 +00003389
Douglas Gregora16548e2009-08-11 05:31:07 +00003390 return getDerived().RebuildSizeOfAlignOf(move(SubExpr), E->getOperatorLoc(),
3391 E->isSizeOf(),
3392 E->getSourceRange());
3393}
Mike Stump11289f42009-09-09 15:08:12 +00003394
Douglas Gregora16548e2009-08-11 05:31:07 +00003395template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003396Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003397TreeTransform<Derived>::TransformArraySubscriptExpr(ArraySubscriptExpr *E) {
3398 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3399 if (LHS.isInvalid())
3400 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003401
Douglas Gregora16548e2009-08-11 05:31:07 +00003402 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3403 if (RHS.isInvalid())
3404 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003405
3406
Douglas Gregora16548e2009-08-11 05:31:07 +00003407 if (!getDerived().AlwaysRebuild() &&
3408 LHS.get() == E->getLHS() &&
3409 RHS.get() == E->getRHS())
3410 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003411
Douglas Gregora16548e2009-08-11 05:31:07 +00003412 return getDerived().RebuildArraySubscriptExpr(move(LHS),
3413 /*FIXME:*/E->getLHS()->getLocStart(),
3414 move(RHS),
3415 E->getRBracketLoc());
3416}
Mike Stump11289f42009-09-09 15:08:12 +00003417
3418template<typename Derived>
3419Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003420TreeTransform<Derived>::TransformCallExpr(CallExpr *E) {
3421 // Transform the callee.
3422 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
3423 if (Callee.isInvalid())
3424 return SemaRef.ExprError();
3425
3426 // Transform arguments.
3427 bool ArgChanged = false;
3428 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
3429 llvm::SmallVector<SourceLocation, 4> FakeCommaLocs;
3430 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) {
3431 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I));
3432 if (Arg.isInvalid())
3433 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003434
Douglas Gregora16548e2009-08-11 05:31:07 +00003435 // FIXME: Wrong source location information for the ','.
3436 FakeCommaLocs.push_back(
3437 SemaRef.PP.getLocForEndOfToken(E->getArg(I)->getSourceRange().getEnd()));
Mike Stump11289f42009-09-09 15:08:12 +00003438
3439 ArgChanged = ArgChanged || Arg.get() != E->getArg(I);
Douglas Gregora16548e2009-08-11 05:31:07 +00003440 Args.push_back(Arg.takeAs<Expr>());
3441 }
Mike Stump11289f42009-09-09 15:08:12 +00003442
Douglas Gregora16548e2009-08-11 05:31:07 +00003443 if (!getDerived().AlwaysRebuild() &&
3444 Callee.get() == E->getCallee() &&
3445 !ArgChanged)
3446 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003447
Douglas Gregora16548e2009-08-11 05:31:07 +00003448 // FIXME: Wrong source location information for the '('.
Mike Stump11289f42009-09-09 15:08:12 +00003449 SourceLocation FakeLParenLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003450 = ((Expr *)Callee.get())->getSourceRange().getBegin();
3451 return getDerived().RebuildCallExpr(move(Callee), FakeLParenLoc,
3452 move_arg(Args),
3453 FakeCommaLocs.data(),
3454 E->getRParenLoc());
3455}
Mike Stump11289f42009-09-09 15:08:12 +00003456
3457template<typename Derived>
3458Sema::OwningExprResult
3459TreeTransform<Derived>::TransformMemberExpr(MemberExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003460 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
3461 if (Base.isInvalid())
3462 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003463
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003464 NestedNameSpecifier *Qualifier = 0;
3465 if (E->hasQualifier()) {
Mike Stump11289f42009-09-09 15:08:12 +00003466 Qualifier
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003467 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
3468 E->getQualifierRange());
Douglas Gregor84f14dd2009-09-01 00:37:14 +00003469 if (Qualifier == 0)
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003470 return SemaRef.ExprError();
3471 }
Mike Stump11289f42009-09-09 15:08:12 +00003472
3473 NamedDecl *Member
Douglas Gregora16548e2009-08-11 05:31:07 +00003474 = cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getMemberDecl()));
3475 if (!Member)
3476 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003477
Douglas Gregora16548e2009-08-11 05:31:07 +00003478 if (!getDerived().AlwaysRebuild() &&
3479 Base.get() == E->getBase() &&
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003480 Qualifier == E->getQualifier() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00003481 Member == E->getMemberDecl())
Mike Stump11289f42009-09-09 15:08:12 +00003482 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003483
3484 // FIXME: Bogus source location for the operator
3485 SourceLocation FakeOperatorLoc
3486 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getSourceRange().getEnd());
3487
3488 return getDerived().RebuildMemberExpr(move(Base), FakeOperatorLoc,
3489 E->isArrow(),
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003490 Qualifier,
3491 E->getQualifierRange(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003492 E->getMemberLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003493 Member);
Douglas Gregora16548e2009-08-11 05:31:07 +00003494}
Mike Stump11289f42009-09-09 15:08:12 +00003495
Douglas Gregora16548e2009-08-11 05:31:07 +00003496template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003497Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003498TreeTransform<Derived>::TransformCastExpr(CastExpr *E) {
3499 assert(false && "Cannot transform abstract class");
3500 return SemaRef.Owned(E->Retain());
3501}
3502
3503template<typename Derived>
3504Sema::OwningExprResult
3505TreeTransform<Derived>::TransformBinaryOperator(BinaryOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003506 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3507 if (LHS.isInvalid())
3508 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003509
Douglas Gregora16548e2009-08-11 05:31:07 +00003510 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3511 if (RHS.isInvalid())
3512 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003513
Douglas Gregora16548e2009-08-11 05:31:07 +00003514 if (!getDerived().AlwaysRebuild() &&
3515 LHS.get() == E->getLHS() &&
3516 RHS.get() == E->getRHS())
Mike Stump11289f42009-09-09 15:08:12 +00003517 return SemaRef.Owned(E->Retain());
3518
Douglas Gregora16548e2009-08-11 05:31:07 +00003519 return getDerived().RebuildBinaryOperator(E->getOperatorLoc(), E->getOpcode(),
3520 move(LHS), move(RHS));
3521}
3522
Mike Stump11289f42009-09-09 15:08:12 +00003523template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003524Sema::OwningExprResult
3525TreeTransform<Derived>::TransformCompoundAssignOperator(
3526 CompoundAssignOperator *E) {
3527 return getDerived().TransformBinaryOperator(E);
3528}
Mike Stump11289f42009-09-09 15:08:12 +00003529
Douglas Gregora16548e2009-08-11 05:31:07 +00003530template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003531Sema::OwningExprResult
3532TreeTransform<Derived>::TransformConditionalOperator(ConditionalOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003533 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3534 if (Cond.isInvalid())
3535 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003536
Douglas Gregora16548e2009-08-11 05:31:07 +00003537 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3538 if (LHS.isInvalid())
3539 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003540
Douglas Gregora16548e2009-08-11 05:31:07 +00003541 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3542 if (RHS.isInvalid())
3543 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003544
Douglas Gregora16548e2009-08-11 05:31:07 +00003545 if (!getDerived().AlwaysRebuild() &&
3546 Cond.get() == E->getCond() &&
3547 LHS.get() == E->getLHS() &&
3548 RHS.get() == E->getRHS())
3549 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003550
3551 return getDerived().RebuildConditionalOperator(move(Cond),
Douglas Gregor7e112b02009-08-26 14:37:04 +00003552 E->getQuestionLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003553 move(LHS),
Douglas Gregor7e112b02009-08-26 14:37:04 +00003554 E->getColonLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003555 move(RHS));
3556}
Mike Stump11289f42009-09-09 15:08:12 +00003557
3558template<typename Derived>
3559Sema::OwningExprResult
3560TreeTransform<Derived>::TransformImplicitCastExpr(ImplicitCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003561 QualType T = getDerived().TransformType(E->getType());
3562 if (T.isNull())
3563 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003564
Douglas Gregora16548e2009-08-11 05:31:07 +00003565 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3566 if (SubExpr.isInvalid())
3567 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003568
Douglas Gregora16548e2009-08-11 05:31:07 +00003569 if (!getDerived().AlwaysRebuild() &&
3570 T == E->getType() &&
3571 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003572 return SemaRef.Owned(E->Retain());
3573
Douglas Gregora16548e2009-08-11 05:31:07 +00003574 return getDerived().RebuildImplicitCastExpr(T, E->getCastKind(),
Mike Stump11289f42009-09-09 15:08:12 +00003575 move(SubExpr),
Douglas Gregora16548e2009-08-11 05:31:07 +00003576 E->isLvalueCast());
3577}
Mike Stump11289f42009-09-09 15:08:12 +00003578
Douglas Gregora16548e2009-08-11 05:31:07 +00003579template<typename Derived>
3580Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003581TreeTransform<Derived>::TransformExplicitCastExpr(ExplicitCastExpr *E) {
3582 assert(false && "Cannot transform abstract class");
3583 return SemaRef.Owned(E->Retain());
3584}
3585
3586template<typename Derived>
3587Sema::OwningExprResult
3588TreeTransform<Derived>::TransformCStyleCastExpr(CStyleCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003589 QualType T;
3590 {
3591 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003592 SourceLocation TypeStartLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003593 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3594 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003595
Douglas Gregora16548e2009-08-11 05:31:07 +00003596 T = getDerived().TransformType(E->getTypeAsWritten());
3597 if (T.isNull())
3598 return SemaRef.ExprError();
3599 }
Mike Stump11289f42009-09-09 15:08:12 +00003600
Douglas Gregora16548e2009-08-11 05:31:07 +00003601 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3602 if (SubExpr.isInvalid())
3603 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003604
Douglas Gregora16548e2009-08-11 05:31:07 +00003605 if (!getDerived().AlwaysRebuild() &&
3606 T == E->getTypeAsWritten() &&
3607 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003608 return SemaRef.Owned(E->Retain());
3609
Douglas Gregora16548e2009-08-11 05:31:07 +00003610 return getDerived().RebuildCStyleCaseExpr(E->getLParenLoc(), T,
3611 E->getRParenLoc(),
3612 move(SubExpr));
3613}
Mike Stump11289f42009-09-09 15:08:12 +00003614
Douglas Gregora16548e2009-08-11 05:31:07 +00003615template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003616Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003617TreeTransform<Derived>::TransformCompoundLiteralExpr(CompoundLiteralExpr *E) {
3618 QualType T;
3619 {
3620 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003621 SourceLocation FakeTypeLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003622 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3623 TemporaryBase Rebase(*this, FakeTypeLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003624
Douglas Gregora16548e2009-08-11 05:31:07 +00003625 T = getDerived().TransformType(E->getType());
3626 if (T.isNull())
3627 return SemaRef.ExprError();
3628 }
Mike Stump11289f42009-09-09 15:08:12 +00003629
Douglas Gregora16548e2009-08-11 05:31:07 +00003630 OwningExprResult Init = getDerived().TransformExpr(E->getInitializer());
3631 if (Init.isInvalid())
3632 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003633
Douglas Gregora16548e2009-08-11 05:31:07 +00003634 if (!getDerived().AlwaysRebuild() &&
3635 T == E->getType() &&
3636 Init.get() == E->getInitializer())
Mike Stump11289f42009-09-09 15:08:12 +00003637 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003638
3639 return getDerived().RebuildCompoundLiteralExpr(E->getLParenLoc(), T,
3640 /*FIXME:*/E->getInitializer()->getLocEnd(),
3641 move(Init));
3642}
Mike Stump11289f42009-09-09 15:08:12 +00003643
Douglas Gregora16548e2009-08-11 05:31:07 +00003644template<typename Derived>
3645Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003646TreeTransform<Derived>::TransformExtVectorElementExpr(ExtVectorElementExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003647 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
3648 if (Base.isInvalid())
3649 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003650
Douglas Gregora16548e2009-08-11 05:31:07 +00003651 if (!getDerived().AlwaysRebuild() &&
3652 Base.get() == E->getBase())
Mike Stump11289f42009-09-09 15:08:12 +00003653 return SemaRef.Owned(E->Retain());
3654
Douglas Gregora16548e2009-08-11 05:31:07 +00003655 // FIXME: Bad source location
Mike Stump11289f42009-09-09 15:08:12 +00003656 SourceLocation FakeOperatorLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003657 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getLocEnd());
3658 return getDerived().RebuildExtVectorElementExpr(move(Base), FakeOperatorLoc,
3659 E->getAccessorLoc(),
3660 E->getAccessor());
3661}
Mike Stump11289f42009-09-09 15:08:12 +00003662
Douglas Gregora16548e2009-08-11 05:31:07 +00003663template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003664Sema::OwningExprResult
3665TreeTransform<Derived>::TransformInitListExpr(InitListExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003666 bool InitChanged = false;
Mike Stump11289f42009-09-09 15:08:12 +00003667
Douglas Gregora16548e2009-08-11 05:31:07 +00003668 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3669 for (unsigned I = 0, N = E->getNumInits(); I != N; ++I) {
3670 OwningExprResult Init = getDerived().TransformExpr(E->getInit(I));
3671 if (Init.isInvalid())
3672 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003673
Douglas Gregora16548e2009-08-11 05:31:07 +00003674 InitChanged = InitChanged || Init.get() != E->getInit(I);
3675 Inits.push_back(Init.takeAs<Expr>());
3676 }
Mike Stump11289f42009-09-09 15:08:12 +00003677
Douglas Gregora16548e2009-08-11 05:31:07 +00003678 if (!getDerived().AlwaysRebuild() && !InitChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003679 return SemaRef.Owned(E->Retain());
3680
Douglas Gregora16548e2009-08-11 05:31:07 +00003681 return getDerived().RebuildInitList(E->getLBraceLoc(), move_arg(Inits),
3682 E->getRBraceLoc());
3683}
Mike Stump11289f42009-09-09 15:08:12 +00003684
Douglas Gregora16548e2009-08-11 05:31:07 +00003685template<typename Derived>
3686Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003687TreeTransform<Derived>::TransformDesignatedInitExpr(DesignatedInitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003688 Designation Desig;
Mike Stump11289f42009-09-09 15:08:12 +00003689
Douglas Gregorebe10102009-08-20 07:17:43 +00003690 // transform the initializer value
Douglas Gregora16548e2009-08-11 05:31:07 +00003691 OwningExprResult Init = getDerived().TransformExpr(E->getInit());
3692 if (Init.isInvalid())
3693 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003694
Douglas Gregorebe10102009-08-20 07:17:43 +00003695 // transform the designators.
Douglas Gregora16548e2009-08-11 05:31:07 +00003696 ASTOwningVector<&ActionBase::DeleteExpr, 4> ArrayExprs(SemaRef);
3697 bool ExprChanged = false;
3698 for (DesignatedInitExpr::designators_iterator D = E->designators_begin(),
3699 DEnd = E->designators_end();
3700 D != DEnd; ++D) {
3701 if (D->isFieldDesignator()) {
3702 Desig.AddDesignator(Designator::getField(D->getFieldName(),
3703 D->getDotLoc(),
3704 D->getFieldLoc()));
3705 continue;
3706 }
Mike Stump11289f42009-09-09 15:08:12 +00003707
Douglas Gregora16548e2009-08-11 05:31:07 +00003708 if (D->isArrayDesignator()) {
3709 OwningExprResult Index = getDerived().TransformExpr(E->getArrayIndex(*D));
3710 if (Index.isInvalid())
3711 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003712
3713 Desig.AddDesignator(Designator::getArray(Index.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003714 D->getLBracketLoc()));
Mike Stump11289f42009-09-09 15:08:12 +00003715
Douglas Gregora16548e2009-08-11 05:31:07 +00003716 ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(*D);
3717 ArrayExprs.push_back(Index.release());
3718 continue;
3719 }
Mike Stump11289f42009-09-09 15:08:12 +00003720
Douglas Gregora16548e2009-08-11 05:31:07 +00003721 assert(D->isArrayRangeDesignator() && "New kind of designator?");
Mike Stump11289f42009-09-09 15:08:12 +00003722 OwningExprResult Start
Douglas Gregora16548e2009-08-11 05:31:07 +00003723 = getDerived().TransformExpr(E->getArrayRangeStart(*D));
3724 if (Start.isInvalid())
3725 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003726
Douglas Gregora16548e2009-08-11 05:31:07 +00003727 OwningExprResult End = getDerived().TransformExpr(E->getArrayRangeEnd(*D));
3728 if (End.isInvalid())
3729 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003730
3731 Desig.AddDesignator(Designator::getArrayRange(Start.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003732 End.get(),
3733 D->getLBracketLoc(),
3734 D->getEllipsisLoc()));
Mike Stump11289f42009-09-09 15:08:12 +00003735
Douglas Gregora16548e2009-08-11 05:31:07 +00003736 ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(*D) ||
3737 End.get() != E->getArrayRangeEnd(*D);
Mike Stump11289f42009-09-09 15:08:12 +00003738
Douglas Gregora16548e2009-08-11 05:31:07 +00003739 ArrayExprs.push_back(Start.release());
3740 ArrayExprs.push_back(End.release());
3741 }
Mike Stump11289f42009-09-09 15:08:12 +00003742
Douglas Gregora16548e2009-08-11 05:31:07 +00003743 if (!getDerived().AlwaysRebuild() &&
3744 Init.get() == E->getInit() &&
3745 !ExprChanged)
3746 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003747
Douglas Gregora16548e2009-08-11 05:31:07 +00003748 return getDerived().RebuildDesignatedInitExpr(Desig, move_arg(ArrayExprs),
3749 E->getEqualOrColonLoc(),
3750 E->usesGNUSyntax(), move(Init));
3751}
Mike Stump11289f42009-09-09 15:08:12 +00003752
Douglas Gregora16548e2009-08-11 05:31:07 +00003753template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003754Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003755TreeTransform<Derived>::TransformImplicitValueInitExpr(
Mike Stump11289f42009-09-09 15:08:12 +00003756 ImplicitValueInitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003757 QualType T = getDerived().TransformType(E->getType());
3758 if (T.isNull())
3759 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003760
Douglas Gregora16548e2009-08-11 05:31:07 +00003761 if (!getDerived().AlwaysRebuild() &&
3762 T == E->getType())
Mike Stump11289f42009-09-09 15:08:12 +00003763 return SemaRef.Owned(E->Retain());
3764
Douglas Gregora16548e2009-08-11 05:31:07 +00003765 return getDerived().RebuildImplicitValueInitExpr(T);
3766}
Mike Stump11289f42009-09-09 15:08:12 +00003767
Douglas Gregora16548e2009-08-11 05:31:07 +00003768template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003769Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003770TreeTransform<Derived>::TransformVAArgExpr(VAArgExpr *E) {
3771 // FIXME: Do we want the type as written?
3772 QualType T;
Mike Stump11289f42009-09-09 15:08:12 +00003773
Douglas Gregora16548e2009-08-11 05:31:07 +00003774 {
3775 // FIXME: Source location isn't quite accurate.
3776 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
3777 T = getDerived().TransformType(E->getType());
3778 if (T.isNull())
3779 return SemaRef.ExprError();
3780 }
Mike Stump11289f42009-09-09 15:08:12 +00003781
Douglas Gregora16548e2009-08-11 05:31:07 +00003782 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3783 if (SubExpr.isInvalid())
3784 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003785
Douglas Gregora16548e2009-08-11 05:31:07 +00003786 if (!getDerived().AlwaysRebuild() &&
3787 T == E->getType() &&
3788 SubExpr.get() == E->getSubExpr())
3789 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003790
Douglas Gregora16548e2009-08-11 05:31:07 +00003791 return getDerived().RebuildVAArgExpr(E->getBuiltinLoc(), move(SubExpr),
3792 T, E->getRParenLoc());
3793}
3794
3795template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003796Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003797TreeTransform<Derived>::TransformParenListExpr(ParenListExpr *E) {
3798 bool ArgumentChanged = false;
3799 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3800 for (unsigned I = 0, N = E->getNumExprs(); I != N; ++I) {
3801 OwningExprResult Init = getDerived().TransformExpr(E->getExpr(I));
3802 if (Init.isInvalid())
3803 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003804
Douglas Gregora16548e2009-08-11 05:31:07 +00003805 ArgumentChanged = ArgumentChanged || Init.get() != E->getExpr(I);
3806 Inits.push_back(Init.takeAs<Expr>());
3807 }
Mike Stump11289f42009-09-09 15:08:12 +00003808
Douglas Gregora16548e2009-08-11 05:31:07 +00003809 return getDerived().RebuildParenListExpr(E->getLParenLoc(),
3810 move_arg(Inits),
3811 E->getRParenLoc());
3812}
Mike Stump11289f42009-09-09 15:08:12 +00003813
Douglas Gregora16548e2009-08-11 05:31:07 +00003814/// \brief Transform an address-of-label expression.
3815///
3816/// By default, the transformation of an address-of-label expression always
3817/// rebuilds the expression, so that the label identifier can be resolved to
3818/// the corresponding label statement by semantic analysis.
3819template<typename Derived>
3820Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003821TreeTransform<Derived>::TransformAddrLabelExpr(AddrLabelExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003822 return getDerived().RebuildAddrLabelExpr(E->getAmpAmpLoc(), E->getLabelLoc(),
3823 E->getLabel());
3824}
Mike Stump11289f42009-09-09 15:08:12 +00003825
3826template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003827Sema::OwningExprResult TreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) {
Mike Stump11289f42009-09-09 15:08:12 +00003828 OwningStmtResult SubStmt
Douglas Gregora16548e2009-08-11 05:31:07 +00003829 = getDerived().TransformCompoundStmt(E->getSubStmt(), true);
3830 if (SubStmt.isInvalid())
3831 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003832
Douglas Gregora16548e2009-08-11 05:31:07 +00003833 if (!getDerived().AlwaysRebuild() &&
3834 SubStmt.get() == E->getSubStmt())
3835 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003836
3837 return getDerived().RebuildStmtExpr(E->getLParenLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003838 move(SubStmt),
3839 E->getRParenLoc());
3840}
Mike Stump11289f42009-09-09 15:08:12 +00003841
Douglas Gregora16548e2009-08-11 05:31:07 +00003842template<typename Derived>
3843Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003844TreeTransform<Derived>::TransformTypesCompatibleExpr(TypesCompatibleExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003845 QualType T1, T2;
3846 {
3847 // FIXME: Source location isn't quite accurate.
3848 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003849
Douglas Gregora16548e2009-08-11 05:31:07 +00003850 T1 = getDerived().TransformType(E->getArgType1());
3851 if (T1.isNull())
3852 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003853
Douglas Gregora16548e2009-08-11 05:31:07 +00003854 T2 = getDerived().TransformType(E->getArgType2());
3855 if (T2.isNull())
3856 return SemaRef.ExprError();
3857 }
3858
3859 if (!getDerived().AlwaysRebuild() &&
3860 T1 == E->getArgType1() &&
3861 T2 == E->getArgType2())
Mike Stump11289f42009-09-09 15:08:12 +00003862 return SemaRef.Owned(E->Retain());
3863
Douglas Gregora16548e2009-08-11 05:31:07 +00003864 return getDerived().RebuildTypesCompatibleExpr(E->getBuiltinLoc(),
3865 T1, T2, E->getRParenLoc());
3866}
Mike Stump11289f42009-09-09 15:08:12 +00003867
Douglas Gregora16548e2009-08-11 05:31:07 +00003868template<typename Derived>
3869Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003870TreeTransform<Derived>::TransformChooseExpr(ChooseExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003871 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3872 if (Cond.isInvalid())
3873 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003874
Douglas Gregora16548e2009-08-11 05:31:07 +00003875 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3876 if (LHS.isInvalid())
3877 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003878
Douglas Gregora16548e2009-08-11 05:31:07 +00003879 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3880 if (RHS.isInvalid())
3881 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003882
Douglas Gregora16548e2009-08-11 05:31:07 +00003883 if (!getDerived().AlwaysRebuild() &&
3884 Cond.get() == E->getCond() &&
3885 LHS.get() == E->getLHS() &&
3886 RHS.get() == E->getRHS())
Mike Stump11289f42009-09-09 15:08:12 +00003887 return SemaRef.Owned(E->Retain());
3888
Douglas Gregora16548e2009-08-11 05:31:07 +00003889 return getDerived().RebuildChooseExpr(E->getBuiltinLoc(),
3890 move(Cond), move(LHS), move(RHS),
3891 E->getRParenLoc());
3892}
Mike Stump11289f42009-09-09 15:08:12 +00003893
Douglas Gregora16548e2009-08-11 05:31:07 +00003894template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003895Sema::OwningExprResult
3896TreeTransform<Derived>::TransformGNUNullExpr(GNUNullExpr *E) {
3897 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003898}
3899
3900template<typename Derived>
3901Sema::OwningExprResult
3902TreeTransform<Derived>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr *E) {
3903 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
3904 if (Callee.isInvalid())
3905 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003906
Douglas Gregora16548e2009-08-11 05:31:07 +00003907 OwningExprResult First = getDerived().TransformExpr(E->getArg(0));
3908 if (First.isInvalid())
3909 return SemaRef.ExprError();
3910
3911 OwningExprResult Second(SemaRef);
3912 if (E->getNumArgs() == 2) {
3913 Second = getDerived().TransformExpr(E->getArg(1));
3914 if (Second.isInvalid())
3915 return SemaRef.ExprError();
3916 }
Mike Stump11289f42009-09-09 15:08:12 +00003917
Douglas Gregora16548e2009-08-11 05:31:07 +00003918 if (!getDerived().AlwaysRebuild() &&
3919 Callee.get() == E->getCallee() &&
3920 First.get() == E->getArg(0) &&
Mike Stump11289f42009-09-09 15:08:12 +00003921 (E->getNumArgs() != 2 || Second.get() == E->getArg(1)))
3922 return SemaRef.Owned(E->Retain());
3923
Douglas Gregora16548e2009-08-11 05:31:07 +00003924 return getDerived().RebuildCXXOperatorCallExpr(E->getOperator(),
3925 E->getOperatorLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003926 move(Callee),
Douglas Gregora16548e2009-08-11 05:31:07 +00003927 move(First),
3928 move(Second));
3929}
Mike Stump11289f42009-09-09 15:08:12 +00003930
Douglas Gregora16548e2009-08-11 05:31:07 +00003931template<typename Derived>
3932Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003933TreeTransform<Derived>::TransformCXXMemberCallExpr(CXXMemberCallExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003934 return getDerived().TransformCallExpr(E);
3935}
Mike Stump11289f42009-09-09 15:08:12 +00003936
Douglas Gregora16548e2009-08-11 05:31:07 +00003937template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003938Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003939TreeTransform<Derived>::TransformCXXNamedCastExpr(CXXNamedCastExpr *E) {
3940 QualType ExplicitTy;
3941 {
3942 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003943 SourceLocation TypeStartLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003944 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3945 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003946
Douglas Gregora16548e2009-08-11 05:31:07 +00003947 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
3948 if (ExplicitTy.isNull())
3949 return SemaRef.ExprError();
3950 }
Mike Stump11289f42009-09-09 15:08:12 +00003951
Douglas Gregora16548e2009-08-11 05:31:07 +00003952 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3953 if (SubExpr.isInvalid())
3954 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003955
Douglas Gregora16548e2009-08-11 05:31:07 +00003956 if (!getDerived().AlwaysRebuild() &&
3957 ExplicitTy == E->getTypeAsWritten() &&
3958 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003959 return SemaRef.Owned(E->Retain());
3960
Douglas Gregora16548e2009-08-11 05:31:07 +00003961 // FIXME: Poor source location information here.
Mike Stump11289f42009-09-09 15:08:12 +00003962 SourceLocation FakeLAngleLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003963 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3964 SourceLocation FakeRAngleLoc = E->getSubExpr()->getSourceRange().getBegin();
3965 SourceLocation FakeRParenLoc
3966 = SemaRef.PP.getLocForEndOfToken(
3967 E->getSubExpr()->getSourceRange().getEnd());
3968 return getDerived().RebuildCXXNamedCastExpr(E->getOperatorLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003969 E->getStmtClass(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003970 FakeLAngleLoc,
3971 ExplicitTy,
3972 FakeRAngleLoc,
3973 FakeRAngleLoc,
3974 move(SubExpr),
3975 FakeRParenLoc);
3976}
Mike Stump11289f42009-09-09 15:08:12 +00003977
Douglas Gregora16548e2009-08-11 05:31:07 +00003978template<typename Derived>
3979Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003980TreeTransform<Derived>::TransformCXXStaticCastExpr(CXXStaticCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003981 return getDerived().TransformCXXNamedCastExpr(E);
3982}
Mike Stump11289f42009-09-09 15:08:12 +00003983
3984template<typename Derived>
3985Sema::OwningExprResult
3986TreeTransform<Derived>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr *E) {
3987 return getDerived().TransformCXXNamedCastExpr(E);
3988}
3989
Douglas Gregora16548e2009-08-11 05:31:07 +00003990template<typename Derived>
3991Sema::OwningExprResult
3992TreeTransform<Derived>::TransformCXXReinterpretCastExpr(
Mike Stump11289f42009-09-09 15:08:12 +00003993 CXXReinterpretCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003994 return getDerived().TransformCXXNamedCastExpr(E);
3995}
Mike Stump11289f42009-09-09 15:08:12 +00003996
Douglas Gregora16548e2009-08-11 05:31:07 +00003997template<typename Derived>
3998Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003999TreeTransform<Derived>::TransformCXXConstCastExpr(CXXConstCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004000 return getDerived().TransformCXXNamedCastExpr(E);
4001}
Mike Stump11289f42009-09-09 15:08:12 +00004002
Douglas Gregora16548e2009-08-11 05:31:07 +00004003template<typename Derived>
4004Sema::OwningExprResult
4005TreeTransform<Derived>::TransformCXXFunctionalCastExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004006 CXXFunctionalCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004007 QualType ExplicitTy;
4008 {
4009 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004010
Douglas Gregora16548e2009-08-11 05:31:07 +00004011 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
4012 if (ExplicitTy.isNull())
4013 return SemaRef.ExprError();
4014 }
Mike Stump11289f42009-09-09 15:08:12 +00004015
Douglas Gregora16548e2009-08-11 05:31:07 +00004016 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4017 if (SubExpr.isInvalid())
4018 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004019
Douglas Gregora16548e2009-08-11 05:31:07 +00004020 if (!getDerived().AlwaysRebuild() &&
4021 ExplicitTy == E->getTypeAsWritten() &&
4022 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00004023 return SemaRef.Owned(E->Retain());
4024
Douglas Gregora16548e2009-08-11 05:31:07 +00004025 // FIXME: The end of the type's source range is wrong
4026 return getDerived().RebuildCXXFunctionalCastExpr(
4027 /*FIXME:*/SourceRange(E->getTypeBeginLoc()),
4028 ExplicitTy,
4029 /*FIXME:*/E->getSubExpr()->getLocStart(),
4030 move(SubExpr),
4031 E->getRParenLoc());
4032}
Mike Stump11289f42009-09-09 15:08:12 +00004033
Douglas Gregora16548e2009-08-11 05:31:07 +00004034template<typename Derived>
4035Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004036TreeTransform<Derived>::TransformCXXTypeidExpr(CXXTypeidExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004037 if (E->isTypeOperand()) {
4038 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004039
Douglas Gregora16548e2009-08-11 05:31:07 +00004040 QualType T = getDerived().TransformType(E->getTypeOperand());
4041 if (T.isNull())
4042 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004043
Douglas Gregora16548e2009-08-11 05:31:07 +00004044 if (!getDerived().AlwaysRebuild() &&
4045 T == E->getTypeOperand())
4046 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004047
Douglas Gregora16548e2009-08-11 05:31:07 +00004048 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
4049 /*FIXME:*/E->getLocStart(),
4050 T,
4051 E->getLocEnd());
4052 }
Mike Stump11289f42009-09-09 15:08:12 +00004053
Douglas Gregora16548e2009-08-11 05:31:07 +00004054 // We don't know whether the expression is potentially evaluated until
4055 // after we perform semantic analysis, so the expression is potentially
4056 // potentially evaluated.
Mike Stump11289f42009-09-09 15:08:12 +00004057 EnterExpressionEvaluationContext Unevaluated(SemaRef,
Douglas Gregora16548e2009-08-11 05:31:07 +00004058 Action::PotentiallyPotentiallyEvaluated);
Mike Stump11289f42009-09-09 15:08:12 +00004059
Douglas Gregora16548e2009-08-11 05:31:07 +00004060 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand());
4061 if (SubExpr.isInvalid())
4062 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004063
Douglas Gregora16548e2009-08-11 05:31:07 +00004064 if (!getDerived().AlwaysRebuild() &&
4065 SubExpr.get() == E->getExprOperand())
Mike Stump11289f42009-09-09 15:08:12 +00004066 return SemaRef.Owned(E->Retain());
4067
Douglas Gregora16548e2009-08-11 05:31:07 +00004068 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
4069 /*FIXME:*/E->getLocStart(),
4070 move(SubExpr),
4071 E->getLocEnd());
4072}
4073
4074template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004075Sema::OwningExprResult
4076TreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) {
4077 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004078}
Mike Stump11289f42009-09-09 15:08:12 +00004079
Douglas Gregora16548e2009-08-11 05:31:07 +00004080template<typename Derived>
4081Sema::OwningExprResult
4082TreeTransform<Derived>::TransformCXXNullPtrLiteralExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004083 CXXNullPtrLiteralExpr *E) {
4084 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004085}
Mike Stump11289f42009-09-09 15:08:12 +00004086
Douglas Gregora16548e2009-08-11 05:31:07 +00004087template<typename Derived>
4088Sema::OwningExprResult
4089TreeTransform<Derived>::TransformCXXThisExpr(CXXThisExpr *E) {
4090 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004091
Douglas Gregora16548e2009-08-11 05:31:07 +00004092 QualType T = getDerived().TransformType(E->getType());
4093 if (T.isNull())
4094 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004095
Douglas Gregora16548e2009-08-11 05:31:07 +00004096 if (!getDerived().AlwaysRebuild() &&
4097 T == E->getType())
4098 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004099
Douglas Gregora16548e2009-08-11 05:31:07 +00004100 return getDerived().RebuildCXXThisExpr(E->getLocStart(), T);
4101}
Mike Stump11289f42009-09-09 15:08:12 +00004102
Douglas Gregora16548e2009-08-11 05:31:07 +00004103template<typename Derived>
4104Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004105TreeTransform<Derived>::TransformCXXThrowExpr(CXXThrowExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004106 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4107 if (SubExpr.isInvalid())
4108 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004109
Douglas Gregora16548e2009-08-11 05:31:07 +00004110 if (!getDerived().AlwaysRebuild() &&
4111 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00004112 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004113
4114 return getDerived().RebuildCXXThrowExpr(E->getThrowLoc(), move(SubExpr));
4115}
Mike Stump11289f42009-09-09 15:08:12 +00004116
Douglas Gregora16548e2009-08-11 05:31:07 +00004117template<typename Derived>
4118Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004119TreeTransform<Derived>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E) {
4120 ParmVarDecl *Param
Douglas Gregora16548e2009-08-11 05:31:07 +00004121 = cast_or_null<ParmVarDecl>(getDerived().TransformDecl(E->getParam()));
4122 if (!Param)
4123 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004124
Douglas Gregora16548e2009-08-11 05:31:07 +00004125 if (getDerived().AlwaysRebuild() &&
4126 Param == E->getParam())
4127 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004128
Douglas Gregora16548e2009-08-11 05:31:07 +00004129 return getDerived().RebuildCXXDefaultArgExpr(Param);
4130}
Mike Stump11289f42009-09-09 15:08:12 +00004131
Douglas Gregora16548e2009-08-11 05:31:07 +00004132template<typename Derived>
4133Sema::OwningExprResult
4134TreeTransform<Derived>::TransformCXXZeroInitValueExpr(CXXZeroInitValueExpr *E) {
4135 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4136
4137 QualType T = getDerived().TransformType(E->getType());
4138 if (T.isNull())
4139 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004140
Douglas Gregora16548e2009-08-11 05:31:07 +00004141 if (!getDerived().AlwaysRebuild() &&
4142 T == E->getType())
Mike Stump11289f42009-09-09 15:08:12 +00004143 return SemaRef.Owned(E->Retain());
4144
4145 return getDerived().RebuildCXXZeroInitValueExpr(E->getTypeBeginLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004146 /*FIXME:*/E->getTypeBeginLoc(),
4147 T,
4148 E->getRParenLoc());
4149}
Mike Stump11289f42009-09-09 15:08:12 +00004150
Douglas Gregora16548e2009-08-11 05:31:07 +00004151template<typename Derived>
4152Sema::OwningExprResult
4153TreeTransform<Derived>::TransformCXXConditionDeclExpr(CXXConditionDeclExpr *E) {
Mike Stump11289f42009-09-09 15:08:12 +00004154 VarDecl *Var
Douglas Gregorebe10102009-08-20 07:17:43 +00004155 = cast_or_null<VarDecl>(getDerived().TransformDefinition(E->getVarDecl()));
Douglas Gregora16548e2009-08-11 05:31:07 +00004156 if (!Var)
4157 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004158
Douglas Gregora16548e2009-08-11 05:31:07 +00004159 if (!getDerived().AlwaysRebuild() &&
Mike Stump11289f42009-09-09 15:08:12 +00004160 Var == E->getVarDecl())
Douglas Gregora16548e2009-08-11 05:31:07 +00004161 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004162
4163 return getDerived().RebuildCXXConditionDeclExpr(E->getStartLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004164 /*FIXME:*/E->getStartLoc(),
4165 Var);
4166}
Mike Stump11289f42009-09-09 15:08:12 +00004167
Douglas Gregora16548e2009-08-11 05:31:07 +00004168template<typename Derived>
4169Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004170TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004171 // Transform the type that we're allocating
4172 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
4173 QualType AllocType = getDerived().TransformType(E->getAllocatedType());
4174 if (AllocType.isNull())
4175 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004176
Douglas Gregora16548e2009-08-11 05:31:07 +00004177 // Transform the size of the array we're allocating (if any).
4178 OwningExprResult ArraySize = getDerived().TransformExpr(E->getArraySize());
4179 if (ArraySize.isInvalid())
4180 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004181
Douglas Gregora16548e2009-08-11 05:31:07 +00004182 // Transform the placement arguments (if any).
4183 bool ArgumentChanged = false;
4184 ASTOwningVector<&ActionBase::DeleteExpr> PlacementArgs(SemaRef);
4185 for (unsigned I = 0, N = E->getNumPlacementArgs(); I != N; ++I) {
4186 OwningExprResult Arg = getDerived().TransformExpr(E->getPlacementArg(I));
4187 if (Arg.isInvalid())
4188 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004189
Douglas Gregora16548e2009-08-11 05:31:07 +00004190 ArgumentChanged = ArgumentChanged || Arg.get() != E->getPlacementArg(I);
4191 PlacementArgs.push_back(Arg.take());
4192 }
Mike Stump11289f42009-09-09 15:08:12 +00004193
Douglas Gregorebe10102009-08-20 07:17:43 +00004194 // transform the constructor arguments (if any).
Douglas Gregora16548e2009-08-11 05:31:07 +00004195 ASTOwningVector<&ActionBase::DeleteExpr> ConstructorArgs(SemaRef);
4196 for (unsigned I = 0, N = E->getNumConstructorArgs(); I != N; ++I) {
4197 OwningExprResult Arg = getDerived().TransformExpr(E->getConstructorArg(I));
4198 if (Arg.isInvalid())
4199 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004200
Douglas Gregora16548e2009-08-11 05:31:07 +00004201 ArgumentChanged = ArgumentChanged || Arg.get() != E->getConstructorArg(I);
4202 ConstructorArgs.push_back(Arg.take());
4203 }
Mike Stump11289f42009-09-09 15:08:12 +00004204
Douglas Gregora16548e2009-08-11 05:31:07 +00004205 if (!getDerived().AlwaysRebuild() &&
4206 AllocType == E->getAllocatedType() &&
4207 ArraySize.get() == E->getArraySize() &&
4208 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004209 return SemaRef.Owned(E->Retain());
4210
Douglas Gregora16548e2009-08-11 05:31:07 +00004211 return getDerived().RebuildCXXNewExpr(E->getLocStart(),
4212 E->isGlobalNew(),
4213 /*FIXME:*/E->getLocStart(),
4214 move_arg(PlacementArgs),
4215 /*FIXME:*/E->getLocStart(),
4216 E->isParenTypeId(),
4217 AllocType,
4218 /*FIXME:*/E->getLocStart(),
4219 /*FIXME:*/SourceRange(),
4220 move(ArraySize),
4221 /*FIXME:*/E->getLocStart(),
4222 move_arg(ConstructorArgs),
Mike Stump11289f42009-09-09 15:08:12 +00004223 E->getLocEnd());
Douglas Gregora16548e2009-08-11 05:31:07 +00004224}
Mike Stump11289f42009-09-09 15:08:12 +00004225
Douglas Gregora16548e2009-08-11 05:31:07 +00004226template<typename Derived>
4227Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004228TreeTransform<Derived>::TransformCXXDeleteExpr(CXXDeleteExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004229 OwningExprResult Operand = getDerived().TransformExpr(E->getArgument());
4230 if (Operand.isInvalid())
4231 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004232
Douglas Gregora16548e2009-08-11 05:31:07 +00004233 if (!getDerived().AlwaysRebuild() &&
Mike Stump11289f42009-09-09 15:08:12 +00004234 Operand.get() == E->getArgument())
4235 return SemaRef.Owned(E->Retain());
4236
Douglas Gregora16548e2009-08-11 05:31:07 +00004237 return getDerived().RebuildCXXDeleteExpr(E->getLocStart(),
4238 E->isGlobalDelete(),
4239 E->isArrayForm(),
4240 move(Operand));
4241}
Mike Stump11289f42009-09-09 15:08:12 +00004242
Douglas Gregora16548e2009-08-11 05:31:07 +00004243template<typename Derived>
4244Sema::OwningExprResult
Douglas Gregorad8a3362009-09-04 17:36:40 +00004245TreeTransform<Derived>::TransformCXXPseudoDestructorExpr(
4246 CXXPseudoDestructorExpr *E) {
4247 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
4248 if (Base.isInvalid())
4249 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004250
Douglas Gregorad8a3362009-09-04 17:36:40 +00004251 NestedNameSpecifier *Qualifier
4252 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4253 E->getQualifierRange());
4254 if (E->getQualifier() && !Qualifier)
4255 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004256
Douglas Gregorad8a3362009-09-04 17:36:40 +00004257 QualType DestroyedType;
4258 {
4259 TemporaryBase Rebase(*this, E->getDestroyedTypeLoc(), DeclarationName());
4260 DestroyedType = getDerived().TransformType(E->getDestroyedType());
4261 if (DestroyedType.isNull())
4262 return SemaRef.ExprError();
4263 }
Mike Stump11289f42009-09-09 15:08:12 +00004264
Douglas Gregorad8a3362009-09-04 17:36:40 +00004265 if (!getDerived().AlwaysRebuild() &&
4266 Base.get() == E->getBase() &&
4267 Qualifier == E->getQualifier() &&
4268 DestroyedType == E->getDestroyedType())
4269 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004270
Douglas Gregorad8a3362009-09-04 17:36:40 +00004271 return getDerived().RebuildCXXPseudoDestructorExpr(move(Base),
4272 E->getOperatorLoc(),
4273 E->isArrow(),
4274 E->getDestroyedTypeLoc(),
4275 DestroyedType,
4276 Qualifier,
4277 E->getQualifierRange());
4278}
Mike Stump11289f42009-09-09 15:08:12 +00004279
Douglas Gregorad8a3362009-09-04 17:36:40 +00004280template<typename Derived>
4281Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00004282TreeTransform<Derived>::TransformUnresolvedFunctionNameExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004283 UnresolvedFunctionNameExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004284 // There is no transformation we can apply to an unresolved function name.
Mike Stump11289f42009-09-09 15:08:12 +00004285 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004286}
Mike Stump11289f42009-09-09 15:08:12 +00004287
Douglas Gregora16548e2009-08-11 05:31:07 +00004288template<typename Derived>
4289Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004290TreeTransform<Derived>::TransformUnaryTypeTraitExpr(UnaryTypeTraitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004291 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004292
Douglas Gregora16548e2009-08-11 05:31:07 +00004293 QualType T = getDerived().TransformType(E->getQueriedType());
4294 if (T.isNull())
4295 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004296
Douglas Gregora16548e2009-08-11 05:31:07 +00004297 if (!getDerived().AlwaysRebuild() &&
4298 T == E->getQueriedType())
4299 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004300
Douglas Gregora16548e2009-08-11 05:31:07 +00004301 // FIXME: Bad location information
4302 SourceLocation FakeLParenLoc
4303 = SemaRef.PP.getLocForEndOfToken(E->getLocStart());
Mike Stump11289f42009-09-09 15:08:12 +00004304
4305 return getDerived().RebuildUnaryTypeTrait(E->getTrait(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004306 E->getLocStart(),
4307 /*FIXME:*/FakeLParenLoc,
4308 T,
4309 E->getLocEnd());
4310}
Mike Stump11289f42009-09-09 15:08:12 +00004311
Douglas Gregora16548e2009-08-11 05:31:07 +00004312template<typename Derived>
4313Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00004314TreeTransform<Derived>::TransformUnresolvedDeclRefExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004315 UnresolvedDeclRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004316 NestedNameSpecifier *NNS
Douglas Gregord019ff62009-10-22 17:20:55 +00004317 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4318 E->getQualifierRange());
Douglas Gregora16548e2009-08-11 05:31:07 +00004319 if (!NNS)
4320 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004321
4322 DeclarationName Name
Douglas Gregorf816bd72009-09-03 22:13:48 +00004323 = getDerived().TransformDeclarationName(E->getDeclName(), E->getLocation());
4324 if (!Name)
4325 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004326
4327 if (!getDerived().AlwaysRebuild() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00004328 NNS == E->getQualifier() &&
4329 Name == E->getDeclName())
Mike Stump11289f42009-09-09 15:08:12 +00004330 return SemaRef.Owned(E->Retain());
4331
4332 return getDerived().RebuildUnresolvedDeclRefExpr(NNS,
Douglas Gregora16548e2009-08-11 05:31:07 +00004333 E->getQualifierRange(),
4334 Name,
4335 E->getLocation(),
4336 /*FIXME:*/false);
4337}
4338
4339template<typename Derived>
4340Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004341TreeTransform<Derived>::TransformTemplateIdRefExpr(TemplateIdRefExpr *E) {
4342 TemplateName Template
Douglas Gregora16548e2009-08-11 05:31:07 +00004343 = getDerived().TransformTemplateName(E->getTemplateName());
4344 if (Template.isNull())
4345 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004346
Douglas Gregord019ff62009-10-22 17:20:55 +00004347 NestedNameSpecifier *Qualifier = 0;
4348 if (E->getQualifier()) {
4349 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4350 E->getQualifierRange());
4351 if (!Qualifier)
4352 return SemaRef.ExprError();
4353 }
4354
Douglas Gregora16548e2009-08-11 05:31:07 +00004355 llvm::SmallVector<TemplateArgument, 4> TransArgs;
4356 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00004357 TemplateArgument TransArg
Douglas Gregora16548e2009-08-11 05:31:07 +00004358 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
4359 if (TransArg.isNull())
4360 return SemaRef.ExprError();
4361
4362 TransArgs.push_back(TransArg);
4363 }
4364
4365 // FIXME: Would like to avoid rebuilding if nothing changed, but we can't
4366 // compare template arguments (yet).
Mike Stump11289f42009-09-09 15:08:12 +00004367
4368 // FIXME: It's possible that we'll find out now that the template name
Douglas Gregora16548e2009-08-11 05:31:07 +00004369 // actually refers to a type, in which case the caller is actually dealing
4370 // with a functional cast. Give a reasonable error message!
Douglas Gregord019ff62009-10-22 17:20:55 +00004371 return getDerived().RebuildTemplateIdExpr(Qualifier, E->getQualifierRange(),
4372 Template, E->getTemplateNameLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004373 E->getLAngleLoc(),
4374 TransArgs.data(),
4375 TransArgs.size(),
4376 E->getRAngleLoc());
4377}
4378
4379template<typename Derived>
4380Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004381TreeTransform<Derived>::TransformCXXConstructExpr(CXXConstructExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004382 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
4383
4384 QualType T = getDerived().TransformType(E->getType());
4385 if (T.isNull())
4386 return SemaRef.ExprError();
4387
4388 CXXConstructorDecl *Constructor
4389 = cast_or_null<CXXConstructorDecl>(
4390 getDerived().TransformDecl(E->getConstructor()));
4391 if (!Constructor)
4392 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004393
Douglas Gregora16548e2009-08-11 05:31:07 +00004394 bool ArgumentChanged = false;
4395 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
Mike Stump11289f42009-09-09 15:08:12 +00004396 for (CXXConstructExpr::arg_iterator Arg = E->arg_begin(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004397 ArgEnd = E->arg_end();
4398 Arg != ArgEnd; ++Arg) {
4399 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4400 if (TransArg.isInvalid())
4401 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004402
Douglas Gregora16548e2009-08-11 05:31:07 +00004403 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4404 Args.push_back(TransArg.takeAs<Expr>());
4405 }
4406
4407 if (!getDerived().AlwaysRebuild() &&
4408 T == E->getType() &&
4409 Constructor == E->getConstructor() &&
4410 !ArgumentChanged)
4411 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004412
Douglas Gregora16548e2009-08-11 05:31:07 +00004413 return getDerived().RebuildCXXConstructExpr(T, Constructor, E->isElidable(),
4414 move_arg(Args));
4415}
Mike Stump11289f42009-09-09 15:08:12 +00004416
Douglas Gregora16548e2009-08-11 05:31:07 +00004417/// \brief Transform a C++ temporary-binding expression.
4418///
Mike Stump11289f42009-09-09 15:08:12 +00004419/// The transformation of a temporary-binding expression always attempts to
4420/// bind a new temporary variable to its subexpression, even if the
Douglas Gregora16548e2009-08-11 05:31:07 +00004421/// subexpression itself did not change, because the temporary variable itself
4422/// must be unique.
4423template<typename Derived>
4424Sema::OwningExprResult
4425TreeTransform<Derived>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr *E) {
4426 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4427 if (SubExpr.isInvalid())
4428 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004429
Douglas Gregora16548e2009-08-11 05:31:07 +00004430 return SemaRef.MaybeBindToTemporary(SubExpr.takeAs<Expr>());
4431}
Mike Stump11289f42009-09-09 15:08:12 +00004432
4433/// \brief Transform a C++ expression that contains temporaries that should
Douglas Gregora16548e2009-08-11 05:31:07 +00004434/// be destroyed after the expression is evaluated.
4435///
Mike Stump11289f42009-09-09 15:08:12 +00004436/// The transformation of a full expression always attempts to build a new
4437/// CXXExprWithTemporaries expression, even if the
Douglas Gregora16548e2009-08-11 05:31:07 +00004438/// subexpression itself did not change, because it will need to capture the
4439/// the new temporary variables introduced in the subexpression.
4440template<typename Derived>
4441Sema::OwningExprResult
4442TreeTransform<Derived>::TransformCXXExprWithTemporaries(
Mike Stump11289f42009-09-09 15:08:12 +00004443 CXXExprWithTemporaries *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004444 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4445 if (SubExpr.isInvalid())
4446 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004447
Douglas Gregora16548e2009-08-11 05:31:07 +00004448 return SemaRef.Owned(
4449 SemaRef.MaybeCreateCXXExprWithTemporaries(SubExpr.takeAs<Expr>(),
4450 E->shouldDestroyTemporaries()));
4451}
Mike Stump11289f42009-09-09 15:08:12 +00004452
Douglas Gregora16548e2009-08-11 05:31:07 +00004453template<typename Derived>
4454Sema::OwningExprResult
4455TreeTransform<Derived>::TransformCXXTemporaryObjectExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004456 CXXTemporaryObjectExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004457 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4458 QualType T = getDerived().TransformType(E->getType());
4459 if (T.isNull())
4460 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004461
Douglas Gregora16548e2009-08-11 05:31:07 +00004462 CXXConstructorDecl *Constructor
4463 = cast_or_null<CXXConstructorDecl>(
4464 getDerived().TransformDecl(E->getConstructor()));
4465 if (!Constructor)
4466 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004467
Douglas Gregora16548e2009-08-11 05:31:07 +00004468 bool ArgumentChanged = false;
4469 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
4470 Args.reserve(E->getNumArgs());
Mike Stump11289f42009-09-09 15:08:12 +00004471 for (CXXTemporaryObjectExpr::arg_iterator Arg = E->arg_begin(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004472 ArgEnd = E->arg_end();
4473 Arg != ArgEnd; ++Arg) {
4474 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4475 if (TransArg.isInvalid())
4476 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004477
Douglas Gregora16548e2009-08-11 05:31:07 +00004478 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4479 Args.push_back((Expr *)TransArg.release());
4480 }
Mike Stump11289f42009-09-09 15:08:12 +00004481
Douglas Gregora16548e2009-08-11 05:31:07 +00004482 if (!getDerived().AlwaysRebuild() &&
4483 T == E->getType() &&
4484 Constructor == E->getConstructor() &&
4485 !ArgumentChanged)
4486 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004487
Douglas Gregora16548e2009-08-11 05:31:07 +00004488 // FIXME: Bogus location information
4489 SourceLocation CommaLoc;
4490 if (Args.size() > 1) {
4491 Expr *First = (Expr *)Args[0];
Mike Stump11289f42009-09-09 15:08:12 +00004492 CommaLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00004493 = SemaRef.PP.getLocForEndOfToken(First->getSourceRange().getEnd());
4494 }
4495 return getDerived().RebuildCXXTemporaryObjectExpr(E->getTypeBeginLoc(),
4496 T,
4497 /*FIXME:*/E->getTypeBeginLoc(),
4498 move_arg(Args),
4499 &CommaLoc,
4500 E->getLocEnd());
4501}
Mike Stump11289f42009-09-09 15:08:12 +00004502
Douglas Gregora16548e2009-08-11 05:31:07 +00004503template<typename Derived>
4504Sema::OwningExprResult
4505TreeTransform<Derived>::TransformCXXUnresolvedConstructExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004506 CXXUnresolvedConstructExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004507 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4508 QualType T = getDerived().TransformType(E->getTypeAsWritten());
4509 if (T.isNull())
4510 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004511
Douglas Gregora16548e2009-08-11 05:31:07 +00004512 bool ArgumentChanged = false;
4513 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
4514 llvm::SmallVector<SourceLocation, 8> FakeCommaLocs;
4515 for (CXXUnresolvedConstructExpr::arg_iterator Arg = E->arg_begin(),
4516 ArgEnd = E->arg_end();
4517 Arg != ArgEnd; ++Arg) {
4518 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4519 if (TransArg.isInvalid())
4520 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004521
Douglas Gregora16548e2009-08-11 05:31:07 +00004522 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4523 FakeCommaLocs.push_back(
4524 SemaRef.PP.getLocForEndOfToken((*Arg)->getLocEnd()));
4525 Args.push_back(TransArg.takeAs<Expr>());
4526 }
Mike Stump11289f42009-09-09 15:08:12 +00004527
Douglas Gregora16548e2009-08-11 05:31:07 +00004528 if (!getDerived().AlwaysRebuild() &&
4529 T == E->getTypeAsWritten() &&
4530 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004531 return SemaRef.Owned(E->Retain());
4532
Douglas Gregora16548e2009-08-11 05:31:07 +00004533 // FIXME: we're faking the locations of the commas
4534 return getDerived().RebuildCXXUnresolvedConstructExpr(E->getTypeBeginLoc(),
4535 T,
4536 E->getLParenLoc(),
4537 move_arg(Args),
4538 FakeCommaLocs.data(),
4539 E->getRParenLoc());
4540}
Mike Stump11289f42009-09-09 15:08:12 +00004541
Douglas Gregora16548e2009-08-11 05:31:07 +00004542template<typename Derived>
4543Sema::OwningExprResult
4544TreeTransform<Derived>::TransformCXXUnresolvedMemberExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004545 CXXUnresolvedMemberExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004546 // Transform the base of the expression.
4547 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
4548 if (Base.isInvalid())
4549 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004550
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004551 // Start the member reference and compute the object's type.
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004552 Sema::TypeTy *ObjectType = 0;
Mike Stump11289f42009-09-09 15:08:12 +00004553 Base = SemaRef.ActOnStartCXXMemberReference(0, move(Base),
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004554 E->getOperatorLoc(),
4555 E->isArrow()? tok::arrow : tok::period,
4556 ObjectType);
4557 if (Base.isInvalid())
4558 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004559
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004560 // Transform the first part of the nested-name-specifier that qualifies
4561 // the member name.
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004562 NamedDecl *FirstQualifierInScope
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004563 = getDerived().TransformFirstQualifierInScope(
4564 E->getFirstQualifierFoundInScope(),
4565 E->getQualifierRange().getBegin());
Mike Stump11289f42009-09-09 15:08:12 +00004566
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004567 NestedNameSpecifier *Qualifier = 0;
4568 if (E->getQualifier()) {
4569 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4570 E->getQualifierRange(),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004571 QualType::getFromOpaquePtr(ObjectType),
4572 FirstQualifierInScope);
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004573 if (!Qualifier)
4574 return SemaRef.ExprError();
4575 }
Mike Stump11289f42009-09-09 15:08:12 +00004576
4577 DeclarationName Name
Douglas Gregorc59e5612009-10-19 22:04:39 +00004578 = getDerived().TransformDeclarationName(E->getMember(), E->getMemberLoc(),
4579 QualType::getFromOpaquePtr(ObjectType));
Douglas Gregorf816bd72009-09-03 22:13:48 +00004580 if (!Name)
4581 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004582
Douglas Gregor308047d2009-09-09 00:23:06 +00004583 if (!E->hasExplicitTemplateArgumentList()) {
4584 // This is a reference to a member without an explicitly-specified
4585 // template argument list. Optimize for this common case.
4586 if (!getDerived().AlwaysRebuild() &&
4587 Base.get() == E->getBase() &&
4588 Qualifier == E->getQualifier() &&
4589 Name == E->getMember() &&
4590 FirstQualifierInScope == E->getFirstQualifierFoundInScope())
Mike Stump11289f42009-09-09 15:08:12 +00004591 return SemaRef.Owned(E->Retain());
4592
Douglas Gregor308047d2009-09-09 00:23:06 +00004593 return getDerived().RebuildCXXUnresolvedMemberExpr(move(Base),
4594 E->isArrow(),
4595 E->getOperatorLoc(),
4596 Qualifier,
4597 E->getQualifierRange(),
4598 Name,
4599 E->getMemberLoc(),
4600 FirstQualifierInScope);
4601 }
4602
4603 // FIXME: This is an ugly hack, which forces the same template name to
4604 // be looked up multiple times. Yuck!
4605 // FIXME: This also won't work for, e.g., x->template operator+<int>
4606 TemplateName OrigTemplateName
4607 = SemaRef.Context.getDependentTemplateName(0, Name.getAsIdentifierInfo());
Mike Stump11289f42009-09-09 15:08:12 +00004608
4609 TemplateName Template
4610 = getDerived().TransformTemplateName(OrigTemplateName,
Douglas Gregor308047d2009-09-09 00:23:06 +00004611 QualType::getFromOpaquePtr(ObjectType));
4612 if (Template.isNull())
4613 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004614
Douglas Gregor308047d2009-09-09 00:23:06 +00004615 llvm::SmallVector<TemplateArgument, 4> TransArgs;
4616 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00004617 TemplateArgument TransArg
Douglas Gregor308047d2009-09-09 00:23:06 +00004618 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
4619 if (TransArg.isNull())
4620 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004621
Douglas Gregor308047d2009-09-09 00:23:06 +00004622 TransArgs.push_back(TransArg);
4623 }
Mike Stump11289f42009-09-09 15:08:12 +00004624
Douglas Gregora16548e2009-08-11 05:31:07 +00004625 return getDerived().RebuildCXXUnresolvedMemberExpr(move(Base),
4626 E->isArrow(),
4627 E->getOperatorLoc(),
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004628 Qualifier,
4629 E->getQualifierRange(),
Douglas Gregor308047d2009-09-09 00:23:06 +00004630 Template,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004631 E->getMemberLoc(),
Douglas Gregor308047d2009-09-09 00:23:06 +00004632 FirstQualifierInScope,
4633 E->getLAngleLoc(),
4634 TransArgs.data(),
4635 TransArgs.size(),
4636 E->getRAngleLoc());
Douglas Gregora16548e2009-08-11 05:31:07 +00004637}
4638
4639template<typename Derived>
4640Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004641TreeTransform<Derived>::TransformObjCStringLiteral(ObjCStringLiteral *E) {
4642 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004643}
4644
Mike Stump11289f42009-09-09 15:08:12 +00004645template<typename Derived>
4646Sema::OwningExprResult
4647TreeTransform<Derived>::TransformObjCEncodeExpr(ObjCEncodeExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004648 // FIXME: poor source location
4649 TemporaryBase Rebase(*this, E->getAtLoc(), DeclarationName());
4650 QualType EncodedType = getDerived().TransformType(E->getEncodedType());
4651 if (EncodedType.isNull())
4652 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004653
Douglas Gregora16548e2009-08-11 05:31:07 +00004654 if (!getDerived().AlwaysRebuild() &&
4655 EncodedType == E->getEncodedType())
Mike Stump11289f42009-09-09 15:08:12 +00004656 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004657
4658 return getDerived().RebuildObjCEncodeExpr(E->getAtLoc(),
4659 EncodedType,
4660 E->getRParenLoc());
4661}
Mike Stump11289f42009-09-09 15:08:12 +00004662
Douglas Gregora16548e2009-08-11 05:31:07 +00004663template<typename Derived>
4664Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004665TreeTransform<Derived>::TransformObjCMessageExpr(ObjCMessageExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004666 // FIXME: Implement this!
4667 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004668 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004669}
4670
Mike Stump11289f42009-09-09 15:08:12 +00004671template<typename Derived>
4672Sema::OwningExprResult
4673TreeTransform<Derived>::TransformObjCSelectorExpr(ObjCSelectorExpr *E) {
4674 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004675}
4676
Mike Stump11289f42009-09-09 15:08:12 +00004677template<typename Derived>
4678Sema::OwningExprResult
4679TreeTransform<Derived>::TransformObjCProtocolExpr(ObjCProtocolExpr *E) {
4680 ObjCProtocolDecl *Protocol
Douglas Gregora16548e2009-08-11 05:31:07 +00004681 = cast_or_null<ObjCProtocolDecl>(
4682 getDerived().TransformDecl(E->getProtocol()));
4683 if (!Protocol)
4684 return SemaRef.ExprError();
4685
4686 if (!getDerived().AlwaysRebuild() &&
4687 Protocol == E->getProtocol())
Mike Stump11289f42009-09-09 15:08:12 +00004688 return SemaRef.Owned(E->Retain());
4689
Douglas Gregora16548e2009-08-11 05:31:07 +00004690 return getDerived().RebuildObjCProtocolExpr(Protocol,
4691 E->getAtLoc(),
4692 /*FIXME:*/E->getAtLoc(),
4693 /*FIXME:*/E->getAtLoc(),
4694 E->getRParenLoc());
Mike Stump11289f42009-09-09 15:08:12 +00004695
Douglas Gregora16548e2009-08-11 05:31:07 +00004696}
4697
Mike Stump11289f42009-09-09 15:08:12 +00004698template<typename Derived>
4699Sema::OwningExprResult
4700TreeTransform<Derived>::TransformObjCIvarRefExpr(ObjCIvarRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004701 // FIXME: Implement this!
4702 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004703 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004704}
4705
Mike Stump11289f42009-09-09 15:08:12 +00004706template<typename Derived>
4707Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00004708TreeTransform<Derived>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr *E) {
4709 // FIXME: Implement this!
4710 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004711 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004712}
4713
Mike Stump11289f42009-09-09 15:08:12 +00004714template<typename Derived>
4715Sema::OwningExprResult
Fariborz Jahanian9a846652009-08-20 17:02:02 +00004716TreeTransform<Derived>::TransformObjCImplicitSetterGetterRefExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004717 ObjCImplicitSetterGetterRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004718 // FIXME: Implement this!
4719 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004720 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004721}
4722
Mike Stump11289f42009-09-09 15:08:12 +00004723template<typename Derived>
4724Sema::OwningExprResult
4725TreeTransform<Derived>::TransformObjCSuperExpr(ObjCSuperExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004726 // FIXME: Implement this!
4727 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004728 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004729}
4730
Mike Stump11289f42009-09-09 15:08:12 +00004731template<typename Derived>
4732Sema::OwningExprResult
4733TreeTransform<Derived>::TransformObjCIsaExpr(ObjCIsaExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004734 // FIXME: Implement this!
4735 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004736 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004737}
4738
Mike Stump11289f42009-09-09 15:08:12 +00004739template<typename Derived>
4740Sema::OwningExprResult
4741TreeTransform<Derived>::TransformShuffleVectorExpr(ShuffleVectorExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004742 bool ArgumentChanged = false;
4743 ASTOwningVector<&ActionBase::DeleteExpr> SubExprs(SemaRef);
4744 for (unsigned I = 0, N = E->getNumSubExprs(); I != N; ++I) {
4745 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExpr(I));
4746 if (SubExpr.isInvalid())
4747 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004748
Douglas Gregora16548e2009-08-11 05:31:07 +00004749 ArgumentChanged = ArgumentChanged || SubExpr.get() != E->getExpr(I);
4750 SubExprs.push_back(SubExpr.takeAs<Expr>());
4751 }
Mike Stump11289f42009-09-09 15:08:12 +00004752
Douglas Gregora16548e2009-08-11 05:31:07 +00004753 if (!getDerived().AlwaysRebuild() &&
4754 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004755 return SemaRef.Owned(E->Retain());
4756
Douglas Gregora16548e2009-08-11 05:31:07 +00004757 return getDerived().RebuildShuffleVectorExpr(E->getBuiltinLoc(),
4758 move_arg(SubExprs),
4759 E->getRParenLoc());
4760}
4761
Mike Stump11289f42009-09-09 15:08:12 +00004762template<typename Derived>
4763Sema::OwningExprResult
4764TreeTransform<Derived>::TransformBlockExpr(BlockExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004765 // FIXME: Implement this!
4766 assert(false && "Cannot transform block expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004767 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004768}
4769
Mike Stump11289f42009-09-09 15:08:12 +00004770template<typename Derived>
4771Sema::OwningExprResult
4772TreeTransform<Derived>::TransformBlockDeclRefExpr(BlockDeclRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004773 // FIXME: Implement this!
4774 assert(false && "Cannot transform block-related expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004775 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004776}
Mike Stump11289f42009-09-09 15:08:12 +00004777
Douglas Gregora16548e2009-08-11 05:31:07 +00004778//===----------------------------------------------------------------------===//
Douglas Gregord6ff3322009-08-04 16:50:30 +00004779// Type reconstruction
4780//===----------------------------------------------------------------------===//
4781
Mike Stump11289f42009-09-09 15:08:12 +00004782template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00004783QualType TreeTransform<Derived>::RebuildPointerType(QualType PointeeType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004784 return SemaRef.BuildPointerType(PointeeType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004785 getDerived().getBaseLocation(),
4786 getDerived().getBaseEntity());
4787}
4788
Mike Stump11289f42009-09-09 15:08:12 +00004789template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00004790QualType TreeTransform<Derived>::RebuildBlockPointerType(QualType PointeeType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004791 return SemaRef.BuildBlockPointerType(PointeeType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004792 getDerived().getBaseLocation(),
4793 getDerived().getBaseEntity());
4794}
4795
Mike Stump11289f42009-09-09 15:08:12 +00004796template<typename Derived>
4797QualType
Douglas Gregord6ff3322009-08-04 16:50:30 +00004798TreeTransform<Derived>::RebuildLValueReferenceType(QualType ReferentType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004799 return SemaRef.BuildReferenceType(ReferentType, true, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004800 getDerived().getBaseLocation(),
4801 getDerived().getBaseEntity());
4802}
4803
4804template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004805QualType
4806TreeTransform<Derived>::RebuildRValueReferenceType(QualType ReferentType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004807 return SemaRef.BuildReferenceType(ReferentType, false, Qualifiers(),
Mike Stump11289f42009-09-09 15:08:12 +00004808 getDerived().getBaseLocation(),
4809 getDerived().getBaseEntity());
4810}
4811
4812template<typename Derived>
4813QualType TreeTransform<Derived>::RebuildMemberPointerType(QualType PointeeType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004814 QualType ClassType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004815 return SemaRef.BuildMemberPointerType(PointeeType, ClassType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004816 getDerived().getBaseLocation(),
4817 getDerived().getBaseEntity());
4818}
4819
4820template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004821QualType
John McCall550e0c22009-10-21 00:40:46 +00004822TreeTransform<Derived>::RebuildObjCObjectPointerType(QualType PointeeType) {
4823 return SemaRef.BuildPointerType(PointeeType, Qualifiers(),
4824 getDerived().getBaseLocation(),
4825 getDerived().getBaseEntity());
4826}
4827
4828template<typename Derived>
4829QualType
Douglas Gregord6ff3322009-08-04 16:50:30 +00004830TreeTransform<Derived>::RebuildArrayType(QualType ElementType,
4831 ArrayType::ArraySizeModifier SizeMod,
4832 const llvm::APInt *Size,
4833 Expr *SizeExpr,
4834 unsigned IndexTypeQuals,
4835 SourceRange BracketsRange) {
4836 if (SizeExpr || !Size)
4837 return SemaRef.BuildArrayType(ElementType, SizeMod, SizeExpr,
4838 IndexTypeQuals, BracketsRange,
4839 getDerived().getBaseEntity());
Mike Stump11289f42009-09-09 15:08:12 +00004840
4841 QualType Types[] = {
4842 SemaRef.Context.UnsignedCharTy, SemaRef.Context.UnsignedShortTy,
4843 SemaRef.Context.UnsignedIntTy, SemaRef.Context.UnsignedLongTy,
4844 SemaRef.Context.UnsignedLongLongTy, SemaRef.Context.UnsignedInt128Ty
Douglas Gregord6ff3322009-08-04 16:50:30 +00004845 };
4846 const unsigned NumTypes = sizeof(Types) / sizeof(QualType);
4847 QualType SizeType;
4848 for (unsigned I = 0; I != NumTypes; ++I)
4849 if (Size->getBitWidth() == SemaRef.Context.getIntWidth(Types[I])) {
4850 SizeType = Types[I];
4851 break;
4852 }
Mike Stump11289f42009-09-09 15:08:12 +00004853
Douglas Gregord6ff3322009-08-04 16:50:30 +00004854 if (SizeType.isNull())
4855 SizeType = SemaRef.Context.getFixedWidthIntType(Size->getBitWidth(), false);
Mike Stump11289f42009-09-09 15:08:12 +00004856
Douglas Gregord6ff3322009-08-04 16:50:30 +00004857 IntegerLiteral ArraySize(*Size, SizeType, /*FIXME*/BracketsRange.getBegin());
Mike Stump11289f42009-09-09 15:08:12 +00004858 return SemaRef.BuildArrayType(ElementType, SizeMod, &ArraySize,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004859 IndexTypeQuals, BracketsRange,
Mike Stump11289f42009-09-09 15:08:12 +00004860 getDerived().getBaseEntity());
Douglas Gregord6ff3322009-08-04 16:50:30 +00004861}
Mike Stump11289f42009-09-09 15:08:12 +00004862
Douglas Gregord6ff3322009-08-04 16:50:30 +00004863template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004864QualType
4865TreeTransform<Derived>::RebuildConstantArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004866 ArrayType::ArraySizeModifier SizeMod,
4867 const llvm::APInt &Size,
4868 unsigned IndexTypeQuals) {
Mike Stump11289f42009-09-09 15:08:12 +00004869 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004870 IndexTypeQuals, SourceRange());
4871}
4872
4873template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004874QualType
Mike Stump11289f42009-09-09 15:08:12 +00004875TreeTransform<Derived>::RebuildIncompleteArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004876 ArrayType::ArraySizeModifier SizeMod,
4877 unsigned IndexTypeQuals) {
Mike Stump11289f42009-09-09 15:08:12 +00004878 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004879 IndexTypeQuals, SourceRange());
4880}
Mike Stump11289f42009-09-09 15:08:12 +00004881
Douglas Gregord6ff3322009-08-04 16:50:30 +00004882template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004883QualType
4884TreeTransform<Derived>::RebuildVariableArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004885 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +00004886 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004887 unsigned IndexTypeQuals,
4888 SourceRange BracketsRange) {
Mike Stump11289f42009-09-09 15:08:12 +00004889 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004890 SizeExpr.takeAs<Expr>(),
4891 IndexTypeQuals, BracketsRange);
4892}
4893
4894template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004895QualType
4896TreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004897 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +00004898 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004899 unsigned IndexTypeQuals,
4900 SourceRange BracketsRange) {
Mike Stump11289f42009-09-09 15:08:12 +00004901 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004902 SizeExpr.takeAs<Expr>(),
4903 IndexTypeQuals, BracketsRange);
4904}
4905
4906template<typename Derived>
4907QualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType,
4908 unsigned NumElements) {
4909 // FIXME: semantic checking!
4910 return SemaRef.Context.getVectorType(ElementType, NumElements);
4911}
Mike Stump11289f42009-09-09 15:08:12 +00004912
Douglas Gregord6ff3322009-08-04 16:50:30 +00004913template<typename Derived>
4914QualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType,
4915 unsigned NumElements,
4916 SourceLocation AttributeLoc) {
4917 llvm::APInt numElements(SemaRef.Context.getIntWidth(SemaRef.Context.IntTy),
4918 NumElements, true);
4919 IntegerLiteral *VectorSize
Mike Stump11289f42009-09-09 15:08:12 +00004920 = new (SemaRef.Context) IntegerLiteral(numElements, SemaRef.Context.IntTy,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004921 AttributeLoc);
4922 return SemaRef.BuildExtVectorType(ElementType, SemaRef.Owned(VectorSize),
4923 AttributeLoc);
4924}
Mike Stump11289f42009-09-09 15:08:12 +00004925
Douglas Gregord6ff3322009-08-04 16:50:30 +00004926template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004927QualType
4928TreeTransform<Derived>::RebuildDependentSizedExtVectorType(QualType ElementType,
Douglas Gregora16548e2009-08-11 05:31:07 +00004929 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004930 SourceLocation AttributeLoc) {
4931 return SemaRef.BuildExtVectorType(ElementType, move(SizeExpr), AttributeLoc);
4932}
Mike Stump11289f42009-09-09 15:08:12 +00004933
Douglas Gregord6ff3322009-08-04 16:50:30 +00004934template<typename Derived>
4935QualType TreeTransform<Derived>::RebuildFunctionProtoType(QualType T,
Mike Stump11289f42009-09-09 15:08:12 +00004936 QualType *ParamTypes,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004937 unsigned NumParamTypes,
Mike Stump11289f42009-09-09 15:08:12 +00004938 bool Variadic,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004939 unsigned Quals) {
Mike Stump11289f42009-09-09 15:08:12 +00004940 return SemaRef.BuildFunctionType(T, ParamTypes, NumParamTypes, Variadic,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004941 Quals,
4942 getDerived().getBaseLocation(),
4943 getDerived().getBaseEntity());
4944}
Mike Stump11289f42009-09-09 15:08:12 +00004945
Douglas Gregord6ff3322009-08-04 16:50:30 +00004946template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00004947QualType TreeTransform<Derived>::RebuildFunctionNoProtoType(QualType T) {
4948 return SemaRef.Context.getFunctionNoProtoType(T);
4949}
4950
4951template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00004952QualType TreeTransform<Derived>::RebuildTypeOfExprType(ExprArg E) {
Douglas Gregord6ff3322009-08-04 16:50:30 +00004953 return SemaRef.BuildTypeofExprType(E.takeAs<Expr>());
4954}
4955
4956template<typename Derived>
4957QualType TreeTransform<Derived>::RebuildTypeOfType(QualType Underlying) {
4958 return SemaRef.Context.getTypeOfType(Underlying);
4959}
4960
4961template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00004962QualType TreeTransform<Derived>::RebuildDecltypeType(ExprArg E) {
Douglas Gregord6ff3322009-08-04 16:50:30 +00004963 return SemaRef.BuildDecltypeType(E.takeAs<Expr>());
4964}
4965
4966template<typename Derived>
4967QualType TreeTransform<Derived>::RebuildTemplateSpecializationType(
4968 TemplateName Template,
4969 const TemplateArgument *Args,
4970 unsigned NumArgs) {
4971 // FIXME: Missing source locations for the template name, <, >.
4972 return SemaRef.CheckTemplateIdType(Template, getDerived().getBaseLocation(),
Mike Stump11289f42009-09-09 15:08:12 +00004973 SourceLocation(), Args, NumArgs,
4974 SourceLocation());
Douglas Gregord6ff3322009-08-04 16:50:30 +00004975}
Mike Stump11289f42009-09-09 15:08:12 +00004976
Douglas Gregor1135c352009-08-06 05:28:30 +00004977template<typename Derived>
4978NestedNameSpecifier *
4979TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
4980 SourceRange Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004981 IdentifierInfo &II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004982 QualType ObjectType,
4983 NamedDecl *FirstQualifierInScope) {
Douglas Gregor1135c352009-08-06 05:28:30 +00004984 CXXScopeSpec SS;
4985 // FIXME: The source location information is all wrong.
4986 SS.setRange(Range);
4987 SS.setScopeRep(Prefix);
4988 return static_cast<NestedNameSpecifier *>(
Mike Stump11289f42009-09-09 15:08:12 +00004989 SemaRef.BuildCXXNestedNameSpecifier(0, SS, Range.getEnd(),
Douglas Gregore861bac2009-08-25 22:51:20 +00004990 Range.getEnd(), II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004991 ObjectType,
4992 FirstQualifierInScope,
Douglas Gregore861bac2009-08-25 22:51:20 +00004993 false));
Douglas Gregor1135c352009-08-06 05:28:30 +00004994}
4995
4996template<typename Derived>
4997NestedNameSpecifier *
4998TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
4999 SourceRange Range,
5000 NamespaceDecl *NS) {
5001 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, NS);
5002}
5003
5004template<typename Derived>
5005NestedNameSpecifier *
5006TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
5007 SourceRange Range,
5008 bool TemplateKW,
5009 QualType T) {
5010 if (T->isDependentType() || T->isRecordType() ||
5011 (SemaRef.getLangOptions().CPlusPlus0x && T->isEnumeralType())) {
John McCall8ccfcb52009-09-24 19:53:00 +00005012 assert(!T.hasQualifiers() && "Can't get cv-qualifiers here");
Douglas Gregor1135c352009-08-06 05:28:30 +00005013 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, TemplateKW,
5014 T.getTypePtr());
5015 }
Mike Stump11289f42009-09-09 15:08:12 +00005016
Douglas Gregor1135c352009-08-06 05:28:30 +00005017 SemaRef.Diag(Range.getBegin(), diag::err_nested_name_spec_non_tag) << T;
5018 return 0;
5019}
Mike Stump11289f42009-09-09 15:08:12 +00005020
Douglas Gregor71dc5092009-08-06 06:41:21 +00005021template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005022TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005023TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
5024 bool TemplateKW,
5025 TemplateDecl *Template) {
Mike Stump11289f42009-09-09 15:08:12 +00005026 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW,
Douglas Gregor71dc5092009-08-06 06:41:21 +00005027 Template);
5028}
5029
5030template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005031TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005032TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
5033 bool TemplateKW,
5034 OverloadedFunctionDecl *Ovl) {
5035 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW, Ovl);
5036}
5037
5038template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005039TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005040TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
Douglas Gregor308047d2009-09-09 00:23:06 +00005041 const IdentifierInfo &II,
5042 QualType ObjectType) {
Douglas Gregor71dc5092009-08-06 06:41:21 +00005043 CXXScopeSpec SS;
5044 SS.setRange(SourceRange(getDerived().getBaseLocation()));
Mike Stump11289f42009-09-09 15:08:12 +00005045 SS.setScopeRep(Qualifier);
Douglas Gregor308047d2009-09-09 00:23:06 +00005046 return getSema().ActOnDependentTemplateName(
5047 /*FIXME:*/getDerived().getBaseLocation(),
5048 II,
5049 /*FIXME:*/getDerived().getBaseLocation(),
5050 SS,
5051 ObjectType.getAsOpaquePtr())
5052 .template getAsVal<TemplateName>();
Douglas Gregor71dc5092009-08-06 06:41:21 +00005053}
Mike Stump11289f42009-09-09 15:08:12 +00005054
Douglas Gregora16548e2009-08-11 05:31:07 +00005055template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005056Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00005057TreeTransform<Derived>::RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
5058 SourceLocation OpLoc,
5059 ExprArg Callee,
5060 ExprArg First,
5061 ExprArg Second) {
5062 Expr *FirstExpr = (Expr *)First.get();
5063 Expr *SecondExpr = (Expr *)Second.get();
5064 bool isPostIncDec = SecondExpr && (Op == OO_PlusPlus || Op == OO_MinusMinus);
Mike Stump11289f42009-09-09 15:08:12 +00005065
Douglas Gregora16548e2009-08-11 05:31:07 +00005066 // Determine whether this should be a builtin operation.
5067 if (SecondExpr == 0 || isPostIncDec) {
5068 if (!FirstExpr->getType()->isOverloadableType()) {
5069 // The argument is not of overloadable type, so try to create a
5070 // built-in unary operation.
Mike Stump11289f42009-09-09 15:08:12 +00005071 UnaryOperator::Opcode Opc
Douglas Gregora16548e2009-08-11 05:31:07 +00005072 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
Mike Stump11289f42009-09-09 15:08:12 +00005073
Douglas Gregora16548e2009-08-11 05:31:07 +00005074 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(First));
5075 }
5076 } else {
Mike Stump11289f42009-09-09 15:08:12 +00005077 if (!FirstExpr->getType()->isOverloadableType() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00005078 !SecondExpr->getType()->isOverloadableType()) {
5079 // Neither of the arguments is an overloadable type, so try to
5080 // create a built-in binary operation.
5081 BinaryOperator::Opcode Opc = BinaryOperator::getOverloadedOpcode(Op);
Mike Stump11289f42009-09-09 15:08:12 +00005082 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00005083 = SemaRef.CreateBuiltinBinOp(OpLoc, Opc, FirstExpr, SecondExpr);
5084 if (Result.isInvalid())
5085 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00005086
Douglas Gregora16548e2009-08-11 05:31:07 +00005087 First.release();
5088 Second.release();
5089 return move(Result);
5090 }
5091 }
Mike Stump11289f42009-09-09 15:08:12 +00005092
5093 // Compute the transformed set of functions (and function templates) to be
Douglas Gregora16548e2009-08-11 05:31:07 +00005094 // used during overload resolution.
5095 Sema::FunctionSet Functions;
Mike Stump11289f42009-09-09 15:08:12 +00005096
5097 DeclRefExpr *DRE
Douglas Gregor32e2c842009-09-01 16:58:52 +00005098 = cast<DeclRefExpr>(((Expr *)Callee.get())->IgnoreParenCasts());
Mike Stump11289f42009-09-09 15:08:12 +00005099
Douglas Gregora16548e2009-08-11 05:31:07 +00005100 // FIXME: Do we have to check
5101 // IsAcceptableNonMemberOperatorCandidate for each of these?
Douglas Gregor32e2c842009-09-01 16:58:52 +00005102 for (OverloadIterator F(DRE->getDecl()), FEnd; F != FEnd; ++F)
Douglas Gregora16548e2009-08-11 05:31:07 +00005103 Functions.insert(*F);
Mike Stump11289f42009-09-09 15:08:12 +00005104
Douglas Gregora16548e2009-08-11 05:31:07 +00005105 // Add any functions found via argument-dependent lookup.
5106 Expr *Args[2] = { FirstExpr, SecondExpr };
5107 unsigned NumArgs = 1 + (SecondExpr != 0);
Mike Stump11289f42009-09-09 15:08:12 +00005108 DeclarationName OpName
Douglas Gregora16548e2009-08-11 05:31:07 +00005109 = SemaRef.Context.DeclarationNames.getCXXOperatorName(Op);
Sebastian Redlc057f422009-10-23 19:23:15 +00005110 SemaRef.ArgumentDependentLookup(OpName, /*Operator*/true, Args, NumArgs,
5111 Functions);
Mike Stump11289f42009-09-09 15:08:12 +00005112
Douglas Gregora16548e2009-08-11 05:31:07 +00005113 // Create the overloaded operator invocation for unary operators.
5114 if (NumArgs == 1 || isPostIncDec) {
Mike Stump11289f42009-09-09 15:08:12 +00005115 UnaryOperator::Opcode Opc
Douglas Gregora16548e2009-08-11 05:31:07 +00005116 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
5117 return SemaRef.CreateOverloadedUnaryOp(OpLoc, Opc, Functions, move(First));
5118 }
Mike Stump11289f42009-09-09 15:08:12 +00005119
Douglas Gregora16548e2009-08-11 05:31:07 +00005120 // Create the overloaded operator invocation for binary operators.
Mike Stump11289f42009-09-09 15:08:12 +00005121 BinaryOperator::Opcode Opc =
Douglas Gregora16548e2009-08-11 05:31:07 +00005122 BinaryOperator::getOverloadedOpcode(Op);
Mike Stump11289f42009-09-09 15:08:12 +00005123 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00005124 = SemaRef.CreateOverloadedBinOp(OpLoc, Opc, Functions, Args[0], Args[1]);
5125 if (Result.isInvalid())
5126 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00005127
Douglas Gregora16548e2009-08-11 05:31:07 +00005128 First.release();
5129 Second.release();
Mike Stump11289f42009-09-09 15:08:12 +00005130 return move(Result);
Douglas Gregora16548e2009-08-11 05:31:07 +00005131}
Mike Stump11289f42009-09-09 15:08:12 +00005132
Douglas Gregord6ff3322009-08-04 16:50:30 +00005133} // end namespace clang
5134
5135#endif // LLVM_CLANG_SEMA_TREETRANSFORM_H