blob: 5f06ce5e35dc60603ee63b9853d0ee4e2f1a4dfc [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
John McCall550e0c22009-10-21 00:40:46 +0000517 /// \brief Rebuild an objective C protocol list type.
518 QualType RebuildObjCProtocolListType(QualType BaseType,
519 ObjCProtocolDecl **Protocols,
520 unsigned NumProtocols) {
521 return SemaRef.Context.getObjCProtocolListType(BaseType, Protocols,
522 NumProtocols);
523 }
524
Douglas Gregor1135c352009-08-06 05:28:30 +0000525 /// \brief Build a new nested-name-specifier given the prefix and an
526 /// identifier that names the next step in the nested-name-specifier.
527 ///
528 /// By default, performs semantic analysis when building the new
529 /// nested-name-specifier. Subclasses may override this routine to provide
530 /// different behavior.
531 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
532 SourceRange Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +0000533 IdentifierInfo &II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +0000534 QualType ObjectType,
535 NamedDecl *FirstQualifierInScope);
Douglas Gregor1135c352009-08-06 05:28:30 +0000536
537 /// \brief Build a new nested-name-specifier given the prefix and the
538 /// namespace named in the next step in the nested-name-specifier.
539 ///
540 /// By default, performs semantic analysis when building the new
541 /// nested-name-specifier. Subclasses may override this routine to provide
542 /// different behavior.
543 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
544 SourceRange Range,
545 NamespaceDecl *NS);
546
547 /// \brief Build a new nested-name-specifier given the prefix and the
548 /// type named in the next step in the nested-name-specifier.
549 ///
550 /// By default, performs semantic analysis when building the new
551 /// nested-name-specifier. Subclasses may override this routine to provide
552 /// different behavior.
553 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
554 SourceRange Range,
555 bool TemplateKW,
556 QualType T);
Douglas Gregor71dc5092009-08-06 06:41:21 +0000557
558 /// \brief Build a new template name given a nested name specifier, a flag
559 /// indicating whether the "template" keyword was provided, and the template
560 /// that the template name refers to.
561 ///
562 /// By default, builds the new template name directly. Subclasses may override
563 /// this routine to provide different behavior.
564 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
565 bool TemplateKW,
566 TemplateDecl *Template);
567
568 /// \brief Build a new template name given a nested name specifier, a flag
569 /// indicating whether the "template" keyword was provided, and a set of
570 /// overloaded function templates.
571 ///
572 /// By default, builds the new template name directly. Subclasses may override
573 /// this routine to provide different behavior.
574 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
575 bool TemplateKW,
576 OverloadedFunctionDecl *Ovl);
Mike Stump11289f42009-09-09 15:08:12 +0000577
Douglas Gregor71dc5092009-08-06 06:41:21 +0000578 /// \brief Build a new template name given a nested name specifier and the
579 /// name that is referred to as a template.
580 ///
581 /// By default, performs semantic analysis to determine whether the name can
582 /// be resolved to a specific template, then builds the appropriate kind of
583 /// template name. Subclasses may override this routine to provide different
584 /// behavior.
585 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
Douglas Gregor308047d2009-09-09 00:23:06 +0000586 const IdentifierInfo &II,
587 QualType ObjectType);
Mike Stump11289f42009-09-09 15:08:12 +0000588
589
Douglas Gregorebe10102009-08-20 07:17:43 +0000590 /// \brief Build a new compound statement.
591 ///
592 /// By default, performs semantic analysis to build the new statement.
593 /// Subclasses may override this routine to provide different behavior.
594 OwningStmtResult RebuildCompoundStmt(SourceLocation LBraceLoc,
595 MultiStmtArg Statements,
596 SourceLocation RBraceLoc,
597 bool IsStmtExpr) {
598 return getSema().ActOnCompoundStmt(LBraceLoc, RBraceLoc, move(Statements),
599 IsStmtExpr);
600 }
601
602 /// \brief Build a new case statement.
603 ///
604 /// By default, performs semantic analysis to build the new statement.
605 /// Subclasses may override this routine to provide different behavior.
606 OwningStmtResult RebuildCaseStmt(SourceLocation CaseLoc,
607 ExprArg LHS,
608 SourceLocation EllipsisLoc,
609 ExprArg RHS,
610 SourceLocation ColonLoc) {
Mike Stump11289f42009-09-09 15:08:12 +0000611 return getSema().ActOnCaseStmt(CaseLoc, move(LHS), EllipsisLoc, move(RHS),
Douglas Gregorebe10102009-08-20 07:17:43 +0000612 ColonLoc);
613 }
Mike Stump11289f42009-09-09 15:08:12 +0000614
Douglas Gregorebe10102009-08-20 07:17:43 +0000615 /// \brief Attach the body to a new case statement.
616 ///
617 /// By default, performs semantic analysis to build the new statement.
618 /// Subclasses may override this routine to provide different behavior.
619 OwningStmtResult RebuildCaseStmtBody(StmtArg S, StmtArg Body) {
620 getSema().ActOnCaseStmtBody(S.get(), move(Body));
621 return move(S);
622 }
Mike Stump11289f42009-09-09 15:08:12 +0000623
Douglas Gregorebe10102009-08-20 07:17:43 +0000624 /// \brief Build a new default statement.
625 ///
626 /// By default, performs semantic analysis to build the new statement.
627 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000628 OwningStmtResult RebuildDefaultStmt(SourceLocation DefaultLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000629 SourceLocation ColonLoc,
630 StmtArg SubStmt) {
Mike Stump11289f42009-09-09 15:08:12 +0000631 return getSema().ActOnDefaultStmt(DefaultLoc, ColonLoc, move(SubStmt),
Douglas Gregorebe10102009-08-20 07:17:43 +0000632 /*CurScope=*/0);
633 }
Mike Stump11289f42009-09-09 15:08:12 +0000634
Douglas Gregorebe10102009-08-20 07:17:43 +0000635 /// \brief Build a new label statement.
636 ///
637 /// By default, performs semantic analysis to build the new statement.
638 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000639 OwningStmtResult RebuildLabelStmt(SourceLocation IdentLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000640 IdentifierInfo *Id,
641 SourceLocation ColonLoc,
642 StmtArg SubStmt) {
643 return SemaRef.ActOnLabelStmt(IdentLoc, Id, ColonLoc, move(SubStmt));
644 }
Mike Stump11289f42009-09-09 15:08:12 +0000645
Douglas Gregorebe10102009-08-20 07:17:43 +0000646 /// \brief Build a new "if" statement.
647 ///
648 /// By default, performs semantic analysis to build the new statement.
649 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000650 OwningStmtResult RebuildIfStmt(SourceLocation IfLoc, Sema::FullExprArg Cond,
651 StmtArg Then, SourceLocation ElseLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000652 StmtArg Else) {
653 return getSema().ActOnIfStmt(IfLoc, Cond, move(Then), ElseLoc, move(Else));
654 }
Mike Stump11289f42009-09-09 15:08:12 +0000655
Douglas Gregorebe10102009-08-20 07:17:43 +0000656 /// \brief Start building a new switch statement.
657 ///
658 /// By default, performs semantic analysis to build the new statement.
659 /// Subclasses may override this routine to provide different behavior.
660 OwningStmtResult RebuildSwitchStmtStart(ExprArg Cond) {
661 return getSema().ActOnStartOfSwitchStmt(move(Cond));
662 }
Mike Stump11289f42009-09-09 15:08:12 +0000663
Douglas Gregorebe10102009-08-20 07:17:43 +0000664 /// \brief Attach the body to the switch statement.
665 ///
666 /// By default, performs semantic analysis to build the new statement.
667 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000668 OwningStmtResult RebuildSwitchStmtBody(SourceLocation SwitchLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000669 StmtArg Switch, StmtArg Body) {
670 return getSema().ActOnFinishSwitchStmt(SwitchLoc, move(Switch),
671 move(Body));
672 }
673
674 /// \brief Build a new while statement.
675 ///
676 /// By default, performs semantic analysis to build the new statement.
677 /// Subclasses may override this routine to provide different behavior.
678 OwningStmtResult RebuildWhileStmt(SourceLocation WhileLoc,
679 Sema::FullExprArg Cond,
680 StmtArg Body) {
681 return getSema().ActOnWhileStmt(WhileLoc, Cond, move(Body));
682 }
Mike Stump11289f42009-09-09 15:08:12 +0000683
Douglas Gregorebe10102009-08-20 07:17:43 +0000684 /// \brief Build a new do-while statement.
685 ///
686 /// By default, performs semantic analysis to build the new statement.
687 /// Subclasses may override this routine to provide different behavior.
688 OwningStmtResult RebuildDoStmt(SourceLocation DoLoc, StmtArg Body,
689 SourceLocation WhileLoc,
690 SourceLocation LParenLoc,
691 ExprArg Cond,
692 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +0000693 return getSema().ActOnDoStmt(DoLoc, move(Body), WhileLoc, LParenLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000694 move(Cond), RParenLoc);
695 }
696
697 /// \brief Build a new for statement.
698 ///
699 /// By default, performs semantic analysis to build the new statement.
700 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000701 OwningStmtResult RebuildForStmt(SourceLocation ForLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000702 SourceLocation LParenLoc,
703 StmtArg Init, ExprArg Cond, ExprArg Inc,
704 SourceLocation RParenLoc, StmtArg Body) {
Mike Stump11289f42009-09-09 15:08:12 +0000705 return getSema().ActOnForStmt(ForLoc, LParenLoc, move(Init), move(Cond),
Douglas Gregorebe10102009-08-20 07:17:43 +0000706 move(Inc), RParenLoc, move(Body));
707 }
Mike Stump11289f42009-09-09 15:08:12 +0000708
Douglas Gregorebe10102009-08-20 07:17:43 +0000709 /// \brief Build a new goto statement.
710 ///
711 /// By default, performs semantic analysis to build the new statement.
712 /// Subclasses may override this routine to provide different behavior.
713 OwningStmtResult RebuildGotoStmt(SourceLocation GotoLoc,
714 SourceLocation LabelLoc,
715 LabelStmt *Label) {
716 return getSema().ActOnGotoStmt(GotoLoc, LabelLoc, Label->getID());
717 }
718
719 /// \brief Build a new indirect goto statement.
720 ///
721 /// By default, performs semantic analysis to build the new statement.
722 /// Subclasses may override this routine to provide different behavior.
723 OwningStmtResult RebuildIndirectGotoStmt(SourceLocation GotoLoc,
724 SourceLocation StarLoc,
725 ExprArg Target) {
726 return getSema().ActOnIndirectGotoStmt(GotoLoc, StarLoc, move(Target));
727 }
Mike Stump11289f42009-09-09 15:08:12 +0000728
Douglas Gregorebe10102009-08-20 07:17:43 +0000729 /// \brief Build a new return statement.
730 ///
731 /// By default, performs semantic analysis to build the new statement.
732 /// Subclasses may override this routine to provide different behavior.
733 OwningStmtResult RebuildReturnStmt(SourceLocation ReturnLoc,
734 ExprArg Result) {
Mike Stump11289f42009-09-09 15:08:12 +0000735
Douglas Gregorebe10102009-08-20 07:17:43 +0000736 return getSema().ActOnReturnStmt(ReturnLoc, move(Result));
737 }
Mike Stump11289f42009-09-09 15:08:12 +0000738
Douglas Gregorebe10102009-08-20 07:17:43 +0000739 /// \brief Build a new declaration statement.
740 ///
741 /// By default, performs semantic analysis to build the new statement.
742 /// Subclasses may override this routine to provide different behavior.
743 OwningStmtResult RebuildDeclStmt(Decl **Decls, unsigned NumDecls,
Mike Stump11289f42009-09-09 15:08:12 +0000744 SourceLocation StartLoc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000745 SourceLocation EndLoc) {
746 return getSema().Owned(
747 new (getSema().Context) DeclStmt(
748 DeclGroupRef::Create(getSema().Context,
749 Decls, NumDecls),
750 StartLoc, EndLoc));
751 }
Mike Stump11289f42009-09-09 15:08:12 +0000752
Douglas Gregorebe10102009-08-20 07:17:43 +0000753 /// \brief Build a new C++ exception declaration.
754 ///
755 /// By default, performs semantic analysis to build the new decaration.
756 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000757 VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl, QualType T,
Douglas Gregorebe10102009-08-20 07:17:43 +0000758 DeclaratorInfo *Declarator,
759 IdentifierInfo *Name,
760 SourceLocation Loc,
761 SourceRange TypeRange) {
Mike Stump11289f42009-09-09 15:08:12 +0000762 return getSema().BuildExceptionDeclaration(0, T, Declarator, Name, Loc,
Douglas Gregorebe10102009-08-20 07:17:43 +0000763 TypeRange);
764 }
765
766 /// \brief Build a new C++ catch statement.
767 ///
768 /// By default, performs semantic analysis to build the new statement.
769 /// Subclasses may override this routine to provide different behavior.
770 OwningStmtResult RebuildCXXCatchStmt(SourceLocation CatchLoc,
771 VarDecl *ExceptionDecl,
772 StmtArg Handler) {
773 return getSema().Owned(
Mike Stump11289f42009-09-09 15:08:12 +0000774 new (getSema().Context) CXXCatchStmt(CatchLoc, ExceptionDecl,
Douglas Gregorebe10102009-08-20 07:17:43 +0000775 Handler.takeAs<Stmt>()));
776 }
Mike Stump11289f42009-09-09 15:08:12 +0000777
Douglas Gregorebe10102009-08-20 07:17:43 +0000778 /// \brief Build a new C++ try statement.
779 ///
780 /// By default, performs semantic analysis to build the new statement.
781 /// Subclasses may override this routine to provide different behavior.
782 OwningStmtResult RebuildCXXTryStmt(SourceLocation TryLoc,
783 StmtArg TryBlock,
784 MultiStmtArg Handlers) {
785 return getSema().ActOnCXXTryBlock(TryLoc, move(TryBlock), move(Handlers));
786 }
Mike Stump11289f42009-09-09 15:08:12 +0000787
Douglas Gregora16548e2009-08-11 05:31:07 +0000788 /// \brief Build a new expression that references a declaration.
789 ///
790 /// By default, performs semantic analysis to build the new expression.
791 /// Subclasses may override this routine to provide different behavior.
792 OwningExprResult RebuildDeclRefExpr(NamedDecl *ND, SourceLocation Loc) {
793 return getSema().BuildDeclarationNameExpr(Loc, ND,
794 /*FIXME:*/false,
795 /*SS=*/0,
796 /*FIXME:*/false);
797 }
Mike Stump11289f42009-09-09 15:08:12 +0000798
Douglas Gregora16548e2009-08-11 05:31:07 +0000799 /// \brief Build a new expression in parentheses.
Mike Stump11289f42009-09-09 15:08:12 +0000800 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000801 /// By default, performs semantic analysis to build the new expression.
802 /// Subclasses may override this routine to provide different behavior.
803 OwningExprResult RebuildParenExpr(ExprArg SubExpr, SourceLocation LParen,
804 SourceLocation RParen) {
805 return getSema().ActOnParenExpr(LParen, RParen, move(SubExpr));
806 }
807
Douglas Gregorad8a3362009-09-04 17:36:40 +0000808 /// \brief Build a new pseudo-destructor expression.
Mike Stump11289f42009-09-09 15:08:12 +0000809 ///
Douglas Gregorad8a3362009-09-04 17:36:40 +0000810 /// By default, performs semantic analysis to build the new expression.
811 /// Subclasses may override this routine to provide different behavior.
812 OwningExprResult RebuildCXXPseudoDestructorExpr(ExprArg Base,
813 SourceLocation OperatorLoc,
814 bool isArrow,
815 SourceLocation DestroyedTypeLoc,
816 QualType DestroyedType,
817 NestedNameSpecifier *Qualifier,
818 SourceRange QualifierRange) {
819 CXXScopeSpec SS;
820 if (Qualifier) {
821 SS.setRange(QualifierRange);
822 SS.setScopeRep(Qualifier);
823 }
824
Mike Stump11289f42009-09-09 15:08:12 +0000825 DeclarationName Name
Douglas Gregorad8a3362009-09-04 17:36:40 +0000826 = SemaRef.Context.DeclarationNames.getCXXDestructorName(
827 SemaRef.Context.getCanonicalType(DestroyedType));
Mike Stump11289f42009-09-09 15:08:12 +0000828
829 return getSema().BuildMemberReferenceExpr(/*Scope=*/0, move(Base),
Douglas Gregorad8a3362009-09-04 17:36:40 +0000830 OperatorLoc,
831 isArrow? tok::arrow : tok::period,
832 DestroyedTypeLoc,
833 Name,
834 Sema::DeclPtrTy::make((Decl *)0),
835 &SS);
Mike Stump11289f42009-09-09 15:08:12 +0000836 }
837
Douglas Gregora16548e2009-08-11 05:31:07 +0000838 /// \brief Build a new unary operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000839 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000840 /// By default, performs semantic analysis to build the new expression.
841 /// Subclasses may override this routine to provide different behavior.
842 OwningExprResult RebuildUnaryOperator(SourceLocation OpLoc,
843 UnaryOperator::Opcode Opc,
844 ExprArg SubExpr) {
845 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(SubExpr));
846 }
Mike Stump11289f42009-09-09 15:08:12 +0000847
Douglas Gregora16548e2009-08-11 05:31:07 +0000848 /// \brief Build a new sizeof or alignof expression with a type argument.
Mike Stump11289f42009-09-09 15:08:12 +0000849 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000850 /// By default, performs semantic analysis to build the new expression.
851 /// Subclasses may override this routine to provide different behavior.
852 OwningExprResult RebuildSizeOfAlignOf(QualType T, SourceLocation OpLoc,
853 bool isSizeOf, SourceRange R) {
854 return getSema().CreateSizeOfAlignOfExpr(T, OpLoc, isSizeOf, R);
855 }
856
Mike Stump11289f42009-09-09 15:08:12 +0000857 /// \brief Build a new sizeof or alignof expression with an expression
Douglas Gregora16548e2009-08-11 05:31:07 +0000858 /// argument.
Mike Stump11289f42009-09-09 15:08:12 +0000859 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000860 /// By default, performs semantic analysis to build the new expression.
861 /// Subclasses may override this routine to provide different behavior.
862 OwningExprResult RebuildSizeOfAlignOf(ExprArg SubExpr, SourceLocation OpLoc,
863 bool isSizeOf, SourceRange R) {
Mike Stump11289f42009-09-09 15:08:12 +0000864 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +0000865 = getSema().CreateSizeOfAlignOfExpr((Expr *)SubExpr.get(),
866 OpLoc, isSizeOf, R);
867 if (Result.isInvalid())
868 return getSema().ExprError();
Mike Stump11289f42009-09-09 15:08:12 +0000869
Douglas Gregora16548e2009-08-11 05:31:07 +0000870 SubExpr.release();
871 return move(Result);
872 }
Mike Stump11289f42009-09-09 15:08:12 +0000873
Douglas Gregora16548e2009-08-11 05:31:07 +0000874 /// \brief Build a new array subscript expression.
Mike Stump11289f42009-09-09 15:08:12 +0000875 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000876 /// By default, performs semantic analysis to build the new expression.
877 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +0000878 OwningExprResult RebuildArraySubscriptExpr(ExprArg LHS,
Douglas Gregora16548e2009-08-11 05:31:07 +0000879 SourceLocation LBracketLoc,
880 ExprArg RHS,
881 SourceLocation RBracketLoc) {
882 return getSema().ActOnArraySubscriptExpr(/*Scope=*/0, move(LHS),
Mike Stump11289f42009-09-09 15:08:12 +0000883 LBracketLoc, move(RHS),
Douglas Gregora16548e2009-08-11 05:31:07 +0000884 RBracketLoc);
885 }
886
887 /// \brief Build a new call expression.
Mike Stump11289f42009-09-09 15:08:12 +0000888 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000889 /// By default, performs semantic analysis to build the new expression.
890 /// Subclasses may override this routine to provide different behavior.
891 OwningExprResult RebuildCallExpr(ExprArg Callee, SourceLocation LParenLoc,
892 MultiExprArg Args,
893 SourceLocation *CommaLocs,
894 SourceLocation RParenLoc) {
895 return getSema().ActOnCallExpr(/*Scope=*/0, move(Callee), LParenLoc,
896 move(Args), CommaLocs, RParenLoc);
897 }
898
899 /// \brief Build a new member access expression.
Mike Stump11289f42009-09-09 15:08:12 +0000900 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000901 /// By default, performs semantic analysis to build the new expression.
902 /// Subclasses may override this routine to provide different behavior.
903 OwningExprResult RebuildMemberExpr(ExprArg Base, SourceLocation OpLoc,
Mike Stump11289f42009-09-09 15:08:12 +0000904 bool isArrow,
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000905 NestedNameSpecifier *Qualifier,
906 SourceRange QualifierRange,
907 SourceLocation MemberLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +0000908 NamedDecl *Member) {
Anders Carlsson5da84842009-09-01 04:26:58 +0000909 if (!Member->getDeclName()) {
910 // We have a reference to an unnamed field.
911 assert(!Qualifier && "Can't have an unnamed field with a qualifier!");
Mike Stump11289f42009-09-09 15:08:12 +0000912
913 MemberExpr *ME =
Anders Carlsson5da84842009-09-01 04:26:58 +0000914 new (getSema().Context) MemberExpr(Base.takeAs<Expr>(), isArrow,
915 Member, MemberLoc,
916 cast<FieldDecl>(Member)->getType());
917 return getSema().Owned(ME);
918 }
Mike Stump11289f42009-09-09 15:08:12 +0000919
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000920 CXXScopeSpec SS;
921 if (Qualifier) {
922 SS.setRange(QualifierRange);
923 SS.setScopeRep(Qualifier);
924 }
925
Douglas Gregorf14b46f2009-08-31 20:00:26 +0000926 return getSema().BuildMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +0000927 isArrow? tok::arrow : tok::period,
928 MemberLoc,
Douglas Gregorf14b46f2009-08-31 20:00:26 +0000929 Member->getDeclName(),
Douglas Gregorf405d7e2009-08-31 23:41:50 +0000930 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
931 &SS);
Douglas Gregora16548e2009-08-11 05:31:07 +0000932 }
Mike Stump11289f42009-09-09 15:08:12 +0000933
Douglas Gregora16548e2009-08-11 05:31:07 +0000934 /// \brief Build a new binary operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000935 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000936 /// By default, performs semantic analysis to build the new expression.
937 /// Subclasses may override this routine to provide different behavior.
938 OwningExprResult RebuildBinaryOperator(SourceLocation OpLoc,
939 BinaryOperator::Opcode Opc,
940 ExprArg LHS, ExprArg RHS) {
941 OwningExprResult Result
Mike Stump11289f42009-09-09 15:08:12 +0000942 = getSema().CreateBuiltinBinOp(OpLoc, Opc, (Expr *)LHS.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +0000943 (Expr *)RHS.get());
944 if (Result.isInvalid())
945 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +0000946
Douglas Gregora16548e2009-08-11 05:31:07 +0000947 LHS.release();
948 RHS.release();
949 return move(Result);
950 }
951
952 /// \brief Build a new conditional operator expression.
Mike Stump11289f42009-09-09 15:08:12 +0000953 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000954 /// By default, performs semantic analysis to build the new expression.
955 /// Subclasses may override this routine to provide different behavior.
956 OwningExprResult RebuildConditionalOperator(ExprArg Cond,
957 SourceLocation QuestionLoc,
958 ExprArg LHS,
959 SourceLocation ColonLoc,
960 ExprArg RHS) {
Mike Stump11289f42009-09-09 15:08:12 +0000961 return getSema().ActOnConditionalOp(QuestionLoc, ColonLoc, move(Cond),
Douglas Gregora16548e2009-08-11 05:31:07 +0000962 move(LHS), move(RHS));
963 }
964
965 /// \brief Build a new implicit cast expression.
Mike Stump11289f42009-09-09 15:08:12 +0000966 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000967 /// By default, builds a new implicit cast without any semantic analysis.
968 /// Subclasses may override this routine to provide different behavior.
969 OwningExprResult RebuildImplicitCastExpr(QualType T, CastExpr::CastKind Kind,
970 ExprArg SubExpr, bool isLvalue) {
971 ImplicitCastExpr *ICE
Mike Stump11289f42009-09-09 15:08:12 +0000972 = new (getSema().Context) ImplicitCastExpr(T, Kind,
Douglas Gregora16548e2009-08-11 05:31:07 +0000973 (Expr *)SubExpr.release(),
974 isLvalue);
975 return getSema().Owned(ICE);
976 }
977
978 /// \brief Build a new C-style cast expression.
Mike Stump11289f42009-09-09 15:08:12 +0000979 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000980 /// By default, performs semantic analysis to build the new expression.
981 /// Subclasses may override this routine to provide different behavior.
982 OwningExprResult RebuildCStyleCaseExpr(SourceLocation LParenLoc,
983 QualType ExplicitTy,
984 SourceLocation RParenLoc,
985 ExprArg SubExpr) {
986 return getSema().ActOnCastExpr(/*Scope=*/0,
987 LParenLoc,
988 ExplicitTy.getAsOpaquePtr(),
989 RParenLoc,
990 move(SubExpr));
991 }
Mike Stump11289f42009-09-09 15:08:12 +0000992
Douglas Gregora16548e2009-08-11 05:31:07 +0000993 /// \brief Build a new compound literal expression.
Mike Stump11289f42009-09-09 15:08:12 +0000994 ///
Douglas Gregora16548e2009-08-11 05:31:07 +0000995 /// By default, performs semantic analysis to build the new expression.
996 /// Subclasses may override this routine to provide different behavior.
997 OwningExprResult RebuildCompoundLiteralExpr(SourceLocation LParenLoc,
998 QualType T,
999 SourceLocation RParenLoc,
1000 ExprArg Init) {
1001 return getSema().ActOnCompoundLiteral(LParenLoc, T.getAsOpaquePtr(),
1002 RParenLoc, move(Init));
1003 }
Mike Stump11289f42009-09-09 15:08:12 +00001004
Douglas Gregora16548e2009-08-11 05:31:07 +00001005 /// \brief Build a new extended vector element access expression.
Mike Stump11289f42009-09-09 15:08:12 +00001006 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001007 /// By default, performs semantic analysis to build the new expression.
1008 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001009 OwningExprResult RebuildExtVectorElementExpr(ExprArg Base,
Douglas Gregora16548e2009-08-11 05:31:07 +00001010 SourceLocation OpLoc,
1011 SourceLocation AccessorLoc,
1012 IdentifierInfo &Accessor) {
1013 return getSema().ActOnMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
1014 tok::period, AccessorLoc,
1015 Accessor,
1016 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0));
1017 }
Mike Stump11289f42009-09-09 15:08:12 +00001018
Douglas Gregora16548e2009-08-11 05:31:07 +00001019 /// \brief Build a new initializer list expression.
Mike Stump11289f42009-09-09 15:08:12 +00001020 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001021 /// By default, performs semantic analysis to build the new expression.
1022 /// Subclasses may override this routine to provide different behavior.
1023 OwningExprResult RebuildInitList(SourceLocation LBraceLoc,
1024 MultiExprArg Inits,
1025 SourceLocation RBraceLoc) {
1026 return SemaRef.ActOnInitList(LBraceLoc, move(Inits), RBraceLoc);
1027 }
Mike Stump11289f42009-09-09 15:08:12 +00001028
Douglas Gregora16548e2009-08-11 05:31:07 +00001029 /// \brief Build a new designated initializer expression.
Mike Stump11289f42009-09-09 15:08:12 +00001030 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001031 /// By default, performs semantic analysis to build the new expression.
1032 /// Subclasses may override this routine to provide different behavior.
1033 OwningExprResult RebuildDesignatedInitExpr(Designation &Desig,
1034 MultiExprArg ArrayExprs,
1035 SourceLocation EqualOrColonLoc,
1036 bool GNUSyntax,
1037 ExprArg Init) {
1038 OwningExprResult Result
1039 = SemaRef.ActOnDesignatedInitializer(Desig, EqualOrColonLoc, GNUSyntax,
1040 move(Init));
1041 if (Result.isInvalid())
1042 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001043
Douglas Gregora16548e2009-08-11 05:31:07 +00001044 ArrayExprs.release();
1045 return move(Result);
1046 }
Mike Stump11289f42009-09-09 15:08:12 +00001047
Douglas Gregora16548e2009-08-11 05:31:07 +00001048 /// \brief Build a new value-initialized expression.
Mike Stump11289f42009-09-09 15:08:12 +00001049 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001050 /// By default, builds the implicit value initialization without performing
1051 /// any semantic analysis. Subclasses may override this routine to provide
1052 /// different behavior.
1053 OwningExprResult RebuildImplicitValueInitExpr(QualType T) {
1054 return SemaRef.Owned(new (SemaRef.Context) ImplicitValueInitExpr(T));
1055 }
Mike Stump11289f42009-09-09 15:08:12 +00001056
Douglas Gregora16548e2009-08-11 05:31:07 +00001057 /// \brief Build a new \c va_arg expression.
Mike Stump11289f42009-09-09 15:08:12 +00001058 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001059 /// By default, performs semantic analysis to build the new expression.
1060 /// Subclasses may override this routine to provide different behavior.
1061 OwningExprResult RebuildVAArgExpr(SourceLocation BuiltinLoc, ExprArg SubExpr,
1062 QualType T, SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001063 return getSema().ActOnVAArg(BuiltinLoc, move(SubExpr), T.getAsOpaquePtr(),
Douglas Gregora16548e2009-08-11 05:31:07 +00001064 RParenLoc);
1065 }
1066
1067 /// \brief Build a new expression list in parentheses.
Mike Stump11289f42009-09-09 15:08:12 +00001068 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001069 /// By default, performs semantic analysis to build the new expression.
1070 /// Subclasses may override this routine to provide different behavior.
1071 OwningExprResult RebuildParenListExpr(SourceLocation LParenLoc,
1072 MultiExprArg SubExprs,
1073 SourceLocation RParenLoc) {
1074 return getSema().ActOnParenListExpr(LParenLoc, RParenLoc, move(SubExprs));
1075 }
Mike Stump11289f42009-09-09 15:08:12 +00001076
Douglas Gregora16548e2009-08-11 05:31:07 +00001077 /// \brief Build a new address-of-label expression.
Mike Stump11289f42009-09-09 15:08:12 +00001078 ///
1079 /// By default, performs semantic analysis, using the name of the label
Douglas Gregora16548e2009-08-11 05:31:07 +00001080 /// rather than attempting to map the label statement itself.
1081 /// Subclasses may override this routine to provide different behavior.
1082 OwningExprResult RebuildAddrLabelExpr(SourceLocation AmpAmpLoc,
1083 SourceLocation LabelLoc,
1084 LabelStmt *Label) {
1085 return getSema().ActOnAddrLabel(AmpAmpLoc, LabelLoc, Label->getID());
1086 }
Mike Stump11289f42009-09-09 15:08:12 +00001087
Douglas Gregora16548e2009-08-11 05:31:07 +00001088 /// \brief Build a new GNU statement expression.
Mike Stump11289f42009-09-09 15:08:12 +00001089 ///
Douglas Gregora16548e2009-08-11 05:31:07 +00001090 /// By default, performs semantic analysis to build the new expression.
1091 /// Subclasses may override this routine to provide different behavior.
1092 OwningExprResult RebuildStmtExpr(SourceLocation LParenLoc,
1093 StmtArg SubStmt,
1094 SourceLocation RParenLoc) {
1095 return getSema().ActOnStmtExpr(LParenLoc, move(SubStmt), RParenLoc);
1096 }
Mike Stump11289f42009-09-09 15:08:12 +00001097
Douglas Gregora16548e2009-08-11 05:31:07 +00001098 /// \brief Build a new __builtin_types_compatible_p expression.
1099 ///
1100 /// By default, performs semantic analysis to build the new expression.
1101 /// Subclasses may override this routine to provide different behavior.
1102 OwningExprResult RebuildTypesCompatibleExpr(SourceLocation BuiltinLoc,
1103 QualType T1, QualType T2,
1104 SourceLocation RParenLoc) {
1105 return getSema().ActOnTypesCompatibleExpr(BuiltinLoc,
1106 T1.getAsOpaquePtr(),
1107 T2.getAsOpaquePtr(),
1108 RParenLoc);
1109 }
Mike Stump11289f42009-09-09 15:08:12 +00001110
Douglas Gregora16548e2009-08-11 05:31:07 +00001111 /// \brief Build a new __builtin_choose_expr expression.
1112 ///
1113 /// By default, performs semantic analysis to build the new expression.
1114 /// Subclasses may override this routine to provide different behavior.
1115 OwningExprResult RebuildChooseExpr(SourceLocation BuiltinLoc,
1116 ExprArg Cond, ExprArg LHS, ExprArg RHS,
1117 SourceLocation RParenLoc) {
1118 return SemaRef.ActOnChooseExpr(BuiltinLoc,
1119 move(Cond), move(LHS), move(RHS),
1120 RParenLoc);
1121 }
Mike Stump11289f42009-09-09 15:08:12 +00001122
Douglas Gregora16548e2009-08-11 05:31:07 +00001123 /// \brief Build a new overloaded operator call expression.
1124 ///
1125 /// By default, performs semantic analysis to build the new expression.
1126 /// The semantic analysis provides the behavior of template instantiation,
1127 /// copying with transformations that turn what looks like an overloaded
Mike Stump11289f42009-09-09 15:08:12 +00001128 /// operator call into a use of a builtin operator, performing
Douglas Gregora16548e2009-08-11 05:31:07 +00001129 /// argument-dependent lookup, etc. Subclasses may override this routine to
1130 /// provide different behavior.
1131 OwningExprResult RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
1132 SourceLocation OpLoc,
1133 ExprArg Callee,
1134 ExprArg First,
1135 ExprArg Second);
Mike Stump11289f42009-09-09 15:08:12 +00001136
1137 /// \brief Build a new C++ "named" cast expression, such as static_cast or
Douglas Gregora16548e2009-08-11 05:31:07 +00001138 /// reinterpret_cast.
1139 ///
1140 /// By default, this routine dispatches to one of the more-specific routines
Mike Stump11289f42009-09-09 15:08:12 +00001141 /// for a particular named case, e.g., RebuildCXXStaticCastExpr().
Douglas Gregora16548e2009-08-11 05:31:07 +00001142 /// Subclasses may override this routine to provide different behavior.
1143 OwningExprResult RebuildCXXNamedCastExpr(SourceLocation OpLoc,
1144 Stmt::StmtClass Class,
1145 SourceLocation LAngleLoc,
1146 QualType T,
1147 SourceLocation RAngleLoc,
1148 SourceLocation LParenLoc,
1149 ExprArg SubExpr,
1150 SourceLocation RParenLoc) {
1151 switch (Class) {
1152 case Stmt::CXXStaticCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001153 return getDerived().RebuildCXXStaticCastExpr(OpLoc, LAngleLoc, T,
1154 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001155 move(SubExpr), RParenLoc);
1156
1157 case Stmt::CXXDynamicCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001158 return getDerived().RebuildCXXDynamicCastExpr(OpLoc, LAngleLoc, T,
1159 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001160 move(SubExpr), RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001161
Douglas Gregora16548e2009-08-11 05:31:07 +00001162 case Stmt::CXXReinterpretCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001163 return getDerived().RebuildCXXReinterpretCastExpr(OpLoc, LAngleLoc, T,
1164 RAngleLoc, LParenLoc,
1165 move(SubExpr),
Douglas Gregora16548e2009-08-11 05:31:07 +00001166 RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001167
Douglas Gregora16548e2009-08-11 05:31:07 +00001168 case Stmt::CXXConstCastExprClass:
Mike Stump11289f42009-09-09 15:08:12 +00001169 return getDerived().RebuildCXXConstCastExpr(OpLoc, LAngleLoc, T,
1170 RAngleLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001171 move(SubExpr), RParenLoc);
Mike Stump11289f42009-09-09 15:08:12 +00001172
Douglas Gregora16548e2009-08-11 05:31:07 +00001173 default:
1174 assert(false && "Invalid C++ named cast");
1175 break;
1176 }
Mike Stump11289f42009-09-09 15:08:12 +00001177
Douglas Gregora16548e2009-08-11 05:31:07 +00001178 return getSema().ExprError();
1179 }
Mike Stump11289f42009-09-09 15:08:12 +00001180
Douglas Gregora16548e2009-08-11 05:31:07 +00001181 /// \brief Build a new C++ static_cast expression.
1182 ///
1183 /// By default, performs semantic analysis to build the new expression.
1184 /// Subclasses may override this routine to provide different behavior.
1185 OwningExprResult RebuildCXXStaticCastExpr(SourceLocation OpLoc,
1186 SourceLocation LAngleLoc,
1187 QualType T,
1188 SourceLocation RAngleLoc,
1189 SourceLocation LParenLoc,
1190 ExprArg SubExpr,
1191 SourceLocation RParenLoc) {
1192 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_static_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001193 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001194 LParenLoc, move(SubExpr), RParenLoc);
1195 }
1196
1197 /// \brief Build a new C++ dynamic_cast expression.
1198 ///
1199 /// By default, performs semantic analysis to build the new expression.
1200 /// Subclasses may override this routine to provide different behavior.
1201 OwningExprResult RebuildCXXDynamicCastExpr(SourceLocation OpLoc,
1202 SourceLocation LAngleLoc,
1203 QualType T,
1204 SourceLocation RAngleLoc,
1205 SourceLocation LParenLoc,
1206 ExprArg SubExpr,
1207 SourceLocation RParenLoc) {
1208 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_dynamic_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001209 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001210 LParenLoc, move(SubExpr), RParenLoc);
1211 }
1212
1213 /// \brief Build a new C++ reinterpret_cast expression.
1214 ///
1215 /// By default, performs semantic analysis to build the new expression.
1216 /// Subclasses may override this routine to provide different behavior.
1217 OwningExprResult RebuildCXXReinterpretCastExpr(SourceLocation OpLoc,
1218 SourceLocation LAngleLoc,
1219 QualType T,
1220 SourceLocation RAngleLoc,
1221 SourceLocation LParenLoc,
1222 ExprArg SubExpr,
1223 SourceLocation RParenLoc) {
1224 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_reinterpret_cast,
1225 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1226 LParenLoc, move(SubExpr), RParenLoc);
1227 }
1228
1229 /// \brief Build a new C++ const_cast expression.
1230 ///
1231 /// By default, performs semantic analysis to build the new expression.
1232 /// Subclasses may override this routine to provide different behavior.
1233 OwningExprResult RebuildCXXConstCastExpr(SourceLocation OpLoc,
1234 SourceLocation LAngleLoc,
1235 QualType T,
1236 SourceLocation RAngleLoc,
1237 SourceLocation LParenLoc,
1238 ExprArg SubExpr,
1239 SourceLocation RParenLoc) {
1240 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_const_cast,
Mike Stump11289f42009-09-09 15:08:12 +00001241 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001242 LParenLoc, move(SubExpr), RParenLoc);
1243 }
Mike Stump11289f42009-09-09 15:08:12 +00001244
Douglas Gregora16548e2009-08-11 05:31:07 +00001245 /// \brief Build a new C++ functional-style cast expression.
1246 ///
1247 /// By default, performs semantic analysis to build the new expression.
1248 /// Subclasses may override this routine to provide different behavior.
1249 OwningExprResult RebuildCXXFunctionalCastExpr(SourceRange TypeRange,
1250 QualType T,
1251 SourceLocation LParenLoc,
1252 ExprArg SubExpr,
1253 SourceLocation RParenLoc) {
Chris Lattnerdca19592009-08-24 05:19:01 +00001254 void *Sub = SubExpr.takeAs<Expr>();
Douglas Gregora16548e2009-08-11 05:31:07 +00001255 return getSema().ActOnCXXTypeConstructExpr(TypeRange,
1256 T.getAsOpaquePtr(),
1257 LParenLoc,
Chris Lattnerdca19592009-08-24 05:19:01 +00001258 Sema::MultiExprArg(getSema(), &Sub, 1),
Mike Stump11289f42009-09-09 15:08:12 +00001259 /*CommaLocs=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001260 RParenLoc);
1261 }
Mike Stump11289f42009-09-09 15:08:12 +00001262
Douglas Gregora16548e2009-08-11 05:31:07 +00001263 /// \brief Build a new C++ typeid(type) expression.
1264 ///
1265 /// By default, performs semantic analysis to build the new expression.
1266 /// Subclasses may override this routine to provide different behavior.
1267 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1268 SourceLocation LParenLoc,
1269 QualType T,
1270 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001271 return getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, true,
Douglas Gregora16548e2009-08-11 05:31:07 +00001272 T.getAsOpaquePtr(), RParenLoc);
1273 }
Mike Stump11289f42009-09-09 15:08:12 +00001274
Douglas Gregora16548e2009-08-11 05:31:07 +00001275 /// \brief Build a new C++ typeid(expr) expression.
1276 ///
1277 /// By default, performs semantic analysis to build the new expression.
1278 /// Subclasses may override this routine to provide different behavior.
1279 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1280 SourceLocation LParenLoc,
1281 ExprArg Operand,
1282 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001283 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00001284 = getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, false, Operand.get(),
1285 RParenLoc);
1286 if (Result.isInvalid())
1287 return getSema().ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001288
Douglas Gregora16548e2009-08-11 05:31:07 +00001289 Operand.release(); // FIXME: since ActOnCXXTypeid silently took ownership
1290 return move(Result);
Mike Stump11289f42009-09-09 15:08:12 +00001291 }
1292
Douglas Gregora16548e2009-08-11 05:31:07 +00001293 /// \brief Build a new C++ "this" expression.
1294 ///
1295 /// By default, builds a new "this" expression without performing any
Mike Stump11289f42009-09-09 15:08:12 +00001296 /// semantic analysis. Subclasses may override this routine to provide
Douglas Gregora16548e2009-08-11 05:31:07 +00001297 /// different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001298 OwningExprResult RebuildCXXThisExpr(SourceLocation ThisLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001299 QualType ThisType) {
1300 return getSema().Owned(
1301 new (getSema().Context) CXXThisExpr(ThisLoc, ThisType));
1302 }
1303
1304 /// \brief Build a new C++ throw expression.
1305 ///
1306 /// By default, performs semantic analysis to build the new expression.
1307 /// Subclasses may override this routine to provide different behavior.
1308 OwningExprResult RebuildCXXThrowExpr(SourceLocation ThrowLoc, ExprArg Sub) {
1309 return getSema().ActOnCXXThrow(ThrowLoc, move(Sub));
1310 }
1311
1312 /// \brief Build a new C++ default-argument expression.
1313 ///
1314 /// By default, builds a new default-argument expression, which does not
1315 /// require any semantic analysis. Subclasses may override this routine to
1316 /// provide different behavior.
1317 OwningExprResult RebuildCXXDefaultArgExpr(ParmVarDecl *Param) {
Anders Carlssone8271232009-08-14 18:30:22 +00001318 return getSema().Owned(CXXDefaultArgExpr::Create(getSema().Context, Param));
Douglas Gregora16548e2009-08-11 05:31:07 +00001319 }
1320
1321 /// \brief Build a new C++ zero-initialization expression.
1322 ///
1323 /// By default, performs semantic analysis to build the new expression.
1324 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001325 OwningExprResult RebuildCXXZeroInitValueExpr(SourceLocation TypeStartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001326 SourceLocation LParenLoc,
1327 QualType T,
1328 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001329 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeStartLoc),
1330 T.getAsOpaquePtr(), LParenLoc,
1331 MultiExprArg(getSema(), 0, 0),
Douglas Gregora16548e2009-08-11 05:31:07 +00001332 0, RParenLoc);
1333 }
Mike Stump11289f42009-09-09 15:08:12 +00001334
Douglas Gregora16548e2009-08-11 05:31:07 +00001335 /// \brief Build a new C++ conditional declaration expression.
1336 ///
1337 /// By default, performs semantic analysis to build the new expression.
1338 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001339 OwningExprResult RebuildCXXConditionDeclExpr(SourceLocation StartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001340 SourceLocation EqLoc,
1341 VarDecl *Var) {
1342 return SemaRef.Owned(new (SemaRef.Context) CXXConditionDeclExpr(StartLoc,
1343 EqLoc,
1344 Var));
1345 }
Mike Stump11289f42009-09-09 15:08:12 +00001346
Douglas Gregora16548e2009-08-11 05:31:07 +00001347 /// \brief Build a new C++ "new" expression.
1348 ///
1349 /// By default, performs semantic analysis to build the new expression.
1350 /// Subclasses may override this routine to provide different behavior.
Mike Stump11289f42009-09-09 15:08:12 +00001351 OwningExprResult RebuildCXXNewExpr(SourceLocation StartLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001352 bool UseGlobal,
1353 SourceLocation PlacementLParen,
1354 MultiExprArg PlacementArgs,
1355 SourceLocation PlacementRParen,
Mike Stump11289f42009-09-09 15:08:12 +00001356 bool ParenTypeId,
Douglas Gregora16548e2009-08-11 05:31:07 +00001357 QualType AllocType,
1358 SourceLocation TypeLoc,
1359 SourceRange TypeRange,
1360 ExprArg ArraySize,
1361 SourceLocation ConstructorLParen,
1362 MultiExprArg ConstructorArgs,
1363 SourceLocation ConstructorRParen) {
Mike Stump11289f42009-09-09 15:08:12 +00001364 return getSema().BuildCXXNew(StartLoc, UseGlobal,
Douglas Gregora16548e2009-08-11 05:31:07 +00001365 PlacementLParen,
1366 move(PlacementArgs),
1367 PlacementRParen,
1368 ParenTypeId,
1369 AllocType,
1370 TypeLoc,
1371 TypeRange,
1372 move(ArraySize),
1373 ConstructorLParen,
1374 move(ConstructorArgs),
1375 ConstructorRParen);
1376 }
Mike Stump11289f42009-09-09 15:08:12 +00001377
Douglas Gregora16548e2009-08-11 05:31:07 +00001378 /// \brief Build a new C++ "delete" expression.
1379 ///
1380 /// By default, performs semantic analysis to build the new expression.
1381 /// Subclasses may override this routine to provide different behavior.
1382 OwningExprResult RebuildCXXDeleteExpr(SourceLocation StartLoc,
1383 bool IsGlobalDelete,
1384 bool IsArrayForm,
1385 ExprArg Operand) {
1386 return getSema().ActOnCXXDelete(StartLoc, IsGlobalDelete, IsArrayForm,
1387 move(Operand));
1388 }
Mike Stump11289f42009-09-09 15:08:12 +00001389
Douglas Gregora16548e2009-08-11 05:31:07 +00001390 /// \brief Build a new unary type trait expression.
1391 ///
1392 /// By default, performs semantic analysis to build the new expression.
1393 /// Subclasses may override this routine to provide different behavior.
1394 OwningExprResult RebuildUnaryTypeTrait(UnaryTypeTrait Trait,
1395 SourceLocation StartLoc,
1396 SourceLocation LParenLoc,
1397 QualType T,
1398 SourceLocation RParenLoc) {
Mike Stump11289f42009-09-09 15:08:12 +00001399 return getSema().ActOnUnaryTypeTrait(Trait, StartLoc, LParenLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001400 T.getAsOpaquePtr(), RParenLoc);
1401 }
1402
1403 /// \brief Build a new qualified declaration reference expression.
1404 ///
1405 /// By default, performs semantic analysis to build the new expression.
1406 /// Subclasses may override this routine to provide different behavior.
1407 OwningExprResult RebuildQualifiedDeclRefExpr(NestedNameSpecifier *NNS,
1408 SourceRange QualifierRange,
1409 NamedDecl *ND,
1410 SourceLocation Location,
1411 bool IsAddressOfOperand) {
1412 CXXScopeSpec SS;
1413 SS.setRange(QualifierRange);
1414 SS.setScopeRep(NNS);
Mike Stump11289f42009-09-09 15:08:12 +00001415 return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001416 Location,
1417 ND->getDeclName(),
1418 /*Trailing lparen=*/false,
1419 &SS,
1420 IsAddressOfOperand);
1421 }
1422
Mike Stump11289f42009-09-09 15:08:12 +00001423 /// \brief Build a new (previously unresolved) declaration reference
Douglas Gregora16548e2009-08-11 05:31:07 +00001424 /// expression.
1425 ///
1426 /// By default, performs semantic analysis to build the new expression.
1427 /// Subclasses may override this routine to provide different behavior.
1428 OwningExprResult RebuildUnresolvedDeclRefExpr(NestedNameSpecifier *NNS,
1429 SourceRange QualifierRange,
1430 DeclarationName Name,
1431 SourceLocation Location,
1432 bool IsAddressOfOperand) {
1433 CXXScopeSpec SS;
1434 SS.setRange(QualifierRange);
1435 SS.setScopeRep(NNS);
Mike Stump11289f42009-09-09 15:08:12 +00001436 return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001437 Location,
1438 Name,
1439 /*Trailing lparen=*/false,
1440 &SS,
1441 IsAddressOfOperand);
1442 }
1443
1444 /// \brief Build a new template-id expression.
1445 ///
1446 /// By default, performs semantic analysis to build the new expression.
1447 /// Subclasses may override this routine to provide different behavior.
Douglas Gregord019ff62009-10-22 17:20:55 +00001448 OwningExprResult RebuildTemplateIdExpr(NestedNameSpecifier *Qualifier,
1449 SourceRange QualifierRange,
1450 TemplateName Template,
Douglas Gregora16548e2009-08-11 05:31:07 +00001451 SourceLocation TemplateLoc,
1452 SourceLocation LAngleLoc,
1453 TemplateArgument *TemplateArgs,
1454 unsigned NumTemplateArgs,
1455 SourceLocation RAngleLoc) {
Douglas Gregord019ff62009-10-22 17:20:55 +00001456 return getSema().BuildTemplateIdExpr(Qualifier, QualifierRange,
1457 Template, TemplateLoc,
Douglas Gregora16548e2009-08-11 05:31:07 +00001458 LAngleLoc,
1459 TemplateArgs, NumTemplateArgs,
1460 RAngleLoc);
1461 }
1462
1463 /// \brief Build a new object-construction expression.
1464 ///
1465 /// By default, performs semantic analysis to build the new expression.
1466 /// Subclasses may override this routine to provide different behavior.
1467 OwningExprResult RebuildCXXConstructExpr(QualType T,
1468 CXXConstructorDecl *Constructor,
1469 bool IsElidable,
1470 MultiExprArg Args) {
Anders Carlsson1b4ebfa2009-09-05 07:40:38 +00001471 return getSema().BuildCXXConstructExpr(/*FIXME:ConstructLoc*/
1472 SourceLocation(),
1473 T, Constructor, IsElidable,
Anders Carlsson5995a3e2009-09-07 22:23:31 +00001474 move(Args));
Douglas Gregora16548e2009-08-11 05:31:07 +00001475 }
1476
1477 /// \brief Build a new object-construction expression.
1478 ///
1479 /// By default, performs semantic analysis to build the new expression.
1480 /// Subclasses may override this routine to provide different behavior.
1481 OwningExprResult RebuildCXXTemporaryObjectExpr(SourceLocation TypeBeginLoc,
1482 QualType T,
1483 SourceLocation LParenLoc,
1484 MultiExprArg Args,
1485 SourceLocation *Commas,
1486 SourceLocation RParenLoc) {
1487 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc),
1488 T.getAsOpaquePtr(),
1489 LParenLoc,
1490 move(Args),
1491 Commas,
1492 RParenLoc);
1493 }
1494
1495 /// \brief Build a new object-construction expression.
1496 ///
1497 /// By default, performs semantic analysis to build the new expression.
1498 /// Subclasses may override this routine to provide different behavior.
1499 OwningExprResult RebuildCXXUnresolvedConstructExpr(SourceLocation TypeBeginLoc,
1500 QualType T,
1501 SourceLocation LParenLoc,
1502 MultiExprArg Args,
1503 SourceLocation *Commas,
1504 SourceLocation RParenLoc) {
1505 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc,
1506 /*FIXME*/LParenLoc),
1507 T.getAsOpaquePtr(),
1508 LParenLoc,
1509 move(Args),
1510 Commas,
1511 RParenLoc);
1512 }
Mike Stump11289f42009-09-09 15:08:12 +00001513
Douglas Gregora16548e2009-08-11 05:31:07 +00001514 /// \brief Build a new member reference expression.
1515 ///
1516 /// By default, performs semantic analysis to build the new expression.
1517 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor2168a9f2009-08-11 15:56:57 +00001518 OwningExprResult RebuildCXXUnresolvedMemberExpr(ExprArg BaseE,
Douglas Gregora16548e2009-08-11 05:31:07 +00001519 bool IsArrow,
1520 SourceLocation OperatorLoc,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001521 NestedNameSpecifier *Qualifier,
1522 SourceRange QualifierRange,
Douglas Gregora16548e2009-08-11 05:31:07 +00001523 DeclarationName Name,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001524 SourceLocation MemberLoc,
1525 NamedDecl *FirstQualifierInScope) {
Douglas Gregor2168a9f2009-08-11 15:56:57 +00001526 OwningExprResult Base = move(BaseE);
Douglas Gregora16548e2009-08-11 05:31:07 +00001527 tok::TokenKind OpKind = IsArrow? tok::arrow : tok::period;
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001528
Douglas Gregora16548e2009-08-11 05:31:07 +00001529 CXXScopeSpec SS;
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001530 SS.setRange(QualifierRange);
1531 SS.setScopeRep(Qualifier);
Mike Stump11289f42009-09-09 15:08:12 +00001532
Douglas Gregor308047d2009-09-09 00:23:06 +00001533 return SemaRef.BuildMemberReferenceExpr(/*Scope=*/0,
Douglas Gregora16548e2009-08-11 05:31:07 +00001534 move(Base), OperatorLoc, OpKind,
Douglas Gregorf14b46f2009-08-31 20:00:26 +00001535 MemberLoc,
1536 Name,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001537 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001538 &SS,
1539 FirstQualifierInScope);
Douglas Gregora16548e2009-08-11 05:31:07 +00001540 }
1541
Douglas Gregor308047d2009-09-09 00:23:06 +00001542 /// \brief Build a new member reference expression with explicit template
1543 /// arguments.
1544 ///
1545 /// By default, performs semantic analysis to build the new expression.
1546 /// Subclasses may override this routine to provide different behavior.
1547 OwningExprResult RebuildCXXUnresolvedMemberExpr(ExprArg BaseE,
1548 bool IsArrow,
1549 SourceLocation OperatorLoc,
1550 NestedNameSpecifier *Qualifier,
1551 SourceRange QualifierRange,
1552 TemplateName Template,
1553 SourceLocation TemplateNameLoc,
1554 NamedDecl *FirstQualifierInScope,
1555 SourceLocation LAngleLoc,
1556 const TemplateArgument *TemplateArgs,
1557 unsigned NumTemplateArgs,
1558 SourceLocation RAngleLoc) {
1559 OwningExprResult Base = move(BaseE);
1560 tok::TokenKind OpKind = IsArrow? tok::arrow : tok::period;
Mike Stump11289f42009-09-09 15:08:12 +00001561
Douglas Gregor308047d2009-09-09 00:23:06 +00001562 CXXScopeSpec SS;
1563 SS.setRange(QualifierRange);
1564 SS.setScopeRep(Qualifier);
Mike Stump11289f42009-09-09 15:08:12 +00001565
Douglas Gregor308047d2009-09-09 00:23:06 +00001566 // FIXME: We're going to end up looking up the template based on its name,
1567 // twice! Also, duplicates part of Sema::ActOnMemberTemplateIdReferenceExpr.
1568 DeclarationName Name;
1569 if (TemplateDecl *ActualTemplate = Template.getAsTemplateDecl())
1570 Name = ActualTemplate->getDeclName();
Mike Stump11289f42009-09-09 15:08:12 +00001571 else if (OverloadedFunctionDecl *Ovl
Douglas Gregor308047d2009-09-09 00:23:06 +00001572 = Template.getAsOverloadedFunctionDecl())
1573 Name = Ovl->getDeclName();
1574 else
1575 Name = Template.getAsDependentTemplateName()->getName();
Mike Stump11289f42009-09-09 15:08:12 +00001576
1577 return SemaRef.BuildMemberReferenceExpr(/*Scope=*/0, move(Base),
Douglas Gregor308047d2009-09-09 00:23:06 +00001578 OperatorLoc, OpKind,
1579 TemplateNameLoc, Name, true,
1580 LAngleLoc, TemplateArgs,
1581 NumTemplateArgs, RAngleLoc,
1582 Sema::DeclPtrTy(), &SS);
1583 }
Mike Stump11289f42009-09-09 15:08:12 +00001584
Douglas Gregora16548e2009-08-11 05:31:07 +00001585 /// \brief Build a new Objective-C @encode expression.
1586 ///
1587 /// By default, performs semantic analysis to build the new expression.
1588 /// Subclasses may override this routine to provide different behavior.
1589 OwningExprResult RebuildObjCEncodeExpr(SourceLocation AtLoc,
1590 QualType T,
1591 SourceLocation RParenLoc) {
1592 return SemaRef.Owned(SemaRef.BuildObjCEncodeExpression(AtLoc, T,
1593 RParenLoc));
Mike Stump11289f42009-09-09 15:08:12 +00001594 }
Douglas Gregora16548e2009-08-11 05:31:07 +00001595
1596 /// \brief Build a new Objective-C protocol expression.
1597 ///
1598 /// By default, performs semantic analysis to build the new expression.
1599 /// Subclasses may override this routine to provide different behavior.
1600 OwningExprResult RebuildObjCProtocolExpr(ObjCProtocolDecl *Protocol,
1601 SourceLocation AtLoc,
1602 SourceLocation ProtoLoc,
1603 SourceLocation LParenLoc,
1604 SourceLocation RParenLoc) {
1605 return SemaRef.Owned(SemaRef.ParseObjCProtocolExpression(
1606 Protocol->getIdentifier(),
1607 AtLoc,
1608 ProtoLoc,
1609 LParenLoc,
Mike Stump11289f42009-09-09 15:08:12 +00001610 RParenLoc));
Douglas Gregora16548e2009-08-11 05:31:07 +00001611 }
Mike Stump11289f42009-09-09 15:08:12 +00001612
Douglas Gregora16548e2009-08-11 05:31:07 +00001613 /// \brief Build a new shuffle vector expression.
1614 ///
1615 /// By default, performs semantic analysis to build the new expression.
1616 /// Subclasses may override this routine to provide different behavior.
1617 OwningExprResult RebuildShuffleVectorExpr(SourceLocation BuiltinLoc,
1618 MultiExprArg SubExprs,
1619 SourceLocation RParenLoc) {
1620 // Find the declaration for __builtin_shufflevector
Mike Stump11289f42009-09-09 15:08:12 +00001621 const IdentifierInfo &Name
Douglas Gregora16548e2009-08-11 05:31:07 +00001622 = SemaRef.Context.Idents.get("__builtin_shufflevector");
1623 TranslationUnitDecl *TUDecl = SemaRef.Context.getTranslationUnitDecl();
1624 DeclContext::lookup_result Lookup = TUDecl->lookup(DeclarationName(&Name));
1625 assert(Lookup.first != Lookup.second && "No __builtin_shufflevector?");
Mike Stump11289f42009-09-09 15:08:12 +00001626
Douglas Gregora16548e2009-08-11 05:31:07 +00001627 // Build a reference to the __builtin_shufflevector builtin
1628 FunctionDecl *Builtin = cast<FunctionDecl>(*Lookup.first);
Mike Stump11289f42009-09-09 15:08:12 +00001629 Expr *Callee
Douglas Gregora16548e2009-08-11 05:31:07 +00001630 = new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(),
1631 BuiltinLoc, false, false);
1632 SemaRef.UsualUnaryConversions(Callee);
Mike Stump11289f42009-09-09 15:08:12 +00001633
1634 // Build the CallExpr
Douglas Gregora16548e2009-08-11 05:31:07 +00001635 unsigned NumSubExprs = SubExprs.size();
1636 Expr **Subs = (Expr **)SubExprs.release();
1637 CallExpr *TheCall = new (SemaRef.Context) CallExpr(SemaRef.Context, Callee,
1638 Subs, NumSubExprs,
1639 Builtin->getResultType(),
1640 RParenLoc);
1641 OwningExprResult OwnedCall(SemaRef.Owned(TheCall));
Mike Stump11289f42009-09-09 15:08:12 +00001642
Douglas Gregora16548e2009-08-11 05:31:07 +00001643 // Type-check the __builtin_shufflevector expression.
1644 OwningExprResult Result = SemaRef.SemaBuiltinShuffleVector(TheCall);
1645 if (Result.isInvalid())
1646 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00001647
Douglas Gregora16548e2009-08-11 05:31:07 +00001648 OwnedCall.release();
Mike Stump11289f42009-09-09 15:08:12 +00001649 return move(Result);
Douglas Gregora16548e2009-08-11 05:31:07 +00001650 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00001651};
Douglas Gregora16548e2009-08-11 05:31:07 +00001652
Douglas Gregorebe10102009-08-20 07:17:43 +00001653template<typename Derived>
1654Sema::OwningStmtResult TreeTransform<Derived>::TransformStmt(Stmt *S) {
1655 if (!S)
1656 return SemaRef.Owned(S);
Mike Stump11289f42009-09-09 15:08:12 +00001657
Douglas Gregorebe10102009-08-20 07:17:43 +00001658 switch (S->getStmtClass()) {
1659 case Stmt::NoStmtClass: break;
Mike Stump11289f42009-09-09 15:08:12 +00001660
Douglas Gregorebe10102009-08-20 07:17:43 +00001661 // Transform individual statement nodes
1662#define STMT(Node, Parent) \
1663 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S));
1664#define EXPR(Node, Parent)
1665#include "clang/AST/StmtNodes.def"
Mike Stump11289f42009-09-09 15:08:12 +00001666
Douglas Gregorebe10102009-08-20 07:17:43 +00001667 // Transform expressions by calling TransformExpr.
1668#define STMT(Node, Parent)
1669#define EXPR(Node, Parent) case Stmt::Node##Class:
1670#include "clang/AST/StmtNodes.def"
1671 {
1672 Sema::OwningExprResult E = getDerived().TransformExpr(cast<Expr>(S));
1673 if (E.isInvalid())
1674 return getSema().StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00001675
Douglas Gregorebe10102009-08-20 07:17:43 +00001676 return getSema().Owned(E.takeAs<Stmt>());
1677 }
Mike Stump11289f42009-09-09 15:08:12 +00001678 }
1679
Douglas Gregorebe10102009-08-20 07:17:43 +00001680 return SemaRef.Owned(S->Retain());
1681}
Mike Stump11289f42009-09-09 15:08:12 +00001682
1683
Douglas Gregore922c772009-08-04 22:27:00 +00001684template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00001685Sema::OwningExprResult TreeTransform<Derived>::TransformExpr(Expr *E,
1686 bool isAddressOfOperand) {
1687 if (!E)
1688 return SemaRef.Owned(E);
1689
1690 switch (E->getStmtClass()) {
1691 case Stmt::NoStmtClass: break;
1692#define STMT(Node, Parent) case Stmt::Node##Class: break;
1693#define EXPR(Node, Parent) \
1694 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E));
1695#include "clang/AST/StmtNodes.def"
Mike Stump11289f42009-09-09 15:08:12 +00001696 }
1697
Douglas Gregora16548e2009-08-11 05:31:07 +00001698 return SemaRef.Owned(E->Retain());
Douglas Gregor766b0bb2009-08-06 22:17:10 +00001699}
1700
1701template<typename Derived>
Douglas Gregor1135c352009-08-06 05:28:30 +00001702NestedNameSpecifier *
1703TreeTransform<Derived>::TransformNestedNameSpecifier(NestedNameSpecifier *NNS,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001704 SourceRange Range,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001705 QualType ObjectType,
1706 NamedDecl *FirstQualifierInScope) {
Douglas Gregor96ee7892009-08-31 21:41:48 +00001707 if (!NNS)
1708 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001709
Douglas Gregorebe10102009-08-20 07:17:43 +00001710 // Transform the prefix of this nested name specifier.
Douglas Gregor1135c352009-08-06 05:28:30 +00001711 NestedNameSpecifier *Prefix = NNS->getPrefix();
1712 if (Prefix) {
Mike Stump11289f42009-09-09 15:08:12 +00001713 Prefix = getDerived().TransformNestedNameSpecifier(Prefix, Range,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001714 ObjectType,
1715 FirstQualifierInScope);
Douglas Gregor1135c352009-08-06 05:28:30 +00001716 if (!Prefix)
1717 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001718
1719 // Clear out the object type and the first qualifier in scope; they only
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001720 // apply to the first element in the nested-name-specifier.
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001721 ObjectType = QualType();
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001722 FirstQualifierInScope = 0;
Douglas Gregor1135c352009-08-06 05:28:30 +00001723 }
Mike Stump11289f42009-09-09 15:08:12 +00001724
Douglas Gregor1135c352009-08-06 05:28:30 +00001725 switch (NNS->getKind()) {
1726 case NestedNameSpecifier::Identifier:
Mike Stump11289f42009-09-09 15:08:12 +00001727 assert((Prefix || !ObjectType.isNull()) &&
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001728 "Identifier nested-name-specifier with no prefix or object type");
1729 if (!getDerived().AlwaysRebuild() && Prefix == NNS->getPrefix() &&
1730 ObjectType.isNull())
Douglas Gregor1135c352009-08-06 05:28:30 +00001731 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001732
1733 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00001734 *NNS->getAsIdentifier(),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00001735 ObjectType,
1736 FirstQualifierInScope);
Mike Stump11289f42009-09-09 15:08:12 +00001737
Douglas Gregor1135c352009-08-06 05:28:30 +00001738 case NestedNameSpecifier::Namespace: {
Mike Stump11289f42009-09-09 15:08:12 +00001739 NamespaceDecl *NS
Douglas Gregor1135c352009-08-06 05:28:30 +00001740 = cast_or_null<NamespaceDecl>(
1741 getDerived().TransformDecl(NNS->getAsNamespace()));
Mike Stump11289f42009-09-09 15:08:12 +00001742 if (!getDerived().AlwaysRebuild() &&
Douglas Gregor1135c352009-08-06 05:28:30 +00001743 Prefix == NNS->getPrefix() &&
1744 NS == NNS->getAsNamespace())
1745 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001746
Douglas Gregor1135c352009-08-06 05:28:30 +00001747 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, NS);
1748 }
Mike Stump11289f42009-09-09 15:08:12 +00001749
Douglas Gregor1135c352009-08-06 05:28:30 +00001750 case NestedNameSpecifier::Global:
1751 // There is no meaningful transformation that one could perform on the
1752 // global scope.
1753 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001754
Douglas Gregor1135c352009-08-06 05:28:30 +00001755 case NestedNameSpecifier::TypeSpecWithTemplate:
1756 case NestedNameSpecifier::TypeSpec: {
1757 QualType T = getDerived().TransformType(QualType(NNS->getAsType(), 0));
Douglas Gregor71dc5092009-08-06 06:41:21 +00001758 if (T.isNull())
1759 return 0;
Mike Stump11289f42009-09-09 15:08:12 +00001760
Douglas Gregor1135c352009-08-06 05:28:30 +00001761 if (!getDerived().AlwaysRebuild() &&
1762 Prefix == NNS->getPrefix() &&
1763 T == QualType(NNS->getAsType(), 0))
1764 return NNS;
Mike Stump11289f42009-09-09 15:08:12 +00001765
1766 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
1767 NNS->getKind() == NestedNameSpecifier::TypeSpecWithTemplate,
Douglas Gregor1135c352009-08-06 05:28:30 +00001768 T);
1769 }
1770 }
Mike Stump11289f42009-09-09 15:08:12 +00001771
Douglas Gregor1135c352009-08-06 05:28:30 +00001772 // Required to silence a GCC warning
Mike Stump11289f42009-09-09 15:08:12 +00001773 return 0;
Douglas Gregor1135c352009-08-06 05:28:30 +00001774}
1775
1776template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001777DeclarationName
Douglas Gregorf816bd72009-09-03 22:13:48 +00001778TreeTransform<Derived>::TransformDeclarationName(DeclarationName Name,
Douglas Gregorc59e5612009-10-19 22:04:39 +00001779 SourceLocation Loc,
1780 QualType ObjectType) {
Douglas Gregorf816bd72009-09-03 22:13:48 +00001781 if (!Name)
1782 return Name;
1783
1784 switch (Name.getNameKind()) {
1785 case DeclarationName::Identifier:
1786 case DeclarationName::ObjCZeroArgSelector:
1787 case DeclarationName::ObjCOneArgSelector:
1788 case DeclarationName::ObjCMultiArgSelector:
1789 case DeclarationName::CXXOperatorName:
1790 case DeclarationName::CXXUsingDirective:
1791 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001792
Douglas Gregorf816bd72009-09-03 22:13:48 +00001793 case DeclarationName::CXXConstructorName:
1794 case DeclarationName::CXXDestructorName:
1795 case DeclarationName::CXXConversionFunctionName: {
1796 TemporaryBase Rebase(*this, Loc, Name);
Douglas Gregorc59e5612009-10-19 22:04:39 +00001797 QualType T;
1798 if (!ObjectType.isNull() &&
1799 isa<TemplateSpecializationType>(Name.getCXXNameType())) {
1800 TemplateSpecializationType *SpecType
1801 = cast<TemplateSpecializationType>(Name.getCXXNameType());
1802 T = TransformTemplateSpecializationType(SpecType, ObjectType);
1803 } else
1804 T = getDerived().TransformType(Name.getCXXNameType());
Douglas Gregorf816bd72009-09-03 22:13:48 +00001805 if (T.isNull())
1806 return DeclarationName();
Mike Stump11289f42009-09-09 15:08:12 +00001807
Douglas Gregorf816bd72009-09-03 22:13:48 +00001808 return SemaRef.Context.DeclarationNames.getCXXSpecialName(
Mike Stump11289f42009-09-09 15:08:12 +00001809 Name.getNameKind(),
Douglas Gregorf816bd72009-09-03 22:13:48 +00001810 SemaRef.Context.getCanonicalType(T));
Douglas Gregorf816bd72009-09-03 22:13:48 +00001811 }
Mike Stump11289f42009-09-09 15:08:12 +00001812 }
1813
Douglas Gregorf816bd72009-09-03 22:13:48 +00001814 return DeclarationName();
1815}
1816
1817template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001818TemplateName
Douglas Gregor308047d2009-09-09 00:23:06 +00001819TreeTransform<Derived>::TransformTemplateName(TemplateName Name,
1820 QualType ObjectType) {
Douglas Gregor71dc5092009-08-06 06:41:21 +00001821 if (QualifiedTemplateName *QTN = Name.getAsQualifiedTemplateName()) {
Mike Stump11289f42009-09-09 15:08:12 +00001822 NestedNameSpecifier *NNS
Douglas Gregor71dc5092009-08-06 06:41:21 +00001823 = getDerived().TransformNestedNameSpecifier(QTN->getQualifier(),
1824 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
1825 if (!NNS)
1826 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001827
Douglas Gregor71dc5092009-08-06 06:41:21 +00001828 if (TemplateDecl *Template = QTN->getTemplateDecl()) {
Mike Stump11289f42009-09-09 15:08:12 +00001829 TemplateDecl *TransTemplate
Douglas Gregor71dc5092009-08-06 06:41:21 +00001830 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1831 if (!TransTemplate)
1832 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001833
Douglas Gregor71dc5092009-08-06 06:41:21 +00001834 if (!getDerived().AlwaysRebuild() &&
1835 NNS == QTN->getQualifier() &&
1836 TransTemplate == Template)
1837 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001838
Douglas Gregor71dc5092009-08-06 06:41:21 +00001839 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1840 TransTemplate);
1841 }
Mike Stump11289f42009-09-09 15:08:12 +00001842
Douglas Gregor71dc5092009-08-06 06:41:21 +00001843 OverloadedFunctionDecl *Ovl = QTN->getOverloadedFunctionDecl();
1844 assert(Ovl && "Not a template name or an overload set?");
Mike Stump11289f42009-09-09 15:08:12 +00001845 OverloadedFunctionDecl *TransOvl
Douglas Gregor71dc5092009-08-06 06:41:21 +00001846 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1847 if (!TransOvl)
1848 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001849
Douglas Gregor71dc5092009-08-06 06:41:21 +00001850 if (!getDerived().AlwaysRebuild() &&
1851 NNS == QTN->getQualifier() &&
1852 TransOvl == Ovl)
1853 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001854
Douglas Gregor71dc5092009-08-06 06:41:21 +00001855 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1856 TransOvl);
1857 }
Mike Stump11289f42009-09-09 15:08:12 +00001858
Douglas Gregor71dc5092009-08-06 06:41:21 +00001859 if (DependentTemplateName *DTN = Name.getAsDependentTemplateName()) {
Mike Stump11289f42009-09-09 15:08:12 +00001860 NestedNameSpecifier *NNS
Douglas Gregor71dc5092009-08-06 06:41:21 +00001861 = getDerived().TransformNestedNameSpecifier(DTN->getQualifier(),
1862 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
Douglas Gregor308047d2009-09-09 00:23:06 +00001863 if (!NNS && DTN->getQualifier())
Douglas Gregor71dc5092009-08-06 06:41:21 +00001864 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001865
Douglas Gregor71dc5092009-08-06 06:41:21 +00001866 if (!getDerived().AlwaysRebuild() &&
Douglas Gregorc59e5612009-10-19 22:04:39 +00001867 NNS == DTN->getQualifier() &&
1868 ObjectType.isNull())
Douglas Gregor71dc5092009-08-06 06:41:21 +00001869 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001870
Douglas Gregor308047d2009-09-09 00:23:06 +00001871 return getDerived().RebuildTemplateName(NNS, *DTN->getName(), ObjectType);
Douglas Gregor71dc5092009-08-06 06:41:21 +00001872 }
Mike Stump11289f42009-09-09 15:08:12 +00001873
Douglas Gregor71dc5092009-08-06 06:41:21 +00001874 if (TemplateDecl *Template = Name.getAsTemplateDecl()) {
Mike Stump11289f42009-09-09 15:08:12 +00001875 TemplateDecl *TransTemplate
Douglas Gregor71dc5092009-08-06 06:41:21 +00001876 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1877 if (!TransTemplate)
1878 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001879
Douglas Gregor71dc5092009-08-06 06:41:21 +00001880 if (!getDerived().AlwaysRebuild() &&
1881 TransTemplate == Template)
1882 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001883
Douglas Gregor71dc5092009-08-06 06:41:21 +00001884 return TemplateName(TransTemplate);
1885 }
Mike Stump11289f42009-09-09 15:08:12 +00001886
Douglas Gregor71dc5092009-08-06 06:41:21 +00001887 OverloadedFunctionDecl *Ovl = Name.getAsOverloadedFunctionDecl();
1888 assert(Ovl && "Not a template name or an overload set?");
Mike Stump11289f42009-09-09 15:08:12 +00001889 OverloadedFunctionDecl *TransOvl
Douglas Gregor71dc5092009-08-06 06:41:21 +00001890 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1891 if (!TransOvl)
1892 return TemplateName();
Mike Stump11289f42009-09-09 15:08:12 +00001893
Douglas Gregor71dc5092009-08-06 06:41:21 +00001894 if (!getDerived().AlwaysRebuild() &&
1895 TransOvl == Ovl)
1896 return Name;
Mike Stump11289f42009-09-09 15:08:12 +00001897
Douglas Gregor71dc5092009-08-06 06:41:21 +00001898 return TemplateName(TransOvl);
1899}
1900
1901template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00001902TemplateArgument
Douglas Gregore922c772009-08-04 22:27:00 +00001903TreeTransform<Derived>::TransformTemplateArgument(const TemplateArgument &Arg) {
1904 switch (Arg.getKind()) {
1905 case TemplateArgument::Null:
1906 case TemplateArgument::Integral:
1907 return Arg;
Mike Stump11289f42009-09-09 15:08:12 +00001908
Douglas Gregore922c772009-08-04 22:27:00 +00001909 case TemplateArgument::Type: {
1910 QualType T = getDerived().TransformType(Arg.getAsType());
1911 if (T.isNull())
1912 return TemplateArgument();
1913 return TemplateArgument(Arg.getLocation(), T);
1914 }
Mike Stump11289f42009-09-09 15:08:12 +00001915
Douglas Gregore922c772009-08-04 22:27:00 +00001916 case TemplateArgument::Declaration: {
1917 Decl *D = getDerived().TransformDecl(Arg.getAsDecl());
1918 if (!D)
1919 return TemplateArgument();
1920 return TemplateArgument(Arg.getLocation(), D);
1921 }
Mike Stump11289f42009-09-09 15:08:12 +00001922
Douglas Gregore922c772009-08-04 22:27:00 +00001923 case TemplateArgument::Expression: {
1924 // Template argument expressions are not potentially evaluated.
Mike Stump11289f42009-09-09 15:08:12 +00001925 EnterExpressionEvaluationContext Unevaluated(getSema(),
Douglas Gregore922c772009-08-04 22:27:00 +00001926 Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00001927
Douglas Gregore922c772009-08-04 22:27:00 +00001928 Sema::OwningExprResult E = getDerived().TransformExpr(Arg.getAsExpr());
1929 if (E.isInvalid())
1930 return TemplateArgument();
1931 return TemplateArgument(E.takeAs<Expr>());
1932 }
Mike Stump11289f42009-09-09 15:08:12 +00001933
Douglas Gregore922c772009-08-04 22:27:00 +00001934 case TemplateArgument::Pack: {
1935 llvm::SmallVector<TemplateArgument, 4> TransformedArgs;
1936 TransformedArgs.reserve(Arg.pack_size());
Mike Stump11289f42009-09-09 15:08:12 +00001937 for (TemplateArgument::pack_iterator A = Arg.pack_begin(),
Douglas Gregore922c772009-08-04 22:27:00 +00001938 AEnd = Arg.pack_end();
1939 A != AEnd; ++A) {
1940 TemplateArgument TA = getDerived().TransformTemplateArgument(*A);
1941 if (TA.isNull())
1942 return TA;
Mike Stump11289f42009-09-09 15:08:12 +00001943
Douglas Gregore922c772009-08-04 22:27:00 +00001944 TransformedArgs.push_back(TA);
1945 }
1946 TemplateArgument Result;
Mike Stump11289f42009-09-09 15:08:12 +00001947 Result.setArgumentPack(TransformedArgs.data(), TransformedArgs.size(),
Douglas Gregore922c772009-08-04 22:27:00 +00001948 true);
1949 return Result;
1950 }
1951 }
Mike Stump11289f42009-09-09 15:08:12 +00001952
Douglas Gregore922c772009-08-04 22:27:00 +00001953 // Work around bogus GCC warning
1954 return TemplateArgument();
1955}
1956
Douglas Gregord6ff3322009-08-04 16:50:30 +00001957//===----------------------------------------------------------------------===//
1958// Type transformation
1959//===----------------------------------------------------------------------===//
1960
1961template<typename Derived>
1962QualType TreeTransform<Derived>::TransformType(QualType T) {
1963 if (getDerived().AlreadyTransformed(T))
1964 return T;
Mike Stump11289f42009-09-09 15:08:12 +00001965
John McCall550e0c22009-10-21 00:40:46 +00001966 // Temporary workaround. All of these transformations should
1967 // eventually turn into transformations on TypeLocs.
1968 DeclaratorInfo *DI = getSema().Context.CreateDeclaratorInfo(T);
John McCallde889892009-10-21 00:44:26 +00001969 DI->getTypeLoc().initialize(getDerived().getBaseLocation());
John McCall550e0c22009-10-21 00:40:46 +00001970
1971 DeclaratorInfo *NewDI = getDerived().TransformType(DI);
John McCall8ccfcb52009-09-24 19:53:00 +00001972
John McCall550e0c22009-10-21 00:40:46 +00001973 if (!NewDI)
1974 return QualType();
1975
1976 return NewDI->getType();
1977}
1978
1979template<typename Derived>
1980DeclaratorInfo *TreeTransform<Derived>::TransformType(DeclaratorInfo *DI) {
1981 if (getDerived().AlreadyTransformed(DI->getType()))
1982 return DI;
1983
1984 TypeLocBuilder TLB;
1985
1986 TypeLoc TL = DI->getTypeLoc();
1987 TLB.reserve(TL.getFullDataSize());
1988
1989 QualType Result = getDerived().TransformType(TLB, TL);
1990 if (Result.isNull())
1991 return 0;
1992
1993 return TLB.getDeclaratorInfo(SemaRef.Context, Result);
1994}
1995
1996template<typename Derived>
1997QualType
1998TreeTransform<Derived>::TransformType(TypeLocBuilder &TLB, TypeLoc T) {
1999 switch (T.getTypeLocClass()) {
2000#define ABSTRACT_TYPELOC(CLASS, PARENT)
2001#define TYPELOC(CLASS, PARENT) \
2002 case TypeLoc::CLASS: \
2003 return getDerived().Transform##CLASS##Type(TLB, cast<CLASS##TypeLoc>(T));
2004#include "clang/AST/TypeLocNodes.def"
Douglas Gregord6ff3322009-08-04 16:50:30 +00002005 }
Mike Stump11289f42009-09-09 15:08:12 +00002006
John McCall550e0c22009-10-21 00:40:46 +00002007 llvm::llvm_unreachable("unhandled type loc!");
2008 return QualType();
2009}
2010
2011/// FIXME: By default, this routine adds type qualifiers only to types
2012/// that can have qualifiers, and silently suppresses those qualifiers
2013/// that are not permitted (e.g., qualifiers on reference or function
2014/// types). This is the right thing for template instantiation, but
2015/// probably not for other clients.
2016template<typename Derived>
2017QualType
2018TreeTransform<Derived>::TransformQualifiedType(TypeLocBuilder &TLB,
2019 QualifiedTypeLoc T) {
2020 Qualifiers Quals = T.getType().getQualifiers();
2021
2022 QualType Result = getDerived().TransformType(TLB, T.getUnqualifiedLoc());
2023 if (Result.isNull())
2024 return QualType();
2025
2026 // Silently suppress qualifiers if the result type can't be qualified.
2027 // FIXME: this is the right thing for template instantiation, but
2028 // probably not for other clients.
2029 if (Result->isFunctionType() || Result->isReferenceType())
Douglas Gregord6ff3322009-08-04 16:50:30 +00002030 return Result;
Mike Stump11289f42009-09-09 15:08:12 +00002031
John McCall550e0c22009-10-21 00:40:46 +00002032 Result = SemaRef.Context.getQualifiedType(Result, Quals);
2033
2034 TLB.push<QualifiedTypeLoc>(Result);
2035
2036 // No location information to preserve.
2037
2038 return Result;
2039}
2040
2041template <class TyLoc> static inline
2042QualType TransformTypeSpecType(TypeLocBuilder &TLB, TyLoc T) {
2043 TyLoc NewT = TLB.push<TyLoc>(T.getType());
2044 NewT.setNameLoc(T.getNameLoc());
2045 return T.getType();
2046}
2047
2048// Ugly metaprogramming macros because I couldn't be bothered to make
2049// the equivalent template version work.
2050#define TransformPointerLikeType(TypeClass) do { \
2051 QualType PointeeType \
2052 = getDerived().TransformType(TLB, TL.getPointeeLoc()); \
2053 if (PointeeType.isNull()) \
2054 return QualType(); \
2055 \
2056 QualType Result = TL.getType(); \
2057 if (getDerived().AlwaysRebuild() || \
2058 PointeeType != TL.getPointeeLoc().getType()) { \
2059 Result = getDerived().Rebuild##TypeClass(PointeeType); \
2060 if (Result.isNull()) \
2061 return QualType(); \
2062 } \
2063 \
2064 TypeClass##Loc NewT = TLB.push<TypeClass##Loc>(Result); \
2065 NewT.setSigilLoc(TL.getSigilLoc()); \
2066 \
2067 return Result; \
2068} while(0)
2069
2070// Reference collapsing forces us to transform reference types
2071// differently from the other pointer-like types.
2072#define TransformReferenceType(TypeClass) do { \
2073 QualType PointeeType \
2074 = getDerived().TransformType(TLB, TL.getPointeeLoc()); \
2075 if (PointeeType.isNull()) \
2076 return QualType(); \
2077 \
2078 QualType Result = TL.getType(); \
2079 if (getDerived().AlwaysRebuild() || \
2080 PointeeType != TL.getPointeeLoc().getType()) { \
2081 Result = getDerived().Rebuild##TypeClass(PointeeType); \
2082 if (Result.isNull()) \
2083 return QualType(); \
2084 } \
2085 \
2086 /* Workaround: rebuild doesn't always change the type */ \
2087 /* FIXME: avoid losing this location information. */ \
2088 if (Result == PointeeType) \
2089 return Result; \
2090 ReferenceTypeLoc NewTL; \
2091 if (isa<LValueReferenceType>(Result)) \
2092 NewTL = TLB.push<LValueReferenceTypeLoc>(Result); \
2093 else \
2094 NewTL = TLB.push<RValueReferenceTypeLoc>(Result); \
2095 NewTL.setSigilLoc(TL.getSigilLoc()); \
2096 return Result; \
2097} while (0)
2098
2099template<typename Derived>
2100QualType TreeTransform<Derived>::TransformBuiltinType(TypeLocBuilder &TLB,
2101 BuiltinTypeLoc T) {
2102 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002103}
Mike Stump11289f42009-09-09 15:08:12 +00002104
Douglas Gregord6ff3322009-08-04 16:50:30 +00002105template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002106QualType
John McCall550e0c22009-10-21 00:40:46 +00002107TreeTransform<Derived>::TransformFixedWidthIntType(TypeLocBuilder &TLB,
2108 FixedWidthIntTypeLoc T) {
2109 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002110}
Argyrios Kyrtzidise9189262009-08-19 01:28:17 +00002111
Douglas Gregord6ff3322009-08-04 16:50:30 +00002112template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002113QualType TreeTransform<Derived>::TransformComplexType(TypeLocBuilder &TLB,
2114 ComplexTypeLoc T) {
2115 // FIXME: recurse?
2116 return TransformTypeSpecType(TLB, T);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002117}
Mike Stump11289f42009-09-09 15:08:12 +00002118
Douglas Gregord6ff3322009-08-04 16:50:30 +00002119template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002120QualType TreeTransform<Derived>::TransformPointerType(TypeLocBuilder &TLB,
2121 PointerTypeLoc TL) {
2122 TransformPointerLikeType(PointerType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002123}
Mike Stump11289f42009-09-09 15:08:12 +00002124
2125template<typename Derived>
2126QualType
John McCall550e0c22009-10-21 00:40:46 +00002127TreeTransform<Derived>::TransformBlockPointerType(TypeLocBuilder &TLB,
2128 BlockPointerTypeLoc TL) {
2129 TransformPointerLikeType(BlockPointerType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002130}
2131
Mike Stump11289f42009-09-09 15:08:12 +00002132template<typename Derived>
2133QualType
John McCall550e0c22009-10-21 00:40:46 +00002134TreeTransform<Derived>::TransformLValueReferenceType(TypeLocBuilder &TLB,
2135 LValueReferenceTypeLoc TL) {
2136 TransformReferenceType(LValueReferenceType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002137}
2138
Mike Stump11289f42009-09-09 15:08:12 +00002139template<typename Derived>
2140QualType
John McCall550e0c22009-10-21 00:40:46 +00002141TreeTransform<Derived>::TransformRValueReferenceType(TypeLocBuilder &TLB,
2142 RValueReferenceTypeLoc TL) {
2143 TransformReferenceType(RValueReferenceType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002144}
Mike Stump11289f42009-09-09 15:08:12 +00002145
Douglas Gregord6ff3322009-08-04 16:50:30 +00002146template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002147QualType
John McCall550e0c22009-10-21 00:40:46 +00002148TreeTransform<Derived>::TransformMemberPointerType(TypeLocBuilder &TLB,
2149 MemberPointerTypeLoc TL) {
2150 MemberPointerType *T = TL.getTypePtr();
2151
2152 QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002153 if (PointeeType.isNull())
2154 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002155
John McCall550e0c22009-10-21 00:40:46 +00002156 // TODO: preserve source information for this.
2157 QualType ClassType
2158 = getDerived().TransformType(QualType(T->getClass(), 0));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002159 if (ClassType.isNull())
2160 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002161
John McCall550e0c22009-10-21 00:40:46 +00002162 QualType Result = TL.getType();
2163 if (getDerived().AlwaysRebuild() ||
2164 PointeeType != T->getPointeeType() ||
2165 ClassType != QualType(T->getClass(), 0)) {
2166 Result = getDerived().RebuildMemberPointerType(PointeeType, ClassType);
2167 if (Result.isNull())
2168 return QualType();
2169 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00002170
John McCall550e0c22009-10-21 00:40:46 +00002171 MemberPointerTypeLoc NewTL = TLB.push<MemberPointerTypeLoc>(Result);
2172 NewTL.setSigilLoc(TL.getSigilLoc());
2173
2174 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002175}
2176
Mike Stump11289f42009-09-09 15:08:12 +00002177template<typename Derived>
2178QualType
John McCall550e0c22009-10-21 00:40:46 +00002179TreeTransform<Derived>::TransformConstantArrayType(TypeLocBuilder &TLB,
2180 ConstantArrayTypeLoc TL) {
2181 ConstantArrayType *T = TL.getTypePtr();
2182 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002183 if (ElementType.isNull())
2184 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002185
John McCall550e0c22009-10-21 00:40:46 +00002186 QualType Result = TL.getType();
2187 if (getDerived().AlwaysRebuild() ||
2188 ElementType != T->getElementType()) {
2189 Result = getDerived().RebuildConstantArrayType(ElementType,
2190 T->getSizeModifier(),
2191 T->getSize(),
2192 T->getIndexTypeCVRQualifiers());
2193 if (Result.isNull())
2194 return QualType();
2195 }
2196
2197 ConstantArrayTypeLoc NewTL = TLB.push<ConstantArrayTypeLoc>(Result);
2198 NewTL.setLBracketLoc(TL.getLBracketLoc());
2199 NewTL.setRBracketLoc(TL.getRBracketLoc());
Mike Stump11289f42009-09-09 15:08:12 +00002200
John McCall550e0c22009-10-21 00:40:46 +00002201 Expr *Size = TL.getSizeExpr();
2202 if (Size) {
2203 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2204 Size = getDerived().TransformExpr(Size).template takeAs<Expr>();
2205 }
2206 NewTL.setSizeExpr(Size);
2207
2208 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002209}
Mike Stump11289f42009-09-09 15:08:12 +00002210
Douglas Gregord6ff3322009-08-04 16:50:30 +00002211template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002212QualType TreeTransform<Derived>::TransformIncompleteArrayType(
John McCall550e0c22009-10-21 00:40:46 +00002213 TypeLocBuilder &TLB,
2214 IncompleteArrayTypeLoc TL) {
2215 IncompleteArrayType *T = TL.getTypePtr();
2216 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002217 if (ElementType.isNull())
2218 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002219
John McCall550e0c22009-10-21 00:40:46 +00002220 QualType Result = TL.getType();
2221 if (getDerived().AlwaysRebuild() ||
2222 ElementType != T->getElementType()) {
2223 Result = getDerived().RebuildIncompleteArrayType(ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00002224 T->getSizeModifier(),
John McCall550e0c22009-10-21 00:40:46 +00002225 T->getIndexTypeCVRQualifiers());
2226 if (Result.isNull())
2227 return QualType();
2228 }
2229
2230 IncompleteArrayTypeLoc NewTL = TLB.push<IncompleteArrayTypeLoc>(Result);
2231 NewTL.setLBracketLoc(TL.getLBracketLoc());
2232 NewTL.setRBracketLoc(TL.getRBracketLoc());
2233 NewTL.setSizeExpr(0);
2234
2235 return Result;
2236}
2237
2238template<typename Derived>
2239QualType
2240TreeTransform<Derived>::TransformVariableArrayType(TypeLocBuilder &TLB,
2241 VariableArrayTypeLoc TL) {
2242 VariableArrayType *T = TL.getTypePtr();
2243 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
2244 if (ElementType.isNull())
2245 return QualType();
2246
2247 // Array bounds are not potentially evaluated contexts
2248 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2249
2250 Sema::OwningExprResult SizeResult
2251 = getDerived().TransformExpr(T->getSizeExpr());
2252 if (SizeResult.isInvalid())
2253 return QualType();
2254
2255 Expr *Size = static_cast<Expr*>(SizeResult.get());
2256
2257 QualType Result = TL.getType();
2258 if (getDerived().AlwaysRebuild() ||
2259 ElementType != T->getElementType() ||
2260 Size != T->getSizeExpr()) {
2261 Result = getDerived().RebuildVariableArrayType(ElementType,
2262 T->getSizeModifier(),
2263 move(SizeResult),
2264 T->getIndexTypeCVRQualifiers(),
2265 T->getBracketsRange());
2266 if (Result.isNull())
2267 return QualType();
2268 }
2269 else SizeResult.take();
2270
2271 VariableArrayTypeLoc NewTL = TLB.push<VariableArrayTypeLoc>(Result);
2272 NewTL.setLBracketLoc(TL.getLBracketLoc());
2273 NewTL.setRBracketLoc(TL.getRBracketLoc());
2274 NewTL.setSizeExpr(Size);
2275
2276 return Result;
2277}
2278
2279template<typename Derived>
2280QualType
2281TreeTransform<Derived>::TransformDependentSizedArrayType(TypeLocBuilder &TLB,
2282 DependentSizedArrayTypeLoc TL) {
2283 DependentSizedArrayType *T = TL.getTypePtr();
2284 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc());
2285 if (ElementType.isNull())
2286 return QualType();
2287
2288 // Array bounds are not potentially evaluated contexts
2289 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2290
2291 Sema::OwningExprResult SizeResult
2292 = getDerived().TransformExpr(T->getSizeExpr());
2293 if (SizeResult.isInvalid())
2294 return QualType();
2295
2296 Expr *Size = static_cast<Expr*>(SizeResult.get());
2297
2298 QualType Result = TL.getType();
2299 if (getDerived().AlwaysRebuild() ||
2300 ElementType != T->getElementType() ||
2301 Size != T->getSizeExpr()) {
2302 Result = getDerived().RebuildDependentSizedArrayType(ElementType,
2303 T->getSizeModifier(),
2304 move(SizeResult),
2305 T->getIndexTypeCVRQualifiers(),
2306 T->getBracketsRange());
2307 if (Result.isNull())
2308 return QualType();
2309 }
2310 else SizeResult.take();
2311
2312 // We might have any sort of array type now, but fortunately they
2313 // all have the same location layout.
2314 ArrayTypeLoc NewTL = TLB.push<ArrayTypeLoc>(Result);
2315 NewTL.setLBracketLoc(TL.getLBracketLoc());
2316 NewTL.setRBracketLoc(TL.getRBracketLoc());
2317 NewTL.setSizeExpr(Size);
2318
2319 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002320}
Mike Stump11289f42009-09-09 15:08:12 +00002321
2322template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002323QualType TreeTransform<Derived>::TransformDependentSizedExtVectorType(
John McCall550e0c22009-10-21 00:40:46 +00002324 TypeLocBuilder &TLB,
2325 DependentSizedExtVectorTypeLoc TL) {
2326 DependentSizedExtVectorType *T = TL.getTypePtr();
2327
2328 // FIXME: ext vector locs should be nested
Douglas Gregord6ff3322009-08-04 16:50:30 +00002329 QualType ElementType = getDerived().TransformType(T->getElementType());
2330 if (ElementType.isNull())
2331 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002332
Douglas Gregore922c772009-08-04 22:27:00 +00002333 // Vector sizes are not potentially evaluated contexts
2334 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2335
Douglas Gregord6ff3322009-08-04 16:50:30 +00002336 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
2337 if (Size.isInvalid())
2338 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002339
John McCall550e0c22009-10-21 00:40:46 +00002340 QualType Result = TL.getType();
2341 if (getDerived().AlwaysRebuild() ||
2342 ElementType != T->getElementType() &&
2343 Size.get() != T->getSizeExpr()) {
2344 Result = getDerived().RebuildDependentSizedExtVectorType(ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00002345 move(Size),
2346 T->getAttributeLoc());
John McCall550e0c22009-10-21 00:40:46 +00002347 if (Result.isNull())
2348 return QualType();
2349 }
2350 else Size.take();
2351
2352 // Result might be dependent or not.
2353 if (isa<DependentSizedExtVectorType>(Result)) {
2354 DependentSizedExtVectorTypeLoc NewTL
2355 = TLB.push<DependentSizedExtVectorTypeLoc>(Result);
2356 NewTL.setNameLoc(TL.getNameLoc());
2357 } else {
2358 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result);
2359 NewTL.setNameLoc(TL.getNameLoc());
2360 }
2361
2362 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002363}
Mike Stump11289f42009-09-09 15:08:12 +00002364
2365template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002366QualType TreeTransform<Derived>::TransformVectorType(TypeLocBuilder &TLB,
2367 VectorTypeLoc TL) {
2368 VectorType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002369 QualType ElementType = getDerived().TransformType(T->getElementType());
2370 if (ElementType.isNull())
2371 return QualType();
2372
John McCall550e0c22009-10-21 00:40:46 +00002373 QualType Result = TL.getType();
2374 if (getDerived().AlwaysRebuild() ||
2375 ElementType != T->getElementType()) {
2376 Result = getDerived().RebuildVectorType(ElementType, T->getNumElements());
2377 if (Result.isNull())
2378 return QualType();
2379 }
2380
2381 VectorTypeLoc NewTL = TLB.push<VectorTypeLoc>(Result);
2382 NewTL.setNameLoc(TL.getNameLoc());
Mike Stump11289f42009-09-09 15:08:12 +00002383
John McCall550e0c22009-10-21 00:40:46 +00002384 return Result;
2385}
2386
2387template<typename Derived>
2388QualType TreeTransform<Derived>::TransformExtVectorType(TypeLocBuilder &TLB,
2389 ExtVectorTypeLoc TL) {
2390 VectorType *T = TL.getTypePtr();
2391 QualType ElementType = getDerived().TransformType(T->getElementType());
2392 if (ElementType.isNull())
2393 return QualType();
2394
2395 QualType Result = TL.getType();
2396 if (getDerived().AlwaysRebuild() ||
2397 ElementType != T->getElementType()) {
2398 Result = getDerived().RebuildExtVectorType(ElementType,
2399 T->getNumElements(),
2400 /*FIXME*/ SourceLocation());
2401 if (Result.isNull())
2402 return QualType();
2403 }
2404
2405 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result);
2406 NewTL.setNameLoc(TL.getNameLoc());
2407
2408 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002409}
Mike Stump11289f42009-09-09 15:08:12 +00002410
2411template<typename Derived>
2412QualType
John McCall550e0c22009-10-21 00:40:46 +00002413TreeTransform<Derived>::TransformFunctionProtoType(TypeLocBuilder &TLB,
2414 FunctionProtoTypeLoc TL) {
2415 FunctionProtoType *T = TL.getTypePtr();
2416 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002417 if (ResultType.isNull())
2418 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002419
John McCall550e0c22009-10-21 00:40:46 +00002420 // Transform the parameters.
Douglas Gregord6ff3322009-08-04 16:50:30 +00002421 llvm::SmallVector<QualType, 4> ParamTypes;
John McCall550e0c22009-10-21 00:40:46 +00002422 llvm::SmallVector<ParmVarDecl*, 4> ParamDecls;
2423 for (unsigned i = 0, e = TL.getNumArgs(); i != e; ++i) {
2424 ParmVarDecl *OldParm = TL.getArg(i);
Mike Stump11289f42009-09-09 15:08:12 +00002425
John McCall550e0c22009-10-21 00:40:46 +00002426 QualType NewType;
2427 ParmVarDecl *NewParm;
2428
2429 if (OldParm) {
2430 DeclaratorInfo *OldDI = OldParm->getDeclaratorInfo();
2431 assert(OldDI->getType() == T->getArgType(i));
2432
2433 DeclaratorInfo *NewDI = getDerived().TransformType(OldDI);
2434 if (!NewDI)
2435 return QualType();
2436
2437 if (NewDI == OldDI)
2438 NewParm = OldParm;
2439 else
2440 NewParm = ParmVarDecl::Create(SemaRef.Context,
2441 OldParm->getDeclContext(),
2442 OldParm->getLocation(),
2443 OldParm->getIdentifier(),
2444 NewDI->getType(),
2445 NewDI,
2446 OldParm->getStorageClass(),
2447 /* DefArg */ NULL);
2448 NewType = NewParm->getType();
2449
2450 // Deal with the possibility that we don't have a parameter
2451 // declaration for this parameter.
2452 } else {
2453 NewParm = 0;
2454
2455 QualType OldType = T->getArgType(i);
2456 NewType = getDerived().TransformType(OldType);
2457 if (NewType.isNull())
2458 return QualType();
2459 }
2460
2461 ParamTypes.push_back(NewType);
2462 ParamDecls.push_back(NewParm);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002463 }
Mike Stump11289f42009-09-09 15:08:12 +00002464
John McCall550e0c22009-10-21 00:40:46 +00002465 QualType Result = TL.getType();
2466 if (getDerived().AlwaysRebuild() ||
2467 ResultType != T->getResultType() ||
2468 !std::equal(T->arg_type_begin(), T->arg_type_end(), ParamTypes.begin())) {
2469 Result = getDerived().RebuildFunctionProtoType(ResultType,
2470 ParamTypes.data(),
2471 ParamTypes.size(),
2472 T->isVariadic(),
2473 T->getTypeQuals());
2474 if (Result.isNull())
2475 return QualType();
2476 }
Mike Stump11289f42009-09-09 15:08:12 +00002477
John McCall550e0c22009-10-21 00:40:46 +00002478 FunctionProtoTypeLoc NewTL = TLB.push<FunctionProtoTypeLoc>(Result);
2479 NewTL.setLParenLoc(TL.getLParenLoc());
2480 NewTL.setRParenLoc(TL.getRParenLoc());
2481 for (unsigned i = 0, e = NewTL.getNumArgs(); i != e; ++i)
2482 NewTL.setArg(i, ParamDecls[i]);
2483
2484 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002485}
Mike Stump11289f42009-09-09 15:08:12 +00002486
Douglas Gregord6ff3322009-08-04 16:50:30 +00002487template<typename Derived>
2488QualType TreeTransform<Derived>::TransformFunctionNoProtoType(
John McCall550e0c22009-10-21 00:40:46 +00002489 TypeLocBuilder &TLB,
2490 FunctionNoProtoTypeLoc TL) {
2491 FunctionNoProtoType *T = TL.getTypePtr();
2492 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc());
2493 if (ResultType.isNull())
2494 return QualType();
2495
2496 QualType Result = TL.getType();
2497 if (getDerived().AlwaysRebuild() ||
2498 ResultType != T->getResultType())
2499 Result = getDerived().RebuildFunctionNoProtoType(ResultType);
2500
2501 FunctionNoProtoTypeLoc NewTL = TLB.push<FunctionNoProtoTypeLoc>(Result);
2502 NewTL.setLParenLoc(TL.getLParenLoc());
2503 NewTL.setRParenLoc(TL.getRParenLoc());
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>::TransformTypedefType(TypeLocBuilder &TLB,
2510 TypedefTypeLoc TL) {
2511 TypedefType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002512 TypedefDecl *Typedef
2513 = cast_or_null<TypedefDecl>(getDerived().TransformDecl(T->getDecl()));
2514 if (!Typedef)
2515 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002516
John McCall550e0c22009-10-21 00:40:46 +00002517 QualType Result = TL.getType();
2518 if (getDerived().AlwaysRebuild() ||
2519 Typedef != T->getDecl()) {
2520 Result = getDerived().RebuildTypedefType(Typedef);
2521 if (Result.isNull())
2522 return QualType();
2523 }
Mike Stump11289f42009-09-09 15:08:12 +00002524
John McCall550e0c22009-10-21 00:40:46 +00002525 TypedefTypeLoc NewTL = TLB.push<TypedefTypeLoc>(Result);
2526 NewTL.setNameLoc(TL.getNameLoc());
2527
2528 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002529}
Mike Stump11289f42009-09-09 15:08:12 +00002530
Douglas Gregord6ff3322009-08-04 16:50:30 +00002531template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002532QualType TreeTransform<Derived>::TransformTypeOfExprType(TypeLocBuilder &TLB,
2533 TypeOfExprTypeLoc TL) {
2534 TypeOfExprType *T = TL.getTypePtr();
2535
Douglas Gregore922c772009-08-04 22:27:00 +00002536 // typeof expressions are not potentially evaluated contexts
2537 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002538
Douglas Gregord6ff3322009-08-04 16:50:30 +00002539 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2540 if (E.isInvalid())
2541 return QualType();
2542
John McCall550e0c22009-10-21 00:40:46 +00002543 QualType Result = TL.getType();
2544 if (getDerived().AlwaysRebuild() ||
2545 E.get() != T->getUnderlyingExpr()) {
2546 Result = getDerived().RebuildTypeOfExprType(move(E));
2547 if (Result.isNull())
2548 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002549 }
John McCall550e0c22009-10-21 00:40:46 +00002550 else E.take();
Mike Stump11289f42009-09-09 15:08:12 +00002551
John McCall550e0c22009-10-21 00:40:46 +00002552 TypeOfExprTypeLoc NewTL = TLB.push<TypeOfExprTypeLoc>(Result);
2553 NewTL.setNameLoc(TL.getNameLoc());
2554
2555 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002556}
Mike Stump11289f42009-09-09 15:08:12 +00002557
2558template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002559QualType TreeTransform<Derived>::TransformTypeOfType(TypeLocBuilder &TLB,
2560 TypeOfTypeLoc TL) {
2561 TypeOfType *T = TL.getTypePtr();
2562
2563 // FIXME: should be an inner type, or at least have a DeclaratorInfo.
Douglas Gregord6ff3322009-08-04 16:50:30 +00002564 QualType Underlying = getDerived().TransformType(T->getUnderlyingType());
2565 if (Underlying.isNull())
2566 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002567
John McCall550e0c22009-10-21 00:40:46 +00002568 QualType Result = TL.getType();
2569 if (getDerived().AlwaysRebuild() ||
2570 Underlying != T->getUnderlyingType()) {
2571 Result = getDerived().RebuildTypeOfType(Underlying);
2572 if (Result.isNull())
2573 return QualType();
2574 }
Mike Stump11289f42009-09-09 15:08:12 +00002575
John McCall550e0c22009-10-21 00:40:46 +00002576 TypeOfTypeLoc NewTL = TLB.push<TypeOfTypeLoc>(Result);
2577 NewTL.setNameLoc(TL.getNameLoc());
2578
2579 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002580}
Mike Stump11289f42009-09-09 15:08:12 +00002581
2582template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002583QualType TreeTransform<Derived>::TransformDecltypeType(TypeLocBuilder &TLB,
2584 DecltypeTypeLoc TL) {
2585 DecltypeType *T = TL.getTypePtr();
2586
Douglas Gregore922c772009-08-04 22:27:00 +00002587 // decltype expressions are not potentially evaluated contexts
2588 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002589
Douglas Gregord6ff3322009-08-04 16:50:30 +00002590 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2591 if (E.isInvalid())
2592 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002593
John McCall550e0c22009-10-21 00:40:46 +00002594 QualType Result = TL.getType();
2595 if (getDerived().AlwaysRebuild() ||
2596 E.get() != T->getUnderlyingExpr()) {
2597 Result = getDerived().RebuildDecltypeType(move(E));
2598 if (Result.isNull())
2599 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002600 }
John McCall550e0c22009-10-21 00:40:46 +00002601 else E.take();
Mike Stump11289f42009-09-09 15:08:12 +00002602
John McCall550e0c22009-10-21 00:40:46 +00002603 DecltypeTypeLoc NewTL = TLB.push<DecltypeTypeLoc>(Result);
2604 NewTL.setNameLoc(TL.getNameLoc());
2605
2606 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002607}
2608
2609template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002610QualType TreeTransform<Derived>::TransformRecordType(TypeLocBuilder &TLB,
2611 RecordTypeLoc TL) {
2612 RecordType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002613 RecordDecl *Record
John McCall550e0c22009-10-21 00:40:46 +00002614 = cast_or_null<RecordDecl>(getDerived().TransformDecl(T->getDecl()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002615 if (!Record)
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 Record != T->getDecl()) {
2621 Result = getDerived().RebuildRecordType(Record);
2622 if (Result.isNull())
2623 return QualType();
2624 }
Mike Stump11289f42009-09-09 15:08:12 +00002625
John McCall550e0c22009-10-21 00:40:46 +00002626 RecordTypeLoc NewTL = TLB.push<RecordTypeLoc>(Result);
2627 NewTL.setNameLoc(TL.getNameLoc());
2628
2629 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002630}
Mike Stump11289f42009-09-09 15:08:12 +00002631
2632template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002633QualType TreeTransform<Derived>::TransformEnumType(TypeLocBuilder &TLB,
2634 EnumTypeLoc TL) {
2635 EnumType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002636 EnumDecl *Enum
John McCall550e0c22009-10-21 00:40:46 +00002637 = cast_or_null<EnumDecl>(getDerived().TransformDecl(T->getDecl()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002638 if (!Enum)
2639 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002640
John McCall550e0c22009-10-21 00:40:46 +00002641 QualType Result = TL.getType();
2642 if (getDerived().AlwaysRebuild() ||
2643 Enum != T->getDecl()) {
2644 Result = getDerived().RebuildEnumType(Enum);
2645 if (Result.isNull())
2646 return QualType();
2647 }
Mike Stump11289f42009-09-09 15:08:12 +00002648
John McCall550e0c22009-10-21 00:40:46 +00002649 EnumTypeLoc NewTL = TLB.push<EnumTypeLoc>(Result);
2650 NewTL.setNameLoc(TL.getNameLoc());
2651
2652 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002653}
John McCallfcc33b02009-09-05 00:15:47 +00002654
2655template <typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002656QualType TreeTransform<Derived>::TransformElaboratedType(TypeLocBuilder &TLB,
2657 ElaboratedTypeLoc TL) {
2658 ElaboratedType *T = TL.getTypePtr();
2659
2660 // FIXME: this should be a nested type.
John McCallfcc33b02009-09-05 00:15:47 +00002661 QualType Underlying = getDerived().TransformType(T->getUnderlyingType());
2662 if (Underlying.isNull())
2663 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002664
John McCall550e0c22009-10-21 00:40:46 +00002665 QualType Result = TL.getType();
2666 if (getDerived().AlwaysRebuild() ||
2667 Underlying != T->getUnderlyingType()) {
2668 Result = getDerived().RebuildElaboratedType(Underlying, T->getTagKind());
2669 if (Result.isNull())
2670 return QualType();
2671 }
Mike Stump11289f42009-09-09 15:08:12 +00002672
John McCall550e0c22009-10-21 00:40:46 +00002673 ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result);
2674 NewTL.setNameLoc(TL.getNameLoc());
2675
2676 return Result;
John McCallfcc33b02009-09-05 00:15:47 +00002677}
Mike Stump11289f42009-09-09 15:08:12 +00002678
2679
Douglas Gregord6ff3322009-08-04 16:50:30 +00002680template<typename Derived>
2681QualType TreeTransform<Derived>::TransformTemplateTypeParmType(
John McCall550e0c22009-10-21 00:40:46 +00002682 TypeLocBuilder &TLB,
2683 TemplateTypeParmTypeLoc TL) {
2684 return TransformTypeSpecType(TLB, TL);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002685}
2686
Mike Stump11289f42009-09-09 15:08:12 +00002687template<typename Derived>
John McCallcebee162009-10-18 09:09:24 +00002688QualType TreeTransform<Derived>::TransformSubstTemplateTypeParmType(
John McCall550e0c22009-10-21 00:40:46 +00002689 TypeLocBuilder &TLB,
2690 SubstTemplateTypeParmTypeLoc TL) {
2691 return TransformTypeSpecType(TLB, TL);
John McCallcebee162009-10-18 09:09:24 +00002692}
2693
2694template<typename Derived>
Douglas Gregorc59e5612009-10-19 22:04:39 +00002695inline QualType
2696TreeTransform<Derived>::TransformTemplateSpecializationType(
John McCall550e0c22009-10-21 00:40:46 +00002697 TypeLocBuilder &TLB,
2698 TemplateSpecializationTypeLoc TL) {
2699 // TODO: figure out how make this work with an ObjectType.
2700 QualType Result
2701 = TransformTemplateSpecializationType(TL.getTypePtr(), QualType());
2702 if (Result.isNull())
2703 return QualType();
2704
2705 TemplateSpecializationTypeLoc NewTL
2706 = TLB.push<TemplateSpecializationTypeLoc>(Result);
2707 NewTL.setNameLoc(TL.getNameLoc());
2708
2709 return Result;
Douglas Gregorc59e5612009-10-19 22:04:39 +00002710}
2711
2712template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00002713QualType TreeTransform<Derived>::TransformTemplateSpecializationType(
Douglas Gregorc59e5612009-10-19 22:04:39 +00002714 const TemplateSpecializationType *T,
2715 QualType ObjectType) {
Mike Stump11289f42009-09-09 15:08:12 +00002716 TemplateName Template
Douglas Gregorc59e5612009-10-19 22:04:39 +00002717 = getDerived().TransformTemplateName(T->getTemplateName(), ObjectType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002718 if (Template.isNull())
2719 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002720
Douglas Gregord6ff3322009-08-04 16:50:30 +00002721 llvm::SmallVector<TemplateArgument, 4> NewTemplateArgs;
2722 NewTemplateArgs.reserve(T->getNumArgs());
2723 for (TemplateSpecializationType::iterator Arg = T->begin(), ArgEnd = T->end();
2724 Arg != ArgEnd; ++Arg) {
2725 TemplateArgument NewArg = getDerived().TransformTemplateArgument(*Arg);
2726 if (NewArg.isNull())
2727 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002728
Douglas Gregord6ff3322009-08-04 16:50:30 +00002729 NewTemplateArgs.push_back(NewArg);
2730 }
Mike Stump11289f42009-09-09 15:08:12 +00002731
Douglas Gregord6ff3322009-08-04 16:50:30 +00002732 // FIXME: early abort if all of the template arguments and such are the
2733 // same.
Mike Stump11289f42009-09-09 15:08:12 +00002734
Douglas Gregord6ff3322009-08-04 16:50:30 +00002735 // FIXME: We're missing the locations of the template name, '<', and '>'.
2736 return getDerived().RebuildTemplateSpecializationType(Template,
2737 NewTemplateArgs.data(),
2738 NewTemplateArgs.size());
2739}
Mike Stump11289f42009-09-09 15:08:12 +00002740
2741template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002742QualType
2743TreeTransform<Derived>::TransformQualifiedNameType(TypeLocBuilder &TLB,
2744 QualifiedNameTypeLoc TL) {
2745 QualifiedNameType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002746 NestedNameSpecifier *NNS
2747 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
2748 SourceRange());
2749 if (!NNS)
2750 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002751
Douglas Gregord6ff3322009-08-04 16:50:30 +00002752 QualType Named = getDerived().TransformType(T->getNamedType());
2753 if (Named.isNull())
2754 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002755
John McCall550e0c22009-10-21 00:40:46 +00002756 QualType Result = TL.getType();
2757 if (getDerived().AlwaysRebuild() ||
2758 NNS != T->getQualifier() ||
2759 Named != T->getNamedType()) {
2760 Result = getDerived().RebuildQualifiedNameType(NNS, Named);
2761 if (Result.isNull())
2762 return QualType();
2763 }
Douglas Gregord6ff3322009-08-04 16:50:30 +00002764
John McCall550e0c22009-10-21 00:40:46 +00002765 QualifiedNameTypeLoc NewTL = TLB.push<QualifiedNameTypeLoc>(Result);
2766 NewTL.setNameLoc(TL.getNameLoc());
2767
2768 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002769}
Mike Stump11289f42009-09-09 15:08:12 +00002770
2771template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002772QualType TreeTransform<Derived>::TransformTypenameType(TypeLocBuilder &TLB,
2773 TypenameTypeLoc TL) {
2774 TypenameType *T = TL.getTypePtr();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002775 NestedNameSpecifier *NNS
2776 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
Douglas Gregor15acfb92009-08-06 16:20:37 +00002777 SourceRange(/*FIXME:*/getDerived().getBaseLocation()));
Douglas Gregord6ff3322009-08-04 16:50:30 +00002778 if (!NNS)
2779 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002780
John McCall550e0c22009-10-21 00:40:46 +00002781 QualType Result;
2782
Douglas Gregord6ff3322009-08-04 16:50:30 +00002783 if (const TemplateSpecializationType *TemplateId = T->getTemplateId()) {
Mike Stump11289f42009-09-09 15:08:12 +00002784 QualType NewTemplateId
Douglas Gregord6ff3322009-08-04 16:50:30 +00002785 = getDerived().TransformType(QualType(TemplateId, 0));
2786 if (NewTemplateId.isNull())
2787 return QualType();
Mike Stump11289f42009-09-09 15:08:12 +00002788
Douglas Gregord6ff3322009-08-04 16:50:30 +00002789 if (!getDerived().AlwaysRebuild() &&
2790 NNS == T->getQualifier() &&
2791 NewTemplateId == QualType(TemplateId, 0))
2792 return QualType(T, 0);
Mike Stump11289f42009-09-09 15:08:12 +00002793
John McCall550e0c22009-10-21 00:40:46 +00002794 Result = getDerived().RebuildTypenameType(NNS, NewTemplateId);
2795 } else {
2796 Result = getDerived().RebuildTypenameType(NNS, T->getIdentifier());
Douglas Gregord6ff3322009-08-04 16:50:30 +00002797 }
John McCall550e0c22009-10-21 00:40:46 +00002798 if (Result.isNull())
2799 return QualType();
Douglas Gregord6ff3322009-08-04 16:50:30 +00002800
John McCall550e0c22009-10-21 00:40:46 +00002801 TypenameTypeLoc NewTL = TLB.push<TypenameTypeLoc>(Result);
2802 NewTL.setNameLoc(TL.getNameLoc());
2803
2804 return Result;
Douglas Gregord6ff3322009-08-04 16:50:30 +00002805}
Mike Stump11289f42009-09-09 15:08:12 +00002806
Douglas Gregord6ff3322009-08-04 16:50:30 +00002807template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002808QualType
2809TreeTransform<Derived>::TransformObjCInterfaceType(TypeLocBuilder &TLB,
2810 ObjCInterfaceTypeLoc TL) {
2811 return TransformTypeSpecType(TLB, TL);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002812}
Mike Stump11289f42009-09-09 15:08:12 +00002813
2814template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00002815QualType
2816TreeTransform<Derived>::TransformObjCObjectPointerType(TypeLocBuilder &TLB,
2817 ObjCObjectPointerTypeLoc TL) {
2818 TransformPointerLikeType(ObjCObjectPointerType);
Douglas Gregord6ff3322009-08-04 16:50:30 +00002819}
2820
Argyrios Kyrtzidisa7a36df2009-09-29 19:42:55 +00002821template<typename Derived>
2822QualType TreeTransform<Derived>::TransformObjCProtocolListType(
John McCall550e0c22009-10-21 00:40:46 +00002823 TypeLocBuilder &TLB,
2824 ObjCProtocolListTypeLoc TL) {
2825 ObjCProtocolListType *T = TL.getTypePtr();
2826 QualType BaseType = T->getBaseType();
2827 if (!BaseType.isNull()) {
2828 BaseType = getDerived().TransformType(TLB, TL.getBaseTypeLoc());
2829 if (BaseType.isNull())
2830 return QualType();
2831 }
2832
2833 QualType Result = TL.getType();
2834 if (getDerived().AlwaysRebuild() ||
2835 BaseType != T->getBaseType()) {
2836 // TODO: transform these?
2837 llvm::SmallVector<ObjCProtocolDecl*,4> Protocols(T->getNumProtocols());
2838 std::copy(T->qual_begin(), T->qual_end(), Protocols.begin());
2839 Result = getDerived().RebuildObjCProtocolListType(BaseType,
2840 &Protocols[0],
2841 T->getNumProtocols());
2842 if (Result.isNull())
2843 return QualType();
2844 }
2845
2846 ObjCProtocolListTypeLoc NewTL = TLB.push<ObjCProtocolListTypeLoc>(Result);
2847 NewTL.setLAngleLoc(TL.getLAngleLoc());
2848 NewTL.setRAngleLoc(TL.getRAngleLoc());
2849
2850 assert(NewTL.getNumProtocols() == TL.getNumProtocols());
2851 for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
2852 NewTL.setProtocolLoc(i, TL.getProtocolLoc(i));
2853
2854 return Result;
Argyrios Kyrtzidisa7a36df2009-09-29 19:42:55 +00002855}
2856
Douglas Gregord6ff3322009-08-04 16:50:30 +00002857//===----------------------------------------------------------------------===//
Douglas Gregorebe10102009-08-20 07:17:43 +00002858// Statement transformation
2859//===----------------------------------------------------------------------===//
2860template<typename Derived>
2861Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002862TreeTransform<Derived>::TransformNullStmt(NullStmt *S) {
2863 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00002864}
2865
2866template<typename Derived>
2867Sema::OwningStmtResult
2868TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S) {
2869 return getDerived().TransformCompoundStmt(S, false);
2870}
2871
2872template<typename Derived>
2873Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002874TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S,
Douglas Gregorebe10102009-08-20 07:17:43 +00002875 bool IsStmtExpr) {
2876 bool SubStmtChanged = false;
2877 ASTOwningVector<&ActionBase::DeleteStmt> Statements(getSema());
2878 for (CompoundStmt::body_iterator B = S->body_begin(), BEnd = S->body_end();
2879 B != BEnd; ++B) {
2880 OwningStmtResult Result = getDerived().TransformStmt(*B);
2881 if (Result.isInvalid())
2882 return getSema().StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002883
Douglas Gregorebe10102009-08-20 07:17:43 +00002884 SubStmtChanged = SubStmtChanged || Result.get() != *B;
2885 Statements.push_back(Result.takeAs<Stmt>());
2886 }
Mike Stump11289f42009-09-09 15:08:12 +00002887
Douglas Gregorebe10102009-08-20 07:17:43 +00002888 if (!getDerived().AlwaysRebuild() &&
2889 !SubStmtChanged)
Mike Stump11289f42009-09-09 15:08:12 +00002890 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00002891
2892 return getDerived().RebuildCompoundStmt(S->getLBracLoc(),
2893 move_arg(Statements),
2894 S->getRBracLoc(),
2895 IsStmtExpr);
2896}
Mike Stump11289f42009-09-09 15:08:12 +00002897
Douglas Gregorebe10102009-08-20 07:17:43 +00002898template<typename Derived>
2899Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002900TreeTransform<Derived>::TransformCaseStmt(CaseStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002901 // The case value expressions are not potentially evaluated.
2902 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00002903
Douglas Gregorebe10102009-08-20 07:17:43 +00002904 // Transform the left-hand case value.
2905 OwningExprResult LHS = getDerived().TransformExpr(S->getLHS());
2906 if (LHS.isInvalid())
2907 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002908
Douglas Gregorebe10102009-08-20 07:17:43 +00002909 // Transform the right-hand case value (for the GNU case-range extension).
2910 OwningExprResult RHS = getDerived().TransformExpr(S->getRHS());
2911 if (RHS.isInvalid())
2912 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002913
Douglas Gregorebe10102009-08-20 07:17:43 +00002914 // Build the case statement.
2915 // Case statements are always rebuilt so that they will attached to their
2916 // transformed switch statement.
2917 OwningStmtResult Case = getDerived().RebuildCaseStmt(S->getCaseLoc(),
2918 move(LHS),
2919 S->getEllipsisLoc(),
2920 move(RHS),
2921 S->getColonLoc());
2922 if (Case.isInvalid())
2923 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002924
Douglas Gregorebe10102009-08-20 07:17:43 +00002925 // Transform the statement following the case
2926 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2927 if (SubStmt.isInvalid())
2928 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002929
Douglas Gregorebe10102009-08-20 07:17:43 +00002930 // Attach the body to the case statement
2931 return getDerived().RebuildCaseStmtBody(move(Case), move(SubStmt));
2932}
2933
2934template<typename Derived>
2935Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002936TreeTransform<Derived>::TransformDefaultStmt(DefaultStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002937 // Transform the statement following the default case
2938 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2939 if (SubStmt.isInvalid())
2940 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002941
Douglas Gregorebe10102009-08-20 07:17:43 +00002942 // Default statements are always rebuilt
2943 return getDerived().RebuildDefaultStmt(S->getDefaultLoc(), S->getColonLoc(),
2944 move(SubStmt));
2945}
Mike Stump11289f42009-09-09 15:08:12 +00002946
Douglas Gregorebe10102009-08-20 07:17:43 +00002947template<typename Derived>
2948Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002949TreeTransform<Derived>::TransformLabelStmt(LabelStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002950 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2951 if (SubStmt.isInvalid())
2952 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002953
Douglas Gregorebe10102009-08-20 07:17:43 +00002954 // FIXME: Pass the real colon location in.
2955 SourceLocation ColonLoc = SemaRef.PP.getLocForEndOfToken(S->getIdentLoc());
2956 return getDerived().RebuildLabelStmt(S->getIdentLoc(), S->getID(), ColonLoc,
2957 move(SubStmt));
2958}
Mike Stump11289f42009-09-09 15:08:12 +00002959
Douglas Gregorebe10102009-08-20 07:17:43 +00002960template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00002961Sema::OwningStmtResult
2962TreeTransform<Derived>::TransformIfStmt(IfStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002963 // Transform the condition
2964 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2965 if (Cond.isInvalid())
2966 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002967
Douglas Gregorebe10102009-08-20 07:17:43 +00002968 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
Mike Stump11289f42009-09-09 15:08:12 +00002969
Douglas Gregorebe10102009-08-20 07:17:43 +00002970 // Transform the "then" branch.
2971 OwningStmtResult Then = getDerived().TransformStmt(S->getThen());
2972 if (Then.isInvalid())
2973 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002974
Douglas Gregorebe10102009-08-20 07:17:43 +00002975 // Transform the "else" branch.
2976 OwningStmtResult Else = getDerived().TransformStmt(S->getElse());
2977 if (Else.isInvalid())
2978 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002979
Douglas Gregorebe10102009-08-20 07:17:43 +00002980 if (!getDerived().AlwaysRebuild() &&
2981 FullCond->get() == S->getCond() &&
2982 Then.get() == S->getThen() &&
2983 Else.get() == S->getElse())
Mike Stump11289f42009-09-09 15:08:12 +00002984 return SemaRef.Owned(S->Retain());
2985
Douglas Gregorebe10102009-08-20 07:17:43 +00002986 return getDerived().RebuildIfStmt(S->getIfLoc(), FullCond, move(Then),
Mike Stump11289f42009-09-09 15:08:12 +00002987 S->getElseLoc(), move(Else));
Douglas Gregorebe10102009-08-20 07:17:43 +00002988}
2989
2990template<typename Derived>
2991Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00002992TreeTransform<Derived>::TransformSwitchStmt(SwitchStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00002993 // Transform the condition.
2994 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2995 if (Cond.isInvalid())
2996 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00002997
Douglas Gregorebe10102009-08-20 07:17:43 +00002998 // Rebuild the switch statement.
2999 OwningStmtResult Switch = getDerived().RebuildSwitchStmtStart(move(Cond));
3000 if (Switch.isInvalid())
3001 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003002
Douglas Gregorebe10102009-08-20 07:17:43 +00003003 // Transform the body of the switch statement.
3004 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
3005 if (Body.isInvalid())
3006 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003007
Douglas Gregorebe10102009-08-20 07:17:43 +00003008 // Complete the switch statement.
3009 return getDerived().RebuildSwitchStmtBody(S->getSwitchLoc(), move(Switch),
3010 move(Body));
3011}
Mike Stump11289f42009-09-09 15:08:12 +00003012
Douglas Gregorebe10102009-08-20 07:17:43 +00003013template<typename Derived>
3014Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003015TreeTransform<Derived>::TransformWhileStmt(WhileStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003016 // Transform the condition
3017 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
3018 if (Cond.isInvalid())
3019 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003020
Douglas Gregorebe10102009-08-20 07:17:43 +00003021 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
Mike Stump11289f42009-09-09 15:08:12 +00003022
Douglas Gregorebe10102009-08-20 07:17:43 +00003023 // Transform the body
3024 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
3025 if (Body.isInvalid())
3026 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003027
Douglas Gregorebe10102009-08-20 07:17:43 +00003028 if (!getDerived().AlwaysRebuild() &&
3029 FullCond->get() == S->getCond() &&
3030 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00003031 return SemaRef.Owned(S->Retain());
3032
Douglas Gregorebe10102009-08-20 07:17:43 +00003033 return getDerived().RebuildWhileStmt(S->getWhileLoc(), FullCond, move(Body));
3034}
Mike Stump11289f42009-09-09 15:08:12 +00003035
Douglas Gregorebe10102009-08-20 07:17:43 +00003036template<typename Derived>
3037Sema::OwningStmtResult
3038TreeTransform<Derived>::TransformDoStmt(DoStmt *S) {
3039 // Transform the condition
3040 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
3041 if (Cond.isInvalid())
3042 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003043
Douglas Gregorebe10102009-08-20 07:17:43 +00003044 // Transform the body
3045 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
3046 if (Body.isInvalid())
3047 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003048
Douglas Gregorebe10102009-08-20 07:17:43 +00003049 if (!getDerived().AlwaysRebuild() &&
3050 Cond.get() == S->getCond() &&
3051 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00003052 return SemaRef.Owned(S->Retain());
3053
Douglas Gregorebe10102009-08-20 07:17:43 +00003054 return getDerived().RebuildDoStmt(S->getDoLoc(), move(Body), S->getWhileLoc(),
3055 /*FIXME:*/S->getWhileLoc(), move(Cond),
3056 S->getRParenLoc());
3057}
Mike Stump11289f42009-09-09 15:08:12 +00003058
Douglas Gregorebe10102009-08-20 07:17:43 +00003059template<typename Derived>
3060Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003061TreeTransform<Derived>::TransformForStmt(ForStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003062 // Transform the initialization statement
3063 OwningStmtResult Init = getDerived().TransformStmt(S->getInit());
3064 if (Init.isInvalid())
3065 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003066
Douglas Gregorebe10102009-08-20 07:17:43 +00003067 // Transform the condition
3068 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
3069 if (Cond.isInvalid())
3070 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003071
Douglas Gregorebe10102009-08-20 07:17:43 +00003072 // Transform the increment
3073 OwningExprResult Inc = getDerived().TransformExpr(S->getInc());
3074 if (Inc.isInvalid())
3075 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003076
Douglas Gregorebe10102009-08-20 07:17:43 +00003077 // Transform the body
3078 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
3079 if (Body.isInvalid())
3080 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003081
Douglas Gregorebe10102009-08-20 07:17:43 +00003082 if (!getDerived().AlwaysRebuild() &&
3083 Init.get() == S->getInit() &&
3084 Cond.get() == S->getCond() &&
3085 Inc.get() == S->getInc() &&
3086 Body.get() == S->getBody())
Mike Stump11289f42009-09-09 15:08:12 +00003087 return SemaRef.Owned(S->Retain());
3088
Douglas Gregorebe10102009-08-20 07:17:43 +00003089 return getDerived().RebuildForStmt(S->getForLoc(), S->getLParenLoc(),
3090 move(Init), move(Cond), move(Inc),
3091 S->getRParenLoc(), move(Body));
3092}
3093
3094template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003095Sema::OwningStmtResult
3096TreeTransform<Derived>::TransformGotoStmt(GotoStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003097 // Goto statements must always be rebuilt, to resolve the label.
Mike Stump11289f42009-09-09 15:08:12 +00003098 return getDerived().RebuildGotoStmt(S->getGotoLoc(), S->getLabelLoc(),
Douglas Gregorebe10102009-08-20 07:17:43 +00003099 S->getLabel());
3100}
3101
3102template<typename Derived>
3103Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003104TreeTransform<Derived>::TransformIndirectGotoStmt(IndirectGotoStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003105 OwningExprResult Target = getDerived().TransformExpr(S->getTarget());
3106 if (Target.isInvalid())
3107 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003108
Douglas Gregorebe10102009-08-20 07:17:43 +00003109 if (!getDerived().AlwaysRebuild() &&
3110 Target.get() == S->getTarget())
Mike Stump11289f42009-09-09 15:08:12 +00003111 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003112
3113 return getDerived().RebuildIndirectGotoStmt(S->getGotoLoc(), S->getStarLoc(),
3114 move(Target));
3115}
3116
3117template<typename Derived>
3118Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003119TreeTransform<Derived>::TransformContinueStmt(ContinueStmt *S) {
3120 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003121}
Mike Stump11289f42009-09-09 15:08:12 +00003122
Douglas Gregorebe10102009-08-20 07:17:43 +00003123template<typename Derived>
3124Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003125TreeTransform<Derived>::TransformBreakStmt(BreakStmt *S) {
3126 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003127}
Mike Stump11289f42009-09-09 15:08:12 +00003128
Douglas Gregorebe10102009-08-20 07:17:43 +00003129template<typename Derived>
3130Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003131TreeTransform<Derived>::TransformReturnStmt(ReturnStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003132 Sema::OwningExprResult Result = getDerived().TransformExpr(S->getRetValue());
3133 if (Result.isInvalid())
3134 return SemaRef.StmtError();
3135
Mike Stump11289f42009-09-09 15:08:12 +00003136 // FIXME: We always rebuild the return statement because there is no way
Douglas Gregorebe10102009-08-20 07:17:43 +00003137 // to tell whether the return type of the function has changed.
3138 return getDerived().RebuildReturnStmt(S->getReturnLoc(), move(Result));
3139}
Mike Stump11289f42009-09-09 15:08:12 +00003140
Douglas Gregorebe10102009-08-20 07:17:43 +00003141template<typename Derived>
3142Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003143TreeTransform<Derived>::TransformDeclStmt(DeclStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003144 bool DeclChanged = false;
3145 llvm::SmallVector<Decl *, 4> Decls;
3146 for (DeclStmt::decl_iterator D = S->decl_begin(), DEnd = S->decl_end();
3147 D != DEnd; ++D) {
3148 Decl *Transformed = getDerived().TransformDefinition(*D);
3149 if (!Transformed)
3150 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003151
Douglas Gregorebe10102009-08-20 07:17:43 +00003152 if (Transformed != *D)
3153 DeclChanged = true;
Mike Stump11289f42009-09-09 15:08:12 +00003154
Douglas Gregorebe10102009-08-20 07:17:43 +00003155 Decls.push_back(Transformed);
3156 }
Mike Stump11289f42009-09-09 15:08:12 +00003157
Douglas Gregorebe10102009-08-20 07:17:43 +00003158 if (!getDerived().AlwaysRebuild() && !DeclChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003159 return SemaRef.Owned(S->Retain());
3160
3161 return getDerived().RebuildDeclStmt(Decls.data(), Decls.size(),
Douglas Gregorebe10102009-08-20 07:17:43 +00003162 S->getStartLoc(), S->getEndLoc());
3163}
Mike Stump11289f42009-09-09 15:08:12 +00003164
Douglas Gregorebe10102009-08-20 07:17:43 +00003165template<typename Derived>
3166Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003167TreeTransform<Derived>::TransformSwitchCase(SwitchCase *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003168 assert(false && "SwitchCase is abstract and cannot be transformed");
Mike Stump11289f42009-09-09 15:08:12 +00003169 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003170}
3171
3172template<typename Derived>
3173Sema::OwningStmtResult
3174TreeTransform<Derived>::TransformAsmStmt(AsmStmt *S) {
3175 // FIXME: Implement!
3176 assert(false && "Inline assembly cannot be transformed");
Mike Stump11289f42009-09-09 15:08:12 +00003177 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003178}
3179
3180
3181template<typename Derived>
3182Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003183TreeTransform<Derived>::TransformObjCAtTryStmt(ObjCAtTryStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003184 // FIXME: Implement this
3185 assert(false && "Cannot transform an Objective-C @try statement");
Mike Stump11289f42009-09-09 15:08:12 +00003186 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003187}
Mike Stump11289f42009-09-09 15:08:12 +00003188
Douglas Gregorebe10102009-08-20 07:17:43 +00003189template<typename Derived>
3190Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003191TreeTransform<Derived>::TransformObjCAtCatchStmt(ObjCAtCatchStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003192 // FIXME: Implement this
3193 assert(false && "Cannot transform an Objective-C @catch statement");
3194 return SemaRef.Owned(S->Retain());
3195}
Mike Stump11289f42009-09-09 15:08:12 +00003196
Douglas Gregorebe10102009-08-20 07:17:43 +00003197template<typename Derived>
3198Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003199TreeTransform<Derived>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003200 // FIXME: Implement this
3201 assert(false && "Cannot transform an Objective-C @finally statement");
Mike Stump11289f42009-09-09 15:08:12 +00003202 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003203}
Mike Stump11289f42009-09-09 15:08:12 +00003204
Douglas Gregorebe10102009-08-20 07:17:43 +00003205template<typename Derived>
3206Sema::OwningStmtResult
Mike Stump11289f42009-09-09 15:08:12 +00003207TreeTransform<Derived>::TransformObjCAtThrowStmt(ObjCAtThrowStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003208 // FIXME: Implement this
3209 assert(false && "Cannot transform an Objective-C @throw statement");
Mike Stump11289f42009-09-09 15:08:12 +00003210 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003211}
Mike Stump11289f42009-09-09 15:08:12 +00003212
Douglas Gregorebe10102009-08-20 07:17:43 +00003213template<typename Derived>
3214Sema::OwningStmtResult
3215TreeTransform<Derived>::TransformObjCAtSynchronizedStmt(
Mike Stump11289f42009-09-09 15:08:12 +00003216 ObjCAtSynchronizedStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003217 // FIXME: Implement this
3218 assert(false && "Cannot transform an Objective-C @synchronized statement");
Mike Stump11289f42009-09-09 15:08:12 +00003219 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003220}
3221
3222template<typename Derived>
3223Sema::OwningStmtResult
3224TreeTransform<Derived>::TransformObjCForCollectionStmt(
Mike Stump11289f42009-09-09 15:08:12 +00003225 ObjCForCollectionStmt *S) {
Douglas Gregorebe10102009-08-20 07:17:43 +00003226 // FIXME: Implement this
3227 assert(false && "Cannot transform an Objective-C for-each statement");
Mike Stump11289f42009-09-09 15:08:12 +00003228 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003229}
3230
3231
3232template<typename Derived>
3233Sema::OwningStmtResult
3234TreeTransform<Derived>::TransformCXXCatchStmt(CXXCatchStmt *S) {
3235 // Transform the exception declaration, if any.
3236 VarDecl *Var = 0;
3237 if (S->getExceptionDecl()) {
3238 VarDecl *ExceptionDecl = S->getExceptionDecl();
3239 TemporaryBase Rebase(*this, ExceptionDecl->getLocation(),
3240 ExceptionDecl->getDeclName());
3241
3242 QualType T = getDerived().TransformType(ExceptionDecl->getType());
3243 if (T.isNull())
3244 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003245
Douglas Gregorebe10102009-08-20 07:17:43 +00003246 Var = getDerived().RebuildExceptionDecl(ExceptionDecl,
3247 T,
3248 ExceptionDecl->getDeclaratorInfo(),
3249 ExceptionDecl->getIdentifier(),
3250 ExceptionDecl->getLocation(),
3251 /*FIXME: Inaccurate*/
3252 SourceRange(ExceptionDecl->getLocation()));
3253 if (!Var || Var->isInvalidDecl()) {
3254 if (Var)
3255 Var->Destroy(SemaRef.Context);
3256 return SemaRef.StmtError();
3257 }
3258 }
Mike Stump11289f42009-09-09 15:08:12 +00003259
Douglas Gregorebe10102009-08-20 07:17:43 +00003260 // Transform the actual exception handler.
3261 OwningStmtResult Handler = getDerived().TransformStmt(S->getHandlerBlock());
3262 if (Handler.isInvalid()) {
3263 if (Var)
3264 Var->Destroy(SemaRef.Context);
3265 return SemaRef.StmtError();
3266 }
Mike Stump11289f42009-09-09 15:08:12 +00003267
Douglas Gregorebe10102009-08-20 07:17:43 +00003268 if (!getDerived().AlwaysRebuild() &&
3269 !Var &&
3270 Handler.get() == S->getHandlerBlock())
Mike Stump11289f42009-09-09 15:08:12 +00003271 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003272
3273 return getDerived().RebuildCXXCatchStmt(S->getCatchLoc(),
3274 Var,
3275 move(Handler));
3276}
Mike Stump11289f42009-09-09 15:08:12 +00003277
Douglas Gregorebe10102009-08-20 07:17:43 +00003278template<typename Derived>
3279Sema::OwningStmtResult
3280TreeTransform<Derived>::TransformCXXTryStmt(CXXTryStmt *S) {
3281 // Transform the try block itself.
Mike Stump11289f42009-09-09 15:08:12 +00003282 OwningStmtResult TryBlock
Douglas Gregorebe10102009-08-20 07:17:43 +00003283 = getDerived().TransformCompoundStmt(S->getTryBlock());
3284 if (TryBlock.isInvalid())
3285 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003286
Douglas Gregorebe10102009-08-20 07:17:43 +00003287 // Transform the handlers.
3288 bool HandlerChanged = false;
3289 ASTOwningVector<&ActionBase::DeleteStmt> Handlers(SemaRef);
3290 for (unsigned I = 0, N = S->getNumHandlers(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00003291 OwningStmtResult Handler
Douglas Gregorebe10102009-08-20 07:17:43 +00003292 = getDerived().TransformCXXCatchStmt(S->getHandler(I));
3293 if (Handler.isInvalid())
3294 return SemaRef.StmtError();
Mike Stump11289f42009-09-09 15:08:12 +00003295
Douglas Gregorebe10102009-08-20 07:17:43 +00003296 HandlerChanged = HandlerChanged || Handler.get() != S->getHandler(I);
3297 Handlers.push_back(Handler.takeAs<Stmt>());
3298 }
Mike Stump11289f42009-09-09 15:08:12 +00003299
Douglas Gregorebe10102009-08-20 07:17:43 +00003300 if (!getDerived().AlwaysRebuild() &&
3301 TryBlock.get() == S->getTryBlock() &&
3302 !HandlerChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003303 return SemaRef.Owned(S->Retain());
Douglas Gregorebe10102009-08-20 07:17:43 +00003304
3305 return getDerived().RebuildCXXTryStmt(S->getTryLoc(), move(TryBlock),
Mike Stump11289f42009-09-09 15:08:12 +00003306 move_arg(Handlers));
Douglas Gregorebe10102009-08-20 07:17:43 +00003307}
Mike Stump11289f42009-09-09 15:08:12 +00003308
Douglas Gregorebe10102009-08-20 07:17:43 +00003309//===----------------------------------------------------------------------===//
Douglas Gregora16548e2009-08-11 05:31:07 +00003310// Expression transformation
3311//===----------------------------------------------------------------------===//
Mike Stump11289f42009-09-09 15:08:12 +00003312template<typename Derived>
3313Sema::OwningExprResult
3314TreeTransform<Derived>::TransformPredefinedExpr(PredefinedExpr *E) {
3315 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003316}
Mike Stump11289f42009-09-09 15:08:12 +00003317
3318template<typename Derived>
3319Sema::OwningExprResult
3320TreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) {
3321 NamedDecl *ND
Douglas Gregora16548e2009-08-11 05:31:07 +00003322 = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
3323 if (!ND)
3324 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003325
Douglas Gregora16548e2009-08-11 05:31:07 +00003326 if (!getDerived().AlwaysRebuild() && ND == E->getDecl())
Mike Stump11289f42009-09-09 15:08:12 +00003327 return SemaRef.Owned(E->Retain());
3328
Douglas Gregora16548e2009-08-11 05:31:07 +00003329 return getDerived().RebuildDeclRefExpr(ND, E->getLocation());
3330}
Mike Stump11289f42009-09-09 15:08:12 +00003331
Douglas Gregora16548e2009-08-11 05:31:07 +00003332template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003333Sema::OwningExprResult
3334TreeTransform<Derived>::TransformIntegerLiteral(IntegerLiteral *E) {
3335 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003336}
Mike Stump11289f42009-09-09 15:08:12 +00003337
Douglas Gregora16548e2009-08-11 05:31:07 +00003338template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003339Sema::OwningExprResult
3340TreeTransform<Derived>::TransformFloatingLiteral(FloatingLiteral *E) {
3341 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003342}
Mike Stump11289f42009-09-09 15:08:12 +00003343
Douglas Gregora16548e2009-08-11 05:31:07 +00003344template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003345Sema::OwningExprResult
3346TreeTransform<Derived>::TransformImaginaryLiteral(ImaginaryLiteral *E) {
3347 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003348}
Mike Stump11289f42009-09-09 15:08:12 +00003349
Douglas Gregora16548e2009-08-11 05:31:07 +00003350template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003351Sema::OwningExprResult
3352TreeTransform<Derived>::TransformStringLiteral(StringLiteral *E) {
3353 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003354}
Mike Stump11289f42009-09-09 15:08:12 +00003355
Douglas Gregora16548e2009-08-11 05:31:07 +00003356template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003357Sema::OwningExprResult
3358TreeTransform<Derived>::TransformCharacterLiteral(CharacterLiteral *E) {
3359 return SemaRef.Owned(E->Retain());
3360}
3361
3362template<typename Derived>
3363Sema::OwningExprResult
3364TreeTransform<Derived>::TransformParenExpr(ParenExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003365 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3366 if (SubExpr.isInvalid())
3367 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003368
Douglas Gregora16548e2009-08-11 05:31:07 +00003369 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003370 return SemaRef.Owned(E->Retain());
3371
3372 return getDerived().RebuildParenExpr(move(SubExpr), E->getLParen(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003373 E->getRParen());
3374}
3375
Mike Stump11289f42009-09-09 15:08:12 +00003376template<typename Derived>
3377Sema::OwningExprResult
3378TreeTransform<Derived>::TransformUnaryOperator(UnaryOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003379 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3380 if (SubExpr.isInvalid())
3381 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003382
Douglas Gregora16548e2009-08-11 05:31:07 +00003383 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003384 return SemaRef.Owned(E->Retain());
3385
Douglas Gregora16548e2009-08-11 05:31:07 +00003386 return getDerived().RebuildUnaryOperator(E->getOperatorLoc(),
3387 E->getOpcode(),
3388 move(SubExpr));
3389}
Mike Stump11289f42009-09-09 15:08:12 +00003390
Douglas Gregora16548e2009-08-11 05:31:07 +00003391template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003392Sema::OwningExprResult
3393TreeTransform<Derived>::TransformSizeOfAlignOfExpr(SizeOfAlignOfExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003394 if (E->isArgumentType()) {
3395 QualType T = getDerived().TransformType(E->getArgumentType());
3396 if (T.isNull())
3397 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003398
Douglas Gregora16548e2009-08-11 05:31:07 +00003399 if (!getDerived().AlwaysRebuild() && T == E->getArgumentType())
3400 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003401
3402 return getDerived().RebuildSizeOfAlignOf(T, E->getOperatorLoc(),
3403 E->isSizeOf(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003404 E->getSourceRange());
3405 }
Mike Stump11289f42009-09-09 15:08:12 +00003406
Douglas Gregora16548e2009-08-11 05:31:07 +00003407 Sema::OwningExprResult SubExpr(SemaRef);
Mike Stump11289f42009-09-09 15:08:12 +00003408 {
Douglas Gregora16548e2009-08-11 05:31:07 +00003409 // C++0x [expr.sizeof]p1:
3410 // The operand is either an expression, which is an unevaluated operand
3411 // [...]
3412 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
Mike Stump11289f42009-09-09 15:08:12 +00003413
Douglas Gregora16548e2009-08-11 05:31:07 +00003414 SubExpr = getDerived().TransformExpr(E->getArgumentExpr());
3415 if (SubExpr.isInvalid())
3416 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003417
Douglas Gregora16548e2009-08-11 05:31:07 +00003418 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr())
3419 return SemaRef.Owned(E->Retain());
3420 }
Mike Stump11289f42009-09-09 15:08:12 +00003421
Douglas Gregora16548e2009-08-11 05:31:07 +00003422 return getDerived().RebuildSizeOfAlignOf(move(SubExpr), E->getOperatorLoc(),
3423 E->isSizeOf(),
3424 E->getSourceRange());
3425}
Mike Stump11289f42009-09-09 15:08:12 +00003426
Douglas Gregora16548e2009-08-11 05:31:07 +00003427template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003428Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003429TreeTransform<Derived>::TransformArraySubscriptExpr(ArraySubscriptExpr *E) {
3430 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3431 if (LHS.isInvalid())
3432 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003433
Douglas Gregora16548e2009-08-11 05:31:07 +00003434 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3435 if (RHS.isInvalid())
3436 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003437
3438
Douglas Gregora16548e2009-08-11 05:31:07 +00003439 if (!getDerived().AlwaysRebuild() &&
3440 LHS.get() == E->getLHS() &&
3441 RHS.get() == E->getRHS())
3442 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003443
Douglas Gregora16548e2009-08-11 05:31:07 +00003444 return getDerived().RebuildArraySubscriptExpr(move(LHS),
3445 /*FIXME:*/E->getLHS()->getLocStart(),
3446 move(RHS),
3447 E->getRBracketLoc());
3448}
Mike Stump11289f42009-09-09 15:08:12 +00003449
3450template<typename Derived>
3451Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003452TreeTransform<Derived>::TransformCallExpr(CallExpr *E) {
3453 // Transform the callee.
3454 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
3455 if (Callee.isInvalid())
3456 return SemaRef.ExprError();
3457
3458 // Transform arguments.
3459 bool ArgChanged = false;
3460 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
3461 llvm::SmallVector<SourceLocation, 4> FakeCommaLocs;
3462 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) {
3463 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I));
3464 if (Arg.isInvalid())
3465 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003466
Douglas Gregora16548e2009-08-11 05:31:07 +00003467 // FIXME: Wrong source location information for the ','.
3468 FakeCommaLocs.push_back(
3469 SemaRef.PP.getLocForEndOfToken(E->getArg(I)->getSourceRange().getEnd()));
Mike Stump11289f42009-09-09 15:08:12 +00003470
3471 ArgChanged = ArgChanged || Arg.get() != E->getArg(I);
Douglas Gregora16548e2009-08-11 05:31:07 +00003472 Args.push_back(Arg.takeAs<Expr>());
3473 }
Mike Stump11289f42009-09-09 15:08:12 +00003474
Douglas Gregora16548e2009-08-11 05:31:07 +00003475 if (!getDerived().AlwaysRebuild() &&
3476 Callee.get() == E->getCallee() &&
3477 !ArgChanged)
3478 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003479
Douglas Gregora16548e2009-08-11 05:31:07 +00003480 // FIXME: Wrong source location information for the '('.
Mike Stump11289f42009-09-09 15:08:12 +00003481 SourceLocation FakeLParenLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003482 = ((Expr *)Callee.get())->getSourceRange().getBegin();
3483 return getDerived().RebuildCallExpr(move(Callee), FakeLParenLoc,
3484 move_arg(Args),
3485 FakeCommaLocs.data(),
3486 E->getRParenLoc());
3487}
Mike Stump11289f42009-09-09 15:08:12 +00003488
3489template<typename Derived>
3490Sema::OwningExprResult
3491TreeTransform<Derived>::TransformMemberExpr(MemberExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003492 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
3493 if (Base.isInvalid())
3494 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003495
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003496 NestedNameSpecifier *Qualifier = 0;
3497 if (E->hasQualifier()) {
Mike Stump11289f42009-09-09 15:08:12 +00003498 Qualifier
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003499 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
3500 E->getQualifierRange());
Douglas Gregor84f14dd2009-09-01 00:37:14 +00003501 if (Qualifier == 0)
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003502 return SemaRef.ExprError();
3503 }
Mike Stump11289f42009-09-09 15:08:12 +00003504
3505 NamedDecl *Member
Douglas Gregora16548e2009-08-11 05:31:07 +00003506 = cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getMemberDecl()));
3507 if (!Member)
3508 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003509
Douglas Gregora16548e2009-08-11 05:31:07 +00003510 if (!getDerived().AlwaysRebuild() &&
3511 Base.get() == E->getBase() &&
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003512 Qualifier == E->getQualifier() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00003513 Member == E->getMemberDecl())
Mike Stump11289f42009-09-09 15:08:12 +00003514 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003515
3516 // FIXME: Bogus source location for the operator
3517 SourceLocation FakeOperatorLoc
3518 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getSourceRange().getEnd());
3519
3520 return getDerived().RebuildMemberExpr(move(Base), FakeOperatorLoc,
3521 E->isArrow(),
Douglas Gregorf405d7e2009-08-31 23:41:50 +00003522 Qualifier,
3523 E->getQualifierRange(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003524 E->getMemberLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003525 Member);
Douglas Gregora16548e2009-08-11 05:31:07 +00003526}
Mike Stump11289f42009-09-09 15:08:12 +00003527
Douglas Gregora16548e2009-08-11 05:31:07 +00003528template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003529Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003530TreeTransform<Derived>::TransformCastExpr(CastExpr *E) {
3531 assert(false && "Cannot transform abstract class");
3532 return SemaRef.Owned(E->Retain());
3533}
3534
3535template<typename Derived>
3536Sema::OwningExprResult
3537TreeTransform<Derived>::TransformBinaryOperator(BinaryOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003538 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3539 if (LHS.isInvalid())
3540 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003541
Douglas Gregora16548e2009-08-11 05:31:07 +00003542 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3543 if (RHS.isInvalid())
3544 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003545
Douglas Gregora16548e2009-08-11 05:31:07 +00003546 if (!getDerived().AlwaysRebuild() &&
3547 LHS.get() == E->getLHS() &&
3548 RHS.get() == E->getRHS())
Mike Stump11289f42009-09-09 15:08:12 +00003549 return SemaRef.Owned(E->Retain());
3550
Douglas Gregora16548e2009-08-11 05:31:07 +00003551 return getDerived().RebuildBinaryOperator(E->getOperatorLoc(), E->getOpcode(),
3552 move(LHS), move(RHS));
3553}
3554
Mike Stump11289f42009-09-09 15:08:12 +00003555template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003556Sema::OwningExprResult
3557TreeTransform<Derived>::TransformCompoundAssignOperator(
3558 CompoundAssignOperator *E) {
3559 return getDerived().TransformBinaryOperator(E);
3560}
Mike Stump11289f42009-09-09 15:08:12 +00003561
Douglas Gregora16548e2009-08-11 05:31:07 +00003562template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003563Sema::OwningExprResult
3564TreeTransform<Derived>::TransformConditionalOperator(ConditionalOperator *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003565 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3566 if (Cond.isInvalid())
3567 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003568
Douglas Gregora16548e2009-08-11 05:31:07 +00003569 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3570 if (LHS.isInvalid())
3571 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003572
Douglas Gregora16548e2009-08-11 05:31:07 +00003573 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3574 if (RHS.isInvalid())
3575 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003576
Douglas Gregora16548e2009-08-11 05:31:07 +00003577 if (!getDerived().AlwaysRebuild() &&
3578 Cond.get() == E->getCond() &&
3579 LHS.get() == E->getLHS() &&
3580 RHS.get() == E->getRHS())
3581 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003582
3583 return getDerived().RebuildConditionalOperator(move(Cond),
Douglas Gregor7e112b02009-08-26 14:37:04 +00003584 E->getQuestionLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003585 move(LHS),
Douglas Gregor7e112b02009-08-26 14:37:04 +00003586 E->getColonLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003587 move(RHS));
3588}
Mike Stump11289f42009-09-09 15:08:12 +00003589
3590template<typename Derived>
3591Sema::OwningExprResult
3592TreeTransform<Derived>::TransformImplicitCastExpr(ImplicitCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003593 QualType T = getDerived().TransformType(E->getType());
3594 if (T.isNull())
3595 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003596
Douglas Gregora16548e2009-08-11 05:31:07 +00003597 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3598 if (SubExpr.isInvalid())
3599 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003600
Douglas Gregora16548e2009-08-11 05:31:07 +00003601 if (!getDerived().AlwaysRebuild() &&
3602 T == E->getType() &&
3603 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003604 return SemaRef.Owned(E->Retain());
3605
Douglas Gregora16548e2009-08-11 05:31:07 +00003606 return getDerived().RebuildImplicitCastExpr(T, E->getCastKind(),
Mike Stump11289f42009-09-09 15:08:12 +00003607 move(SubExpr),
Douglas Gregora16548e2009-08-11 05:31:07 +00003608 E->isLvalueCast());
3609}
Mike Stump11289f42009-09-09 15:08:12 +00003610
Douglas Gregora16548e2009-08-11 05:31:07 +00003611template<typename Derived>
3612Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003613TreeTransform<Derived>::TransformExplicitCastExpr(ExplicitCastExpr *E) {
3614 assert(false && "Cannot transform abstract class");
3615 return SemaRef.Owned(E->Retain());
3616}
3617
3618template<typename Derived>
3619Sema::OwningExprResult
3620TreeTransform<Derived>::TransformCStyleCastExpr(CStyleCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003621 QualType T;
3622 {
3623 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003624 SourceLocation TypeStartLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003625 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3626 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003627
Douglas Gregora16548e2009-08-11 05:31:07 +00003628 T = getDerived().TransformType(E->getTypeAsWritten());
3629 if (T.isNull())
3630 return SemaRef.ExprError();
3631 }
Mike Stump11289f42009-09-09 15:08:12 +00003632
Douglas Gregora16548e2009-08-11 05:31:07 +00003633 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3634 if (SubExpr.isInvalid())
3635 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003636
Douglas Gregora16548e2009-08-11 05:31:07 +00003637 if (!getDerived().AlwaysRebuild() &&
3638 T == E->getTypeAsWritten() &&
3639 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003640 return SemaRef.Owned(E->Retain());
3641
Douglas Gregora16548e2009-08-11 05:31:07 +00003642 return getDerived().RebuildCStyleCaseExpr(E->getLParenLoc(), T,
3643 E->getRParenLoc(),
3644 move(SubExpr));
3645}
Mike Stump11289f42009-09-09 15:08:12 +00003646
Douglas Gregora16548e2009-08-11 05:31:07 +00003647template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003648Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003649TreeTransform<Derived>::TransformCompoundLiteralExpr(CompoundLiteralExpr *E) {
3650 QualType T;
3651 {
3652 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003653 SourceLocation FakeTypeLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003654 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3655 TemporaryBase Rebase(*this, FakeTypeLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003656
Douglas Gregora16548e2009-08-11 05:31:07 +00003657 T = getDerived().TransformType(E->getType());
3658 if (T.isNull())
3659 return SemaRef.ExprError();
3660 }
Mike Stump11289f42009-09-09 15:08:12 +00003661
Douglas Gregora16548e2009-08-11 05:31:07 +00003662 OwningExprResult Init = getDerived().TransformExpr(E->getInitializer());
3663 if (Init.isInvalid())
3664 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003665
Douglas Gregora16548e2009-08-11 05:31:07 +00003666 if (!getDerived().AlwaysRebuild() &&
3667 T == E->getType() &&
3668 Init.get() == E->getInitializer())
Mike Stump11289f42009-09-09 15:08:12 +00003669 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003670
3671 return getDerived().RebuildCompoundLiteralExpr(E->getLParenLoc(), T,
3672 /*FIXME:*/E->getInitializer()->getLocEnd(),
3673 move(Init));
3674}
Mike Stump11289f42009-09-09 15:08:12 +00003675
Douglas Gregora16548e2009-08-11 05:31:07 +00003676template<typename Derived>
3677Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003678TreeTransform<Derived>::TransformExtVectorElementExpr(ExtVectorElementExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003679 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
3680 if (Base.isInvalid())
3681 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003682
Douglas Gregora16548e2009-08-11 05:31:07 +00003683 if (!getDerived().AlwaysRebuild() &&
3684 Base.get() == E->getBase())
Mike Stump11289f42009-09-09 15:08:12 +00003685 return SemaRef.Owned(E->Retain());
3686
Douglas Gregora16548e2009-08-11 05:31:07 +00003687 // FIXME: Bad source location
Mike Stump11289f42009-09-09 15:08:12 +00003688 SourceLocation FakeOperatorLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003689 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getLocEnd());
3690 return getDerived().RebuildExtVectorElementExpr(move(Base), FakeOperatorLoc,
3691 E->getAccessorLoc(),
3692 E->getAccessor());
3693}
Mike Stump11289f42009-09-09 15:08:12 +00003694
Douglas Gregora16548e2009-08-11 05:31:07 +00003695template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003696Sema::OwningExprResult
3697TreeTransform<Derived>::TransformInitListExpr(InitListExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003698 bool InitChanged = false;
Mike Stump11289f42009-09-09 15:08:12 +00003699
Douglas Gregora16548e2009-08-11 05:31:07 +00003700 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3701 for (unsigned I = 0, N = E->getNumInits(); I != N; ++I) {
3702 OwningExprResult Init = getDerived().TransformExpr(E->getInit(I));
3703 if (Init.isInvalid())
3704 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003705
Douglas Gregora16548e2009-08-11 05:31:07 +00003706 InitChanged = InitChanged || Init.get() != E->getInit(I);
3707 Inits.push_back(Init.takeAs<Expr>());
3708 }
Mike Stump11289f42009-09-09 15:08:12 +00003709
Douglas Gregora16548e2009-08-11 05:31:07 +00003710 if (!getDerived().AlwaysRebuild() && !InitChanged)
Mike Stump11289f42009-09-09 15:08:12 +00003711 return SemaRef.Owned(E->Retain());
3712
Douglas Gregora16548e2009-08-11 05:31:07 +00003713 return getDerived().RebuildInitList(E->getLBraceLoc(), move_arg(Inits),
3714 E->getRBraceLoc());
3715}
Mike Stump11289f42009-09-09 15:08:12 +00003716
Douglas Gregora16548e2009-08-11 05:31:07 +00003717template<typename Derived>
3718Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003719TreeTransform<Derived>::TransformDesignatedInitExpr(DesignatedInitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003720 Designation Desig;
Mike Stump11289f42009-09-09 15:08:12 +00003721
Douglas Gregorebe10102009-08-20 07:17:43 +00003722 // transform the initializer value
Douglas Gregora16548e2009-08-11 05:31:07 +00003723 OwningExprResult Init = getDerived().TransformExpr(E->getInit());
3724 if (Init.isInvalid())
3725 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003726
Douglas Gregorebe10102009-08-20 07:17:43 +00003727 // transform the designators.
Douglas Gregora16548e2009-08-11 05:31:07 +00003728 ASTOwningVector<&ActionBase::DeleteExpr, 4> ArrayExprs(SemaRef);
3729 bool ExprChanged = false;
3730 for (DesignatedInitExpr::designators_iterator D = E->designators_begin(),
3731 DEnd = E->designators_end();
3732 D != DEnd; ++D) {
3733 if (D->isFieldDesignator()) {
3734 Desig.AddDesignator(Designator::getField(D->getFieldName(),
3735 D->getDotLoc(),
3736 D->getFieldLoc()));
3737 continue;
3738 }
Mike Stump11289f42009-09-09 15:08:12 +00003739
Douglas Gregora16548e2009-08-11 05:31:07 +00003740 if (D->isArrayDesignator()) {
3741 OwningExprResult Index = getDerived().TransformExpr(E->getArrayIndex(*D));
3742 if (Index.isInvalid())
3743 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003744
3745 Desig.AddDesignator(Designator::getArray(Index.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003746 D->getLBracketLoc()));
Mike Stump11289f42009-09-09 15:08:12 +00003747
Douglas Gregora16548e2009-08-11 05:31:07 +00003748 ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(*D);
3749 ArrayExprs.push_back(Index.release());
3750 continue;
3751 }
Mike Stump11289f42009-09-09 15:08:12 +00003752
Douglas Gregora16548e2009-08-11 05:31:07 +00003753 assert(D->isArrayRangeDesignator() && "New kind of designator?");
Mike Stump11289f42009-09-09 15:08:12 +00003754 OwningExprResult Start
Douglas Gregora16548e2009-08-11 05:31:07 +00003755 = getDerived().TransformExpr(E->getArrayRangeStart(*D));
3756 if (Start.isInvalid())
3757 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003758
Douglas Gregora16548e2009-08-11 05:31:07 +00003759 OwningExprResult End = getDerived().TransformExpr(E->getArrayRangeEnd(*D));
3760 if (End.isInvalid())
3761 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003762
3763 Desig.AddDesignator(Designator::getArrayRange(Start.get(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003764 End.get(),
3765 D->getLBracketLoc(),
3766 D->getEllipsisLoc()));
Mike Stump11289f42009-09-09 15:08:12 +00003767
Douglas Gregora16548e2009-08-11 05:31:07 +00003768 ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(*D) ||
3769 End.get() != E->getArrayRangeEnd(*D);
Mike Stump11289f42009-09-09 15:08:12 +00003770
Douglas Gregora16548e2009-08-11 05:31:07 +00003771 ArrayExprs.push_back(Start.release());
3772 ArrayExprs.push_back(End.release());
3773 }
Mike Stump11289f42009-09-09 15:08:12 +00003774
Douglas Gregora16548e2009-08-11 05:31:07 +00003775 if (!getDerived().AlwaysRebuild() &&
3776 Init.get() == E->getInit() &&
3777 !ExprChanged)
3778 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003779
Douglas Gregora16548e2009-08-11 05:31:07 +00003780 return getDerived().RebuildDesignatedInitExpr(Desig, move_arg(ArrayExprs),
3781 E->getEqualOrColonLoc(),
3782 E->usesGNUSyntax(), move(Init));
3783}
Mike Stump11289f42009-09-09 15:08:12 +00003784
Douglas Gregora16548e2009-08-11 05:31:07 +00003785template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003786Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003787TreeTransform<Derived>::TransformImplicitValueInitExpr(
Mike Stump11289f42009-09-09 15:08:12 +00003788 ImplicitValueInitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003789 QualType T = getDerived().TransformType(E->getType());
3790 if (T.isNull())
3791 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003792
Douglas Gregora16548e2009-08-11 05:31:07 +00003793 if (!getDerived().AlwaysRebuild() &&
3794 T == E->getType())
Mike Stump11289f42009-09-09 15:08:12 +00003795 return SemaRef.Owned(E->Retain());
3796
Douglas Gregora16548e2009-08-11 05:31:07 +00003797 return getDerived().RebuildImplicitValueInitExpr(T);
3798}
Mike Stump11289f42009-09-09 15:08:12 +00003799
Douglas Gregora16548e2009-08-11 05:31:07 +00003800template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003801Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003802TreeTransform<Derived>::TransformVAArgExpr(VAArgExpr *E) {
3803 // FIXME: Do we want the type as written?
3804 QualType T;
Mike Stump11289f42009-09-09 15:08:12 +00003805
Douglas Gregora16548e2009-08-11 05:31:07 +00003806 {
3807 // FIXME: Source location isn't quite accurate.
3808 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
3809 T = getDerived().TransformType(E->getType());
3810 if (T.isNull())
3811 return SemaRef.ExprError();
3812 }
Mike Stump11289f42009-09-09 15:08:12 +00003813
Douglas Gregora16548e2009-08-11 05:31:07 +00003814 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3815 if (SubExpr.isInvalid())
3816 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003817
Douglas Gregora16548e2009-08-11 05:31:07 +00003818 if (!getDerived().AlwaysRebuild() &&
3819 T == E->getType() &&
3820 SubExpr.get() == E->getSubExpr())
3821 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003822
Douglas Gregora16548e2009-08-11 05:31:07 +00003823 return getDerived().RebuildVAArgExpr(E->getBuiltinLoc(), move(SubExpr),
3824 T, E->getRParenLoc());
3825}
3826
3827template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003828Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003829TreeTransform<Derived>::TransformParenListExpr(ParenListExpr *E) {
3830 bool ArgumentChanged = false;
3831 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3832 for (unsigned I = 0, N = E->getNumExprs(); I != N; ++I) {
3833 OwningExprResult Init = getDerived().TransformExpr(E->getExpr(I));
3834 if (Init.isInvalid())
3835 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003836
Douglas Gregora16548e2009-08-11 05:31:07 +00003837 ArgumentChanged = ArgumentChanged || Init.get() != E->getExpr(I);
3838 Inits.push_back(Init.takeAs<Expr>());
3839 }
Mike Stump11289f42009-09-09 15:08:12 +00003840
Douglas Gregora16548e2009-08-11 05:31:07 +00003841 return getDerived().RebuildParenListExpr(E->getLParenLoc(),
3842 move_arg(Inits),
3843 E->getRParenLoc());
3844}
Mike Stump11289f42009-09-09 15:08:12 +00003845
Douglas Gregora16548e2009-08-11 05:31:07 +00003846/// \brief Transform an address-of-label expression.
3847///
3848/// By default, the transformation of an address-of-label expression always
3849/// rebuilds the expression, so that the label identifier can be resolved to
3850/// the corresponding label statement by semantic analysis.
3851template<typename Derived>
3852Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003853TreeTransform<Derived>::TransformAddrLabelExpr(AddrLabelExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003854 return getDerived().RebuildAddrLabelExpr(E->getAmpAmpLoc(), E->getLabelLoc(),
3855 E->getLabel());
3856}
Mike Stump11289f42009-09-09 15:08:12 +00003857
3858template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00003859Sema::OwningExprResult TreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) {
Mike Stump11289f42009-09-09 15:08:12 +00003860 OwningStmtResult SubStmt
Douglas Gregora16548e2009-08-11 05:31:07 +00003861 = getDerived().TransformCompoundStmt(E->getSubStmt(), true);
3862 if (SubStmt.isInvalid())
3863 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003864
Douglas Gregora16548e2009-08-11 05:31:07 +00003865 if (!getDerived().AlwaysRebuild() &&
3866 SubStmt.get() == E->getSubStmt())
3867 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00003868
3869 return getDerived().RebuildStmtExpr(E->getLParenLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00003870 move(SubStmt),
3871 E->getRParenLoc());
3872}
Mike Stump11289f42009-09-09 15:08:12 +00003873
Douglas Gregora16548e2009-08-11 05:31:07 +00003874template<typename Derived>
3875Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003876TreeTransform<Derived>::TransformTypesCompatibleExpr(TypesCompatibleExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003877 QualType T1, T2;
3878 {
3879 // FIXME: Source location isn't quite accurate.
3880 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003881
Douglas Gregora16548e2009-08-11 05:31:07 +00003882 T1 = getDerived().TransformType(E->getArgType1());
3883 if (T1.isNull())
3884 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003885
Douglas Gregora16548e2009-08-11 05:31:07 +00003886 T2 = getDerived().TransformType(E->getArgType2());
3887 if (T2.isNull())
3888 return SemaRef.ExprError();
3889 }
3890
3891 if (!getDerived().AlwaysRebuild() &&
3892 T1 == E->getArgType1() &&
3893 T2 == E->getArgType2())
Mike Stump11289f42009-09-09 15:08:12 +00003894 return SemaRef.Owned(E->Retain());
3895
Douglas Gregora16548e2009-08-11 05:31:07 +00003896 return getDerived().RebuildTypesCompatibleExpr(E->getBuiltinLoc(),
3897 T1, T2, E->getRParenLoc());
3898}
Mike Stump11289f42009-09-09 15:08:12 +00003899
Douglas Gregora16548e2009-08-11 05:31:07 +00003900template<typename Derived>
3901Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003902TreeTransform<Derived>::TransformChooseExpr(ChooseExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003903 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3904 if (Cond.isInvalid())
3905 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003906
Douglas Gregora16548e2009-08-11 05:31:07 +00003907 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3908 if (LHS.isInvalid())
3909 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003910
Douglas Gregora16548e2009-08-11 05:31:07 +00003911 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3912 if (RHS.isInvalid())
3913 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003914
Douglas Gregora16548e2009-08-11 05:31:07 +00003915 if (!getDerived().AlwaysRebuild() &&
3916 Cond.get() == E->getCond() &&
3917 LHS.get() == E->getLHS() &&
3918 RHS.get() == E->getRHS())
Mike Stump11289f42009-09-09 15:08:12 +00003919 return SemaRef.Owned(E->Retain());
3920
Douglas Gregora16548e2009-08-11 05:31:07 +00003921 return getDerived().RebuildChooseExpr(E->getBuiltinLoc(),
3922 move(Cond), move(LHS), move(RHS),
3923 E->getRParenLoc());
3924}
Mike Stump11289f42009-09-09 15:08:12 +00003925
Douglas Gregora16548e2009-08-11 05:31:07 +00003926template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003927Sema::OwningExprResult
3928TreeTransform<Derived>::TransformGNUNullExpr(GNUNullExpr *E) {
3929 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00003930}
3931
3932template<typename Derived>
3933Sema::OwningExprResult
3934TreeTransform<Derived>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr *E) {
3935 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
3936 if (Callee.isInvalid())
3937 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003938
Douglas Gregora16548e2009-08-11 05:31:07 +00003939 OwningExprResult First = getDerived().TransformExpr(E->getArg(0));
3940 if (First.isInvalid())
3941 return SemaRef.ExprError();
3942
3943 OwningExprResult Second(SemaRef);
3944 if (E->getNumArgs() == 2) {
3945 Second = getDerived().TransformExpr(E->getArg(1));
3946 if (Second.isInvalid())
3947 return SemaRef.ExprError();
3948 }
Mike Stump11289f42009-09-09 15:08:12 +00003949
Douglas Gregora16548e2009-08-11 05:31:07 +00003950 if (!getDerived().AlwaysRebuild() &&
3951 Callee.get() == E->getCallee() &&
3952 First.get() == E->getArg(0) &&
Mike Stump11289f42009-09-09 15:08:12 +00003953 (E->getNumArgs() != 2 || Second.get() == E->getArg(1)))
3954 return SemaRef.Owned(E->Retain());
3955
Douglas Gregora16548e2009-08-11 05:31:07 +00003956 return getDerived().RebuildCXXOperatorCallExpr(E->getOperator(),
3957 E->getOperatorLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00003958 move(Callee),
Douglas Gregora16548e2009-08-11 05:31:07 +00003959 move(First),
3960 move(Second));
3961}
Mike Stump11289f42009-09-09 15:08:12 +00003962
Douglas Gregora16548e2009-08-11 05:31:07 +00003963template<typename Derived>
3964Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00003965TreeTransform<Derived>::TransformCXXMemberCallExpr(CXXMemberCallExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00003966 return getDerived().TransformCallExpr(E);
3967}
Mike Stump11289f42009-09-09 15:08:12 +00003968
Douglas Gregora16548e2009-08-11 05:31:07 +00003969template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00003970Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00003971TreeTransform<Derived>::TransformCXXNamedCastExpr(CXXNamedCastExpr *E) {
3972 QualType ExplicitTy;
3973 {
3974 // FIXME: Source location isn't quite accurate.
Mike Stump11289f42009-09-09 15:08:12 +00003975 SourceLocation TypeStartLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003976 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3977 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00003978
Douglas Gregora16548e2009-08-11 05:31:07 +00003979 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
3980 if (ExplicitTy.isNull())
3981 return SemaRef.ExprError();
3982 }
Mike Stump11289f42009-09-09 15:08:12 +00003983
Douglas Gregora16548e2009-08-11 05:31:07 +00003984 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3985 if (SubExpr.isInvalid())
3986 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00003987
Douglas Gregora16548e2009-08-11 05:31:07 +00003988 if (!getDerived().AlwaysRebuild() &&
3989 ExplicitTy == E->getTypeAsWritten() &&
3990 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00003991 return SemaRef.Owned(E->Retain());
3992
Douglas Gregora16548e2009-08-11 05:31:07 +00003993 // FIXME: Poor source location information here.
Mike Stump11289f42009-09-09 15:08:12 +00003994 SourceLocation FakeLAngleLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00003995 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3996 SourceLocation FakeRAngleLoc = E->getSubExpr()->getSourceRange().getBegin();
3997 SourceLocation FakeRParenLoc
3998 = SemaRef.PP.getLocForEndOfToken(
3999 E->getSubExpr()->getSourceRange().getEnd());
4000 return getDerived().RebuildCXXNamedCastExpr(E->getOperatorLoc(),
Mike Stump11289f42009-09-09 15:08:12 +00004001 E->getStmtClass(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004002 FakeLAngleLoc,
4003 ExplicitTy,
4004 FakeRAngleLoc,
4005 FakeRAngleLoc,
4006 move(SubExpr),
4007 FakeRParenLoc);
4008}
Mike Stump11289f42009-09-09 15:08:12 +00004009
Douglas Gregora16548e2009-08-11 05:31:07 +00004010template<typename Derived>
4011Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004012TreeTransform<Derived>::TransformCXXStaticCastExpr(CXXStaticCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004013 return getDerived().TransformCXXNamedCastExpr(E);
4014}
Mike Stump11289f42009-09-09 15:08:12 +00004015
4016template<typename Derived>
4017Sema::OwningExprResult
4018TreeTransform<Derived>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr *E) {
4019 return getDerived().TransformCXXNamedCastExpr(E);
4020}
4021
Douglas Gregora16548e2009-08-11 05:31:07 +00004022template<typename Derived>
4023Sema::OwningExprResult
4024TreeTransform<Derived>::TransformCXXReinterpretCastExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004025 CXXReinterpretCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004026 return getDerived().TransformCXXNamedCastExpr(E);
4027}
Mike Stump11289f42009-09-09 15:08:12 +00004028
Douglas Gregora16548e2009-08-11 05:31:07 +00004029template<typename Derived>
4030Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004031TreeTransform<Derived>::TransformCXXConstCastExpr(CXXConstCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004032 return getDerived().TransformCXXNamedCastExpr(E);
4033}
Mike Stump11289f42009-09-09 15:08:12 +00004034
Douglas Gregora16548e2009-08-11 05:31:07 +00004035template<typename Derived>
4036Sema::OwningExprResult
4037TreeTransform<Derived>::TransformCXXFunctionalCastExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004038 CXXFunctionalCastExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004039 QualType ExplicitTy;
4040 {
4041 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004042
Douglas Gregora16548e2009-08-11 05:31:07 +00004043 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
4044 if (ExplicitTy.isNull())
4045 return SemaRef.ExprError();
4046 }
Mike Stump11289f42009-09-09 15:08:12 +00004047
Douglas Gregora16548e2009-08-11 05:31:07 +00004048 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4049 if (SubExpr.isInvalid())
4050 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004051
Douglas Gregora16548e2009-08-11 05:31:07 +00004052 if (!getDerived().AlwaysRebuild() &&
4053 ExplicitTy == E->getTypeAsWritten() &&
4054 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00004055 return SemaRef.Owned(E->Retain());
4056
Douglas Gregora16548e2009-08-11 05:31:07 +00004057 // FIXME: The end of the type's source range is wrong
4058 return getDerived().RebuildCXXFunctionalCastExpr(
4059 /*FIXME:*/SourceRange(E->getTypeBeginLoc()),
4060 ExplicitTy,
4061 /*FIXME:*/E->getSubExpr()->getLocStart(),
4062 move(SubExpr),
4063 E->getRParenLoc());
4064}
Mike Stump11289f42009-09-09 15:08:12 +00004065
Douglas Gregora16548e2009-08-11 05:31:07 +00004066template<typename Derived>
4067Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004068TreeTransform<Derived>::TransformCXXTypeidExpr(CXXTypeidExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004069 if (E->isTypeOperand()) {
4070 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004071
Douglas Gregora16548e2009-08-11 05:31:07 +00004072 QualType T = getDerived().TransformType(E->getTypeOperand());
4073 if (T.isNull())
4074 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004075
Douglas Gregora16548e2009-08-11 05:31:07 +00004076 if (!getDerived().AlwaysRebuild() &&
4077 T == E->getTypeOperand())
4078 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004079
Douglas Gregora16548e2009-08-11 05:31:07 +00004080 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
4081 /*FIXME:*/E->getLocStart(),
4082 T,
4083 E->getLocEnd());
4084 }
Mike Stump11289f42009-09-09 15:08:12 +00004085
Douglas Gregora16548e2009-08-11 05:31:07 +00004086 // We don't know whether the expression is potentially evaluated until
4087 // after we perform semantic analysis, so the expression is potentially
4088 // potentially evaluated.
Mike Stump11289f42009-09-09 15:08:12 +00004089 EnterExpressionEvaluationContext Unevaluated(SemaRef,
Douglas Gregora16548e2009-08-11 05:31:07 +00004090 Action::PotentiallyPotentiallyEvaluated);
Mike Stump11289f42009-09-09 15:08:12 +00004091
Douglas Gregora16548e2009-08-11 05:31:07 +00004092 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand());
4093 if (SubExpr.isInvalid())
4094 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004095
Douglas Gregora16548e2009-08-11 05:31:07 +00004096 if (!getDerived().AlwaysRebuild() &&
4097 SubExpr.get() == E->getExprOperand())
Mike Stump11289f42009-09-09 15:08:12 +00004098 return SemaRef.Owned(E->Retain());
4099
Douglas Gregora16548e2009-08-11 05:31:07 +00004100 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
4101 /*FIXME:*/E->getLocStart(),
4102 move(SubExpr),
4103 E->getLocEnd());
4104}
4105
4106template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004107Sema::OwningExprResult
4108TreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) {
4109 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004110}
Mike Stump11289f42009-09-09 15:08:12 +00004111
Douglas Gregora16548e2009-08-11 05:31:07 +00004112template<typename Derived>
4113Sema::OwningExprResult
4114TreeTransform<Derived>::TransformCXXNullPtrLiteralExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004115 CXXNullPtrLiteralExpr *E) {
4116 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004117}
Mike Stump11289f42009-09-09 15:08:12 +00004118
Douglas Gregora16548e2009-08-11 05:31:07 +00004119template<typename Derived>
4120Sema::OwningExprResult
4121TreeTransform<Derived>::TransformCXXThisExpr(CXXThisExpr *E) {
4122 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004123
Douglas Gregora16548e2009-08-11 05:31:07 +00004124 QualType T = getDerived().TransformType(E->getType());
4125 if (T.isNull())
4126 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004127
Douglas Gregora16548e2009-08-11 05:31:07 +00004128 if (!getDerived().AlwaysRebuild() &&
4129 T == E->getType())
4130 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004131
Douglas Gregora16548e2009-08-11 05:31:07 +00004132 return getDerived().RebuildCXXThisExpr(E->getLocStart(), T);
4133}
Mike Stump11289f42009-09-09 15:08:12 +00004134
Douglas Gregora16548e2009-08-11 05:31:07 +00004135template<typename Derived>
4136Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004137TreeTransform<Derived>::TransformCXXThrowExpr(CXXThrowExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004138 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4139 if (SubExpr.isInvalid())
4140 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004141
Douglas Gregora16548e2009-08-11 05:31:07 +00004142 if (!getDerived().AlwaysRebuild() &&
4143 SubExpr.get() == E->getSubExpr())
Mike Stump11289f42009-09-09 15:08:12 +00004144 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004145
4146 return getDerived().RebuildCXXThrowExpr(E->getThrowLoc(), move(SubExpr));
4147}
Mike Stump11289f42009-09-09 15:08:12 +00004148
Douglas Gregora16548e2009-08-11 05:31:07 +00004149template<typename Derived>
4150Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004151TreeTransform<Derived>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E) {
4152 ParmVarDecl *Param
Douglas Gregora16548e2009-08-11 05:31:07 +00004153 = cast_or_null<ParmVarDecl>(getDerived().TransformDecl(E->getParam()));
4154 if (!Param)
4155 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004156
Douglas Gregora16548e2009-08-11 05:31:07 +00004157 if (getDerived().AlwaysRebuild() &&
4158 Param == E->getParam())
4159 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004160
Douglas Gregora16548e2009-08-11 05:31:07 +00004161 return getDerived().RebuildCXXDefaultArgExpr(Param);
4162}
Mike Stump11289f42009-09-09 15:08:12 +00004163
Douglas Gregora16548e2009-08-11 05:31:07 +00004164template<typename Derived>
4165Sema::OwningExprResult
4166TreeTransform<Derived>::TransformCXXZeroInitValueExpr(CXXZeroInitValueExpr *E) {
4167 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4168
4169 QualType T = getDerived().TransformType(E->getType());
4170 if (T.isNull())
4171 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004172
Douglas Gregora16548e2009-08-11 05:31:07 +00004173 if (!getDerived().AlwaysRebuild() &&
4174 T == E->getType())
Mike Stump11289f42009-09-09 15:08:12 +00004175 return SemaRef.Owned(E->Retain());
4176
4177 return getDerived().RebuildCXXZeroInitValueExpr(E->getTypeBeginLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004178 /*FIXME:*/E->getTypeBeginLoc(),
4179 T,
4180 E->getRParenLoc());
4181}
Mike Stump11289f42009-09-09 15:08:12 +00004182
Douglas Gregora16548e2009-08-11 05:31:07 +00004183template<typename Derived>
4184Sema::OwningExprResult
4185TreeTransform<Derived>::TransformCXXConditionDeclExpr(CXXConditionDeclExpr *E) {
Mike Stump11289f42009-09-09 15:08:12 +00004186 VarDecl *Var
Douglas Gregorebe10102009-08-20 07:17:43 +00004187 = cast_or_null<VarDecl>(getDerived().TransformDefinition(E->getVarDecl()));
Douglas Gregora16548e2009-08-11 05:31:07 +00004188 if (!Var)
4189 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004190
Douglas Gregora16548e2009-08-11 05:31:07 +00004191 if (!getDerived().AlwaysRebuild() &&
Mike Stump11289f42009-09-09 15:08:12 +00004192 Var == E->getVarDecl())
Douglas Gregora16548e2009-08-11 05:31:07 +00004193 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004194
4195 return getDerived().RebuildCXXConditionDeclExpr(E->getStartLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004196 /*FIXME:*/E->getStartLoc(),
4197 Var);
4198}
Mike Stump11289f42009-09-09 15:08:12 +00004199
Douglas Gregora16548e2009-08-11 05:31:07 +00004200template<typename Derived>
4201Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004202TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004203 // Transform the type that we're allocating
4204 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
4205 QualType AllocType = getDerived().TransformType(E->getAllocatedType());
4206 if (AllocType.isNull())
4207 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004208
Douglas Gregora16548e2009-08-11 05:31:07 +00004209 // Transform the size of the array we're allocating (if any).
4210 OwningExprResult ArraySize = getDerived().TransformExpr(E->getArraySize());
4211 if (ArraySize.isInvalid())
4212 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004213
Douglas Gregora16548e2009-08-11 05:31:07 +00004214 // Transform the placement arguments (if any).
4215 bool ArgumentChanged = false;
4216 ASTOwningVector<&ActionBase::DeleteExpr> PlacementArgs(SemaRef);
4217 for (unsigned I = 0, N = E->getNumPlacementArgs(); I != N; ++I) {
4218 OwningExprResult Arg = getDerived().TransformExpr(E->getPlacementArg(I));
4219 if (Arg.isInvalid())
4220 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004221
Douglas Gregora16548e2009-08-11 05:31:07 +00004222 ArgumentChanged = ArgumentChanged || Arg.get() != E->getPlacementArg(I);
4223 PlacementArgs.push_back(Arg.take());
4224 }
Mike Stump11289f42009-09-09 15:08:12 +00004225
Douglas Gregorebe10102009-08-20 07:17:43 +00004226 // transform the constructor arguments (if any).
Douglas Gregora16548e2009-08-11 05:31:07 +00004227 ASTOwningVector<&ActionBase::DeleteExpr> ConstructorArgs(SemaRef);
4228 for (unsigned I = 0, N = E->getNumConstructorArgs(); I != N; ++I) {
4229 OwningExprResult Arg = getDerived().TransformExpr(E->getConstructorArg(I));
4230 if (Arg.isInvalid())
4231 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004232
Douglas Gregora16548e2009-08-11 05:31:07 +00004233 ArgumentChanged = ArgumentChanged || Arg.get() != E->getConstructorArg(I);
4234 ConstructorArgs.push_back(Arg.take());
4235 }
Mike Stump11289f42009-09-09 15:08:12 +00004236
Douglas Gregora16548e2009-08-11 05:31:07 +00004237 if (!getDerived().AlwaysRebuild() &&
4238 AllocType == E->getAllocatedType() &&
4239 ArraySize.get() == E->getArraySize() &&
4240 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004241 return SemaRef.Owned(E->Retain());
4242
Douglas Gregora16548e2009-08-11 05:31:07 +00004243 return getDerived().RebuildCXXNewExpr(E->getLocStart(),
4244 E->isGlobalNew(),
4245 /*FIXME:*/E->getLocStart(),
4246 move_arg(PlacementArgs),
4247 /*FIXME:*/E->getLocStart(),
4248 E->isParenTypeId(),
4249 AllocType,
4250 /*FIXME:*/E->getLocStart(),
4251 /*FIXME:*/SourceRange(),
4252 move(ArraySize),
4253 /*FIXME:*/E->getLocStart(),
4254 move_arg(ConstructorArgs),
Mike Stump11289f42009-09-09 15:08:12 +00004255 E->getLocEnd());
Douglas Gregora16548e2009-08-11 05:31:07 +00004256}
Mike Stump11289f42009-09-09 15:08:12 +00004257
Douglas Gregora16548e2009-08-11 05:31:07 +00004258template<typename Derived>
4259Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004260TreeTransform<Derived>::TransformCXXDeleteExpr(CXXDeleteExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004261 OwningExprResult Operand = getDerived().TransformExpr(E->getArgument());
4262 if (Operand.isInvalid())
4263 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004264
Douglas Gregora16548e2009-08-11 05:31:07 +00004265 if (!getDerived().AlwaysRebuild() &&
Mike Stump11289f42009-09-09 15:08:12 +00004266 Operand.get() == E->getArgument())
4267 return SemaRef.Owned(E->Retain());
4268
Douglas Gregora16548e2009-08-11 05:31:07 +00004269 return getDerived().RebuildCXXDeleteExpr(E->getLocStart(),
4270 E->isGlobalDelete(),
4271 E->isArrayForm(),
4272 move(Operand));
4273}
Mike Stump11289f42009-09-09 15:08:12 +00004274
Douglas Gregora16548e2009-08-11 05:31:07 +00004275template<typename Derived>
4276Sema::OwningExprResult
Douglas Gregorad8a3362009-09-04 17:36:40 +00004277TreeTransform<Derived>::TransformCXXPseudoDestructorExpr(
4278 CXXPseudoDestructorExpr *E) {
4279 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
4280 if (Base.isInvalid())
4281 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004282
Douglas Gregorad8a3362009-09-04 17:36:40 +00004283 NestedNameSpecifier *Qualifier
4284 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4285 E->getQualifierRange());
4286 if (E->getQualifier() && !Qualifier)
4287 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004288
Douglas Gregorad8a3362009-09-04 17:36:40 +00004289 QualType DestroyedType;
4290 {
4291 TemporaryBase Rebase(*this, E->getDestroyedTypeLoc(), DeclarationName());
4292 DestroyedType = getDerived().TransformType(E->getDestroyedType());
4293 if (DestroyedType.isNull())
4294 return SemaRef.ExprError();
4295 }
Mike Stump11289f42009-09-09 15:08:12 +00004296
Douglas Gregorad8a3362009-09-04 17:36:40 +00004297 if (!getDerived().AlwaysRebuild() &&
4298 Base.get() == E->getBase() &&
4299 Qualifier == E->getQualifier() &&
4300 DestroyedType == E->getDestroyedType())
4301 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004302
Douglas Gregorad8a3362009-09-04 17:36:40 +00004303 return getDerived().RebuildCXXPseudoDestructorExpr(move(Base),
4304 E->getOperatorLoc(),
4305 E->isArrow(),
4306 E->getDestroyedTypeLoc(),
4307 DestroyedType,
4308 Qualifier,
4309 E->getQualifierRange());
4310}
Mike Stump11289f42009-09-09 15:08:12 +00004311
Douglas Gregorad8a3362009-09-04 17:36:40 +00004312template<typename Derived>
4313Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00004314TreeTransform<Derived>::TransformUnresolvedFunctionNameExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004315 UnresolvedFunctionNameExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004316 // There is no transformation we can apply to an unresolved function name.
Mike Stump11289f42009-09-09 15:08:12 +00004317 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004318}
Mike Stump11289f42009-09-09 15:08:12 +00004319
Douglas Gregora16548e2009-08-11 05:31:07 +00004320template<typename Derived>
4321Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004322TreeTransform<Derived>::TransformUnaryTypeTraitExpr(UnaryTypeTraitExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004323 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
Mike Stump11289f42009-09-09 15:08:12 +00004324
Douglas Gregora16548e2009-08-11 05:31:07 +00004325 QualType T = getDerived().TransformType(E->getQueriedType());
4326 if (T.isNull())
4327 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004328
Douglas Gregora16548e2009-08-11 05:31:07 +00004329 if (!getDerived().AlwaysRebuild() &&
4330 T == E->getQueriedType())
4331 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004332
Douglas Gregora16548e2009-08-11 05:31:07 +00004333 // FIXME: Bad location information
4334 SourceLocation FakeLParenLoc
4335 = SemaRef.PP.getLocForEndOfToken(E->getLocStart());
Mike Stump11289f42009-09-09 15:08:12 +00004336
4337 return getDerived().RebuildUnaryTypeTrait(E->getTrait(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004338 E->getLocStart(),
4339 /*FIXME:*/FakeLParenLoc,
4340 T,
4341 E->getLocEnd());
4342}
Mike Stump11289f42009-09-09 15:08:12 +00004343
Douglas Gregora16548e2009-08-11 05:31:07 +00004344template<typename Derived>
4345Sema::OwningExprResult
4346TreeTransform<Derived>::TransformQualifiedDeclRefExpr(QualifiedDeclRefExpr *E) {
4347 NestedNameSpecifier *NNS
4348 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4349 E->getQualifierRange());
4350 if (!NNS)
4351 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004352
4353 NamedDecl *ND
Douglas Gregora16548e2009-08-11 05:31:07 +00004354 = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
4355 if (!ND)
4356 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004357
4358 if (!getDerived().AlwaysRebuild() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00004359 NNS == E->getQualifier() &&
4360 ND == E->getDecl())
Mike Stump11289f42009-09-09 15:08:12 +00004361 return SemaRef.Owned(E->Retain());
4362
4363 return getDerived().RebuildQualifiedDeclRefExpr(NNS,
Douglas Gregora16548e2009-08-11 05:31:07 +00004364 E->getQualifierRange(),
4365 ND,
4366 E->getLocation(),
4367 /*FIXME:*/false);
4368}
Mike Stump11289f42009-09-09 15:08:12 +00004369
Douglas Gregora16548e2009-08-11 05:31:07 +00004370template<typename Derived>
4371Sema::OwningExprResult
4372TreeTransform<Derived>::TransformUnresolvedDeclRefExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004373 UnresolvedDeclRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004374 NestedNameSpecifier *NNS
Douglas Gregord019ff62009-10-22 17:20:55 +00004375 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4376 E->getQualifierRange());
Douglas Gregora16548e2009-08-11 05:31:07 +00004377 if (!NNS)
4378 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004379
4380 DeclarationName Name
Douglas Gregorf816bd72009-09-03 22:13:48 +00004381 = getDerived().TransformDeclarationName(E->getDeclName(), E->getLocation());
4382 if (!Name)
4383 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004384
4385 if (!getDerived().AlwaysRebuild() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00004386 NNS == E->getQualifier() &&
4387 Name == E->getDeclName())
Mike Stump11289f42009-09-09 15:08:12 +00004388 return SemaRef.Owned(E->Retain());
4389
4390 return getDerived().RebuildUnresolvedDeclRefExpr(NNS,
Douglas Gregora16548e2009-08-11 05:31:07 +00004391 E->getQualifierRange(),
4392 Name,
4393 E->getLocation(),
4394 /*FIXME:*/false);
4395}
4396
4397template<typename Derived>
4398Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004399TreeTransform<Derived>::TransformTemplateIdRefExpr(TemplateIdRefExpr *E) {
4400 TemplateName Template
Douglas Gregora16548e2009-08-11 05:31:07 +00004401 = getDerived().TransformTemplateName(E->getTemplateName());
4402 if (Template.isNull())
4403 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004404
Douglas Gregord019ff62009-10-22 17:20:55 +00004405 NestedNameSpecifier *Qualifier = 0;
4406 if (E->getQualifier()) {
4407 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4408 E->getQualifierRange());
4409 if (!Qualifier)
4410 return SemaRef.ExprError();
4411 }
4412
Douglas Gregora16548e2009-08-11 05:31:07 +00004413 llvm::SmallVector<TemplateArgument, 4> TransArgs;
4414 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00004415 TemplateArgument TransArg
Douglas Gregora16548e2009-08-11 05:31:07 +00004416 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
4417 if (TransArg.isNull())
4418 return SemaRef.ExprError();
4419
4420 TransArgs.push_back(TransArg);
4421 }
4422
4423 // FIXME: Would like to avoid rebuilding if nothing changed, but we can't
4424 // compare template arguments (yet).
Mike Stump11289f42009-09-09 15:08:12 +00004425
4426 // FIXME: It's possible that we'll find out now that the template name
Douglas Gregora16548e2009-08-11 05:31:07 +00004427 // actually refers to a type, in which case the caller is actually dealing
4428 // with a functional cast. Give a reasonable error message!
Douglas Gregord019ff62009-10-22 17:20:55 +00004429 return getDerived().RebuildTemplateIdExpr(Qualifier, E->getQualifierRange(),
4430 Template, E->getTemplateNameLoc(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004431 E->getLAngleLoc(),
4432 TransArgs.data(),
4433 TransArgs.size(),
4434 E->getRAngleLoc());
4435}
4436
4437template<typename Derived>
4438Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004439TreeTransform<Derived>::TransformCXXConstructExpr(CXXConstructExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004440 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
4441
4442 QualType T = getDerived().TransformType(E->getType());
4443 if (T.isNull())
4444 return SemaRef.ExprError();
4445
4446 CXXConstructorDecl *Constructor
4447 = cast_or_null<CXXConstructorDecl>(
4448 getDerived().TransformDecl(E->getConstructor()));
4449 if (!Constructor)
4450 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004451
Douglas Gregora16548e2009-08-11 05:31:07 +00004452 bool ArgumentChanged = false;
4453 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
Mike Stump11289f42009-09-09 15:08:12 +00004454 for (CXXConstructExpr::arg_iterator Arg = E->arg_begin(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004455 ArgEnd = E->arg_end();
4456 Arg != ArgEnd; ++Arg) {
4457 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4458 if (TransArg.isInvalid())
4459 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004460
Douglas Gregora16548e2009-08-11 05:31:07 +00004461 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4462 Args.push_back(TransArg.takeAs<Expr>());
4463 }
4464
4465 if (!getDerived().AlwaysRebuild() &&
4466 T == E->getType() &&
4467 Constructor == E->getConstructor() &&
4468 !ArgumentChanged)
4469 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004470
Douglas Gregora16548e2009-08-11 05:31:07 +00004471 return getDerived().RebuildCXXConstructExpr(T, Constructor, E->isElidable(),
4472 move_arg(Args));
4473}
Mike Stump11289f42009-09-09 15:08:12 +00004474
Douglas Gregora16548e2009-08-11 05:31:07 +00004475/// \brief Transform a C++ temporary-binding expression.
4476///
Mike Stump11289f42009-09-09 15:08:12 +00004477/// The transformation of a temporary-binding expression always attempts to
4478/// bind a new temporary variable to its subexpression, even if the
Douglas Gregora16548e2009-08-11 05:31:07 +00004479/// subexpression itself did not change, because the temporary variable itself
4480/// must be unique.
4481template<typename Derived>
4482Sema::OwningExprResult
4483TreeTransform<Derived>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr *E) {
4484 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4485 if (SubExpr.isInvalid())
4486 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004487
Douglas Gregora16548e2009-08-11 05:31:07 +00004488 return SemaRef.MaybeBindToTemporary(SubExpr.takeAs<Expr>());
4489}
Mike Stump11289f42009-09-09 15:08:12 +00004490
4491/// \brief Transform a C++ expression that contains temporaries that should
Douglas Gregora16548e2009-08-11 05:31:07 +00004492/// be destroyed after the expression is evaluated.
4493///
Mike Stump11289f42009-09-09 15:08:12 +00004494/// The transformation of a full expression always attempts to build a new
4495/// CXXExprWithTemporaries expression, even if the
Douglas Gregora16548e2009-08-11 05:31:07 +00004496/// subexpression itself did not change, because it will need to capture the
4497/// the new temporary variables introduced in the subexpression.
4498template<typename Derived>
4499Sema::OwningExprResult
4500TreeTransform<Derived>::TransformCXXExprWithTemporaries(
Mike Stump11289f42009-09-09 15:08:12 +00004501 CXXExprWithTemporaries *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004502 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
4503 if (SubExpr.isInvalid())
4504 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004505
Douglas Gregora16548e2009-08-11 05:31:07 +00004506 return SemaRef.Owned(
4507 SemaRef.MaybeCreateCXXExprWithTemporaries(SubExpr.takeAs<Expr>(),
4508 E->shouldDestroyTemporaries()));
4509}
Mike Stump11289f42009-09-09 15:08:12 +00004510
Douglas Gregora16548e2009-08-11 05:31:07 +00004511template<typename Derived>
4512Sema::OwningExprResult
4513TreeTransform<Derived>::TransformCXXTemporaryObjectExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004514 CXXTemporaryObjectExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004515 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4516 QualType T = getDerived().TransformType(E->getType());
4517 if (T.isNull())
4518 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004519
Douglas Gregora16548e2009-08-11 05:31:07 +00004520 CXXConstructorDecl *Constructor
4521 = cast_or_null<CXXConstructorDecl>(
4522 getDerived().TransformDecl(E->getConstructor()));
4523 if (!Constructor)
4524 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004525
Douglas Gregora16548e2009-08-11 05:31:07 +00004526 bool ArgumentChanged = false;
4527 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
4528 Args.reserve(E->getNumArgs());
Mike Stump11289f42009-09-09 15:08:12 +00004529 for (CXXTemporaryObjectExpr::arg_iterator Arg = E->arg_begin(),
Douglas Gregora16548e2009-08-11 05:31:07 +00004530 ArgEnd = E->arg_end();
4531 Arg != ArgEnd; ++Arg) {
4532 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4533 if (TransArg.isInvalid())
4534 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004535
Douglas Gregora16548e2009-08-11 05:31:07 +00004536 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4537 Args.push_back((Expr *)TransArg.release());
4538 }
Mike Stump11289f42009-09-09 15:08:12 +00004539
Douglas Gregora16548e2009-08-11 05:31:07 +00004540 if (!getDerived().AlwaysRebuild() &&
4541 T == E->getType() &&
4542 Constructor == E->getConstructor() &&
4543 !ArgumentChanged)
4544 return SemaRef.Owned(E->Retain());
Mike Stump11289f42009-09-09 15:08:12 +00004545
Douglas Gregora16548e2009-08-11 05:31:07 +00004546 // FIXME: Bogus location information
4547 SourceLocation CommaLoc;
4548 if (Args.size() > 1) {
4549 Expr *First = (Expr *)Args[0];
Mike Stump11289f42009-09-09 15:08:12 +00004550 CommaLoc
Douglas Gregora16548e2009-08-11 05:31:07 +00004551 = SemaRef.PP.getLocForEndOfToken(First->getSourceRange().getEnd());
4552 }
4553 return getDerived().RebuildCXXTemporaryObjectExpr(E->getTypeBeginLoc(),
4554 T,
4555 /*FIXME:*/E->getTypeBeginLoc(),
4556 move_arg(Args),
4557 &CommaLoc,
4558 E->getLocEnd());
4559}
Mike Stump11289f42009-09-09 15:08:12 +00004560
Douglas Gregora16548e2009-08-11 05:31:07 +00004561template<typename Derived>
4562Sema::OwningExprResult
4563TreeTransform<Derived>::TransformCXXUnresolvedConstructExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004564 CXXUnresolvedConstructExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004565 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4566 QualType T = getDerived().TransformType(E->getTypeAsWritten());
4567 if (T.isNull())
4568 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004569
Douglas Gregora16548e2009-08-11 05:31:07 +00004570 bool ArgumentChanged = false;
4571 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
4572 llvm::SmallVector<SourceLocation, 8> FakeCommaLocs;
4573 for (CXXUnresolvedConstructExpr::arg_iterator Arg = E->arg_begin(),
4574 ArgEnd = E->arg_end();
4575 Arg != ArgEnd; ++Arg) {
4576 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4577 if (TransArg.isInvalid())
4578 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004579
Douglas Gregora16548e2009-08-11 05:31:07 +00004580 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4581 FakeCommaLocs.push_back(
4582 SemaRef.PP.getLocForEndOfToken((*Arg)->getLocEnd()));
4583 Args.push_back(TransArg.takeAs<Expr>());
4584 }
Mike Stump11289f42009-09-09 15:08:12 +00004585
Douglas Gregora16548e2009-08-11 05:31:07 +00004586 if (!getDerived().AlwaysRebuild() &&
4587 T == E->getTypeAsWritten() &&
4588 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004589 return SemaRef.Owned(E->Retain());
4590
Douglas Gregora16548e2009-08-11 05:31:07 +00004591 // FIXME: we're faking the locations of the commas
4592 return getDerived().RebuildCXXUnresolvedConstructExpr(E->getTypeBeginLoc(),
4593 T,
4594 E->getLParenLoc(),
4595 move_arg(Args),
4596 FakeCommaLocs.data(),
4597 E->getRParenLoc());
4598}
Mike Stump11289f42009-09-09 15:08:12 +00004599
Douglas Gregora16548e2009-08-11 05:31:07 +00004600template<typename Derived>
4601Sema::OwningExprResult
4602TreeTransform<Derived>::TransformCXXUnresolvedMemberExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004603 CXXUnresolvedMemberExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004604 // Transform the base of the expression.
4605 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
4606 if (Base.isInvalid())
4607 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004608
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004609 // Start the member reference and compute the object's type.
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004610 Sema::TypeTy *ObjectType = 0;
Mike Stump11289f42009-09-09 15:08:12 +00004611 Base = SemaRef.ActOnStartCXXMemberReference(0, move(Base),
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004612 E->getOperatorLoc(),
4613 E->isArrow()? tok::arrow : tok::period,
4614 ObjectType);
4615 if (Base.isInvalid())
4616 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004617
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004618 // Transform the first part of the nested-name-specifier that qualifies
4619 // the member name.
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004620 NamedDecl *FirstQualifierInScope
Douglas Gregora5cb6da2009-10-20 05:58:46 +00004621 = getDerived().TransformFirstQualifierInScope(
4622 E->getFirstQualifierFoundInScope(),
4623 E->getQualifierRange().getBegin());
Mike Stump11289f42009-09-09 15:08:12 +00004624
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004625 NestedNameSpecifier *Qualifier = 0;
4626 if (E->getQualifier()) {
4627 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4628 E->getQualifierRange(),
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004629 QualType::getFromOpaquePtr(ObjectType),
4630 FirstQualifierInScope);
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004631 if (!Qualifier)
4632 return SemaRef.ExprError();
4633 }
Mike Stump11289f42009-09-09 15:08:12 +00004634
4635 DeclarationName Name
Douglas Gregorc59e5612009-10-19 22:04:39 +00004636 = getDerived().TransformDeclarationName(E->getMember(), E->getMemberLoc(),
4637 QualType::getFromOpaquePtr(ObjectType));
Douglas Gregorf816bd72009-09-03 22:13:48 +00004638 if (!Name)
4639 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004640
Douglas Gregor308047d2009-09-09 00:23:06 +00004641 if (!E->hasExplicitTemplateArgumentList()) {
4642 // This is a reference to a member without an explicitly-specified
4643 // template argument list. Optimize for this common case.
4644 if (!getDerived().AlwaysRebuild() &&
4645 Base.get() == E->getBase() &&
4646 Qualifier == E->getQualifier() &&
4647 Name == E->getMember() &&
4648 FirstQualifierInScope == E->getFirstQualifierFoundInScope())
Mike Stump11289f42009-09-09 15:08:12 +00004649 return SemaRef.Owned(E->Retain());
4650
Douglas Gregor308047d2009-09-09 00:23:06 +00004651 return getDerived().RebuildCXXUnresolvedMemberExpr(move(Base),
4652 E->isArrow(),
4653 E->getOperatorLoc(),
4654 Qualifier,
4655 E->getQualifierRange(),
4656 Name,
4657 E->getMemberLoc(),
4658 FirstQualifierInScope);
4659 }
4660
4661 // FIXME: This is an ugly hack, which forces the same template name to
4662 // be looked up multiple times. Yuck!
4663 // FIXME: This also won't work for, e.g., x->template operator+<int>
4664 TemplateName OrigTemplateName
4665 = SemaRef.Context.getDependentTemplateName(0, Name.getAsIdentifierInfo());
Mike Stump11289f42009-09-09 15:08:12 +00004666
4667 TemplateName Template
4668 = getDerived().TransformTemplateName(OrigTemplateName,
Douglas Gregor308047d2009-09-09 00:23:06 +00004669 QualType::getFromOpaquePtr(ObjectType));
4670 if (Template.isNull())
4671 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004672
Douglas Gregor308047d2009-09-09 00:23:06 +00004673 llvm::SmallVector<TemplateArgument, 4> TransArgs;
4674 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
Mike Stump11289f42009-09-09 15:08:12 +00004675 TemplateArgument TransArg
Douglas Gregor308047d2009-09-09 00:23:06 +00004676 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
4677 if (TransArg.isNull())
4678 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004679
Douglas Gregor308047d2009-09-09 00:23:06 +00004680 TransArgs.push_back(TransArg);
4681 }
Mike Stump11289f42009-09-09 15:08:12 +00004682
Douglas Gregora16548e2009-08-11 05:31:07 +00004683 return getDerived().RebuildCXXUnresolvedMemberExpr(move(Base),
4684 E->isArrow(),
4685 E->getOperatorLoc(),
Douglas Gregorc26e0f62009-09-03 16:14:30 +00004686 Qualifier,
4687 E->getQualifierRange(),
Douglas Gregor308047d2009-09-09 00:23:06 +00004688 Template,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00004689 E->getMemberLoc(),
Douglas Gregor308047d2009-09-09 00:23:06 +00004690 FirstQualifierInScope,
4691 E->getLAngleLoc(),
4692 TransArgs.data(),
4693 TransArgs.size(),
4694 E->getRAngleLoc());
Douglas Gregora16548e2009-08-11 05:31:07 +00004695}
4696
4697template<typename Derived>
4698Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004699TreeTransform<Derived>::TransformObjCStringLiteral(ObjCStringLiteral *E) {
4700 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004701}
4702
Mike Stump11289f42009-09-09 15:08:12 +00004703template<typename Derived>
4704Sema::OwningExprResult
4705TreeTransform<Derived>::TransformObjCEncodeExpr(ObjCEncodeExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004706 // FIXME: poor source location
4707 TemporaryBase Rebase(*this, E->getAtLoc(), DeclarationName());
4708 QualType EncodedType = getDerived().TransformType(E->getEncodedType());
4709 if (EncodedType.isNull())
4710 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004711
Douglas Gregora16548e2009-08-11 05:31:07 +00004712 if (!getDerived().AlwaysRebuild() &&
4713 EncodedType == E->getEncodedType())
Mike Stump11289f42009-09-09 15:08:12 +00004714 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004715
4716 return getDerived().RebuildObjCEncodeExpr(E->getAtLoc(),
4717 EncodedType,
4718 E->getRParenLoc());
4719}
Mike Stump11289f42009-09-09 15:08:12 +00004720
Douglas Gregora16548e2009-08-11 05:31:07 +00004721template<typename Derived>
4722Sema::OwningExprResult
Mike Stump11289f42009-09-09 15:08:12 +00004723TreeTransform<Derived>::TransformObjCMessageExpr(ObjCMessageExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004724 // FIXME: Implement this!
4725 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004726 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004727}
4728
Mike Stump11289f42009-09-09 15:08:12 +00004729template<typename Derived>
4730Sema::OwningExprResult
4731TreeTransform<Derived>::TransformObjCSelectorExpr(ObjCSelectorExpr *E) {
4732 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004733}
4734
Mike Stump11289f42009-09-09 15:08:12 +00004735template<typename Derived>
4736Sema::OwningExprResult
4737TreeTransform<Derived>::TransformObjCProtocolExpr(ObjCProtocolExpr *E) {
4738 ObjCProtocolDecl *Protocol
Douglas Gregora16548e2009-08-11 05:31:07 +00004739 = cast_or_null<ObjCProtocolDecl>(
4740 getDerived().TransformDecl(E->getProtocol()));
4741 if (!Protocol)
4742 return SemaRef.ExprError();
4743
4744 if (!getDerived().AlwaysRebuild() &&
4745 Protocol == E->getProtocol())
Mike Stump11289f42009-09-09 15:08:12 +00004746 return SemaRef.Owned(E->Retain());
4747
Douglas Gregora16548e2009-08-11 05:31:07 +00004748 return getDerived().RebuildObjCProtocolExpr(Protocol,
4749 E->getAtLoc(),
4750 /*FIXME:*/E->getAtLoc(),
4751 /*FIXME:*/E->getAtLoc(),
4752 E->getRParenLoc());
Mike Stump11289f42009-09-09 15:08:12 +00004753
Douglas Gregora16548e2009-08-11 05:31:07 +00004754}
4755
Mike Stump11289f42009-09-09 15:08:12 +00004756template<typename Derived>
4757Sema::OwningExprResult
4758TreeTransform<Derived>::TransformObjCIvarRefExpr(ObjCIvarRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004759 // FIXME: Implement this!
4760 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004761 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004762}
4763
Mike Stump11289f42009-09-09 15:08:12 +00004764template<typename Derived>
4765Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00004766TreeTransform<Derived>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr *E) {
4767 // FIXME: Implement this!
4768 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004769 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004770}
4771
Mike Stump11289f42009-09-09 15:08:12 +00004772template<typename Derived>
4773Sema::OwningExprResult
Fariborz Jahanian9a846652009-08-20 17:02:02 +00004774TreeTransform<Derived>::TransformObjCImplicitSetterGetterRefExpr(
Mike Stump11289f42009-09-09 15:08:12 +00004775 ObjCImplicitSetterGetterRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004776 // FIXME: Implement this!
4777 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004778 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004779}
4780
Mike Stump11289f42009-09-09 15:08:12 +00004781template<typename Derived>
4782Sema::OwningExprResult
4783TreeTransform<Derived>::TransformObjCSuperExpr(ObjCSuperExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004784 // FIXME: Implement this!
4785 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004786 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004787}
4788
Mike Stump11289f42009-09-09 15:08:12 +00004789template<typename Derived>
4790Sema::OwningExprResult
4791TreeTransform<Derived>::TransformObjCIsaExpr(ObjCIsaExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004792 // FIXME: Implement this!
4793 assert(false && "Cannot transform Objective-C expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004794 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004795}
4796
Mike Stump11289f42009-09-09 15:08:12 +00004797template<typename Derived>
4798Sema::OwningExprResult
4799TreeTransform<Derived>::TransformShuffleVectorExpr(ShuffleVectorExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004800 bool ArgumentChanged = false;
4801 ASTOwningVector<&ActionBase::DeleteExpr> SubExprs(SemaRef);
4802 for (unsigned I = 0, N = E->getNumSubExprs(); I != N; ++I) {
4803 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExpr(I));
4804 if (SubExpr.isInvalid())
4805 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00004806
Douglas Gregora16548e2009-08-11 05:31:07 +00004807 ArgumentChanged = ArgumentChanged || SubExpr.get() != E->getExpr(I);
4808 SubExprs.push_back(SubExpr.takeAs<Expr>());
4809 }
Mike Stump11289f42009-09-09 15:08:12 +00004810
Douglas Gregora16548e2009-08-11 05:31:07 +00004811 if (!getDerived().AlwaysRebuild() &&
4812 !ArgumentChanged)
Mike Stump11289f42009-09-09 15:08:12 +00004813 return SemaRef.Owned(E->Retain());
4814
Douglas Gregora16548e2009-08-11 05:31:07 +00004815 return getDerived().RebuildShuffleVectorExpr(E->getBuiltinLoc(),
4816 move_arg(SubExprs),
4817 E->getRParenLoc());
4818}
4819
Mike Stump11289f42009-09-09 15:08:12 +00004820template<typename Derived>
4821Sema::OwningExprResult
4822TreeTransform<Derived>::TransformBlockExpr(BlockExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004823 // FIXME: Implement this!
4824 assert(false && "Cannot transform block expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004825 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004826}
4827
Mike Stump11289f42009-09-09 15:08:12 +00004828template<typename Derived>
4829Sema::OwningExprResult
4830TreeTransform<Derived>::TransformBlockDeclRefExpr(BlockDeclRefExpr *E) {
Douglas Gregora16548e2009-08-11 05:31:07 +00004831 // FIXME: Implement this!
4832 assert(false && "Cannot transform block-related expressions yet");
Mike Stump11289f42009-09-09 15:08:12 +00004833 return SemaRef.Owned(E->Retain());
Douglas Gregora16548e2009-08-11 05:31:07 +00004834}
Mike Stump11289f42009-09-09 15:08:12 +00004835
Douglas Gregora16548e2009-08-11 05:31:07 +00004836//===----------------------------------------------------------------------===//
Douglas Gregord6ff3322009-08-04 16:50:30 +00004837// Type reconstruction
4838//===----------------------------------------------------------------------===//
4839
Mike Stump11289f42009-09-09 15:08:12 +00004840template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00004841QualType TreeTransform<Derived>::RebuildPointerType(QualType PointeeType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004842 return SemaRef.BuildPointerType(PointeeType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004843 getDerived().getBaseLocation(),
4844 getDerived().getBaseEntity());
4845}
4846
Mike Stump11289f42009-09-09 15:08:12 +00004847template<typename Derived>
Douglas Gregord6ff3322009-08-04 16:50:30 +00004848QualType TreeTransform<Derived>::RebuildBlockPointerType(QualType PointeeType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004849 return SemaRef.BuildBlockPointerType(PointeeType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004850 getDerived().getBaseLocation(),
4851 getDerived().getBaseEntity());
4852}
4853
Mike Stump11289f42009-09-09 15:08:12 +00004854template<typename Derived>
4855QualType
Douglas Gregord6ff3322009-08-04 16:50:30 +00004856TreeTransform<Derived>::RebuildLValueReferenceType(QualType ReferentType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004857 return SemaRef.BuildReferenceType(ReferentType, true, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004858 getDerived().getBaseLocation(),
4859 getDerived().getBaseEntity());
4860}
4861
4862template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004863QualType
4864TreeTransform<Derived>::RebuildRValueReferenceType(QualType ReferentType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004865 return SemaRef.BuildReferenceType(ReferentType, false, Qualifiers(),
Mike Stump11289f42009-09-09 15:08:12 +00004866 getDerived().getBaseLocation(),
4867 getDerived().getBaseEntity());
4868}
4869
4870template<typename Derived>
4871QualType TreeTransform<Derived>::RebuildMemberPointerType(QualType PointeeType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004872 QualType ClassType) {
John McCall8ccfcb52009-09-24 19:53:00 +00004873 return SemaRef.BuildMemberPointerType(PointeeType, ClassType, Qualifiers(),
Douglas Gregord6ff3322009-08-04 16:50:30 +00004874 getDerived().getBaseLocation(),
4875 getDerived().getBaseEntity());
4876}
4877
4878template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004879QualType
John McCall550e0c22009-10-21 00:40:46 +00004880TreeTransform<Derived>::RebuildObjCObjectPointerType(QualType PointeeType) {
4881 return SemaRef.BuildPointerType(PointeeType, Qualifiers(),
4882 getDerived().getBaseLocation(),
4883 getDerived().getBaseEntity());
4884}
4885
4886template<typename Derived>
4887QualType
Douglas Gregord6ff3322009-08-04 16:50:30 +00004888TreeTransform<Derived>::RebuildArrayType(QualType ElementType,
4889 ArrayType::ArraySizeModifier SizeMod,
4890 const llvm::APInt *Size,
4891 Expr *SizeExpr,
4892 unsigned IndexTypeQuals,
4893 SourceRange BracketsRange) {
4894 if (SizeExpr || !Size)
4895 return SemaRef.BuildArrayType(ElementType, SizeMod, SizeExpr,
4896 IndexTypeQuals, BracketsRange,
4897 getDerived().getBaseEntity());
Mike Stump11289f42009-09-09 15:08:12 +00004898
4899 QualType Types[] = {
4900 SemaRef.Context.UnsignedCharTy, SemaRef.Context.UnsignedShortTy,
4901 SemaRef.Context.UnsignedIntTy, SemaRef.Context.UnsignedLongTy,
4902 SemaRef.Context.UnsignedLongLongTy, SemaRef.Context.UnsignedInt128Ty
Douglas Gregord6ff3322009-08-04 16:50:30 +00004903 };
4904 const unsigned NumTypes = sizeof(Types) / sizeof(QualType);
4905 QualType SizeType;
4906 for (unsigned I = 0; I != NumTypes; ++I)
4907 if (Size->getBitWidth() == SemaRef.Context.getIntWidth(Types[I])) {
4908 SizeType = Types[I];
4909 break;
4910 }
Mike Stump11289f42009-09-09 15:08:12 +00004911
Douglas Gregord6ff3322009-08-04 16:50:30 +00004912 if (SizeType.isNull())
4913 SizeType = SemaRef.Context.getFixedWidthIntType(Size->getBitWidth(), false);
Mike Stump11289f42009-09-09 15:08:12 +00004914
Douglas Gregord6ff3322009-08-04 16:50:30 +00004915 IntegerLiteral ArraySize(*Size, SizeType, /*FIXME*/BracketsRange.getBegin());
Mike Stump11289f42009-09-09 15:08:12 +00004916 return SemaRef.BuildArrayType(ElementType, SizeMod, &ArraySize,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004917 IndexTypeQuals, BracketsRange,
Mike Stump11289f42009-09-09 15:08:12 +00004918 getDerived().getBaseEntity());
Douglas Gregord6ff3322009-08-04 16:50:30 +00004919}
Mike Stump11289f42009-09-09 15:08:12 +00004920
Douglas Gregord6ff3322009-08-04 16:50:30 +00004921template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004922QualType
4923TreeTransform<Derived>::RebuildConstantArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004924 ArrayType::ArraySizeModifier SizeMod,
4925 const llvm::APInt &Size,
4926 unsigned IndexTypeQuals) {
Mike Stump11289f42009-09-09 15:08:12 +00004927 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004928 IndexTypeQuals, SourceRange());
4929}
4930
4931template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004932QualType
Mike Stump11289f42009-09-09 15:08:12 +00004933TreeTransform<Derived>::RebuildIncompleteArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004934 ArrayType::ArraySizeModifier SizeMod,
4935 unsigned IndexTypeQuals) {
Mike Stump11289f42009-09-09 15:08:12 +00004936 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004937 IndexTypeQuals, SourceRange());
4938}
Mike Stump11289f42009-09-09 15:08:12 +00004939
Douglas Gregord6ff3322009-08-04 16:50:30 +00004940template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004941QualType
4942TreeTransform<Derived>::RebuildVariableArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004943 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +00004944 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004945 unsigned IndexTypeQuals,
4946 SourceRange BracketsRange) {
Mike Stump11289f42009-09-09 15:08:12 +00004947 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004948 SizeExpr.takeAs<Expr>(),
4949 IndexTypeQuals, BracketsRange);
4950}
4951
4952template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004953QualType
4954TreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004955 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregora16548e2009-08-11 05:31:07 +00004956 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004957 unsigned IndexTypeQuals,
4958 SourceRange BracketsRange) {
Mike Stump11289f42009-09-09 15:08:12 +00004959 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004960 SizeExpr.takeAs<Expr>(),
4961 IndexTypeQuals, BracketsRange);
4962}
4963
4964template<typename Derived>
4965QualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType,
4966 unsigned NumElements) {
4967 // FIXME: semantic checking!
4968 return SemaRef.Context.getVectorType(ElementType, NumElements);
4969}
Mike Stump11289f42009-09-09 15:08:12 +00004970
Douglas Gregord6ff3322009-08-04 16:50:30 +00004971template<typename Derived>
4972QualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType,
4973 unsigned NumElements,
4974 SourceLocation AttributeLoc) {
4975 llvm::APInt numElements(SemaRef.Context.getIntWidth(SemaRef.Context.IntTy),
4976 NumElements, true);
4977 IntegerLiteral *VectorSize
Mike Stump11289f42009-09-09 15:08:12 +00004978 = new (SemaRef.Context) IntegerLiteral(numElements, SemaRef.Context.IntTy,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004979 AttributeLoc);
4980 return SemaRef.BuildExtVectorType(ElementType, SemaRef.Owned(VectorSize),
4981 AttributeLoc);
4982}
Mike Stump11289f42009-09-09 15:08:12 +00004983
Douglas Gregord6ff3322009-08-04 16:50:30 +00004984template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00004985QualType
4986TreeTransform<Derived>::RebuildDependentSizedExtVectorType(QualType ElementType,
Douglas Gregora16548e2009-08-11 05:31:07 +00004987 ExprArg SizeExpr,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004988 SourceLocation AttributeLoc) {
4989 return SemaRef.BuildExtVectorType(ElementType, move(SizeExpr), AttributeLoc);
4990}
Mike Stump11289f42009-09-09 15:08:12 +00004991
Douglas Gregord6ff3322009-08-04 16:50:30 +00004992template<typename Derived>
4993QualType TreeTransform<Derived>::RebuildFunctionProtoType(QualType T,
Mike Stump11289f42009-09-09 15:08:12 +00004994 QualType *ParamTypes,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004995 unsigned NumParamTypes,
Mike Stump11289f42009-09-09 15:08:12 +00004996 bool Variadic,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004997 unsigned Quals) {
Mike Stump11289f42009-09-09 15:08:12 +00004998 return SemaRef.BuildFunctionType(T, ParamTypes, NumParamTypes, Variadic,
Douglas Gregord6ff3322009-08-04 16:50:30 +00004999 Quals,
5000 getDerived().getBaseLocation(),
5001 getDerived().getBaseEntity());
5002}
Mike Stump11289f42009-09-09 15:08:12 +00005003
Douglas Gregord6ff3322009-08-04 16:50:30 +00005004template<typename Derived>
John McCall550e0c22009-10-21 00:40:46 +00005005QualType TreeTransform<Derived>::RebuildFunctionNoProtoType(QualType T) {
5006 return SemaRef.Context.getFunctionNoProtoType(T);
5007}
5008
5009template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00005010QualType TreeTransform<Derived>::RebuildTypeOfExprType(ExprArg E) {
Douglas Gregord6ff3322009-08-04 16:50:30 +00005011 return SemaRef.BuildTypeofExprType(E.takeAs<Expr>());
5012}
5013
5014template<typename Derived>
5015QualType TreeTransform<Derived>::RebuildTypeOfType(QualType Underlying) {
5016 return SemaRef.Context.getTypeOfType(Underlying);
5017}
5018
5019template<typename Derived>
Douglas Gregora16548e2009-08-11 05:31:07 +00005020QualType TreeTransform<Derived>::RebuildDecltypeType(ExprArg E) {
Douglas Gregord6ff3322009-08-04 16:50:30 +00005021 return SemaRef.BuildDecltypeType(E.takeAs<Expr>());
5022}
5023
5024template<typename Derived>
5025QualType TreeTransform<Derived>::RebuildTemplateSpecializationType(
5026 TemplateName Template,
5027 const TemplateArgument *Args,
5028 unsigned NumArgs) {
5029 // FIXME: Missing source locations for the template name, <, >.
5030 return SemaRef.CheckTemplateIdType(Template, getDerived().getBaseLocation(),
Mike Stump11289f42009-09-09 15:08:12 +00005031 SourceLocation(), Args, NumArgs,
5032 SourceLocation());
Douglas Gregord6ff3322009-08-04 16:50:30 +00005033}
Mike Stump11289f42009-09-09 15:08:12 +00005034
Douglas Gregor1135c352009-08-06 05:28:30 +00005035template<typename Derived>
5036NestedNameSpecifier *
5037TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
5038 SourceRange Range,
Douglas Gregorc26e0f62009-09-03 16:14:30 +00005039 IdentifierInfo &II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00005040 QualType ObjectType,
5041 NamedDecl *FirstQualifierInScope) {
Douglas Gregor1135c352009-08-06 05:28:30 +00005042 CXXScopeSpec SS;
5043 // FIXME: The source location information is all wrong.
5044 SS.setRange(Range);
5045 SS.setScopeRep(Prefix);
5046 return static_cast<NestedNameSpecifier *>(
Mike Stump11289f42009-09-09 15:08:12 +00005047 SemaRef.BuildCXXNestedNameSpecifier(0, SS, Range.getEnd(),
Douglas Gregore861bac2009-08-25 22:51:20 +00005048 Range.getEnd(), II,
Douglas Gregor2b6ca462009-09-03 21:38:09 +00005049 ObjectType,
5050 FirstQualifierInScope,
Douglas Gregore861bac2009-08-25 22:51:20 +00005051 false));
Douglas Gregor1135c352009-08-06 05:28:30 +00005052}
5053
5054template<typename Derived>
5055NestedNameSpecifier *
5056TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
5057 SourceRange Range,
5058 NamespaceDecl *NS) {
5059 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, NS);
5060}
5061
5062template<typename Derived>
5063NestedNameSpecifier *
5064TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
5065 SourceRange Range,
5066 bool TemplateKW,
5067 QualType T) {
5068 if (T->isDependentType() || T->isRecordType() ||
5069 (SemaRef.getLangOptions().CPlusPlus0x && T->isEnumeralType())) {
John McCall8ccfcb52009-09-24 19:53:00 +00005070 assert(!T.hasQualifiers() && "Can't get cv-qualifiers here");
Douglas Gregor1135c352009-08-06 05:28:30 +00005071 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, TemplateKW,
5072 T.getTypePtr());
5073 }
Mike Stump11289f42009-09-09 15:08:12 +00005074
Douglas Gregor1135c352009-08-06 05:28:30 +00005075 SemaRef.Diag(Range.getBegin(), diag::err_nested_name_spec_non_tag) << T;
5076 return 0;
5077}
Mike Stump11289f42009-09-09 15:08:12 +00005078
Douglas Gregor71dc5092009-08-06 06:41:21 +00005079template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005080TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005081TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
5082 bool TemplateKW,
5083 TemplateDecl *Template) {
Mike Stump11289f42009-09-09 15:08:12 +00005084 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW,
Douglas Gregor71dc5092009-08-06 06:41:21 +00005085 Template);
5086}
5087
5088template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005089TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005090TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
5091 bool TemplateKW,
5092 OverloadedFunctionDecl *Ovl) {
5093 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW, Ovl);
5094}
5095
5096template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005097TemplateName
Douglas Gregor71dc5092009-08-06 06:41:21 +00005098TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
Douglas Gregor308047d2009-09-09 00:23:06 +00005099 const IdentifierInfo &II,
5100 QualType ObjectType) {
Douglas Gregor71dc5092009-08-06 06:41:21 +00005101 CXXScopeSpec SS;
5102 SS.setRange(SourceRange(getDerived().getBaseLocation()));
Mike Stump11289f42009-09-09 15:08:12 +00005103 SS.setScopeRep(Qualifier);
Douglas Gregor308047d2009-09-09 00:23:06 +00005104 return getSema().ActOnDependentTemplateName(
5105 /*FIXME:*/getDerived().getBaseLocation(),
5106 II,
5107 /*FIXME:*/getDerived().getBaseLocation(),
5108 SS,
5109 ObjectType.getAsOpaquePtr())
5110 .template getAsVal<TemplateName>();
Douglas Gregor71dc5092009-08-06 06:41:21 +00005111}
Mike Stump11289f42009-09-09 15:08:12 +00005112
Douglas Gregora16548e2009-08-11 05:31:07 +00005113template<typename Derived>
Mike Stump11289f42009-09-09 15:08:12 +00005114Sema::OwningExprResult
Douglas Gregora16548e2009-08-11 05:31:07 +00005115TreeTransform<Derived>::RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
5116 SourceLocation OpLoc,
5117 ExprArg Callee,
5118 ExprArg First,
5119 ExprArg Second) {
5120 Expr *FirstExpr = (Expr *)First.get();
5121 Expr *SecondExpr = (Expr *)Second.get();
5122 bool isPostIncDec = SecondExpr && (Op == OO_PlusPlus || Op == OO_MinusMinus);
Mike Stump11289f42009-09-09 15:08:12 +00005123
Douglas Gregora16548e2009-08-11 05:31:07 +00005124 // Determine whether this should be a builtin operation.
5125 if (SecondExpr == 0 || isPostIncDec) {
5126 if (!FirstExpr->getType()->isOverloadableType()) {
5127 // The argument is not of overloadable type, so try to create a
5128 // built-in unary operation.
Mike Stump11289f42009-09-09 15:08:12 +00005129 UnaryOperator::Opcode Opc
Douglas Gregora16548e2009-08-11 05:31:07 +00005130 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
Mike Stump11289f42009-09-09 15:08:12 +00005131
Douglas Gregora16548e2009-08-11 05:31:07 +00005132 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(First));
5133 }
5134 } else {
Mike Stump11289f42009-09-09 15:08:12 +00005135 if (!FirstExpr->getType()->isOverloadableType() &&
Douglas Gregora16548e2009-08-11 05:31:07 +00005136 !SecondExpr->getType()->isOverloadableType()) {
5137 // Neither of the arguments is an overloadable type, so try to
5138 // create a built-in binary operation.
5139 BinaryOperator::Opcode Opc = BinaryOperator::getOverloadedOpcode(Op);
Mike Stump11289f42009-09-09 15:08:12 +00005140 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00005141 = SemaRef.CreateBuiltinBinOp(OpLoc, Opc, FirstExpr, SecondExpr);
5142 if (Result.isInvalid())
5143 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00005144
Douglas Gregora16548e2009-08-11 05:31:07 +00005145 First.release();
5146 Second.release();
5147 return move(Result);
5148 }
5149 }
Mike Stump11289f42009-09-09 15:08:12 +00005150
5151 // Compute the transformed set of functions (and function templates) to be
Douglas Gregora16548e2009-08-11 05:31:07 +00005152 // used during overload resolution.
5153 Sema::FunctionSet Functions;
Mike Stump11289f42009-09-09 15:08:12 +00005154
5155 DeclRefExpr *DRE
Douglas Gregor32e2c842009-09-01 16:58:52 +00005156 = cast<DeclRefExpr>(((Expr *)Callee.get())->IgnoreParenCasts());
Mike Stump11289f42009-09-09 15:08:12 +00005157
Douglas Gregora16548e2009-08-11 05:31:07 +00005158 // FIXME: Do we have to check
5159 // IsAcceptableNonMemberOperatorCandidate for each of these?
Douglas Gregor32e2c842009-09-01 16:58:52 +00005160 for (OverloadIterator F(DRE->getDecl()), FEnd; F != FEnd; ++F)
Douglas Gregora16548e2009-08-11 05:31:07 +00005161 Functions.insert(*F);
Mike Stump11289f42009-09-09 15:08:12 +00005162
Douglas Gregora16548e2009-08-11 05:31:07 +00005163 // Add any functions found via argument-dependent lookup.
5164 Expr *Args[2] = { FirstExpr, SecondExpr };
5165 unsigned NumArgs = 1 + (SecondExpr != 0);
Mike Stump11289f42009-09-09 15:08:12 +00005166 DeclarationName OpName
Douglas Gregora16548e2009-08-11 05:31:07 +00005167 = SemaRef.Context.DeclarationNames.getCXXOperatorName(Op);
5168 SemaRef.ArgumentDependentLookup(OpName, Args, NumArgs, Functions);
Mike Stump11289f42009-09-09 15:08:12 +00005169
Douglas Gregora16548e2009-08-11 05:31:07 +00005170 // Create the overloaded operator invocation for unary operators.
5171 if (NumArgs == 1 || isPostIncDec) {
Mike Stump11289f42009-09-09 15:08:12 +00005172 UnaryOperator::Opcode Opc
Douglas Gregora16548e2009-08-11 05:31:07 +00005173 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
5174 return SemaRef.CreateOverloadedUnaryOp(OpLoc, Opc, Functions, move(First));
5175 }
Mike Stump11289f42009-09-09 15:08:12 +00005176
Douglas Gregora16548e2009-08-11 05:31:07 +00005177 // Create the overloaded operator invocation for binary operators.
Mike Stump11289f42009-09-09 15:08:12 +00005178 BinaryOperator::Opcode Opc =
Douglas Gregora16548e2009-08-11 05:31:07 +00005179 BinaryOperator::getOverloadedOpcode(Op);
Mike Stump11289f42009-09-09 15:08:12 +00005180 OwningExprResult Result
Douglas Gregora16548e2009-08-11 05:31:07 +00005181 = SemaRef.CreateOverloadedBinOp(OpLoc, Opc, Functions, Args[0], Args[1]);
5182 if (Result.isInvalid())
5183 return SemaRef.ExprError();
Mike Stump11289f42009-09-09 15:08:12 +00005184
Douglas Gregora16548e2009-08-11 05:31:07 +00005185 First.release();
5186 Second.release();
Mike Stump11289f42009-09-09 15:08:12 +00005187 return move(Result);
Douglas Gregora16548e2009-08-11 05:31:07 +00005188}
Mike Stump11289f42009-09-09 15:08:12 +00005189
Douglas Gregord6ff3322009-08-04 16:50:30 +00005190} // end namespace clang
5191
5192#endif // LLVM_CLANG_SEMA_TREETRANSFORM_H