blob: 7babcf76b7acc8eb2c03a91f0a4577b5ee9a2b48 [file] [log] [blame]
Douglas Gregor841324a2009-08-04 16:50:30 +00001//===------- TreeTransform.h - Semantic Tree Transformation ---------------===/
2//
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 Gregor12431cb2009-08-06 05:28:30 +000017#include "clang/Sema/SemaDiagnostic.h"
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +000018#include "clang/AST/Decl.h"
Douglas Gregor72f34bb2009-08-06 22:17:10 +000019#include "clang/AST/Expr.h"
Douglas Gregor9d879762009-08-11 05:31:07 +000020#include "clang/AST/ExprCXX.h"
21#include "clang/AST/ExprObjC.h"
Douglas Gregor23a44be2009-08-20 07:17:43 +000022#include "clang/AST/Stmt.h"
23#include "clang/AST/StmtCXX.h"
24#include "clang/AST/StmtObjC.h"
Douglas Gregor9d879762009-08-11 05:31:07 +000025#include "clang/Parse/Ownership.h"
26#include "clang/Parse/Designator.h"
27#include "clang/Lex/Preprocessor.h"
Douglas Gregor841324a2009-08-04 16:50:30 +000028#include <algorithm>
29
30namespace clang {
31
32/// \brief A semantic tree transformation that allows one to transform one
33/// abstract syntax tree into another.
34///
35/// A new tree transformation is defined by creating a new subclass \c X of
36/// \c TreeTransform<X> and then overriding certain operations to provide
37/// behavior specific to that transformation. For example, template
38/// instantiation is implemented as a tree transformation where the
39/// transformation of TemplateTypeParmType nodes involves substituting the
40/// template arguments for their corresponding template parameters; a similar
41/// transformation is performed for non-type template parameters and
42/// template template parameters.
43///
44/// This tree-transformation template uses static polymorphism to allow
45/// subclasses to customize any of its operations. Thus, a subclass can
46/// override any of the transformation or rebuild operators by providing an
47/// operation with the same signature as the default implementation. The
48/// overridding function should not be virtual.
49///
50/// Semantic tree transformations are split into two stages, either of which
51/// can be replaced by a subclass. The "transform" step transforms an AST node
52/// or the parts of an AST node using the various transformation functions,
53/// then passes the pieces on to the "rebuild" step, which constructs a new AST
54/// node of the appropriate kind from the pieces. The default transformation
55/// routines recursively transform the operands to composite AST nodes (e.g.,
56/// the pointee type of a PointerType node) and, if any of those operand nodes
57/// were changed by the transformation, invokes the rebuild operation to create
58/// a new AST node.
59///
60/// Subclasses can customize the transformation at various levels. The
Douglas Gregor2999faa2009-08-04 22:27:00 +000061/// most coarse-grained transformations involve replacing TransformType(),
Douglas Gregor841324a2009-08-04 16:50:30 +000062/// TransformExpr(), TransformDecl(), TransformNestedNameSpecifier(),
63/// TransformTemplateName(), or TransformTemplateArgument() with entirely
64/// new implementations.
65///
66/// For more fine-grained transformations, subclasses can replace any of the
67/// \c TransformXXX functions (where XXX is the name of an AST node, e.g.,
Douglas Gregor23a44be2009-08-20 07:17:43 +000068/// PointerType, StmtExpr) to alter the transformation. As mentioned previously,
Douglas Gregor841324a2009-08-04 16:50:30 +000069/// replacing TransformTemplateTypeParmType() allows template instantiation
70/// to substitute template arguments for their corresponding template
71/// parameters. Additionally, subclasses can override the \c RebuildXXX
72/// functions to control how AST nodes are rebuilt when their operands change.
73/// By default, \c TreeTransform will invoke semantic analysis to rebuild
74/// AST nodes. However, certain other tree transformations (e.g, cloning) may
75/// be able to use more efficient rebuild steps.
76///
77/// There are a handful of other functions that can be overridden, allowing one
78/// to avoid traversing nodes that don't need any transformation
79/// (\c AlreadyTransformed()), force rebuilding AST nodes even when their
80/// operands have not changed (\c AlwaysRebuild()), and customize the
81/// default locations and entity names used for type-checking
82/// (\c getBaseLocation(), \c getBaseEntity()).
Douglas Gregor841324a2009-08-04 16:50:30 +000083template<typename Derived>
84class TreeTransform {
85protected:
86 Sema &SemaRef;
87
88public:
Douglas Gregor9d879762009-08-11 05:31:07 +000089 typedef Sema::OwningStmtResult OwningStmtResult;
90 typedef Sema::OwningExprResult OwningExprResult;
91 typedef Sema::StmtArg StmtArg;
92 typedef Sema::ExprArg ExprArg;
93 typedef Sema::MultiExprArg MultiExprArg;
Douglas Gregor23a44be2009-08-20 07:17:43 +000094 typedef Sema::MultiStmtArg MultiStmtArg;
Douglas Gregor9d879762009-08-11 05:31:07 +000095
Douglas Gregor841324a2009-08-04 16:50:30 +000096 /// \brief Initializes a new tree transformer.
97 TreeTransform(Sema &SemaRef) : SemaRef(SemaRef) { }
98
99 /// \brief Retrieves a reference to the derived class.
100 Derived &getDerived() { return static_cast<Derived&>(*this); }
101
102 /// \brief Retrieves a reference to the derived class.
103 const Derived &getDerived() const {
104 return static_cast<const Derived&>(*this);
105 }
106
107 /// \brief Retrieves a reference to the semantic analysis object used for
108 /// this tree transform.
109 Sema &getSema() const { return SemaRef; }
110
111 /// \brief Whether the transformation should always rebuild AST nodes, even
112 /// if none of the children have changed.
113 ///
114 /// Subclasses may override this function to specify when the transformation
115 /// should rebuild all AST nodes.
116 bool AlwaysRebuild() { return false; }
117
118 /// \brief Returns the location of the entity being transformed, if that
119 /// information was not available elsewhere in the AST.
120 ///
121 /// By default, returns no source-location information. Subclasses can
122 /// provide an alternative implementation that provides better location
123 /// information.
124 SourceLocation getBaseLocation() { return SourceLocation(); }
125
126 /// \brief Returns the name of the entity being transformed, if that
127 /// information was not available elsewhere in the AST.
128 ///
129 /// By default, returns an empty name. Subclasses can provide an alternative
130 /// implementation with a more precise name.
131 DeclarationName getBaseEntity() { return DeclarationName(); }
132
Douglas Gregor9d879762009-08-11 05:31:07 +0000133 /// \brief Sets the "base" location and entity when that
134 /// information is known based on another transformation.
135 ///
136 /// By default, the source location and entity are ignored. Subclasses can
137 /// override this function to provide a customized implementation.
138 void setBase(SourceLocation Loc, DeclarationName Entity) { }
139
140 /// \brief RAII object that temporarily sets the base location and entity
141 /// used for reporting diagnostics in types.
142 class TemporaryBase {
143 TreeTransform &Self;
144 SourceLocation OldLocation;
145 DeclarationName OldEntity;
146
147 public:
148 TemporaryBase(TreeTransform &Self, SourceLocation Location,
149 DeclarationName Entity) : Self(Self)
150 {
151 OldLocation = Self.getDerived().getBaseLocation();
152 OldEntity = Self.getDerived().getBaseEntity();
153 Self.getDerived().setBase(Location, Entity);
154 }
155
156 ~TemporaryBase() {
157 Self.getDerived().setBase(OldLocation, OldEntity);
158 }
159 };
160
Douglas Gregor841324a2009-08-04 16:50:30 +0000161 /// \brief Determine whether the given type \p T has already been
162 /// transformed.
163 ///
164 /// Subclasses can provide an alternative implementation of this routine
165 /// to short-circuit evaluation when it is known that a given type will
166 /// not change. For example, template instantiation need not traverse
167 /// non-dependent types.
168 bool AlreadyTransformed(QualType T) {
169 return T.isNull();
170 }
171
172 /// \brief Transforms the given type into another type.
173 ///
174 /// By default, this routine transforms a type by delegating to the
175 /// appropriate TransformXXXType to build a new type, then applying
176 /// the qualifiers on \p T to the resulting type with AddTypeQualifiers.
177 /// Subclasses may override this function (to take over all type
178 /// transformations), some set of the TransformXXXType functions, or
179 /// the AddTypeQualifiers function to alter the transformation.
180 ///
181 /// \returns the transformed type.
182 QualType TransformType(QualType T);
183
184 /// \brief Transform the given type by adding the given set of qualifiers
185 /// and returning the result.
186 ///
187 /// FIXME: By default, this routine adds type qualifiers only to types that
188 /// can have qualifiers, and silently suppresses those qualifiers that are
189 /// not permitted (e.g., qualifiers on reference or function types). This
190 /// is the right thing for template instantiation, but probably not for
191 /// other clients.
192 QualType AddTypeQualifiers(QualType T, unsigned CVRQualifiers);
193
Douglas Gregor72f34bb2009-08-06 22:17:10 +0000194 /// \brief Transform the given statement.
Douglas Gregor841324a2009-08-04 16:50:30 +0000195 ///
Douglas Gregor23a44be2009-08-20 07:17:43 +0000196 /// By default, this routine transforms a statement by delegating to the
197 /// appropriate TransformXXXStmt function to transform a specific kind of
198 /// statement or the TransformExpr() function to transform an expression.
199 /// Subclasses may override this function to transform statements using some
200 /// other mechanism.
201 ///
202 /// \returns the transformed statement.
Douglas Gregor9d879762009-08-11 05:31:07 +0000203 OwningStmtResult TransformStmt(Stmt *S);
Douglas Gregor72f34bb2009-08-06 22:17:10 +0000204
205 /// \brief Transform the given expression.
206 ///
Douglas Gregor9d879762009-08-11 05:31:07 +0000207 /// By default, this routine transforms an expression by delegating to the
208 /// appropriate TransformXXXExpr function to build a new expression.
209 /// Subclasses may override this function to transform expressions using some
210 /// other mechanism.
211 ///
212 /// \returns the transformed expression.
213 OwningExprResult TransformExpr(Expr *E) {
214 return getDerived().TransformExpr(E, /*isAddressOfOperand=*/false);
215 }
216
217 /// \brief Transform the given expression.
218 ///
219 /// By default, this routine transforms an expression by delegating to the
220 /// appropriate TransformXXXExpr function to build a new expression.
221 /// Subclasses may override this function to transform expressions using some
222 /// other mechanism.
223 ///
224 /// \returns the transformed expression.
225 OwningExprResult TransformExpr(Expr *E, bool isAddressOfOperand);
Douglas Gregor841324a2009-08-04 16:50:30 +0000226
227 /// \brief Transform the given declaration, which is referenced from a type
228 /// or expression.
229 ///
Douglas Gregor12431cb2009-08-06 05:28:30 +0000230 /// By default, acts as the identity function on declarations. Subclasses
231 /// may override this function to provide alternate behavior.
232 Decl *TransformDecl(Decl *D) { return D; }
Douglas Gregor23a44be2009-08-20 07:17:43 +0000233
234 /// \brief Transform the definition of the given declaration.
235 ///
236 /// By default, invokes TransformDecl() to transform the declaration.
237 /// Subclasses may override this function to provide alternate behavior.
238 Decl *TransformDefinition(Decl *D) { return getDerived().TransformDecl(D); }
Douglas Gregor841324a2009-08-04 16:50:30 +0000239
240 /// \brief Transform the given nested-name-specifier.
241 ///
Douglas Gregor12431cb2009-08-06 05:28:30 +0000242 /// By default, transforms all of the types and declarations within the
243 /// nested-name-specifier. Subclasses may override this function to provide
244 /// alternate behavior.
Douglas Gregor841324a2009-08-04 16:50:30 +0000245 NestedNameSpecifier *TransformNestedNameSpecifier(NestedNameSpecifier *NNS,
Douglas Gregor0f927cf2009-09-03 16:14:30 +0000246 SourceRange Range,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +0000247 QualType ObjectType = QualType(),
248 NamedDecl *FirstQualifierInScope = 0);
Douglas Gregor841324a2009-08-04 16:50:30 +0000249
250 /// \brief Transform the given template name.
251 ///
Douglas Gregor214d0462009-08-06 06:41:21 +0000252 /// By default, transforms the template name by transforming the declarations
253 /// and nested-name-specifiers that occur within the template name.
254 /// Subclasses may override this function to provide alternate behavior.
255 TemplateName TransformTemplateName(TemplateName Name);
Douglas Gregor841324a2009-08-04 16:50:30 +0000256
257 /// \brief Transform the given template argument.
258 ///
Douglas Gregor2999faa2009-08-04 22:27:00 +0000259 /// By default, this operation transforms the type, expression, or
260 /// declaration stored within the template argument and constructs a
261 /// new template argument from the transformed result. Subclasses may
262 /// override this function to provide alternate behavior.
Douglas Gregor841324a2009-08-04 16:50:30 +0000263 TemplateArgument TransformTemplateArgument(const TemplateArgument &Arg);
264
265#define ABSTRACT_TYPE(CLASS, PARENT)
266#define TYPE(CLASS, PARENT) \
267 QualType Transform##CLASS##Type(const CLASS##Type *T);
268#include "clang/AST/TypeNodes.def"
269
Douglas Gregor23a44be2009-08-20 07:17:43 +0000270 OwningStmtResult TransformCompoundStmt(CompoundStmt *S, bool IsStmtExpr);
Douglas Gregor9d879762009-08-11 05:31:07 +0000271
Douglas Gregor23a44be2009-08-20 07:17:43 +0000272#define STMT(Node, Parent) \
273 OwningStmtResult Transform##Node(Node *S);
Douglas Gregor9d879762009-08-11 05:31:07 +0000274#define EXPR(Node, Parent) \
275 OwningExprResult Transform##Node(Node *E);
276#define ABSTRACT_EXPR(Node, Parent)
277#include "clang/AST/StmtNodes.def"
278
Douglas Gregor841324a2009-08-04 16:50:30 +0000279 /// \brief Build a new pointer type given its pointee type.
280 ///
281 /// By default, performs semantic analysis when building the pointer type.
282 /// Subclasses may override this routine to provide different behavior.
283 QualType RebuildPointerType(QualType PointeeType);
284
285 /// \brief Build a new block pointer type given its pointee type.
286 ///
287 /// By default, performs semantic analysis when building the block pointer
288 /// type. Subclasses may override this routine to provide different behavior.
289 QualType RebuildBlockPointerType(QualType PointeeType);
290
291 /// \brief Build a new lvalue reference type given the type it references.
292 ///
293 /// By default, performs semantic analysis when building the lvalue reference
294 /// type. Subclasses may override this routine to provide different behavior.
295 QualType RebuildLValueReferenceType(QualType ReferentType);
296
297 /// \brief Build a new rvalue reference type given the type it references.
298 ///
299 /// By default, performs semantic analysis when building the rvalue reference
300 /// type. Subclasses may override this routine to provide different behavior.
301 QualType RebuildRValueReferenceType(QualType ReferentType);
302
303 /// \brief Build a new member pointer type given the pointee type and the
304 /// class type it refers into.
305 ///
306 /// By default, performs semantic analysis when building the member pointer
307 /// type. Subclasses may override this routine to provide different behavior.
308 QualType RebuildMemberPointerType(QualType PointeeType, QualType ClassType);
309
310 /// \brief Build a new array type given the element type, size
311 /// modifier, size of the array (if known), size expression, and index type
312 /// qualifiers.
313 ///
314 /// By default, performs semantic analysis when building the array type.
315 /// Subclasses may override this routine to provide different behavior.
316 /// Also by default, all of the other Rebuild*Array
317 QualType RebuildArrayType(QualType ElementType,
318 ArrayType::ArraySizeModifier SizeMod,
319 const llvm::APInt *Size,
320 Expr *SizeExpr,
321 unsigned IndexTypeQuals,
322 SourceRange BracketsRange);
323
324 /// \brief Build a new constant array type given the element type, size
325 /// modifier, (known) size of the array, and index type qualifiers.
326 ///
327 /// By default, performs semantic analysis when building the array type.
328 /// Subclasses may override this routine to provide different behavior.
329 QualType RebuildConstantArrayType(QualType ElementType,
330 ArrayType::ArraySizeModifier SizeMod,
331 const llvm::APInt &Size,
332 unsigned IndexTypeQuals);
333
334 /// \brief Build a new constant array type given the element type, size
335 /// modifier, (known) size of the array, size expression, and index type
336 /// qualifiers.
337 ///
338 /// By default, performs semantic analysis when building the array type.
339 /// Subclasses may override this routine to provide different behavior.
340 QualType RebuildConstantArrayWithExprType(QualType ElementType,
341 ArrayType::ArraySizeModifier SizeMod,
342 const llvm::APInt &Size,
343 Expr *SizeExpr,
344 unsigned IndexTypeQuals,
345 SourceRange BracketsRange);
346
347 /// \brief Build a new constant array type given the element type, size
348 /// modifier, (known) size of the array, and index type qualifiers.
349 ///
350 /// By default, performs semantic analysis when building the array type.
351 /// Subclasses may override this routine to provide different behavior.
352 QualType RebuildConstantArrayWithoutExprType(QualType ElementType,
353 ArrayType::ArraySizeModifier SizeMod,
354 const llvm::APInt &Size,
355 unsigned IndexTypeQuals);
356
357 /// \brief Build a new incomplete array type given the element type, size
358 /// modifier, and index type qualifiers.
359 ///
360 /// By default, performs semantic analysis when building the array type.
361 /// Subclasses may override this routine to provide different behavior.
362 QualType RebuildIncompleteArrayType(QualType ElementType,
363 ArrayType::ArraySizeModifier SizeMod,
364 unsigned IndexTypeQuals);
365
366 /// \brief Build a new variable-length array type given the element type,
367 /// size modifier, size expression, and index type qualifiers.
368 ///
369 /// By default, performs semantic analysis when building the array type.
370 /// Subclasses may override this routine to provide different behavior.
371 QualType RebuildVariableArrayType(QualType ElementType,
372 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregor9d879762009-08-11 05:31:07 +0000373 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +0000374 unsigned IndexTypeQuals,
375 SourceRange BracketsRange);
376
377 /// \brief Build a new dependent-sized array type given the element type,
378 /// size modifier, size expression, and index type qualifiers.
379 ///
380 /// By default, performs semantic analysis when building the array type.
381 /// Subclasses may override this routine to provide different behavior.
382 QualType RebuildDependentSizedArrayType(QualType ElementType,
383 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregor9d879762009-08-11 05:31:07 +0000384 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +0000385 unsigned IndexTypeQuals,
386 SourceRange BracketsRange);
387
388 /// \brief Build a new vector type given the element type and
389 /// number of elements.
390 ///
391 /// By default, performs semantic analysis when building the vector type.
392 /// Subclasses may override this routine to provide different behavior.
393 QualType RebuildVectorType(QualType ElementType, unsigned NumElements);
394
395 /// \brief Build a new extended vector type given the element type and
396 /// number of elements.
397 ///
398 /// By default, performs semantic analysis when building the vector type.
399 /// Subclasses may override this routine to provide different behavior.
400 QualType RebuildExtVectorType(QualType ElementType, unsigned NumElements,
401 SourceLocation AttributeLoc);
402
403 /// \brief Build a new potentially dependently-sized extended vector type
404 /// given the element type and number of elements.
405 ///
406 /// By default, performs semantic analysis when building the vector type.
407 /// Subclasses may override this routine to provide different behavior.
408 QualType RebuildDependentSizedExtVectorType(QualType ElementType,
Douglas Gregor9d879762009-08-11 05:31:07 +0000409 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +0000410 SourceLocation AttributeLoc);
411
412 /// \brief Build a new function type.
413 ///
414 /// By default, performs semantic analysis when building the function type.
415 /// Subclasses may override this routine to provide different behavior.
416 QualType RebuildFunctionProtoType(QualType T,
417 QualType *ParamTypes,
418 unsigned NumParamTypes,
419 bool Variadic, unsigned Quals);
420
421 /// \brief Build a new typedef type.
422 QualType RebuildTypedefType(TypedefDecl *Typedef) {
423 return SemaRef.Context.getTypeDeclType(Typedef);
424 }
425
426 /// \brief Build a new class/struct/union type.
427 QualType RebuildRecordType(RecordDecl *Record) {
428 return SemaRef.Context.getTypeDeclType(Record);
429 }
430
431 /// \brief Build a new Enum type.
432 QualType RebuildEnumType(EnumDecl *Enum) {
433 return SemaRef.Context.getTypeDeclType(Enum);
434 }
435
436 /// \brief Build a new typeof(expr) type.
437 ///
438 /// By default, performs semantic analysis when building the typeof type.
439 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor9d879762009-08-11 05:31:07 +0000440 QualType RebuildTypeOfExprType(ExprArg Underlying);
Douglas Gregor841324a2009-08-04 16:50:30 +0000441
442 /// \brief Build a new typeof(type) type.
443 ///
444 /// By default, builds a new TypeOfType with the given underlying type.
445 QualType RebuildTypeOfType(QualType Underlying);
446
447 /// \brief Build a new C++0x decltype type.
448 ///
449 /// By default, performs semantic analysis when building the decltype type.
450 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor9d879762009-08-11 05:31:07 +0000451 QualType RebuildDecltypeType(ExprArg Underlying);
Douglas Gregor841324a2009-08-04 16:50:30 +0000452
453 /// \brief Build a new template specialization type.
454 ///
455 /// By default, performs semantic analysis when building the template
456 /// specialization type. Subclasses may override this routine to provide
457 /// different behavior.
458 QualType RebuildTemplateSpecializationType(TemplateName Template,
459 const TemplateArgument *Args,
460 unsigned NumArgs);
461
462 /// \brief Build a new qualified name type.
463 ///
464 /// By default, builds a new QualifiedNameType type from the
465 /// nested-name-specifier and the named type. Subclasses may override
466 /// this routine to provide different behavior.
467 QualType RebuildQualifiedNameType(NestedNameSpecifier *NNS, QualType Named) {
468 return SemaRef.Context.getQualifiedNameType(NNS, Named);
469 }
470
471 /// \brief Build a new typename type that refers to a template-id.
472 ///
473 /// By default, builds a new TypenameType type from the nested-name-specifier
474 /// and the given type. Subclasses may override this routine to provide
475 /// different behavior.
476 QualType RebuildTypenameType(NestedNameSpecifier *NNS, QualType T) {
477 if (NNS->isDependent())
478 return SemaRef.Context.getTypenameType(NNS,
479 cast<TemplateSpecializationType>(T));
480
481 return SemaRef.Context.getQualifiedNameType(NNS, T);
482 }
483
484 /// \brief Build a new typename type that refers to an identifier.
485 ///
486 /// By default, performs semantic analysis when building the typename type
487 /// (or qualified name type). Subclasses may override this routine to provide
488 /// different behavior.
489 QualType RebuildTypenameType(NestedNameSpecifier *NNS,
490 const IdentifierInfo *Id) {
491 return SemaRef.CheckTypenameType(NNS, *Id,
492 SourceRange(getDerived().getBaseLocation()));
Douglas Gregor12431cb2009-08-06 05:28:30 +0000493 }
494
495 /// \brief Build a new nested-name-specifier given the prefix and an
496 /// identifier that names the next step in the nested-name-specifier.
497 ///
498 /// By default, performs semantic analysis when building the new
499 /// nested-name-specifier. Subclasses may override this routine to provide
500 /// different behavior.
501 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
502 SourceRange Range,
Douglas Gregor0f927cf2009-09-03 16:14:30 +0000503 IdentifierInfo &II,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +0000504 QualType ObjectType,
505 NamedDecl *FirstQualifierInScope);
Douglas Gregor12431cb2009-08-06 05:28:30 +0000506
507 /// \brief Build a new nested-name-specifier given the prefix and the
508 /// namespace named in the next step in the nested-name-specifier.
509 ///
510 /// By default, performs semantic analysis when building the new
511 /// nested-name-specifier. Subclasses may override this routine to provide
512 /// different behavior.
513 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
514 SourceRange Range,
515 NamespaceDecl *NS);
516
517 /// \brief Build a new nested-name-specifier given the prefix and the
518 /// type named in the next step in the nested-name-specifier.
519 ///
520 /// By default, performs semantic analysis when building the new
521 /// nested-name-specifier. Subclasses may override this routine to provide
522 /// different behavior.
523 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
524 SourceRange Range,
525 bool TemplateKW,
526 QualType T);
Douglas Gregor214d0462009-08-06 06:41:21 +0000527
528 /// \brief Build a new template name given a nested name specifier, a flag
529 /// indicating whether the "template" keyword was provided, and the template
530 /// that the template name refers to.
531 ///
532 /// By default, builds the new template name directly. Subclasses may override
533 /// this routine to provide different behavior.
534 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
535 bool TemplateKW,
536 TemplateDecl *Template);
537
538 /// \brief Build a new template name given a nested name specifier, a flag
539 /// indicating whether the "template" keyword was provided, and a set of
540 /// overloaded function templates.
541 ///
542 /// By default, builds the new template name directly. Subclasses may override
543 /// this routine to provide different behavior.
544 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
545 bool TemplateKW,
546 OverloadedFunctionDecl *Ovl);
547
548 /// \brief Build a new template name given a nested name specifier and the
549 /// name that is referred to as a template.
550 ///
551 /// By default, performs semantic analysis to determine whether the name can
552 /// be resolved to a specific template, then builds the appropriate kind of
553 /// template name. Subclasses may override this routine to provide different
554 /// behavior.
555 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier,
556 const IdentifierInfo &II);
Douglas Gregor9d879762009-08-11 05:31:07 +0000557
558
Douglas Gregor23a44be2009-08-20 07:17:43 +0000559 /// \brief Build a new compound statement.
560 ///
561 /// By default, performs semantic analysis to build the new statement.
562 /// Subclasses may override this routine to provide different behavior.
563 OwningStmtResult RebuildCompoundStmt(SourceLocation LBraceLoc,
564 MultiStmtArg Statements,
565 SourceLocation RBraceLoc,
566 bool IsStmtExpr) {
567 return getSema().ActOnCompoundStmt(LBraceLoc, RBraceLoc, move(Statements),
568 IsStmtExpr);
569 }
570
571 /// \brief Build a new case statement.
572 ///
573 /// By default, performs semantic analysis to build the new statement.
574 /// Subclasses may override this routine to provide different behavior.
575 OwningStmtResult RebuildCaseStmt(SourceLocation CaseLoc,
576 ExprArg LHS,
577 SourceLocation EllipsisLoc,
578 ExprArg RHS,
579 SourceLocation ColonLoc) {
580 return getSema().ActOnCaseStmt(CaseLoc, move(LHS), EllipsisLoc, move(RHS),
581 ColonLoc);
582 }
583
584 /// \brief Attach the body to a new case statement.
585 ///
586 /// By default, performs semantic analysis to build the new statement.
587 /// Subclasses may override this routine to provide different behavior.
588 OwningStmtResult RebuildCaseStmtBody(StmtArg S, StmtArg Body) {
589 getSema().ActOnCaseStmtBody(S.get(), move(Body));
590 return move(S);
591 }
592
593 /// \brief Build a new default statement.
594 ///
595 /// By default, performs semantic analysis to build the new statement.
596 /// Subclasses may override this routine to provide different behavior.
597 OwningStmtResult RebuildDefaultStmt(SourceLocation DefaultLoc,
598 SourceLocation ColonLoc,
599 StmtArg SubStmt) {
600 return getSema().ActOnDefaultStmt(DefaultLoc, ColonLoc, move(SubStmt),
601 /*CurScope=*/0);
602 }
603
604 /// \brief Build a new label statement.
605 ///
606 /// By default, performs semantic analysis to build the new statement.
607 /// Subclasses may override this routine to provide different behavior.
608 OwningStmtResult RebuildLabelStmt(SourceLocation IdentLoc,
609 IdentifierInfo *Id,
610 SourceLocation ColonLoc,
611 StmtArg SubStmt) {
612 return SemaRef.ActOnLabelStmt(IdentLoc, Id, ColonLoc, move(SubStmt));
613 }
614
615 /// \brief Build a new "if" 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 RebuildIfStmt(SourceLocation IfLoc, Sema::FullExprArg Cond,
620 StmtArg Then, SourceLocation ElseLoc,
621 StmtArg Else) {
622 return getSema().ActOnIfStmt(IfLoc, Cond, move(Then), ElseLoc, move(Else));
623 }
624
625 /// \brief Start building a new switch statement.
626 ///
627 /// By default, performs semantic analysis to build the new statement.
628 /// Subclasses may override this routine to provide different behavior.
629 OwningStmtResult RebuildSwitchStmtStart(ExprArg Cond) {
630 return getSema().ActOnStartOfSwitchStmt(move(Cond));
631 }
632
633 /// \brief Attach the body to the switch statement.
634 ///
635 /// By default, performs semantic analysis to build the new statement.
636 /// Subclasses may override this routine to provide different behavior.
637 OwningStmtResult RebuildSwitchStmtBody(SourceLocation SwitchLoc,
638 StmtArg Switch, StmtArg Body) {
639 return getSema().ActOnFinishSwitchStmt(SwitchLoc, move(Switch),
640 move(Body));
641 }
642
643 /// \brief Build a new while statement.
644 ///
645 /// By default, performs semantic analysis to build the new statement.
646 /// Subclasses may override this routine to provide different behavior.
647 OwningStmtResult RebuildWhileStmt(SourceLocation WhileLoc,
648 Sema::FullExprArg Cond,
649 StmtArg Body) {
650 return getSema().ActOnWhileStmt(WhileLoc, Cond, move(Body));
651 }
652
653 /// \brief Build a new do-while statement.
654 ///
655 /// By default, performs semantic analysis to build the new statement.
656 /// Subclasses may override this routine to provide different behavior.
657 OwningStmtResult RebuildDoStmt(SourceLocation DoLoc, StmtArg Body,
658 SourceLocation WhileLoc,
659 SourceLocation LParenLoc,
660 ExprArg Cond,
661 SourceLocation RParenLoc) {
662 return getSema().ActOnDoStmt(DoLoc, move(Body), WhileLoc, LParenLoc,
663 move(Cond), RParenLoc);
664 }
665
666 /// \brief Build a new for statement.
667 ///
668 /// By default, performs semantic analysis to build the new statement.
669 /// Subclasses may override this routine to provide different behavior.
670 OwningStmtResult RebuildForStmt(SourceLocation ForLoc,
671 SourceLocation LParenLoc,
672 StmtArg Init, ExprArg Cond, ExprArg Inc,
673 SourceLocation RParenLoc, StmtArg Body) {
674 return getSema().ActOnForStmt(ForLoc, LParenLoc, move(Init), move(Cond),
675 move(Inc), RParenLoc, move(Body));
676 }
677
678 /// \brief Build a new goto statement.
679 ///
680 /// By default, performs semantic analysis to build the new statement.
681 /// Subclasses may override this routine to provide different behavior.
682 OwningStmtResult RebuildGotoStmt(SourceLocation GotoLoc,
683 SourceLocation LabelLoc,
684 LabelStmt *Label) {
685 return getSema().ActOnGotoStmt(GotoLoc, LabelLoc, Label->getID());
686 }
687
688 /// \brief Build a new indirect goto statement.
689 ///
690 /// By default, performs semantic analysis to build the new statement.
691 /// Subclasses may override this routine to provide different behavior.
692 OwningStmtResult RebuildIndirectGotoStmt(SourceLocation GotoLoc,
693 SourceLocation StarLoc,
694 ExprArg Target) {
695 return getSema().ActOnIndirectGotoStmt(GotoLoc, StarLoc, move(Target));
696 }
697
698 /// \brief Build a new return statement.
699 ///
700 /// By default, performs semantic analysis to build the new statement.
701 /// Subclasses may override this routine to provide different behavior.
702 OwningStmtResult RebuildReturnStmt(SourceLocation ReturnLoc,
703 ExprArg Result) {
704
705 return getSema().ActOnReturnStmt(ReturnLoc, move(Result));
706 }
707
708 /// \brief Build a new declaration statement.
709 ///
710 /// By default, performs semantic analysis to build the new statement.
711 /// Subclasses may override this routine to provide different behavior.
712 OwningStmtResult RebuildDeclStmt(Decl **Decls, unsigned NumDecls,
713 SourceLocation StartLoc,
714 SourceLocation EndLoc) {
715 return getSema().Owned(
716 new (getSema().Context) DeclStmt(
717 DeclGroupRef::Create(getSema().Context,
718 Decls, NumDecls),
719 StartLoc, EndLoc));
720 }
721
722 /// \brief Build a new C++ exception declaration.
723 ///
724 /// By default, performs semantic analysis to build the new decaration.
725 /// Subclasses may override this routine to provide different behavior.
726 VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl, QualType T,
727 DeclaratorInfo *Declarator,
728 IdentifierInfo *Name,
729 SourceLocation Loc,
730 SourceRange TypeRange) {
731 return getSema().BuildExceptionDeclaration(0, T, Declarator, Name, Loc,
732 TypeRange);
733 }
734
735 /// \brief Build a new C++ catch statement.
736 ///
737 /// By default, performs semantic analysis to build the new statement.
738 /// Subclasses may override this routine to provide different behavior.
739 OwningStmtResult RebuildCXXCatchStmt(SourceLocation CatchLoc,
740 VarDecl *ExceptionDecl,
741 StmtArg Handler) {
742 return getSema().Owned(
743 new (getSema().Context) CXXCatchStmt(CatchLoc, ExceptionDecl,
744 Handler.takeAs<Stmt>()));
745 }
746
747 /// \brief Build a new C++ try statement.
748 ///
749 /// By default, performs semantic analysis to build the new statement.
750 /// Subclasses may override this routine to provide different behavior.
751 OwningStmtResult RebuildCXXTryStmt(SourceLocation TryLoc,
752 StmtArg TryBlock,
753 MultiStmtArg Handlers) {
754 return getSema().ActOnCXXTryBlock(TryLoc, move(TryBlock), move(Handlers));
755 }
756
Douglas Gregor9d879762009-08-11 05:31:07 +0000757 /// \brief Build a new expression that references a declaration.
758 ///
759 /// By default, performs semantic analysis to build the new expression.
760 /// Subclasses may override this routine to provide different behavior.
761 OwningExprResult RebuildDeclRefExpr(NamedDecl *ND, SourceLocation Loc) {
762 return getSema().BuildDeclarationNameExpr(Loc, ND,
763 /*FIXME:*/false,
764 /*SS=*/0,
765 /*FIXME:*/false);
766 }
767
768 /// \brief Build a new expression in parentheses.
769 ///
770 /// By default, performs semantic analysis to build the new expression.
771 /// Subclasses may override this routine to provide different behavior.
772 OwningExprResult RebuildParenExpr(ExprArg SubExpr, SourceLocation LParen,
773 SourceLocation RParen) {
774 return getSema().ActOnParenExpr(LParen, RParen, move(SubExpr));
775 }
776
777 /// \brief Build a new unary operator expression.
778 ///
779 /// By default, performs semantic analysis to build the new expression.
780 /// Subclasses may override this routine to provide different behavior.
781 OwningExprResult RebuildUnaryOperator(SourceLocation OpLoc,
782 UnaryOperator::Opcode Opc,
783 ExprArg SubExpr) {
784 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(SubExpr));
785 }
786
787 /// \brief Build a new sizeof or alignof expression with a type argument.
788 ///
789 /// By default, performs semantic analysis to build the new expression.
790 /// Subclasses may override this routine to provide different behavior.
791 OwningExprResult RebuildSizeOfAlignOf(QualType T, SourceLocation OpLoc,
792 bool isSizeOf, SourceRange R) {
793 return getSema().CreateSizeOfAlignOfExpr(T, OpLoc, isSizeOf, R);
794 }
795
796 /// \brief Build a new sizeof or alignof expression with an expression
797 /// argument.
798 ///
799 /// By default, performs semantic analysis to build the new expression.
800 /// Subclasses may override this routine to provide different behavior.
801 OwningExprResult RebuildSizeOfAlignOf(ExprArg SubExpr, SourceLocation OpLoc,
802 bool isSizeOf, SourceRange R) {
803 OwningExprResult Result
804 = getSema().CreateSizeOfAlignOfExpr((Expr *)SubExpr.get(),
805 OpLoc, isSizeOf, R);
806 if (Result.isInvalid())
807 return getSema().ExprError();
808
809 SubExpr.release();
810 return move(Result);
811 }
812
813 /// \brief Build a new array subscript expression.
814 ///
815 /// By default, performs semantic analysis to build the new expression.
816 /// Subclasses may override this routine to provide different behavior.
817 OwningExprResult RebuildArraySubscriptExpr(ExprArg LHS,
818 SourceLocation LBracketLoc,
819 ExprArg RHS,
820 SourceLocation RBracketLoc) {
821 return getSema().ActOnArraySubscriptExpr(/*Scope=*/0, move(LHS),
822 LBracketLoc, move(RHS),
823 RBracketLoc);
824 }
825
826 /// \brief Build a new call expression.
827 ///
828 /// By default, performs semantic analysis to build the new expression.
829 /// Subclasses may override this routine to provide different behavior.
830 OwningExprResult RebuildCallExpr(ExprArg Callee, SourceLocation LParenLoc,
831 MultiExprArg Args,
832 SourceLocation *CommaLocs,
833 SourceLocation RParenLoc) {
834 return getSema().ActOnCallExpr(/*Scope=*/0, move(Callee), LParenLoc,
835 move(Args), CommaLocs, RParenLoc);
836 }
837
838 /// \brief Build a new member access expression.
839 ///
840 /// By default, performs semantic analysis to build the new expression.
841 /// Subclasses may override this routine to provide different behavior.
842 OwningExprResult RebuildMemberExpr(ExprArg Base, SourceLocation OpLoc,
Douglas Gregorc1991bf2009-08-31 23:41:50 +0000843 bool isArrow,
844 NestedNameSpecifier *Qualifier,
845 SourceRange QualifierRange,
846 SourceLocation MemberLoc,
Douglas Gregor9d879762009-08-11 05:31:07 +0000847 NamedDecl *Member) {
Anders Carlsson20c55142009-09-01 04:26:58 +0000848 if (!Member->getDeclName()) {
849 // We have a reference to an unnamed field.
850 assert(!Qualifier && "Can't have an unnamed field with a qualifier!");
851
852 MemberExpr *ME =
853 new (getSema().Context) MemberExpr(Base.takeAs<Expr>(), isArrow,
854 Member, MemberLoc,
855 cast<FieldDecl>(Member)->getType());
856 return getSema().Owned(ME);
857 }
858
Douglas Gregorc1991bf2009-08-31 23:41:50 +0000859 CXXScopeSpec SS;
860 if (Qualifier) {
861 SS.setRange(QualifierRange);
862 SS.setScopeRep(Qualifier);
863 }
864
Douglas Gregor3b4dc7c2009-08-31 20:00:26 +0000865 return getSema().BuildMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
Douglas Gregor9d879762009-08-11 05:31:07 +0000866 isArrow? tok::arrow : tok::period,
867 MemberLoc,
Douglas Gregor3b4dc7c2009-08-31 20:00:26 +0000868 Member->getDeclName(),
Douglas Gregorc1991bf2009-08-31 23:41:50 +0000869 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
870 &SS);
Douglas Gregor9d879762009-08-11 05:31:07 +0000871 }
872
873 /// \brief Build a new binary operator expression.
874 ///
875 /// By default, performs semantic analysis to build the new expression.
876 /// Subclasses may override this routine to provide different behavior.
877 OwningExprResult RebuildBinaryOperator(SourceLocation OpLoc,
878 BinaryOperator::Opcode Opc,
879 ExprArg LHS, ExprArg RHS) {
880 OwningExprResult Result
881 = getSema().CreateBuiltinBinOp(OpLoc, Opc, (Expr *)LHS.get(),
882 (Expr *)RHS.get());
883 if (Result.isInvalid())
884 return SemaRef.ExprError();
885
886 LHS.release();
887 RHS.release();
888 return move(Result);
889 }
890
891 /// \brief Build a new conditional operator expression.
892 ///
893 /// By default, performs semantic analysis to build the new expression.
894 /// Subclasses may override this routine to provide different behavior.
895 OwningExprResult RebuildConditionalOperator(ExprArg Cond,
896 SourceLocation QuestionLoc,
897 ExprArg LHS,
898 SourceLocation ColonLoc,
899 ExprArg RHS) {
900 return getSema().ActOnConditionalOp(QuestionLoc, ColonLoc, move(Cond),
901 move(LHS), move(RHS));
902 }
903
904 /// \brief Build a new implicit cast expression.
905 ///
906 /// By default, builds a new implicit cast without any semantic analysis.
907 /// Subclasses may override this routine to provide different behavior.
908 OwningExprResult RebuildImplicitCastExpr(QualType T, CastExpr::CastKind Kind,
909 ExprArg SubExpr, bool isLvalue) {
910 ImplicitCastExpr *ICE
911 = new (getSema().Context) ImplicitCastExpr(T, Kind,
912 (Expr *)SubExpr.release(),
913 isLvalue);
914 return getSema().Owned(ICE);
915 }
916
917 /// \brief Build a new C-style cast expression.
918 ///
919 /// By default, performs semantic analysis to build the new expression.
920 /// Subclasses may override this routine to provide different behavior.
921 OwningExprResult RebuildCStyleCaseExpr(SourceLocation LParenLoc,
922 QualType ExplicitTy,
923 SourceLocation RParenLoc,
924 ExprArg SubExpr) {
925 return getSema().ActOnCastExpr(/*Scope=*/0,
926 LParenLoc,
927 ExplicitTy.getAsOpaquePtr(),
928 RParenLoc,
929 move(SubExpr));
930 }
931
932 /// \brief Build a new compound literal expression.
933 ///
934 /// By default, performs semantic analysis to build the new expression.
935 /// Subclasses may override this routine to provide different behavior.
936 OwningExprResult RebuildCompoundLiteralExpr(SourceLocation LParenLoc,
937 QualType T,
938 SourceLocation RParenLoc,
939 ExprArg Init) {
940 return getSema().ActOnCompoundLiteral(LParenLoc, T.getAsOpaquePtr(),
941 RParenLoc, move(Init));
942 }
943
944 /// \brief Build a new extended vector element access expression.
945 ///
946 /// By default, performs semantic analysis to build the new expression.
947 /// Subclasses may override this routine to provide different behavior.
948 OwningExprResult RebuildExtVectorElementExpr(ExprArg Base,
949 SourceLocation OpLoc,
950 SourceLocation AccessorLoc,
951 IdentifierInfo &Accessor) {
952 return getSema().ActOnMemberReferenceExpr(/*Scope=*/0, move(Base), OpLoc,
953 tok::period, AccessorLoc,
954 Accessor,
955 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0));
956 }
957
958 /// \brief Build a new initializer list expression.
959 ///
960 /// By default, performs semantic analysis to build the new expression.
961 /// Subclasses may override this routine to provide different behavior.
962 OwningExprResult RebuildInitList(SourceLocation LBraceLoc,
963 MultiExprArg Inits,
964 SourceLocation RBraceLoc) {
965 return SemaRef.ActOnInitList(LBraceLoc, move(Inits), RBraceLoc);
966 }
967
968 /// \brief Build a new designated initializer expression.
969 ///
970 /// By default, performs semantic analysis to build the new expression.
971 /// Subclasses may override this routine to provide different behavior.
972 OwningExprResult RebuildDesignatedInitExpr(Designation &Desig,
973 MultiExprArg ArrayExprs,
974 SourceLocation EqualOrColonLoc,
975 bool GNUSyntax,
976 ExprArg Init) {
977 OwningExprResult Result
978 = SemaRef.ActOnDesignatedInitializer(Desig, EqualOrColonLoc, GNUSyntax,
979 move(Init));
980 if (Result.isInvalid())
981 return SemaRef.ExprError();
982
983 ArrayExprs.release();
984 return move(Result);
985 }
986
987 /// \brief Build a new value-initialized expression.
988 ///
989 /// By default, builds the implicit value initialization without performing
990 /// any semantic analysis. Subclasses may override this routine to provide
991 /// different behavior.
992 OwningExprResult RebuildImplicitValueInitExpr(QualType T) {
993 return SemaRef.Owned(new (SemaRef.Context) ImplicitValueInitExpr(T));
994 }
995
996 /// \brief Build a new \c va_arg expression.
997 ///
998 /// By default, performs semantic analysis to build the new expression.
999 /// Subclasses may override this routine to provide different behavior.
1000 OwningExprResult RebuildVAArgExpr(SourceLocation BuiltinLoc, ExprArg SubExpr,
1001 QualType T, SourceLocation RParenLoc) {
1002 return getSema().ActOnVAArg(BuiltinLoc, move(SubExpr), T.getAsOpaquePtr(),
1003 RParenLoc);
1004 }
1005
1006 /// \brief Build a new expression list in parentheses.
1007 ///
1008 /// By default, performs semantic analysis to build the new expression.
1009 /// Subclasses may override this routine to provide different behavior.
1010 OwningExprResult RebuildParenListExpr(SourceLocation LParenLoc,
1011 MultiExprArg SubExprs,
1012 SourceLocation RParenLoc) {
1013 return getSema().ActOnParenListExpr(LParenLoc, RParenLoc, move(SubExprs));
1014 }
1015
1016 /// \brief Build a new address-of-label expression.
1017 ///
1018 /// By default, performs semantic analysis, using the name of the label
1019 /// rather than attempting to map the label statement itself.
1020 /// Subclasses may override this routine to provide different behavior.
1021 OwningExprResult RebuildAddrLabelExpr(SourceLocation AmpAmpLoc,
1022 SourceLocation LabelLoc,
1023 LabelStmt *Label) {
1024 return getSema().ActOnAddrLabel(AmpAmpLoc, LabelLoc, Label->getID());
1025 }
1026
1027 /// \brief Build a new GNU statement expression.
1028 ///
1029 /// By default, performs semantic analysis to build the new expression.
1030 /// Subclasses may override this routine to provide different behavior.
1031 OwningExprResult RebuildStmtExpr(SourceLocation LParenLoc,
1032 StmtArg SubStmt,
1033 SourceLocation RParenLoc) {
1034 return getSema().ActOnStmtExpr(LParenLoc, move(SubStmt), RParenLoc);
1035 }
1036
1037 /// \brief Build a new __builtin_types_compatible_p expression.
1038 ///
1039 /// By default, performs semantic analysis to build the new expression.
1040 /// Subclasses may override this routine to provide different behavior.
1041 OwningExprResult RebuildTypesCompatibleExpr(SourceLocation BuiltinLoc,
1042 QualType T1, QualType T2,
1043 SourceLocation RParenLoc) {
1044 return getSema().ActOnTypesCompatibleExpr(BuiltinLoc,
1045 T1.getAsOpaquePtr(),
1046 T2.getAsOpaquePtr(),
1047 RParenLoc);
1048 }
1049
1050 /// \brief Build a new __builtin_choose_expr expression.
1051 ///
1052 /// By default, performs semantic analysis to build the new expression.
1053 /// Subclasses may override this routine to provide different behavior.
1054 OwningExprResult RebuildChooseExpr(SourceLocation BuiltinLoc,
1055 ExprArg Cond, ExprArg LHS, ExprArg RHS,
1056 SourceLocation RParenLoc) {
1057 return SemaRef.ActOnChooseExpr(BuiltinLoc,
1058 move(Cond), move(LHS), move(RHS),
1059 RParenLoc);
1060 }
1061
1062 /// \brief Build a new overloaded operator call expression.
1063 ///
1064 /// By default, performs semantic analysis to build the new expression.
1065 /// The semantic analysis provides the behavior of template instantiation,
1066 /// copying with transformations that turn what looks like an overloaded
1067 /// operator call into a use of a builtin operator, performing
1068 /// argument-dependent lookup, etc. Subclasses may override this routine to
1069 /// provide different behavior.
1070 OwningExprResult RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
1071 SourceLocation OpLoc,
1072 ExprArg Callee,
1073 ExprArg First,
1074 ExprArg Second);
1075
1076 /// \brief Build a new C++ "named" cast expression, such as static_cast or
1077 /// reinterpret_cast.
1078 ///
1079 /// By default, this routine dispatches to one of the more-specific routines
1080 /// for a particular named case, e.g., RebuildCXXStaticCastExpr().
1081 /// Subclasses may override this routine to provide different behavior.
1082 OwningExprResult RebuildCXXNamedCastExpr(SourceLocation OpLoc,
1083 Stmt::StmtClass Class,
1084 SourceLocation LAngleLoc,
1085 QualType T,
1086 SourceLocation RAngleLoc,
1087 SourceLocation LParenLoc,
1088 ExprArg SubExpr,
1089 SourceLocation RParenLoc) {
1090 switch (Class) {
1091 case Stmt::CXXStaticCastExprClass:
1092 return getDerived().RebuildCXXStaticCastExpr(OpLoc, LAngleLoc, T,
1093 RAngleLoc, LParenLoc,
1094 move(SubExpr), RParenLoc);
1095
1096 case Stmt::CXXDynamicCastExprClass:
1097 return getDerived().RebuildCXXDynamicCastExpr(OpLoc, LAngleLoc, T,
1098 RAngleLoc, LParenLoc,
1099 move(SubExpr), RParenLoc);
1100
1101 case Stmt::CXXReinterpretCastExprClass:
1102 return getDerived().RebuildCXXReinterpretCastExpr(OpLoc, LAngleLoc, T,
1103 RAngleLoc, LParenLoc,
1104 move(SubExpr),
1105 RParenLoc);
1106
1107 case Stmt::CXXConstCastExprClass:
1108 return getDerived().RebuildCXXConstCastExpr(OpLoc, LAngleLoc, T,
1109 RAngleLoc, LParenLoc,
1110 move(SubExpr), RParenLoc);
1111
1112 default:
1113 assert(false && "Invalid C++ named cast");
1114 break;
1115 }
1116
1117 return getSema().ExprError();
1118 }
1119
1120 /// \brief Build a new C++ static_cast expression.
1121 ///
1122 /// By default, performs semantic analysis to build the new expression.
1123 /// Subclasses may override this routine to provide different behavior.
1124 OwningExprResult RebuildCXXStaticCastExpr(SourceLocation OpLoc,
1125 SourceLocation LAngleLoc,
1126 QualType T,
1127 SourceLocation RAngleLoc,
1128 SourceLocation LParenLoc,
1129 ExprArg SubExpr,
1130 SourceLocation RParenLoc) {
1131 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_static_cast,
1132 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1133 LParenLoc, move(SubExpr), RParenLoc);
1134 }
1135
1136 /// \brief Build a new C++ dynamic_cast expression.
1137 ///
1138 /// By default, performs semantic analysis to build the new expression.
1139 /// Subclasses may override this routine to provide different behavior.
1140 OwningExprResult RebuildCXXDynamicCastExpr(SourceLocation OpLoc,
1141 SourceLocation LAngleLoc,
1142 QualType T,
1143 SourceLocation RAngleLoc,
1144 SourceLocation LParenLoc,
1145 ExprArg SubExpr,
1146 SourceLocation RParenLoc) {
1147 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_dynamic_cast,
1148 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1149 LParenLoc, move(SubExpr), RParenLoc);
1150 }
1151
1152 /// \brief Build a new C++ reinterpret_cast expression.
1153 ///
1154 /// By default, performs semantic analysis to build the new expression.
1155 /// Subclasses may override this routine to provide different behavior.
1156 OwningExprResult RebuildCXXReinterpretCastExpr(SourceLocation OpLoc,
1157 SourceLocation LAngleLoc,
1158 QualType T,
1159 SourceLocation RAngleLoc,
1160 SourceLocation LParenLoc,
1161 ExprArg SubExpr,
1162 SourceLocation RParenLoc) {
1163 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_reinterpret_cast,
1164 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1165 LParenLoc, move(SubExpr), RParenLoc);
1166 }
1167
1168 /// \brief Build a new C++ const_cast expression.
1169 ///
1170 /// By default, performs semantic analysis to build the new expression.
1171 /// Subclasses may override this routine to provide different behavior.
1172 OwningExprResult RebuildCXXConstCastExpr(SourceLocation OpLoc,
1173 SourceLocation LAngleLoc,
1174 QualType T,
1175 SourceLocation RAngleLoc,
1176 SourceLocation LParenLoc,
1177 ExprArg SubExpr,
1178 SourceLocation RParenLoc) {
1179 return getSema().ActOnCXXNamedCast(OpLoc, tok::kw_const_cast,
1180 LAngleLoc, T.getAsOpaquePtr(), RAngleLoc,
1181 LParenLoc, move(SubExpr), RParenLoc);
1182 }
1183
1184 /// \brief Build a new C++ functional-style cast expression.
1185 ///
1186 /// By default, performs semantic analysis to build the new expression.
1187 /// Subclasses may override this routine to provide different behavior.
1188 OwningExprResult RebuildCXXFunctionalCastExpr(SourceRange TypeRange,
1189 QualType T,
1190 SourceLocation LParenLoc,
1191 ExprArg SubExpr,
1192 SourceLocation RParenLoc) {
Chris Lattnercf9d6a02009-08-24 05:19:01 +00001193 void *Sub = SubExpr.takeAs<Expr>();
Douglas Gregor9d879762009-08-11 05:31:07 +00001194 return getSema().ActOnCXXTypeConstructExpr(TypeRange,
1195 T.getAsOpaquePtr(),
1196 LParenLoc,
Chris Lattnercf9d6a02009-08-24 05:19:01 +00001197 Sema::MultiExprArg(getSema(), &Sub, 1),
Douglas Gregor9d879762009-08-11 05:31:07 +00001198 /*CommaLocs=*/0,
1199 RParenLoc);
1200 }
1201
1202 /// \brief Build a new C++ typeid(type) expression.
1203 ///
1204 /// By default, performs semantic analysis to build the new expression.
1205 /// Subclasses may override this routine to provide different behavior.
1206 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1207 SourceLocation LParenLoc,
1208 QualType T,
1209 SourceLocation RParenLoc) {
1210 return getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, true,
1211 T.getAsOpaquePtr(), RParenLoc);
1212 }
1213
1214 /// \brief Build a new C++ typeid(expr) expression.
1215 ///
1216 /// By default, performs semantic analysis to build the new expression.
1217 /// Subclasses may override this routine to provide different behavior.
1218 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc,
1219 SourceLocation LParenLoc,
1220 ExprArg Operand,
1221 SourceLocation RParenLoc) {
1222 OwningExprResult Result
1223 = getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, false, Operand.get(),
1224 RParenLoc);
1225 if (Result.isInvalid())
1226 return getSema().ExprError();
1227
1228 Operand.release(); // FIXME: since ActOnCXXTypeid silently took ownership
1229 return move(Result);
1230 }
1231
1232 /// \brief Build a new C++ "this" expression.
1233 ///
1234 /// By default, builds a new "this" expression without performing any
1235 /// semantic analysis. Subclasses may override this routine to provide
1236 /// different behavior.
1237 OwningExprResult RebuildCXXThisExpr(SourceLocation ThisLoc,
1238 QualType ThisType) {
1239 return getSema().Owned(
1240 new (getSema().Context) CXXThisExpr(ThisLoc, ThisType));
1241 }
1242
1243 /// \brief Build a new C++ throw expression.
1244 ///
1245 /// By default, performs semantic analysis to build the new expression.
1246 /// Subclasses may override this routine to provide different behavior.
1247 OwningExprResult RebuildCXXThrowExpr(SourceLocation ThrowLoc, ExprArg Sub) {
1248 return getSema().ActOnCXXThrow(ThrowLoc, move(Sub));
1249 }
1250
1251 /// \brief Build a new C++ default-argument expression.
1252 ///
1253 /// By default, builds a new default-argument expression, which does not
1254 /// require any semantic analysis. Subclasses may override this routine to
1255 /// provide different behavior.
1256 OwningExprResult RebuildCXXDefaultArgExpr(ParmVarDecl *Param) {
Anders Carlsson3d752db2009-08-14 18:30:22 +00001257 return getSema().Owned(CXXDefaultArgExpr::Create(getSema().Context, Param));
Douglas Gregor9d879762009-08-11 05:31:07 +00001258 }
1259
1260 /// \brief Build a new C++ zero-initialization expression.
1261 ///
1262 /// By default, performs semantic analysis to build the new expression.
1263 /// Subclasses may override this routine to provide different behavior.
1264 OwningExprResult RebuildCXXZeroInitValueExpr(SourceLocation TypeStartLoc,
1265 SourceLocation LParenLoc,
1266 QualType T,
1267 SourceLocation RParenLoc) {
1268 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeStartLoc),
1269 T.getAsOpaquePtr(), LParenLoc,
1270 MultiExprArg(getSema(), 0, 0),
1271 0, RParenLoc);
1272 }
1273
1274 /// \brief Build a new C++ conditional declaration expression.
1275 ///
1276 /// By default, performs semantic analysis to build the new expression.
1277 /// Subclasses may override this routine to provide different behavior.
1278 OwningExprResult RebuildCXXConditionDeclExpr(SourceLocation StartLoc,
1279 SourceLocation EqLoc,
1280 VarDecl *Var) {
1281 return SemaRef.Owned(new (SemaRef.Context) CXXConditionDeclExpr(StartLoc,
1282 EqLoc,
1283 Var));
1284 }
1285
1286 /// \brief Build a new C++ "new" expression.
1287 ///
1288 /// By default, performs semantic analysis to build the new expression.
1289 /// Subclasses may override this routine to provide different behavior.
1290 OwningExprResult RebuildCXXNewExpr(SourceLocation StartLoc,
1291 bool UseGlobal,
1292 SourceLocation PlacementLParen,
1293 MultiExprArg PlacementArgs,
1294 SourceLocation PlacementRParen,
1295 bool ParenTypeId,
1296 QualType AllocType,
1297 SourceLocation TypeLoc,
1298 SourceRange TypeRange,
1299 ExprArg ArraySize,
1300 SourceLocation ConstructorLParen,
1301 MultiExprArg ConstructorArgs,
1302 SourceLocation ConstructorRParen) {
1303 return getSema().BuildCXXNew(StartLoc, UseGlobal,
1304 PlacementLParen,
1305 move(PlacementArgs),
1306 PlacementRParen,
1307 ParenTypeId,
1308 AllocType,
1309 TypeLoc,
1310 TypeRange,
1311 move(ArraySize),
1312 ConstructorLParen,
1313 move(ConstructorArgs),
1314 ConstructorRParen);
1315 }
1316
1317 /// \brief Build a new C++ "delete" expression.
1318 ///
1319 /// By default, performs semantic analysis to build the new expression.
1320 /// Subclasses may override this routine to provide different behavior.
1321 OwningExprResult RebuildCXXDeleteExpr(SourceLocation StartLoc,
1322 bool IsGlobalDelete,
1323 bool IsArrayForm,
1324 ExprArg Operand) {
1325 return getSema().ActOnCXXDelete(StartLoc, IsGlobalDelete, IsArrayForm,
1326 move(Operand));
1327 }
1328
1329 /// \brief Build a new unary type trait expression.
1330 ///
1331 /// By default, performs semantic analysis to build the new expression.
1332 /// Subclasses may override this routine to provide different behavior.
1333 OwningExprResult RebuildUnaryTypeTrait(UnaryTypeTrait Trait,
1334 SourceLocation StartLoc,
1335 SourceLocation LParenLoc,
1336 QualType T,
1337 SourceLocation RParenLoc) {
1338 return getSema().ActOnUnaryTypeTrait(Trait, StartLoc, LParenLoc,
1339 T.getAsOpaquePtr(), RParenLoc);
1340 }
1341
1342 /// \brief Build a new qualified declaration reference expression.
1343 ///
1344 /// By default, performs semantic analysis to build the new expression.
1345 /// Subclasses may override this routine to provide different behavior.
1346 OwningExprResult RebuildQualifiedDeclRefExpr(NestedNameSpecifier *NNS,
1347 SourceRange QualifierRange,
1348 NamedDecl *ND,
1349 SourceLocation Location,
1350 bool IsAddressOfOperand) {
1351 CXXScopeSpec SS;
1352 SS.setRange(QualifierRange);
1353 SS.setScopeRep(NNS);
1354 return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
1355 Location,
1356 ND->getDeclName(),
1357 /*Trailing lparen=*/false,
1358 &SS,
1359 IsAddressOfOperand);
1360 }
1361
1362 /// \brief Build a new (previously unresolved) declaration reference
1363 /// expression.
1364 ///
1365 /// By default, performs semantic analysis to build the new expression.
1366 /// Subclasses may override this routine to provide different behavior.
1367 OwningExprResult RebuildUnresolvedDeclRefExpr(NestedNameSpecifier *NNS,
1368 SourceRange QualifierRange,
1369 DeclarationName Name,
1370 SourceLocation Location,
1371 bool IsAddressOfOperand) {
1372 CXXScopeSpec SS;
1373 SS.setRange(QualifierRange);
1374 SS.setScopeRep(NNS);
1375 return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
1376 Location,
1377 Name,
1378 /*Trailing lparen=*/false,
1379 &SS,
1380 IsAddressOfOperand);
1381 }
1382
1383 /// \brief Build a new template-id expression.
1384 ///
1385 /// By default, performs semantic analysis to build the new expression.
1386 /// Subclasses may override this routine to provide different behavior.
1387 OwningExprResult RebuildTemplateIdExpr(TemplateName Template,
1388 SourceLocation TemplateLoc,
1389 SourceLocation LAngleLoc,
1390 TemplateArgument *TemplateArgs,
1391 unsigned NumTemplateArgs,
1392 SourceLocation RAngleLoc) {
1393 return getSema().BuildTemplateIdExpr(Template, TemplateLoc,
1394 LAngleLoc,
1395 TemplateArgs, NumTemplateArgs,
1396 RAngleLoc);
1397 }
1398
1399 /// \brief Build a new object-construction expression.
1400 ///
1401 /// By default, performs semantic analysis to build the new expression.
1402 /// Subclasses may override this routine to provide different behavior.
1403 OwningExprResult RebuildCXXConstructExpr(QualType T,
1404 CXXConstructorDecl *Constructor,
1405 bool IsElidable,
1406 MultiExprArg Args) {
1407 unsigned NumArgs = Args.size();
1408 Expr **ArgsExprs = (Expr **)Args.release();
Anders Carlsson665e4692009-08-25 05:12:04 +00001409 return getSema().BuildCXXConstructExpr(T, Constructor, IsElidable,
1410 ArgsExprs, NumArgs);
Douglas Gregor9d879762009-08-11 05:31:07 +00001411 }
1412
1413 /// \brief Build a new object-construction expression.
1414 ///
1415 /// By default, performs semantic analysis to build the new expression.
1416 /// Subclasses may override this routine to provide different behavior.
1417 OwningExprResult RebuildCXXTemporaryObjectExpr(SourceLocation TypeBeginLoc,
1418 QualType T,
1419 SourceLocation LParenLoc,
1420 MultiExprArg Args,
1421 SourceLocation *Commas,
1422 SourceLocation RParenLoc) {
1423 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc),
1424 T.getAsOpaquePtr(),
1425 LParenLoc,
1426 move(Args),
1427 Commas,
1428 RParenLoc);
1429 }
1430
1431 /// \brief Build a new object-construction expression.
1432 ///
1433 /// By default, performs semantic analysis to build the new expression.
1434 /// Subclasses may override this routine to provide different behavior.
1435 OwningExprResult RebuildCXXUnresolvedConstructExpr(SourceLocation TypeBeginLoc,
1436 QualType T,
1437 SourceLocation LParenLoc,
1438 MultiExprArg Args,
1439 SourceLocation *Commas,
1440 SourceLocation RParenLoc) {
1441 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc,
1442 /*FIXME*/LParenLoc),
1443 T.getAsOpaquePtr(),
1444 LParenLoc,
1445 move(Args),
1446 Commas,
1447 RParenLoc);
1448 }
1449
1450 /// \brief Build a new member reference expression.
1451 ///
1452 /// By default, performs semantic analysis to build the new expression.
1453 /// Subclasses may override this routine to provide different behavior.
Douglas Gregor6ffe7b42009-08-11 15:56:57 +00001454 OwningExprResult RebuildCXXUnresolvedMemberExpr(ExprArg BaseE,
Douglas Gregor9d879762009-08-11 05:31:07 +00001455 bool IsArrow,
1456 SourceLocation OperatorLoc,
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001457 NestedNameSpecifier *Qualifier,
1458 SourceRange QualifierRange,
Douglas Gregor9d879762009-08-11 05:31:07 +00001459 DeclarationName Name,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001460 SourceLocation MemberLoc,
1461 NamedDecl *FirstQualifierInScope) {
Douglas Gregor6ffe7b42009-08-11 15:56:57 +00001462 OwningExprResult Base = move(BaseE);
Douglas Gregor9d879762009-08-11 05:31:07 +00001463 tok::TokenKind OpKind = IsArrow? tok::arrow : tok::period;
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001464
Douglas Gregor9d879762009-08-11 05:31:07 +00001465 CXXScopeSpec SS;
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001466 SS.setRange(QualifierRange);
1467 SS.setScopeRep(Qualifier);
1468
Douglas Gregor3b4dc7c2009-08-31 20:00:26 +00001469 Base = SemaRef.BuildMemberReferenceExpr(/*Scope=*/0,
Douglas Gregor9d879762009-08-11 05:31:07 +00001470 move(Base), OperatorLoc, OpKind,
Douglas Gregor3b4dc7c2009-08-31 20:00:26 +00001471 MemberLoc,
1472 Name,
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001473 /*FIXME?*/Sema::DeclPtrTy::make((Decl*)0),
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001474 &SS,
1475 FirstQualifierInScope);
Douglas Gregor9d879762009-08-11 05:31:07 +00001476 return move(Base);
1477 }
1478
1479 /// \brief Build a new Objective-C @encode expression.
1480 ///
1481 /// By default, performs semantic analysis to build the new expression.
1482 /// Subclasses may override this routine to provide different behavior.
1483 OwningExprResult RebuildObjCEncodeExpr(SourceLocation AtLoc,
1484 QualType T,
1485 SourceLocation RParenLoc) {
1486 return SemaRef.Owned(SemaRef.BuildObjCEncodeExpression(AtLoc, T,
1487 RParenLoc));
1488 }
1489
1490 /// \brief Build a new Objective-C protocol expression.
1491 ///
1492 /// By default, performs semantic analysis to build the new expression.
1493 /// Subclasses may override this routine to provide different behavior.
1494 OwningExprResult RebuildObjCProtocolExpr(ObjCProtocolDecl *Protocol,
1495 SourceLocation AtLoc,
1496 SourceLocation ProtoLoc,
1497 SourceLocation LParenLoc,
1498 SourceLocation RParenLoc) {
1499 return SemaRef.Owned(SemaRef.ParseObjCProtocolExpression(
1500 Protocol->getIdentifier(),
1501 AtLoc,
1502 ProtoLoc,
1503 LParenLoc,
1504 RParenLoc));
1505 }
1506
1507 /// \brief Build a new shuffle vector expression.
1508 ///
1509 /// By default, performs semantic analysis to build the new expression.
1510 /// Subclasses may override this routine to provide different behavior.
1511 OwningExprResult RebuildShuffleVectorExpr(SourceLocation BuiltinLoc,
1512 MultiExprArg SubExprs,
1513 SourceLocation RParenLoc) {
1514 // Find the declaration for __builtin_shufflevector
1515 const IdentifierInfo &Name
1516 = SemaRef.Context.Idents.get("__builtin_shufflevector");
1517 TranslationUnitDecl *TUDecl = SemaRef.Context.getTranslationUnitDecl();
1518 DeclContext::lookup_result Lookup = TUDecl->lookup(DeclarationName(&Name));
1519 assert(Lookup.first != Lookup.second && "No __builtin_shufflevector?");
1520
1521 // Build a reference to the __builtin_shufflevector builtin
1522 FunctionDecl *Builtin = cast<FunctionDecl>(*Lookup.first);
1523 Expr *Callee
1524 = new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(),
1525 BuiltinLoc, false, false);
1526 SemaRef.UsualUnaryConversions(Callee);
1527
1528 // Build the CallExpr
1529 unsigned NumSubExprs = SubExprs.size();
1530 Expr **Subs = (Expr **)SubExprs.release();
1531 CallExpr *TheCall = new (SemaRef.Context) CallExpr(SemaRef.Context, Callee,
1532 Subs, NumSubExprs,
1533 Builtin->getResultType(),
1534 RParenLoc);
1535 OwningExprResult OwnedCall(SemaRef.Owned(TheCall));
1536
1537 // Type-check the __builtin_shufflevector expression.
1538 OwningExprResult Result = SemaRef.SemaBuiltinShuffleVector(TheCall);
1539 if (Result.isInvalid())
1540 return SemaRef.ExprError();
1541
1542 OwnedCall.release();
1543 return move(Result);
1544 }
Douglas Gregor841324a2009-08-04 16:50:30 +00001545};
Douglas Gregor9d879762009-08-11 05:31:07 +00001546
Douglas Gregor23a44be2009-08-20 07:17:43 +00001547template<typename Derived>
1548Sema::OwningStmtResult TreeTransform<Derived>::TransformStmt(Stmt *S) {
1549 if (!S)
1550 return SemaRef.Owned(S);
1551
1552 switch (S->getStmtClass()) {
1553 case Stmt::NoStmtClass: break;
1554
1555 // Transform individual statement nodes
1556#define STMT(Node, Parent) \
1557 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S));
1558#define EXPR(Node, Parent)
1559#include "clang/AST/StmtNodes.def"
1560
1561 // Transform expressions by calling TransformExpr.
1562#define STMT(Node, Parent)
1563#define EXPR(Node, Parent) case Stmt::Node##Class:
1564#include "clang/AST/StmtNodes.def"
1565 {
1566 Sema::OwningExprResult E = getDerived().TransformExpr(cast<Expr>(S));
1567 if (E.isInvalid())
1568 return getSema().StmtError();
1569
1570 return getSema().Owned(E.takeAs<Stmt>());
1571 }
1572 }
1573
1574 return SemaRef.Owned(S->Retain());
1575}
1576
Douglas Gregor841324a2009-08-04 16:50:30 +00001577
Douglas Gregor2999faa2009-08-04 22:27:00 +00001578template<typename Derived>
Douglas Gregor9d879762009-08-11 05:31:07 +00001579Sema::OwningExprResult TreeTransform<Derived>::TransformExpr(Expr *E,
1580 bool isAddressOfOperand) {
1581 if (!E)
1582 return SemaRef.Owned(E);
1583
1584 switch (E->getStmtClass()) {
1585 case Stmt::NoStmtClass: break;
1586#define STMT(Node, Parent) case Stmt::Node##Class: break;
1587#define EXPR(Node, Parent) \
1588 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E));
1589#include "clang/AST/StmtNodes.def"
1590 }
1591
1592 return SemaRef.Owned(E->Retain());
Douglas Gregor72f34bb2009-08-06 22:17:10 +00001593}
1594
1595template<typename Derived>
Douglas Gregor12431cb2009-08-06 05:28:30 +00001596NestedNameSpecifier *
1597TreeTransform<Derived>::TransformNestedNameSpecifier(NestedNameSpecifier *NNS,
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001598 SourceRange Range,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001599 QualType ObjectType,
1600 NamedDecl *FirstQualifierInScope) {
Douglas Gregorefccbec2009-08-31 21:41:48 +00001601 if (!NNS)
1602 return 0;
1603
Douglas Gregor23a44be2009-08-20 07:17:43 +00001604 // Transform the prefix of this nested name specifier.
Douglas Gregor12431cb2009-08-06 05:28:30 +00001605 NestedNameSpecifier *Prefix = NNS->getPrefix();
1606 if (Prefix) {
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001607 Prefix = getDerived().TransformNestedNameSpecifier(Prefix, Range,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001608 ObjectType,
1609 FirstQualifierInScope);
Douglas Gregor12431cb2009-08-06 05:28:30 +00001610 if (!Prefix)
1611 return 0;
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001612
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001613 // Clear out the object type and the first qualifier in scope; they only
1614 // apply to the first element in the nested-name-specifier.
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001615 ObjectType = QualType();
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001616 FirstQualifierInScope = 0;
Douglas Gregor12431cb2009-08-06 05:28:30 +00001617 }
1618
1619 switch (NNS->getKind()) {
1620 case NestedNameSpecifier::Identifier:
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001621 assert((Prefix || !ObjectType.isNull()) &&
1622 "Identifier nested-name-specifier with no prefix or object type");
1623 if (!getDerived().AlwaysRebuild() && Prefix == NNS->getPrefix() &&
1624 ObjectType.isNull())
Douglas Gregor12431cb2009-08-06 05:28:30 +00001625 return NNS;
1626
1627 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
Douglas Gregor0f927cf2009-09-03 16:14:30 +00001628 *NNS->getAsIdentifier(),
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00001629 ObjectType,
1630 FirstQualifierInScope);
Douglas Gregor12431cb2009-08-06 05:28:30 +00001631
1632 case NestedNameSpecifier::Namespace: {
1633 NamespaceDecl *NS
1634 = cast_or_null<NamespaceDecl>(
1635 getDerived().TransformDecl(NNS->getAsNamespace()));
1636 if (!getDerived().AlwaysRebuild() &&
1637 Prefix == NNS->getPrefix() &&
1638 NS == NNS->getAsNamespace())
1639 return NNS;
1640
1641 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, NS);
1642 }
1643
1644 case NestedNameSpecifier::Global:
1645 // There is no meaningful transformation that one could perform on the
1646 // global scope.
1647 return NNS;
1648
1649 case NestedNameSpecifier::TypeSpecWithTemplate:
1650 case NestedNameSpecifier::TypeSpec: {
1651 QualType T = getDerived().TransformType(QualType(NNS->getAsType(), 0));
Douglas Gregor214d0462009-08-06 06:41:21 +00001652 if (T.isNull())
1653 return 0;
1654
Douglas Gregor12431cb2009-08-06 05:28:30 +00001655 if (!getDerived().AlwaysRebuild() &&
1656 Prefix == NNS->getPrefix() &&
1657 T == QualType(NNS->getAsType(), 0))
1658 return NNS;
1659
1660 return getDerived().RebuildNestedNameSpecifier(Prefix, Range,
1661 NNS->getKind() == NestedNameSpecifier::TypeSpecWithTemplate,
1662 T);
1663 }
1664 }
1665
1666 // Required to silence a GCC warning
1667 return 0;
1668}
1669
1670template<typename Derived>
Douglas Gregor214d0462009-08-06 06:41:21 +00001671TemplateName
1672TreeTransform<Derived>::TransformTemplateName(TemplateName Name) {
1673 if (QualifiedTemplateName *QTN = Name.getAsQualifiedTemplateName()) {
1674 NestedNameSpecifier *NNS
1675 = getDerived().TransformNestedNameSpecifier(QTN->getQualifier(),
1676 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
1677 if (!NNS)
1678 return TemplateName();
1679
1680 if (TemplateDecl *Template = QTN->getTemplateDecl()) {
1681 TemplateDecl *TransTemplate
1682 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1683 if (!TransTemplate)
1684 return TemplateName();
1685
1686 if (!getDerived().AlwaysRebuild() &&
1687 NNS == QTN->getQualifier() &&
1688 TransTemplate == Template)
1689 return Name;
1690
1691 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1692 TransTemplate);
1693 }
1694
1695 OverloadedFunctionDecl *Ovl = QTN->getOverloadedFunctionDecl();
1696 assert(Ovl && "Not a template name or an overload set?");
1697 OverloadedFunctionDecl *TransOvl
1698 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1699 if (!TransOvl)
1700 return TemplateName();
1701
1702 if (!getDerived().AlwaysRebuild() &&
1703 NNS == QTN->getQualifier() &&
1704 TransOvl == Ovl)
1705 return Name;
1706
1707 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(),
1708 TransOvl);
1709 }
1710
1711 if (DependentTemplateName *DTN = Name.getAsDependentTemplateName()) {
1712 NestedNameSpecifier *NNS
1713 = getDerived().TransformNestedNameSpecifier(DTN->getQualifier(),
1714 /*FIXME:*/SourceRange(getDerived().getBaseLocation()));
1715 if (!NNS)
1716 return TemplateName();
1717
1718 if (!getDerived().AlwaysRebuild() &&
1719 NNS == DTN->getQualifier())
1720 return Name;
1721
1722 return getDerived().RebuildTemplateName(NNS, *DTN->getName());
1723 }
1724
1725 if (TemplateDecl *Template = Name.getAsTemplateDecl()) {
1726 TemplateDecl *TransTemplate
1727 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Template));
1728 if (!TransTemplate)
1729 return TemplateName();
1730
1731 if (!getDerived().AlwaysRebuild() &&
1732 TransTemplate == Template)
1733 return Name;
1734
1735 return TemplateName(TransTemplate);
1736 }
1737
1738 OverloadedFunctionDecl *Ovl = Name.getAsOverloadedFunctionDecl();
1739 assert(Ovl && "Not a template name or an overload set?");
1740 OverloadedFunctionDecl *TransOvl
1741 = cast_or_null<OverloadedFunctionDecl>(getDerived().TransformDecl(Ovl));
1742 if (!TransOvl)
1743 return TemplateName();
1744
1745 if (!getDerived().AlwaysRebuild() &&
1746 TransOvl == Ovl)
1747 return Name;
1748
1749 return TemplateName(TransOvl);
1750}
1751
1752template<typename Derived>
Douglas Gregor2999faa2009-08-04 22:27:00 +00001753TemplateArgument
1754TreeTransform<Derived>::TransformTemplateArgument(const TemplateArgument &Arg) {
1755 switch (Arg.getKind()) {
1756 case TemplateArgument::Null:
1757 case TemplateArgument::Integral:
1758 return Arg;
1759
1760 case TemplateArgument::Type: {
1761 QualType T = getDerived().TransformType(Arg.getAsType());
1762 if (T.isNull())
1763 return TemplateArgument();
1764 return TemplateArgument(Arg.getLocation(), T);
1765 }
1766
1767 case TemplateArgument::Declaration: {
1768 Decl *D = getDerived().TransformDecl(Arg.getAsDecl());
1769 if (!D)
1770 return TemplateArgument();
1771 return TemplateArgument(Arg.getLocation(), D);
1772 }
1773
1774 case TemplateArgument::Expression: {
1775 // Template argument expressions are not potentially evaluated.
1776 EnterExpressionEvaluationContext Unevaluated(getSema(),
1777 Action::Unevaluated);
1778
1779 Sema::OwningExprResult E = getDerived().TransformExpr(Arg.getAsExpr());
1780 if (E.isInvalid())
1781 return TemplateArgument();
1782 return TemplateArgument(E.takeAs<Expr>());
1783 }
1784
1785 case TemplateArgument::Pack: {
1786 llvm::SmallVector<TemplateArgument, 4> TransformedArgs;
1787 TransformedArgs.reserve(Arg.pack_size());
1788 for (TemplateArgument::pack_iterator A = Arg.pack_begin(),
1789 AEnd = Arg.pack_end();
1790 A != AEnd; ++A) {
1791 TemplateArgument TA = getDerived().TransformTemplateArgument(*A);
1792 if (TA.isNull())
1793 return TA;
1794
1795 TransformedArgs.push_back(TA);
1796 }
1797 TemplateArgument Result;
1798 Result.setArgumentPack(TransformedArgs.data(), TransformedArgs.size(),
1799 true);
1800 return Result;
1801 }
1802 }
1803
1804 // Work around bogus GCC warning
1805 return TemplateArgument();
1806}
1807
Douglas Gregor841324a2009-08-04 16:50:30 +00001808//===----------------------------------------------------------------------===//
1809// Type transformation
1810//===----------------------------------------------------------------------===//
1811
1812template<typename Derived>
1813QualType TreeTransform<Derived>::TransformType(QualType T) {
1814 if (getDerived().AlreadyTransformed(T))
1815 return T;
1816
1817 QualType Result;
1818 switch (T->getTypeClass()) {
1819#define ABSTRACT_TYPE(CLASS, PARENT)
1820#define TYPE(CLASS, PARENT) \
1821 case Type::CLASS: \
1822 Result = getDerived().Transform##CLASS##Type( \
1823 static_cast<CLASS##Type*>(T.getTypePtr())); \
1824 break;
1825#include "clang/AST/TypeNodes.def"
1826 }
1827
1828 if (Result.isNull() || T == Result)
1829 return Result;
1830
1831 return getDerived().AddTypeQualifiers(Result, T.getCVRQualifiers());
1832}
1833
1834template<typename Derived>
1835QualType
1836TreeTransform<Derived>::AddTypeQualifiers(QualType T, unsigned CVRQualifiers) {
1837 if (CVRQualifiers && !T->isFunctionType() && !T->isReferenceType())
1838 return T.getWithAdditionalQualifiers(CVRQualifiers);
1839
1840 return T;
1841}
Argiris Kirtzidisfd3d5fd2009-08-19 01:28:17 +00001842
Douglas Gregor841324a2009-08-04 16:50:30 +00001843template<typename Derived>
1844QualType TreeTransform<Derived>::TransformExtQualType(const ExtQualType *T) {
1845 // FIXME: Implement
1846 return QualType(T, 0);
1847}
1848
1849template<typename Derived>
1850QualType TreeTransform<Derived>::TransformBuiltinType(const BuiltinType *T) {
1851 // Nothing to do
1852 return QualType(T, 0);
1853}
1854
1855template<typename Derived>
1856QualType TreeTransform<Derived>::TransformFixedWidthIntType(
1857 const FixedWidthIntType *T) {
1858 // FIXME: Implement
1859 return QualType(T, 0);
1860}
1861
1862template<typename Derived>
1863QualType TreeTransform<Derived>::TransformComplexType(const ComplexType *T) {
1864 // FIXME: Implement
1865 return QualType(T, 0);
1866}
1867
1868template<typename Derived>
1869QualType TreeTransform<Derived>::TransformPointerType(const PointerType *T) {
1870 QualType PointeeType = getDerived().TransformType(T->getPointeeType());
1871 if (PointeeType.isNull())
1872 return QualType();
1873
1874 if (!getDerived().AlwaysRebuild() &&
1875 PointeeType == T->getPointeeType())
1876 return QualType(T, 0);
1877
1878 return getDerived().RebuildPointerType(PointeeType);
1879}
1880
1881template<typename Derived>
1882QualType
1883TreeTransform<Derived>::TransformBlockPointerType(const BlockPointerType *T) {
1884 QualType PointeeType = getDerived().TransformType(T->getPointeeType());
1885 if (PointeeType.isNull())
1886 return QualType();
1887
1888 if (!getDerived().AlwaysRebuild() &&
1889 PointeeType == T->getPointeeType())
1890 return QualType(T, 0);
1891
1892 return getDerived().RebuildBlockPointerType(PointeeType);
1893}
1894
1895template<typename Derived>
1896QualType
1897TreeTransform<Derived>::TransformLValueReferenceType(
1898 const LValueReferenceType *T) {
1899 QualType PointeeType = getDerived().TransformType(T->getPointeeType());
1900 if (PointeeType.isNull())
1901 return QualType();
1902
1903 if (!getDerived().AlwaysRebuild() &&
1904 PointeeType == T->getPointeeType())
1905 return QualType(T, 0);
1906
1907 return getDerived().RebuildLValueReferenceType(PointeeType);
1908}
1909
1910template<typename Derived>
1911QualType
1912TreeTransform<Derived>::TransformRValueReferenceType(
1913 const RValueReferenceType *T) {
1914 QualType PointeeType = getDerived().TransformType(T->getPointeeType());
1915 if (PointeeType.isNull())
1916 return QualType();
1917
1918 if (!getDerived().AlwaysRebuild() &&
1919 PointeeType == T->getPointeeType())
1920 return QualType(T, 0);
1921
1922 return getDerived().RebuildRValueReferenceType(PointeeType);
1923}
1924
1925template<typename Derived>
1926QualType
1927TreeTransform<Derived>::TransformMemberPointerType(const MemberPointerType *T) {
1928 QualType PointeeType = getDerived().TransformType(T->getPointeeType());
1929 if (PointeeType.isNull())
1930 return QualType();
1931
1932 QualType ClassType = getDerived().TransformType(QualType(T->getClass(), 0));
1933 if (ClassType.isNull())
1934 return QualType();
1935
1936 if (!getDerived().AlwaysRebuild() &&
1937 PointeeType == T->getPointeeType() &&
1938 ClassType == QualType(T->getClass(), 0))
1939 return QualType(T, 0);
1940
1941 return getDerived().RebuildMemberPointerType(PointeeType, ClassType);
1942}
1943
1944template<typename Derived>
1945QualType
1946TreeTransform<Derived>::TransformConstantArrayType(const ConstantArrayType *T) {
1947 QualType ElementType = getDerived().TransformType(T->getElementType());
1948 if (ElementType.isNull())
1949 return QualType();
1950
1951 if (!getDerived().AlwaysRebuild() &&
1952 ElementType == T->getElementType())
1953 return QualType(T, 0);
1954
1955 return getDerived().RebuildConstantArrayType(ElementType,
1956 T->getSizeModifier(),
1957 T->getSize(),
1958 T->getIndexTypeQualifier());
1959}
1960
1961template<typename Derived>
1962QualType
1963TreeTransform<Derived>::TransformConstantArrayWithExprType(
1964 const ConstantArrayWithExprType *T) {
1965 QualType ElementType = getDerived().TransformType(T->getElementType());
1966 if (ElementType.isNull())
1967 return QualType();
1968
Douglas Gregor2999faa2009-08-04 22:27:00 +00001969 // Array bounds are not potentially evaluated contexts
1970 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
1971
1972 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
1973 if (Size.isInvalid())
1974 return QualType();
1975
Douglas Gregor841324a2009-08-04 16:50:30 +00001976 if (!getDerived().AlwaysRebuild() &&
Douglas Gregor2999faa2009-08-04 22:27:00 +00001977 ElementType == T->getElementType() &&
1978 Size.get() == T->getSizeExpr())
Douglas Gregor841324a2009-08-04 16:50:30 +00001979 return QualType(T, 0);
1980
1981 return getDerived().RebuildConstantArrayWithExprType(ElementType,
1982 T->getSizeModifier(),
1983 T->getSize(),
Douglas Gregor2999faa2009-08-04 22:27:00 +00001984 Size.takeAs<Expr>(),
Douglas Gregor841324a2009-08-04 16:50:30 +00001985 T->getIndexTypeQualifier(),
1986 T->getBracketsRange());
1987}
1988
1989template<typename Derived>
1990QualType
1991TreeTransform<Derived>::TransformConstantArrayWithoutExprType(
1992 const ConstantArrayWithoutExprType *T) {
1993 QualType ElementType = getDerived().TransformType(T->getElementType());
1994 if (ElementType.isNull())
1995 return QualType();
1996
1997 if (!getDerived().AlwaysRebuild() &&
1998 ElementType == T->getElementType())
1999 return QualType(T, 0);
2000
2001 return getDerived().RebuildConstantArrayWithoutExprType(ElementType,
2002 T->getSizeModifier(),
2003 T->getSize(),
2004 T->getIndexTypeQualifier());
2005}
2006
2007template<typename Derived>
2008QualType TreeTransform<Derived>::TransformIncompleteArrayType(
2009 const IncompleteArrayType *T) {
2010 QualType ElementType = getDerived().TransformType(T->getElementType());
2011 if (ElementType.isNull())
2012 return QualType();
2013
2014 if (!getDerived().AlwaysRebuild() &&
2015 ElementType == T->getElementType())
2016 return QualType(T, 0);
2017
2018 return getDerived().RebuildIncompleteArrayType(ElementType,
2019 T->getSizeModifier(),
2020 T->getIndexTypeQualifier());
2021}
2022
2023template<typename Derived>
2024QualType TreeTransform<Derived>::TransformVariableArrayType(
2025 const VariableArrayType *T) {
2026 QualType ElementType = getDerived().TransformType(T->getElementType());
2027 if (ElementType.isNull())
2028 return QualType();
2029
Douglas Gregor2999faa2009-08-04 22:27:00 +00002030 // Array bounds are not potentially evaluated contexts
2031 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2032
Douglas Gregor841324a2009-08-04 16:50:30 +00002033 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
2034 if (Size.isInvalid())
2035 return QualType();
2036
2037 if (!getDerived().AlwaysRebuild() &&
2038 ElementType == T->getElementType() &&
2039 Size.get() == T->getSizeExpr()) {
2040 Size.take();
2041 return QualType(T, 0);
2042 }
2043
2044 return getDerived().RebuildVariableArrayType(ElementType,
2045 T->getSizeModifier(),
2046 move(Size),
2047 T->getIndexTypeQualifier(),
2048 T->getBracketsRange());
2049}
2050
2051template<typename Derived>
2052QualType TreeTransform<Derived>::TransformDependentSizedArrayType(
2053 const DependentSizedArrayType *T) {
2054 QualType ElementType = getDerived().TransformType(T->getElementType());
2055 if (ElementType.isNull())
2056 return QualType();
2057
Douglas Gregor2999faa2009-08-04 22:27:00 +00002058 // Array bounds are not potentially evaluated contexts
2059 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2060
Douglas Gregor841324a2009-08-04 16:50:30 +00002061 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
2062 if (Size.isInvalid())
2063 return QualType();
2064
2065 if (!getDerived().AlwaysRebuild() &&
2066 ElementType == T->getElementType() &&
2067 Size.get() == T->getSizeExpr()) {
2068 Size.take();
2069 return QualType(T, 0);
2070 }
2071
2072 return getDerived().RebuildDependentSizedArrayType(ElementType,
2073 T->getSizeModifier(),
2074 move(Size),
2075 T->getIndexTypeQualifier(),
2076 T->getBracketsRange());
2077}
2078
2079template<typename Derived>
2080QualType TreeTransform<Derived>::TransformDependentSizedExtVectorType(
2081 const DependentSizedExtVectorType *T) {
2082 QualType ElementType = getDerived().TransformType(T->getElementType());
2083 if (ElementType.isNull())
2084 return QualType();
2085
Douglas Gregor2999faa2009-08-04 22:27:00 +00002086 // Vector sizes are not potentially evaluated contexts
2087 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2088
Douglas Gregor841324a2009-08-04 16:50:30 +00002089 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
2090 if (Size.isInvalid())
2091 return QualType();
2092
2093 if (!getDerived().AlwaysRebuild() &&
2094 ElementType == T->getElementType() &&
2095 Size.get() == T->getSizeExpr()) {
2096 Size.take();
2097 return QualType(T, 0);
2098 }
2099
2100 return getDerived().RebuildDependentSizedExtVectorType(ElementType,
2101 move(Size),
2102 T->getAttributeLoc());
2103}
2104
2105template<typename Derived>
2106QualType TreeTransform<Derived>::TransformVectorType(const VectorType *T) {
2107 QualType ElementType = getDerived().TransformType(T->getElementType());
2108 if (ElementType.isNull())
2109 return QualType();
2110
2111 if (!getDerived().AlwaysRebuild() &&
2112 ElementType == T->getElementType())
2113 return QualType(T, 0);
2114
2115 return getDerived().RebuildVectorType(ElementType, T->getNumElements());
2116}
2117
2118template<typename Derived>
2119QualType
2120TreeTransform<Derived>::TransformExtVectorType(const ExtVectorType *T) {
2121 QualType ElementType = getDerived().TransformType(T->getElementType());
2122 if (ElementType.isNull())
2123 return QualType();
2124
2125 if (!getDerived().AlwaysRebuild() &&
2126 ElementType == T->getElementType())
2127 return QualType(T, 0);
2128
2129 return getDerived().RebuildExtVectorType(ElementType, T->getNumElements(),
2130 /*FIXME*/SourceLocation());
2131}
2132
2133template<typename Derived>
2134QualType TreeTransform<Derived>::TransformFunctionProtoType(
2135 const FunctionProtoType *T) {
2136 QualType ResultType = getDerived().TransformType(T->getResultType());
2137 if (ResultType.isNull())
2138 return QualType();
2139
2140 llvm::SmallVector<QualType, 4> ParamTypes;
2141 for (FunctionProtoType::arg_type_iterator Param = T->arg_type_begin(),
2142 ParamEnd = T->arg_type_end();
2143 Param != ParamEnd; ++Param) {
2144 QualType P = getDerived().TransformType(*Param);
2145 if (P.isNull())
2146 return QualType();
2147
2148 ParamTypes.push_back(P);
2149 }
2150
2151 if (!getDerived().AlwaysRebuild() &&
2152 ResultType == T->getResultType() &&
2153 std::equal(T->arg_type_begin(), T->arg_type_end(), ParamTypes.begin()))
2154 return QualType(T, 0);
2155
2156 return getDerived().RebuildFunctionProtoType(ResultType, ParamTypes.data(),
2157 ParamTypes.size(), T->isVariadic(),
2158 T->getTypeQuals());
2159}
2160
2161template<typename Derived>
2162QualType TreeTransform<Derived>::TransformFunctionNoProtoType(
2163 const FunctionNoProtoType *T) {
2164 // FIXME: Implement
2165 return QualType(T, 0);
2166}
2167
2168template<typename Derived>
2169QualType TreeTransform<Derived>::TransformTypedefType(const TypedefType *T) {
2170 TypedefDecl *Typedef
2171 = cast_or_null<TypedefDecl>(getDerived().TransformDecl(T->getDecl()));
2172 if (!Typedef)
2173 return QualType();
2174
2175 if (!getDerived().AlwaysRebuild() &&
2176 Typedef == T->getDecl())
2177 return QualType(T, 0);
2178
2179 return getDerived().RebuildTypedefType(Typedef);
2180}
2181
2182template<typename Derived>
2183QualType TreeTransform<Derived>::TransformTypeOfExprType(
2184 const TypeOfExprType *T) {
Douglas Gregor2999faa2009-08-04 22:27:00 +00002185 // typeof expressions are not potentially evaluated contexts
2186 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2187
Douglas Gregor841324a2009-08-04 16:50:30 +00002188 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2189 if (E.isInvalid())
2190 return QualType();
2191
2192 if (!getDerived().AlwaysRebuild() &&
2193 E.get() == T->getUnderlyingExpr()) {
2194 E.take();
2195 return QualType(T, 0);
2196 }
2197
2198 return getDerived().RebuildTypeOfExprType(move(E));
2199}
2200
2201template<typename Derived>
2202QualType TreeTransform<Derived>::TransformTypeOfType(const TypeOfType *T) {
2203 QualType Underlying = getDerived().TransformType(T->getUnderlyingType());
2204 if (Underlying.isNull())
2205 return QualType();
2206
2207 if (!getDerived().AlwaysRebuild() &&
2208 Underlying == T->getUnderlyingType())
2209 return QualType(T, 0);
2210
2211 return getDerived().RebuildTypeOfType(Underlying);
2212}
2213
2214template<typename Derived>
2215QualType TreeTransform<Derived>::TransformDecltypeType(const DecltypeType *T) {
Douglas Gregor2999faa2009-08-04 22:27:00 +00002216 // decltype expressions are not potentially evaluated contexts
2217 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2218
Douglas Gregor841324a2009-08-04 16:50:30 +00002219 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr());
2220 if (E.isInvalid())
2221 return QualType();
2222
2223 if (!getDerived().AlwaysRebuild() &&
2224 E.get() == T->getUnderlyingExpr()) {
2225 E.take();
2226 return QualType(T, 0);
2227 }
2228
2229 return getDerived().RebuildDecltypeType(move(E));
2230}
2231
2232template<typename Derived>
2233QualType TreeTransform<Derived>::TransformRecordType(const RecordType *T) {
2234 RecordDecl *Record
2235 = cast_or_null<RecordDecl>(getDerived().TransformDecl(T->getDecl()));
2236 if (!Record)
2237 return QualType();
2238
2239 if (!getDerived().AlwaysRebuild() &&
2240 Record == T->getDecl())
2241 return QualType(T, 0);
2242
2243 return getDerived().RebuildRecordType(Record);
2244}
2245
2246template<typename Derived>
2247QualType TreeTransform<Derived>::TransformEnumType(const EnumType *T) {
2248 EnumDecl *Enum
2249 = cast_or_null<EnumDecl>(getDerived().TransformDecl(T->getDecl()));
2250 if (!Enum)
2251 return QualType();
2252
2253 if (!getDerived().AlwaysRebuild() &&
2254 Enum == T->getDecl())
2255 return QualType(T, 0);
2256
2257 return getDerived().RebuildEnumType(Enum);
2258}
2259
2260template<typename Derived>
2261QualType TreeTransform<Derived>::TransformTemplateTypeParmType(
2262 const TemplateTypeParmType *T) {
2263 // Nothing to do
2264 return QualType(T, 0);
2265}
2266
2267template<typename Derived>
2268QualType TreeTransform<Derived>::TransformTemplateSpecializationType(
2269 const TemplateSpecializationType *T) {
2270 TemplateName Template
2271 = getDerived().TransformTemplateName(T->getTemplateName());
2272 if (Template.isNull())
2273 return QualType();
2274
2275 llvm::SmallVector<TemplateArgument, 4> NewTemplateArgs;
2276 NewTemplateArgs.reserve(T->getNumArgs());
2277 for (TemplateSpecializationType::iterator Arg = T->begin(), ArgEnd = T->end();
2278 Arg != ArgEnd; ++Arg) {
2279 TemplateArgument NewArg = getDerived().TransformTemplateArgument(*Arg);
2280 if (NewArg.isNull())
2281 return QualType();
2282
2283 NewTemplateArgs.push_back(NewArg);
2284 }
2285
2286 // FIXME: early abort if all of the template arguments and such are the
2287 // same.
2288
2289 // FIXME: We're missing the locations of the template name, '<', and '>'.
2290 return getDerived().RebuildTemplateSpecializationType(Template,
2291 NewTemplateArgs.data(),
2292 NewTemplateArgs.size());
2293}
2294
2295template<typename Derived>
2296QualType TreeTransform<Derived>::TransformQualifiedNameType(
2297 const QualifiedNameType *T) {
2298 NestedNameSpecifier *NNS
2299 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
2300 SourceRange());
2301 if (!NNS)
2302 return QualType();
2303
2304 QualType Named = getDerived().TransformType(T->getNamedType());
2305 if (Named.isNull())
2306 return QualType();
2307
2308 if (!getDerived().AlwaysRebuild() &&
2309 NNS == T->getQualifier() &&
2310 Named == T->getNamedType())
2311 return QualType(T, 0);
2312
2313 return getDerived().RebuildQualifiedNameType(NNS, Named);
2314}
2315
2316template<typename Derived>
2317QualType TreeTransform<Derived>::TransformTypenameType(const TypenameType *T) {
2318 NestedNameSpecifier *NNS
2319 = getDerived().TransformNestedNameSpecifier(T->getQualifier(),
Douglas Gregor3f220e82009-08-06 16:20:37 +00002320 SourceRange(/*FIXME:*/getDerived().getBaseLocation()));
Douglas Gregor841324a2009-08-04 16:50:30 +00002321 if (!NNS)
2322 return QualType();
2323
2324 if (const TemplateSpecializationType *TemplateId = T->getTemplateId()) {
2325 QualType NewTemplateId
2326 = getDerived().TransformType(QualType(TemplateId, 0));
2327 if (NewTemplateId.isNull())
2328 return QualType();
2329
2330 if (!getDerived().AlwaysRebuild() &&
2331 NNS == T->getQualifier() &&
2332 NewTemplateId == QualType(TemplateId, 0))
2333 return QualType(T, 0);
2334
2335 return getDerived().RebuildTypenameType(NNS, NewTemplateId);
2336 }
2337
2338 return getDerived().RebuildTypenameType(NNS, T->getIdentifier());
2339}
2340
2341template<typename Derived>
2342QualType TreeTransform<Derived>::TransformObjCInterfaceType(
2343 const ObjCInterfaceType *T) {
2344 // FIXME: Implement
2345 return QualType(T, 0);
2346}
2347
2348template<typename Derived>
2349QualType TreeTransform<Derived>::TransformObjCObjectPointerType(
2350 const ObjCObjectPointerType *T) {
2351 // FIXME: Implement
2352 return QualType(T, 0);
2353}
2354
2355//===----------------------------------------------------------------------===//
Douglas Gregor23a44be2009-08-20 07:17:43 +00002356// Statement transformation
2357//===----------------------------------------------------------------------===//
2358template<typename Derived>
2359Sema::OwningStmtResult
2360TreeTransform<Derived>::TransformNullStmt(NullStmt *S) {
2361 return SemaRef.Owned(S->Retain());
2362}
2363
2364template<typename Derived>
2365Sema::OwningStmtResult
2366TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S) {
2367 return getDerived().TransformCompoundStmt(S, false);
2368}
2369
2370template<typename Derived>
2371Sema::OwningStmtResult
2372TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S,
2373 bool IsStmtExpr) {
2374 bool SubStmtChanged = false;
2375 ASTOwningVector<&ActionBase::DeleteStmt> Statements(getSema());
2376 for (CompoundStmt::body_iterator B = S->body_begin(), BEnd = S->body_end();
2377 B != BEnd; ++B) {
2378 OwningStmtResult Result = getDerived().TransformStmt(*B);
2379 if (Result.isInvalid())
2380 return getSema().StmtError();
2381
2382 SubStmtChanged = SubStmtChanged || Result.get() != *B;
2383 Statements.push_back(Result.takeAs<Stmt>());
2384 }
2385
2386 if (!getDerived().AlwaysRebuild() &&
2387 !SubStmtChanged)
2388 return SemaRef.Owned(S->Retain());
2389
2390 return getDerived().RebuildCompoundStmt(S->getLBracLoc(),
2391 move_arg(Statements),
2392 S->getRBracLoc(),
2393 IsStmtExpr);
2394}
2395
2396template<typename Derived>
2397Sema::OwningStmtResult
2398TreeTransform<Derived>::TransformCaseStmt(CaseStmt *S) {
2399 // The case value expressions are not potentially evaluated.
2400 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2401
2402 // Transform the left-hand case value.
2403 OwningExprResult LHS = getDerived().TransformExpr(S->getLHS());
2404 if (LHS.isInvalid())
2405 return SemaRef.StmtError();
2406
2407 // Transform the right-hand case value (for the GNU case-range extension).
2408 OwningExprResult RHS = getDerived().TransformExpr(S->getRHS());
2409 if (RHS.isInvalid())
2410 return SemaRef.StmtError();
2411
2412 // Build the case statement.
2413 // Case statements are always rebuilt so that they will attached to their
2414 // transformed switch statement.
2415 OwningStmtResult Case = getDerived().RebuildCaseStmt(S->getCaseLoc(),
2416 move(LHS),
2417 S->getEllipsisLoc(),
2418 move(RHS),
2419 S->getColonLoc());
2420 if (Case.isInvalid())
2421 return SemaRef.StmtError();
2422
2423 // Transform the statement following the case
2424 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2425 if (SubStmt.isInvalid())
2426 return SemaRef.StmtError();
2427
2428 // Attach the body to the case statement
2429 return getDerived().RebuildCaseStmtBody(move(Case), move(SubStmt));
2430}
2431
2432template<typename Derived>
2433Sema::OwningStmtResult
2434TreeTransform<Derived>::TransformDefaultStmt(DefaultStmt *S) {
2435 // Transform the statement following the default case
2436 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2437 if (SubStmt.isInvalid())
2438 return SemaRef.StmtError();
2439
2440 // Default statements are always rebuilt
2441 return getDerived().RebuildDefaultStmt(S->getDefaultLoc(), S->getColonLoc(),
2442 move(SubStmt));
2443}
2444
2445template<typename Derived>
2446Sema::OwningStmtResult
2447TreeTransform<Derived>::TransformLabelStmt(LabelStmt *S) {
2448 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt());
2449 if (SubStmt.isInvalid())
2450 return SemaRef.StmtError();
2451
2452 // FIXME: Pass the real colon location in.
2453 SourceLocation ColonLoc = SemaRef.PP.getLocForEndOfToken(S->getIdentLoc());
2454 return getDerived().RebuildLabelStmt(S->getIdentLoc(), S->getID(), ColonLoc,
2455 move(SubStmt));
2456}
2457
2458template<typename Derived>
2459Sema::OwningStmtResult
2460TreeTransform<Derived>::TransformIfStmt(IfStmt *S) {
2461 // Transform the condition
2462 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2463 if (Cond.isInvalid())
2464 return SemaRef.StmtError();
2465
2466 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
2467
2468 // Transform the "then" branch.
2469 OwningStmtResult Then = getDerived().TransformStmt(S->getThen());
2470 if (Then.isInvalid())
2471 return SemaRef.StmtError();
2472
2473 // Transform the "else" branch.
2474 OwningStmtResult Else = getDerived().TransformStmt(S->getElse());
2475 if (Else.isInvalid())
2476 return SemaRef.StmtError();
2477
2478 if (!getDerived().AlwaysRebuild() &&
2479 FullCond->get() == S->getCond() &&
2480 Then.get() == S->getThen() &&
2481 Else.get() == S->getElse())
2482 return SemaRef.Owned(S->Retain());
2483
2484 return getDerived().RebuildIfStmt(S->getIfLoc(), FullCond, move(Then),
2485 S->getElseLoc(), move(Else));
2486}
2487
2488template<typename Derived>
2489Sema::OwningStmtResult
2490TreeTransform<Derived>::TransformSwitchStmt(SwitchStmt *S) {
2491 // Transform the condition.
2492 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2493 if (Cond.isInvalid())
2494 return SemaRef.StmtError();
2495
2496 // Rebuild the switch statement.
2497 OwningStmtResult Switch = getDerived().RebuildSwitchStmtStart(move(Cond));
2498 if (Switch.isInvalid())
2499 return SemaRef.StmtError();
2500
2501 // Transform the body of the switch statement.
2502 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2503 if (Body.isInvalid())
2504 return SemaRef.StmtError();
2505
2506 // Complete the switch statement.
2507 return getDerived().RebuildSwitchStmtBody(S->getSwitchLoc(), move(Switch),
2508 move(Body));
2509}
2510
2511template<typename Derived>
2512Sema::OwningStmtResult
2513TreeTransform<Derived>::TransformWhileStmt(WhileStmt *S) {
2514 // Transform the condition
2515 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2516 if (Cond.isInvalid())
2517 return SemaRef.StmtError();
2518
2519 Sema::FullExprArg FullCond(getSema().FullExpr(Cond));
2520
2521 // Transform the body
2522 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2523 if (Body.isInvalid())
2524 return SemaRef.StmtError();
2525
2526 if (!getDerived().AlwaysRebuild() &&
2527 FullCond->get() == S->getCond() &&
2528 Body.get() == S->getBody())
2529 return SemaRef.Owned(S->Retain());
2530
2531 return getDerived().RebuildWhileStmt(S->getWhileLoc(), FullCond, move(Body));
2532}
2533
2534template<typename Derived>
2535Sema::OwningStmtResult
2536TreeTransform<Derived>::TransformDoStmt(DoStmt *S) {
2537 // Transform the condition
2538 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2539 if (Cond.isInvalid())
2540 return SemaRef.StmtError();
2541
2542 // Transform the body
2543 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2544 if (Body.isInvalid())
2545 return SemaRef.StmtError();
2546
2547 if (!getDerived().AlwaysRebuild() &&
2548 Cond.get() == S->getCond() &&
2549 Body.get() == S->getBody())
2550 return SemaRef.Owned(S->Retain());
2551
2552 return getDerived().RebuildDoStmt(S->getDoLoc(), move(Body), S->getWhileLoc(),
2553 /*FIXME:*/S->getWhileLoc(), move(Cond),
2554 S->getRParenLoc());
2555}
2556
2557template<typename Derived>
2558Sema::OwningStmtResult
2559TreeTransform<Derived>::TransformForStmt(ForStmt *S) {
2560 // Transform the initialization statement
2561 OwningStmtResult Init = getDerived().TransformStmt(S->getInit());
2562 if (Init.isInvalid())
2563 return SemaRef.StmtError();
2564
2565 // Transform the condition
2566 OwningExprResult Cond = getDerived().TransformExpr(S->getCond());
2567 if (Cond.isInvalid())
2568 return SemaRef.StmtError();
2569
2570 // Transform the increment
2571 OwningExprResult Inc = getDerived().TransformExpr(S->getInc());
2572 if (Inc.isInvalid())
2573 return SemaRef.StmtError();
2574
2575 // Transform the body
2576 OwningStmtResult Body = getDerived().TransformStmt(S->getBody());
2577 if (Body.isInvalid())
2578 return SemaRef.StmtError();
2579
2580 if (!getDerived().AlwaysRebuild() &&
2581 Init.get() == S->getInit() &&
2582 Cond.get() == S->getCond() &&
2583 Inc.get() == S->getInc() &&
2584 Body.get() == S->getBody())
2585 return SemaRef.Owned(S->Retain());
2586
2587 return getDerived().RebuildForStmt(S->getForLoc(), S->getLParenLoc(),
2588 move(Init), move(Cond), move(Inc),
2589 S->getRParenLoc(), move(Body));
2590}
2591
2592template<typename Derived>
2593Sema::OwningStmtResult
2594TreeTransform<Derived>::TransformGotoStmt(GotoStmt *S) {
2595 // Goto statements must always be rebuilt, to resolve the label.
2596 return getDerived().RebuildGotoStmt(S->getGotoLoc(), S->getLabelLoc(),
2597 S->getLabel());
2598}
2599
2600template<typename Derived>
2601Sema::OwningStmtResult
2602TreeTransform<Derived>::TransformIndirectGotoStmt(IndirectGotoStmt *S) {
2603 OwningExprResult Target = getDerived().TransformExpr(S->getTarget());
2604 if (Target.isInvalid())
2605 return SemaRef.StmtError();
2606
2607 if (!getDerived().AlwaysRebuild() &&
2608 Target.get() == S->getTarget())
2609 return SemaRef.Owned(S->Retain());
2610
2611 return getDerived().RebuildIndirectGotoStmt(S->getGotoLoc(), S->getStarLoc(),
2612 move(Target));
2613}
2614
2615template<typename Derived>
2616Sema::OwningStmtResult
2617TreeTransform<Derived>::TransformContinueStmt(ContinueStmt *S) {
2618 return SemaRef.Owned(S->Retain());
2619}
2620
2621template<typename Derived>
2622Sema::OwningStmtResult
2623TreeTransform<Derived>::TransformBreakStmt(BreakStmt *S) {
2624 return SemaRef.Owned(S->Retain());
2625}
2626
2627template<typename Derived>
2628Sema::OwningStmtResult
2629TreeTransform<Derived>::TransformReturnStmt(ReturnStmt *S) {
2630 Sema::OwningExprResult Result = getDerived().TransformExpr(S->getRetValue());
2631 if (Result.isInvalid())
2632 return SemaRef.StmtError();
2633
2634 // FIXME: We always rebuild the return statement because there is no way
2635 // to tell whether the return type of the function has changed.
2636 return getDerived().RebuildReturnStmt(S->getReturnLoc(), move(Result));
2637}
2638
2639template<typename Derived>
2640Sema::OwningStmtResult
2641TreeTransform<Derived>::TransformDeclStmt(DeclStmt *S) {
2642 bool DeclChanged = false;
2643 llvm::SmallVector<Decl *, 4> Decls;
2644 for (DeclStmt::decl_iterator D = S->decl_begin(), DEnd = S->decl_end();
2645 D != DEnd; ++D) {
2646 Decl *Transformed = getDerived().TransformDefinition(*D);
2647 if (!Transformed)
2648 return SemaRef.StmtError();
2649
2650 if (Transformed != *D)
2651 DeclChanged = true;
2652
2653 Decls.push_back(Transformed);
2654 }
2655
2656 if (!getDerived().AlwaysRebuild() && !DeclChanged)
2657 return SemaRef.Owned(S->Retain());
2658
2659 return getDerived().RebuildDeclStmt(Decls.data(), Decls.size(),
2660 S->getStartLoc(), S->getEndLoc());
2661}
2662
2663template<typename Derived>
2664Sema::OwningStmtResult
2665TreeTransform<Derived>::TransformSwitchCase(SwitchCase *S) {
2666 assert(false && "SwitchCase is abstract and cannot be transformed");
2667 return SemaRef.Owned(S->Retain());
2668}
2669
2670template<typename Derived>
2671Sema::OwningStmtResult
2672TreeTransform<Derived>::TransformAsmStmt(AsmStmt *S) {
2673 // FIXME: Implement!
2674 assert(false && "Inline assembly cannot be transformed");
2675 return SemaRef.Owned(S->Retain());
2676}
2677
2678
2679template<typename Derived>
2680Sema::OwningStmtResult
2681TreeTransform<Derived>::TransformObjCAtTryStmt(ObjCAtTryStmt *S) {
2682 // FIXME: Implement this
2683 assert(false && "Cannot transform an Objective-C @try statement");
2684 return SemaRef.Owned(S->Retain());
2685}
2686
2687template<typename Derived>
2688Sema::OwningStmtResult
2689TreeTransform<Derived>::TransformObjCAtCatchStmt(ObjCAtCatchStmt *S) {
2690 // FIXME: Implement this
2691 assert(false && "Cannot transform an Objective-C @catch statement");
2692 return SemaRef.Owned(S->Retain());
2693}
2694
2695template<typename Derived>
2696Sema::OwningStmtResult
2697TreeTransform<Derived>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt *S) {
2698 // FIXME: Implement this
2699 assert(false && "Cannot transform an Objective-C @finally statement");
2700 return SemaRef.Owned(S->Retain());
2701}
2702
2703template<typename Derived>
2704Sema::OwningStmtResult
2705TreeTransform<Derived>::TransformObjCAtThrowStmt(ObjCAtThrowStmt *S) {
2706 // FIXME: Implement this
2707 assert(false && "Cannot transform an Objective-C @throw statement");
2708 return SemaRef.Owned(S->Retain());
2709}
2710
2711template<typename Derived>
2712Sema::OwningStmtResult
2713TreeTransform<Derived>::TransformObjCAtSynchronizedStmt(
2714 ObjCAtSynchronizedStmt *S) {
2715 // FIXME: Implement this
2716 assert(false && "Cannot transform an Objective-C @synchronized statement");
2717 return SemaRef.Owned(S->Retain());
2718}
2719
2720template<typename Derived>
2721Sema::OwningStmtResult
2722TreeTransform<Derived>::TransformObjCForCollectionStmt(
2723 ObjCForCollectionStmt *S) {
2724 // FIXME: Implement this
2725 assert(false && "Cannot transform an Objective-C for-each statement");
2726 return SemaRef.Owned(S->Retain());
2727}
2728
2729
2730template<typename Derived>
2731Sema::OwningStmtResult
2732TreeTransform<Derived>::TransformCXXCatchStmt(CXXCatchStmt *S) {
2733 // Transform the exception declaration, if any.
2734 VarDecl *Var = 0;
2735 if (S->getExceptionDecl()) {
2736 VarDecl *ExceptionDecl = S->getExceptionDecl();
2737 TemporaryBase Rebase(*this, ExceptionDecl->getLocation(),
2738 ExceptionDecl->getDeclName());
2739
2740 QualType T = getDerived().TransformType(ExceptionDecl->getType());
2741 if (T.isNull())
2742 return SemaRef.StmtError();
2743
2744 Var = getDerived().RebuildExceptionDecl(ExceptionDecl,
2745 T,
2746 ExceptionDecl->getDeclaratorInfo(),
2747 ExceptionDecl->getIdentifier(),
2748 ExceptionDecl->getLocation(),
2749 /*FIXME: Inaccurate*/
2750 SourceRange(ExceptionDecl->getLocation()));
2751 if (!Var || Var->isInvalidDecl()) {
2752 if (Var)
2753 Var->Destroy(SemaRef.Context);
2754 return SemaRef.StmtError();
2755 }
2756 }
2757
2758 // Transform the actual exception handler.
2759 OwningStmtResult Handler = getDerived().TransformStmt(S->getHandlerBlock());
2760 if (Handler.isInvalid()) {
2761 if (Var)
2762 Var->Destroy(SemaRef.Context);
2763 return SemaRef.StmtError();
2764 }
2765
2766 if (!getDerived().AlwaysRebuild() &&
2767 !Var &&
2768 Handler.get() == S->getHandlerBlock())
2769 return SemaRef.Owned(S->Retain());
2770
2771 return getDerived().RebuildCXXCatchStmt(S->getCatchLoc(),
2772 Var,
2773 move(Handler));
2774}
2775
2776template<typename Derived>
2777Sema::OwningStmtResult
2778TreeTransform<Derived>::TransformCXXTryStmt(CXXTryStmt *S) {
2779 // Transform the try block itself.
2780 OwningStmtResult TryBlock
2781 = getDerived().TransformCompoundStmt(S->getTryBlock());
2782 if (TryBlock.isInvalid())
2783 return SemaRef.StmtError();
2784
2785 // Transform the handlers.
2786 bool HandlerChanged = false;
2787 ASTOwningVector<&ActionBase::DeleteStmt> Handlers(SemaRef);
2788 for (unsigned I = 0, N = S->getNumHandlers(); I != N; ++I) {
2789 OwningStmtResult Handler
2790 = getDerived().TransformCXXCatchStmt(S->getHandler(I));
2791 if (Handler.isInvalid())
2792 return SemaRef.StmtError();
2793
2794 HandlerChanged = HandlerChanged || Handler.get() != S->getHandler(I);
2795 Handlers.push_back(Handler.takeAs<Stmt>());
2796 }
2797
2798 if (!getDerived().AlwaysRebuild() &&
2799 TryBlock.get() == S->getTryBlock() &&
2800 !HandlerChanged)
2801 return SemaRef.Owned(S->Retain());
2802
2803 return getDerived().RebuildCXXTryStmt(S->getTryLoc(), move(TryBlock),
2804 move_arg(Handlers));
2805}
2806
2807//===----------------------------------------------------------------------===//
Douglas Gregor9d879762009-08-11 05:31:07 +00002808// Expression transformation
2809//===----------------------------------------------------------------------===//
2810template<typename Derived>
2811Sema::OwningExprResult
2812TreeTransform<Derived>::TransformPredefinedExpr(PredefinedExpr *E) {
2813 return SemaRef.Owned(E->Retain());
2814}
2815
2816template<typename Derived>
2817Sema::OwningExprResult
2818TreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) {
2819 NamedDecl *ND
2820 = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
2821 if (!ND)
2822 return SemaRef.ExprError();
2823
2824 if (!getDerived().AlwaysRebuild() && ND == E->getDecl())
2825 return SemaRef.Owned(E->Retain());
2826
2827 return getDerived().RebuildDeclRefExpr(ND, E->getLocation());
2828}
2829
2830template<typename Derived>
2831Sema::OwningExprResult
2832TreeTransform<Derived>::TransformIntegerLiteral(IntegerLiteral *E) {
2833 return SemaRef.Owned(E->Retain());
2834}
2835
2836template<typename Derived>
2837Sema::OwningExprResult
2838TreeTransform<Derived>::TransformFloatingLiteral(FloatingLiteral *E) {
2839 return SemaRef.Owned(E->Retain());
2840}
2841
2842template<typename Derived>
2843Sema::OwningExprResult
2844TreeTransform<Derived>::TransformImaginaryLiteral(ImaginaryLiteral *E) {
2845 return SemaRef.Owned(E->Retain());
2846}
2847
2848template<typename Derived>
2849Sema::OwningExprResult
2850TreeTransform<Derived>::TransformStringLiteral(StringLiteral *E) {
2851 return SemaRef.Owned(E->Retain());
2852}
2853
2854template<typename Derived>
2855Sema::OwningExprResult
2856TreeTransform<Derived>::TransformCharacterLiteral(CharacterLiteral *E) {
2857 return SemaRef.Owned(E->Retain());
2858}
2859
2860template<typename Derived>
2861Sema::OwningExprResult
2862TreeTransform<Derived>::TransformParenExpr(ParenExpr *E) {
2863 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
2864 if (SubExpr.isInvalid())
2865 return SemaRef.ExprError();
2866
2867 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
2868 return SemaRef.Owned(E->Retain());
2869
2870 return getDerived().RebuildParenExpr(move(SubExpr), E->getLParen(),
2871 E->getRParen());
2872}
2873
2874template<typename Derived>
2875Sema::OwningExprResult
2876TreeTransform<Derived>::TransformUnaryOperator(UnaryOperator *E) {
2877 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
2878 if (SubExpr.isInvalid())
2879 return SemaRef.ExprError();
2880
2881 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr())
2882 return SemaRef.Owned(E->Retain());
2883
2884 return getDerived().RebuildUnaryOperator(E->getOperatorLoc(),
2885 E->getOpcode(),
2886 move(SubExpr));
2887}
2888
2889template<typename Derived>
2890Sema::OwningExprResult
2891TreeTransform<Derived>::TransformSizeOfAlignOfExpr(SizeOfAlignOfExpr *E) {
2892 if (E->isArgumentType()) {
2893 QualType T = getDerived().TransformType(E->getArgumentType());
2894 if (T.isNull())
2895 return SemaRef.ExprError();
2896
2897 if (!getDerived().AlwaysRebuild() && T == E->getArgumentType())
2898 return SemaRef.Owned(E->Retain());
2899
2900 return getDerived().RebuildSizeOfAlignOf(T, E->getOperatorLoc(),
2901 E->isSizeOf(),
2902 E->getSourceRange());
2903 }
2904
2905 Sema::OwningExprResult SubExpr(SemaRef);
2906 {
2907 // C++0x [expr.sizeof]p1:
2908 // The operand is either an expression, which is an unevaluated operand
2909 // [...]
2910 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated);
2911
2912 SubExpr = getDerived().TransformExpr(E->getArgumentExpr());
2913 if (SubExpr.isInvalid())
2914 return SemaRef.ExprError();
2915
2916 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr())
2917 return SemaRef.Owned(E->Retain());
2918 }
2919
2920 return getDerived().RebuildSizeOfAlignOf(move(SubExpr), E->getOperatorLoc(),
2921 E->isSizeOf(),
2922 E->getSourceRange());
2923}
2924
2925template<typename Derived>
2926Sema::OwningExprResult
2927TreeTransform<Derived>::TransformArraySubscriptExpr(ArraySubscriptExpr *E) {
2928 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
2929 if (LHS.isInvalid())
2930 return SemaRef.ExprError();
2931
2932 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
2933 if (RHS.isInvalid())
2934 return SemaRef.ExprError();
2935
2936
2937 if (!getDerived().AlwaysRebuild() &&
2938 LHS.get() == E->getLHS() &&
2939 RHS.get() == E->getRHS())
2940 return SemaRef.Owned(E->Retain());
2941
2942 return getDerived().RebuildArraySubscriptExpr(move(LHS),
2943 /*FIXME:*/E->getLHS()->getLocStart(),
2944 move(RHS),
2945 E->getRBracketLoc());
2946}
2947
2948template<typename Derived>
2949Sema::OwningExprResult
2950TreeTransform<Derived>::TransformCallExpr(CallExpr *E) {
2951 // Transform the callee.
2952 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
2953 if (Callee.isInvalid())
2954 return SemaRef.ExprError();
2955
2956 // Transform arguments.
2957 bool ArgChanged = false;
2958 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
2959 llvm::SmallVector<SourceLocation, 4> FakeCommaLocs;
2960 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) {
2961 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I));
2962 if (Arg.isInvalid())
2963 return SemaRef.ExprError();
2964
2965 // FIXME: Wrong source location information for the ','.
2966 FakeCommaLocs.push_back(
2967 SemaRef.PP.getLocForEndOfToken(E->getArg(I)->getSourceRange().getEnd()));
2968
2969 ArgChanged = ArgChanged || Arg.get() != E->getArg(I);
2970 Args.push_back(Arg.takeAs<Expr>());
2971 }
2972
2973 if (!getDerived().AlwaysRebuild() &&
2974 Callee.get() == E->getCallee() &&
2975 !ArgChanged)
2976 return SemaRef.Owned(E->Retain());
2977
2978 // FIXME: Wrong source location information for the '('.
2979 SourceLocation FakeLParenLoc
2980 = ((Expr *)Callee.get())->getSourceRange().getBegin();
2981 return getDerived().RebuildCallExpr(move(Callee), FakeLParenLoc,
2982 move_arg(Args),
2983 FakeCommaLocs.data(),
2984 E->getRParenLoc());
2985}
2986
2987template<typename Derived>
2988Sema::OwningExprResult
2989TreeTransform<Derived>::TransformMemberExpr(MemberExpr *E) {
2990 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
2991 if (Base.isInvalid())
2992 return SemaRef.ExprError();
2993
Douglas Gregorc1991bf2009-08-31 23:41:50 +00002994 NestedNameSpecifier *Qualifier = 0;
2995 if (E->hasQualifier()) {
2996 Qualifier
2997 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
2998 E->getQualifierRange());
Douglas Gregord33e3282009-09-01 00:37:14 +00002999 if (Qualifier == 0)
Douglas Gregorc1991bf2009-08-31 23:41:50 +00003000 return SemaRef.ExprError();
3001 }
3002
Douglas Gregor9d879762009-08-11 05:31:07 +00003003 NamedDecl *Member
3004 = cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getMemberDecl()));
3005 if (!Member)
3006 return SemaRef.ExprError();
3007
3008 if (!getDerived().AlwaysRebuild() &&
3009 Base.get() == E->getBase() &&
Douglas Gregorc1991bf2009-08-31 23:41:50 +00003010 Qualifier == E->getQualifier() &&
Douglas Gregor9d879762009-08-11 05:31:07 +00003011 Member == E->getMemberDecl())
3012 return SemaRef.Owned(E->Retain());
3013
3014 // FIXME: Bogus source location for the operator
3015 SourceLocation FakeOperatorLoc
3016 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getSourceRange().getEnd());
3017
3018 return getDerived().RebuildMemberExpr(move(Base), FakeOperatorLoc,
3019 E->isArrow(),
Douglas Gregorc1991bf2009-08-31 23:41:50 +00003020 Qualifier,
3021 E->getQualifierRange(),
Douglas Gregor9d879762009-08-11 05:31:07 +00003022 E->getMemberLoc(),
3023 Member);
3024}
3025
3026template<typename Derived>
3027Sema::OwningExprResult
3028TreeTransform<Derived>::TransformCastExpr(CastExpr *E) {
3029 assert(false && "Cannot transform abstract class");
3030 return SemaRef.Owned(E->Retain());
3031}
3032
3033template<typename Derived>
3034Sema::OwningExprResult
3035TreeTransform<Derived>::TransformBinaryOperator(BinaryOperator *E) {
3036 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3037 if (LHS.isInvalid())
3038 return SemaRef.ExprError();
3039
3040 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3041 if (RHS.isInvalid())
3042 return SemaRef.ExprError();
3043
3044 if (!getDerived().AlwaysRebuild() &&
3045 LHS.get() == E->getLHS() &&
3046 RHS.get() == E->getRHS())
3047 return SemaRef.Owned(E->Retain());
3048
3049 return getDerived().RebuildBinaryOperator(E->getOperatorLoc(), E->getOpcode(),
3050 move(LHS), move(RHS));
3051}
3052
3053template<typename Derived>
3054Sema::OwningExprResult
3055TreeTransform<Derived>::TransformCompoundAssignOperator(
3056 CompoundAssignOperator *E) {
3057 return getDerived().TransformBinaryOperator(E);
3058}
3059
3060template<typename Derived>
3061Sema::OwningExprResult
3062TreeTransform<Derived>::TransformConditionalOperator(ConditionalOperator *E) {
3063 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3064 if (Cond.isInvalid())
3065 return SemaRef.ExprError();
3066
3067 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3068 if (LHS.isInvalid())
3069 return SemaRef.ExprError();
3070
3071 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3072 if (RHS.isInvalid())
3073 return SemaRef.ExprError();
3074
3075 if (!getDerived().AlwaysRebuild() &&
3076 Cond.get() == E->getCond() &&
3077 LHS.get() == E->getLHS() &&
3078 RHS.get() == E->getRHS())
3079 return SemaRef.Owned(E->Retain());
3080
Douglas Gregor9d879762009-08-11 05:31:07 +00003081 return getDerived().RebuildConditionalOperator(move(Cond),
Douglas Gregor34619872009-08-26 14:37:04 +00003082 E->getQuestionLoc(),
Douglas Gregor9d879762009-08-11 05:31:07 +00003083 move(LHS),
Douglas Gregor34619872009-08-26 14:37:04 +00003084 E->getColonLoc(),
Douglas Gregor9d879762009-08-11 05:31:07 +00003085 move(RHS));
3086}
3087
3088template<typename Derived>
3089Sema::OwningExprResult
3090TreeTransform<Derived>::TransformImplicitCastExpr(ImplicitCastExpr *E) {
3091 QualType T = getDerived().TransformType(E->getType());
3092 if (T.isNull())
3093 return SemaRef.ExprError();
3094
3095 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3096 if (SubExpr.isInvalid())
3097 return SemaRef.ExprError();
3098
3099 if (!getDerived().AlwaysRebuild() &&
3100 T == E->getType() &&
3101 SubExpr.get() == E->getSubExpr())
3102 return SemaRef.Owned(E->Retain());
3103
3104 return getDerived().RebuildImplicitCastExpr(T, E->getCastKind(),
3105 move(SubExpr),
3106 E->isLvalueCast());
3107}
3108
3109template<typename Derived>
3110Sema::OwningExprResult
3111TreeTransform<Derived>::TransformExplicitCastExpr(ExplicitCastExpr *E) {
3112 assert(false && "Cannot transform abstract class");
3113 return SemaRef.Owned(E->Retain());
3114}
3115
3116template<typename Derived>
3117Sema::OwningExprResult
3118TreeTransform<Derived>::TransformCStyleCastExpr(CStyleCastExpr *E) {
3119 QualType T;
3120 {
3121 // FIXME: Source location isn't quite accurate.
3122 SourceLocation TypeStartLoc
3123 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3124 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
3125
3126 T = getDerived().TransformType(E->getTypeAsWritten());
3127 if (T.isNull())
3128 return SemaRef.ExprError();
3129 }
3130
3131 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3132 if (SubExpr.isInvalid())
3133 return SemaRef.ExprError();
3134
3135 if (!getDerived().AlwaysRebuild() &&
3136 T == E->getTypeAsWritten() &&
3137 SubExpr.get() == E->getSubExpr())
3138 return SemaRef.Owned(E->Retain());
3139
3140 return getDerived().RebuildCStyleCaseExpr(E->getLParenLoc(), T,
3141 E->getRParenLoc(),
3142 move(SubExpr));
3143}
3144
3145template<typename Derived>
3146Sema::OwningExprResult
3147TreeTransform<Derived>::TransformCompoundLiteralExpr(CompoundLiteralExpr *E) {
3148 QualType T;
3149 {
3150 // FIXME: Source location isn't quite accurate.
3151 SourceLocation FakeTypeLoc
3152 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc());
3153 TemporaryBase Rebase(*this, FakeTypeLoc, DeclarationName());
3154
3155 T = getDerived().TransformType(E->getType());
3156 if (T.isNull())
3157 return SemaRef.ExprError();
3158 }
3159
3160 OwningExprResult Init = getDerived().TransformExpr(E->getInitializer());
3161 if (Init.isInvalid())
3162 return SemaRef.ExprError();
3163
3164 if (!getDerived().AlwaysRebuild() &&
3165 T == E->getType() &&
3166 Init.get() == E->getInitializer())
3167 return SemaRef.Owned(E->Retain());
3168
3169 return getDerived().RebuildCompoundLiteralExpr(E->getLParenLoc(), T,
3170 /*FIXME:*/E->getInitializer()->getLocEnd(),
3171 move(Init));
3172}
3173
3174template<typename Derived>
3175Sema::OwningExprResult
3176TreeTransform<Derived>::TransformExtVectorElementExpr(ExtVectorElementExpr *E) {
3177 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
3178 if (Base.isInvalid())
3179 return SemaRef.ExprError();
3180
3181 if (!getDerived().AlwaysRebuild() &&
3182 Base.get() == E->getBase())
3183 return SemaRef.Owned(E->Retain());
3184
3185 // FIXME: Bad source location
3186 SourceLocation FakeOperatorLoc
3187 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getLocEnd());
3188 return getDerived().RebuildExtVectorElementExpr(move(Base), FakeOperatorLoc,
3189 E->getAccessorLoc(),
3190 E->getAccessor());
3191}
3192
3193template<typename Derived>
3194Sema::OwningExprResult
3195TreeTransform<Derived>::TransformInitListExpr(InitListExpr *E) {
3196 bool InitChanged = false;
3197
3198 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3199 for (unsigned I = 0, N = E->getNumInits(); I != N; ++I) {
3200 OwningExprResult Init = getDerived().TransformExpr(E->getInit(I));
3201 if (Init.isInvalid())
3202 return SemaRef.ExprError();
3203
3204 InitChanged = InitChanged || Init.get() != E->getInit(I);
3205 Inits.push_back(Init.takeAs<Expr>());
3206 }
3207
3208 if (!getDerived().AlwaysRebuild() && !InitChanged)
3209 return SemaRef.Owned(E->Retain());
3210
3211 return getDerived().RebuildInitList(E->getLBraceLoc(), move_arg(Inits),
3212 E->getRBraceLoc());
3213}
3214
3215template<typename Derived>
3216Sema::OwningExprResult
3217TreeTransform<Derived>::TransformDesignatedInitExpr(DesignatedInitExpr *E) {
3218 Designation Desig;
3219
Douglas Gregor23a44be2009-08-20 07:17:43 +00003220 // transform the initializer value
Douglas Gregor9d879762009-08-11 05:31:07 +00003221 OwningExprResult Init = getDerived().TransformExpr(E->getInit());
3222 if (Init.isInvalid())
3223 return SemaRef.ExprError();
3224
Douglas Gregor23a44be2009-08-20 07:17:43 +00003225 // transform the designators.
Douglas Gregor9d879762009-08-11 05:31:07 +00003226 ASTOwningVector<&ActionBase::DeleteExpr, 4> ArrayExprs(SemaRef);
3227 bool ExprChanged = false;
3228 for (DesignatedInitExpr::designators_iterator D = E->designators_begin(),
3229 DEnd = E->designators_end();
3230 D != DEnd; ++D) {
3231 if (D->isFieldDesignator()) {
3232 Desig.AddDesignator(Designator::getField(D->getFieldName(),
3233 D->getDotLoc(),
3234 D->getFieldLoc()));
3235 continue;
3236 }
3237
3238 if (D->isArrayDesignator()) {
3239 OwningExprResult Index = getDerived().TransformExpr(E->getArrayIndex(*D));
3240 if (Index.isInvalid())
3241 return SemaRef.ExprError();
3242
3243 Desig.AddDesignator(Designator::getArray(Index.get(),
3244 D->getLBracketLoc()));
3245
3246 ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(*D);
3247 ArrayExprs.push_back(Index.release());
3248 continue;
3249 }
3250
3251 assert(D->isArrayRangeDesignator() && "New kind of designator?");
3252 OwningExprResult Start
3253 = getDerived().TransformExpr(E->getArrayRangeStart(*D));
3254 if (Start.isInvalid())
3255 return SemaRef.ExprError();
3256
3257 OwningExprResult End = getDerived().TransformExpr(E->getArrayRangeEnd(*D));
3258 if (End.isInvalid())
3259 return SemaRef.ExprError();
3260
3261 Desig.AddDesignator(Designator::getArrayRange(Start.get(),
3262 End.get(),
3263 D->getLBracketLoc(),
3264 D->getEllipsisLoc()));
3265
3266 ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(*D) ||
3267 End.get() != E->getArrayRangeEnd(*D);
3268
3269 ArrayExprs.push_back(Start.release());
3270 ArrayExprs.push_back(End.release());
3271 }
3272
3273 if (!getDerived().AlwaysRebuild() &&
3274 Init.get() == E->getInit() &&
3275 !ExprChanged)
3276 return SemaRef.Owned(E->Retain());
3277
3278 return getDerived().RebuildDesignatedInitExpr(Desig, move_arg(ArrayExprs),
3279 E->getEqualOrColonLoc(),
3280 E->usesGNUSyntax(), move(Init));
3281}
3282
3283template<typename Derived>
3284Sema::OwningExprResult
3285TreeTransform<Derived>::TransformImplicitValueInitExpr(
3286 ImplicitValueInitExpr *E) {
3287 QualType T = getDerived().TransformType(E->getType());
3288 if (T.isNull())
3289 return SemaRef.ExprError();
3290
3291 if (!getDerived().AlwaysRebuild() &&
3292 T == E->getType())
3293 return SemaRef.Owned(E->Retain());
3294
3295 return getDerived().RebuildImplicitValueInitExpr(T);
3296}
3297
3298template<typename Derived>
3299Sema::OwningExprResult
3300TreeTransform<Derived>::TransformVAArgExpr(VAArgExpr *E) {
3301 // FIXME: Do we want the type as written?
3302 QualType T;
3303
3304 {
3305 // FIXME: Source location isn't quite accurate.
3306 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
3307 T = getDerived().TransformType(E->getType());
3308 if (T.isNull())
3309 return SemaRef.ExprError();
3310 }
3311
3312 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3313 if (SubExpr.isInvalid())
3314 return SemaRef.ExprError();
3315
3316 if (!getDerived().AlwaysRebuild() &&
3317 T == E->getType() &&
3318 SubExpr.get() == E->getSubExpr())
3319 return SemaRef.Owned(E->Retain());
3320
3321 return getDerived().RebuildVAArgExpr(E->getBuiltinLoc(), move(SubExpr),
3322 T, E->getRParenLoc());
3323}
3324
3325template<typename Derived>
3326Sema::OwningExprResult
3327TreeTransform<Derived>::TransformParenListExpr(ParenListExpr *E) {
3328 bool ArgumentChanged = false;
3329 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef);
3330 for (unsigned I = 0, N = E->getNumExprs(); I != N; ++I) {
3331 OwningExprResult Init = getDerived().TransformExpr(E->getExpr(I));
3332 if (Init.isInvalid())
3333 return SemaRef.ExprError();
3334
3335 ArgumentChanged = ArgumentChanged || Init.get() != E->getExpr(I);
3336 Inits.push_back(Init.takeAs<Expr>());
3337 }
3338
3339 return getDerived().RebuildParenListExpr(E->getLParenLoc(),
3340 move_arg(Inits),
3341 E->getRParenLoc());
3342}
3343
3344/// \brief Transform an address-of-label expression.
3345///
3346/// By default, the transformation of an address-of-label expression always
3347/// rebuilds the expression, so that the label identifier can be resolved to
3348/// the corresponding label statement by semantic analysis.
3349template<typename Derived>
3350Sema::OwningExprResult
3351TreeTransform<Derived>::TransformAddrLabelExpr(AddrLabelExpr *E) {
3352 return getDerived().RebuildAddrLabelExpr(E->getAmpAmpLoc(), E->getLabelLoc(),
3353 E->getLabel());
3354}
3355
3356template<typename Derived>
3357Sema::OwningExprResult TreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) {
3358 OwningStmtResult SubStmt
3359 = getDerived().TransformCompoundStmt(E->getSubStmt(), true);
3360 if (SubStmt.isInvalid())
3361 return SemaRef.ExprError();
3362
3363 if (!getDerived().AlwaysRebuild() &&
3364 SubStmt.get() == E->getSubStmt())
3365 return SemaRef.Owned(E->Retain());
3366
3367 return getDerived().RebuildStmtExpr(E->getLParenLoc(),
3368 move(SubStmt),
3369 E->getRParenLoc());
3370}
3371
3372template<typename Derived>
3373Sema::OwningExprResult
3374TreeTransform<Derived>::TransformTypesCompatibleExpr(TypesCompatibleExpr *E) {
3375 QualType T1, T2;
3376 {
3377 // FIXME: Source location isn't quite accurate.
3378 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName());
3379
3380 T1 = getDerived().TransformType(E->getArgType1());
3381 if (T1.isNull())
3382 return SemaRef.ExprError();
3383
3384 T2 = getDerived().TransformType(E->getArgType2());
3385 if (T2.isNull())
3386 return SemaRef.ExprError();
3387 }
3388
3389 if (!getDerived().AlwaysRebuild() &&
3390 T1 == E->getArgType1() &&
3391 T2 == E->getArgType2())
3392 return SemaRef.Owned(E->Retain());
3393
3394 return getDerived().RebuildTypesCompatibleExpr(E->getBuiltinLoc(),
3395 T1, T2, E->getRParenLoc());
3396}
3397
3398template<typename Derived>
3399Sema::OwningExprResult
3400TreeTransform<Derived>::TransformChooseExpr(ChooseExpr *E) {
3401 OwningExprResult Cond = getDerived().TransformExpr(E->getCond());
3402 if (Cond.isInvalid())
3403 return SemaRef.ExprError();
3404
3405 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS());
3406 if (LHS.isInvalid())
3407 return SemaRef.ExprError();
3408
3409 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS());
3410 if (RHS.isInvalid())
3411 return SemaRef.ExprError();
3412
3413 if (!getDerived().AlwaysRebuild() &&
3414 Cond.get() == E->getCond() &&
3415 LHS.get() == E->getLHS() &&
3416 RHS.get() == E->getRHS())
3417 return SemaRef.Owned(E->Retain());
3418
3419 return getDerived().RebuildChooseExpr(E->getBuiltinLoc(),
3420 move(Cond), move(LHS), move(RHS),
3421 E->getRParenLoc());
3422}
3423
3424template<typename Derived>
3425Sema::OwningExprResult
3426TreeTransform<Derived>::TransformGNUNullExpr(GNUNullExpr *E) {
3427 return SemaRef.Owned(E->Retain());
3428}
3429
3430template<typename Derived>
3431Sema::OwningExprResult
3432TreeTransform<Derived>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr *E) {
3433 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee());
3434 if (Callee.isInvalid())
3435 return SemaRef.ExprError();
3436
3437 OwningExprResult First = getDerived().TransformExpr(E->getArg(0));
3438 if (First.isInvalid())
3439 return SemaRef.ExprError();
3440
3441 OwningExprResult Second(SemaRef);
3442 if (E->getNumArgs() == 2) {
3443 Second = getDerived().TransformExpr(E->getArg(1));
3444 if (Second.isInvalid())
3445 return SemaRef.ExprError();
3446 }
3447
3448 if (!getDerived().AlwaysRebuild() &&
3449 Callee.get() == E->getCallee() &&
3450 First.get() == E->getArg(0) &&
3451 (E->getNumArgs() != 2 || Second.get() == E->getArg(1)))
3452 return SemaRef.Owned(E->Retain());
3453
3454 return getDerived().RebuildCXXOperatorCallExpr(E->getOperator(),
3455 E->getOperatorLoc(),
3456 move(Callee),
3457 move(First),
3458 move(Second));
3459}
3460
3461template<typename Derived>
3462Sema::OwningExprResult
3463TreeTransform<Derived>::TransformCXXMemberCallExpr(CXXMemberCallExpr *E) {
3464 return getDerived().TransformCallExpr(E);
3465}
3466
3467template<typename Derived>
3468Sema::OwningExprResult
3469TreeTransform<Derived>::TransformCXXNamedCastExpr(CXXNamedCastExpr *E) {
3470 QualType ExplicitTy;
3471 {
3472 // FIXME: Source location isn't quite accurate.
3473 SourceLocation TypeStartLoc
3474 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3475 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName());
3476
3477 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
3478 if (ExplicitTy.isNull())
3479 return SemaRef.ExprError();
3480 }
3481
3482 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3483 if (SubExpr.isInvalid())
3484 return SemaRef.ExprError();
3485
3486 if (!getDerived().AlwaysRebuild() &&
3487 ExplicitTy == E->getTypeAsWritten() &&
3488 SubExpr.get() == E->getSubExpr())
3489 return SemaRef.Owned(E->Retain());
3490
3491 // FIXME: Poor source location information here.
3492 SourceLocation FakeLAngleLoc
3493 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc());
3494 SourceLocation FakeRAngleLoc = E->getSubExpr()->getSourceRange().getBegin();
3495 SourceLocation FakeRParenLoc
3496 = SemaRef.PP.getLocForEndOfToken(
3497 E->getSubExpr()->getSourceRange().getEnd());
3498 return getDerived().RebuildCXXNamedCastExpr(E->getOperatorLoc(),
3499 E->getStmtClass(),
3500 FakeLAngleLoc,
3501 ExplicitTy,
3502 FakeRAngleLoc,
3503 FakeRAngleLoc,
3504 move(SubExpr),
3505 FakeRParenLoc);
3506}
3507
3508template<typename Derived>
3509Sema::OwningExprResult
3510TreeTransform<Derived>::TransformCXXStaticCastExpr(CXXStaticCastExpr *E) {
3511 return getDerived().TransformCXXNamedCastExpr(E);
3512}
3513
3514template<typename Derived>
3515Sema::OwningExprResult
3516TreeTransform<Derived>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr *E) {
3517 return getDerived().TransformCXXNamedCastExpr(E);
3518}
3519
3520template<typename Derived>
3521Sema::OwningExprResult
3522TreeTransform<Derived>::TransformCXXReinterpretCastExpr(
3523 CXXReinterpretCastExpr *E) {
3524 return getDerived().TransformCXXNamedCastExpr(E);
3525}
3526
3527template<typename Derived>
3528Sema::OwningExprResult
3529TreeTransform<Derived>::TransformCXXConstCastExpr(CXXConstCastExpr *E) {
3530 return getDerived().TransformCXXNamedCastExpr(E);
3531}
3532
3533template<typename Derived>
3534Sema::OwningExprResult
3535TreeTransform<Derived>::TransformCXXFunctionalCastExpr(
3536 CXXFunctionalCastExpr *E) {
3537 QualType ExplicitTy;
3538 {
3539 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
3540
3541 ExplicitTy = getDerived().TransformType(E->getTypeAsWritten());
3542 if (ExplicitTy.isNull())
3543 return SemaRef.ExprError();
3544 }
3545
3546 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3547 if (SubExpr.isInvalid())
3548 return SemaRef.ExprError();
3549
3550 if (!getDerived().AlwaysRebuild() &&
3551 ExplicitTy == E->getTypeAsWritten() &&
3552 SubExpr.get() == E->getSubExpr())
3553 return SemaRef.Owned(E->Retain());
3554
3555 // FIXME: The end of the type's source range is wrong
3556 return getDerived().RebuildCXXFunctionalCastExpr(
3557 /*FIXME:*/SourceRange(E->getTypeBeginLoc()),
3558 ExplicitTy,
3559 /*FIXME:*/E->getSubExpr()->getLocStart(),
3560 move(SubExpr),
3561 E->getRParenLoc());
3562}
3563
3564template<typename Derived>
3565Sema::OwningExprResult
3566TreeTransform<Derived>::TransformCXXTypeidExpr(CXXTypeidExpr *E) {
3567 if (E->isTypeOperand()) {
3568 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
3569
3570 QualType T = getDerived().TransformType(E->getTypeOperand());
3571 if (T.isNull())
3572 return SemaRef.ExprError();
3573
3574 if (!getDerived().AlwaysRebuild() &&
3575 T == E->getTypeOperand())
3576 return SemaRef.Owned(E->Retain());
3577
3578 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
3579 /*FIXME:*/E->getLocStart(),
3580 T,
3581 E->getLocEnd());
3582 }
3583
3584 // We don't know whether the expression is potentially evaluated until
3585 // after we perform semantic analysis, so the expression is potentially
3586 // potentially evaluated.
3587 EnterExpressionEvaluationContext Unevaluated(SemaRef,
3588 Action::PotentiallyPotentiallyEvaluated);
3589
3590 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand());
3591 if (SubExpr.isInvalid())
3592 return SemaRef.ExprError();
3593
3594 if (!getDerived().AlwaysRebuild() &&
3595 SubExpr.get() == E->getExprOperand())
3596 return SemaRef.Owned(E->Retain());
3597
3598 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(),
3599 /*FIXME:*/E->getLocStart(),
3600 move(SubExpr),
3601 E->getLocEnd());
3602}
3603
3604template<typename Derived>
3605Sema::OwningExprResult
3606TreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) {
3607 return SemaRef.Owned(E->Retain());
3608}
3609
3610template<typename Derived>
3611Sema::OwningExprResult
3612TreeTransform<Derived>::TransformCXXNullPtrLiteralExpr(
3613 CXXNullPtrLiteralExpr *E) {
3614 return SemaRef.Owned(E->Retain());
3615}
3616
3617template<typename Derived>
3618Sema::OwningExprResult
3619TreeTransform<Derived>::TransformCXXThisExpr(CXXThisExpr *E) {
3620 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
3621
3622 QualType T = getDerived().TransformType(E->getType());
3623 if (T.isNull())
3624 return SemaRef.ExprError();
3625
3626 if (!getDerived().AlwaysRebuild() &&
3627 T == E->getType())
3628 return SemaRef.Owned(E->Retain());
3629
3630 return getDerived().RebuildCXXThisExpr(E->getLocStart(), T);
3631}
3632
3633template<typename Derived>
3634Sema::OwningExprResult
3635TreeTransform<Derived>::TransformCXXThrowExpr(CXXThrowExpr *E) {
3636 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3637 if (SubExpr.isInvalid())
3638 return SemaRef.ExprError();
3639
3640 if (!getDerived().AlwaysRebuild() &&
3641 SubExpr.get() == E->getSubExpr())
3642 return SemaRef.Owned(E->Retain());
3643
3644 return getDerived().RebuildCXXThrowExpr(E->getThrowLoc(), move(SubExpr));
3645}
3646
3647template<typename Derived>
3648Sema::OwningExprResult
3649TreeTransform<Derived>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E) {
3650 ParmVarDecl *Param
3651 = cast_or_null<ParmVarDecl>(getDerived().TransformDecl(E->getParam()));
3652 if (!Param)
3653 return SemaRef.ExprError();
3654
3655 if (getDerived().AlwaysRebuild() &&
3656 Param == E->getParam())
3657 return SemaRef.Owned(E->Retain());
3658
3659 return getDerived().RebuildCXXDefaultArgExpr(Param);
3660}
3661
3662template<typename Derived>
3663Sema::OwningExprResult
3664TreeTransform<Derived>::TransformCXXZeroInitValueExpr(CXXZeroInitValueExpr *E) {
3665 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
3666
3667 QualType T = getDerived().TransformType(E->getType());
3668 if (T.isNull())
3669 return SemaRef.ExprError();
3670
3671 if (!getDerived().AlwaysRebuild() &&
3672 T == E->getType())
3673 return SemaRef.Owned(E->Retain());
3674
3675 return getDerived().RebuildCXXZeroInitValueExpr(E->getTypeBeginLoc(),
3676 /*FIXME:*/E->getTypeBeginLoc(),
3677 T,
3678 E->getRParenLoc());
3679}
3680
3681template<typename Derived>
3682Sema::OwningExprResult
3683TreeTransform<Derived>::TransformCXXConditionDeclExpr(CXXConditionDeclExpr *E) {
3684 VarDecl *Var
Douglas Gregor23a44be2009-08-20 07:17:43 +00003685 = cast_or_null<VarDecl>(getDerived().TransformDefinition(E->getVarDecl()));
Douglas Gregor9d879762009-08-11 05:31:07 +00003686 if (!Var)
3687 return SemaRef.ExprError();
3688
3689 if (!getDerived().AlwaysRebuild() &&
3690 Var == E->getVarDecl())
3691 return SemaRef.Owned(E->Retain());
3692
3693 return getDerived().RebuildCXXConditionDeclExpr(E->getStartLoc(),
3694 /*FIXME:*/E->getStartLoc(),
3695 Var);
3696}
3697
3698template<typename Derived>
3699Sema::OwningExprResult
3700TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) {
3701 // Transform the type that we're allocating
3702 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName());
3703 QualType AllocType = getDerived().TransformType(E->getAllocatedType());
3704 if (AllocType.isNull())
3705 return SemaRef.ExprError();
3706
3707 // Transform the size of the array we're allocating (if any).
3708 OwningExprResult ArraySize = getDerived().TransformExpr(E->getArraySize());
3709 if (ArraySize.isInvalid())
3710 return SemaRef.ExprError();
3711
3712 // Transform the placement arguments (if any).
3713 bool ArgumentChanged = false;
3714 ASTOwningVector<&ActionBase::DeleteExpr> PlacementArgs(SemaRef);
3715 for (unsigned I = 0, N = E->getNumPlacementArgs(); I != N; ++I) {
3716 OwningExprResult Arg = getDerived().TransformExpr(E->getPlacementArg(I));
3717 if (Arg.isInvalid())
3718 return SemaRef.ExprError();
3719
3720 ArgumentChanged = ArgumentChanged || Arg.get() != E->getPlacementArg(I);
3721 PlacementArgs.push_back(Arg.take());
3722 }
3723
Douglas Gregor23a44be2009-08-20 07:17:43 +00003724 // transform the constructor arguments (if any).
Douglas Gregor9d879762009-08-11 05:31:07 +00003725 ASTOwningVector<&ActionBase::DeleteExpr> ConstructorArgs(SemaRef);
3726 for (unsigned I = 0, N = E->getNumConstructorArgs(); I != N; ++I) {
3727 OwningExprResult Arg = getDerived().TransformExpr(E->getConstructorArg(I));
3728 if (Arg.isInvalid())
3729 return SemaRef.ExprError();
3730
3731 ArgumentChanged = ArgumentChanged || Arg.get() != E->getConstructorArg(I);
3732 ConstructorArgs.push_back(Arg.take());
3733 }
3734
3735 if (!getDerived().AlwaysRebuild() &&
3736 AllocType == E->getAllocatedType() &&
3737 ArraySize.get() == E->getArraySize() &&
3738 !ArgumentChanged)
3739 return SemaRef.Owned(E->Retain());
3740
3741 return getDerived().RebuildCXXNewExpr(E->getLocStart(),
3742 E->isGlobalNew(),
3743 /*FIXME:*/E->getLocStart(),
3744 move_arg(PlacementArgs),
3745 /*FIXME:*/E->getLocStart(),
3746 E->isParenTypeId(),
3747 AllocType,
3748 /*FIXME:*/E->getLocStart(),
3749 /*FIXME:*/SourceRange(),
3750 move(ArraySize),
3751 /*FIXME:*/E->getLocStart(),
3752 move_arg(ConstructorArgs),
3753 E->getLocEnd());
3754}
3755
3756template<typename Derived>
3757Sema::OwningExprResult
3758TreeTransform<Derived>::TransformCXXDeleteExpr(CXXDeleteExpr *E) {
3759 OwningExprResult Operand = getDerived().TransformExpr(E->getArgument());
3760 if (Operand.isInvalid())
3761 return SemaRef.ExprError();
3762
3763 if (!getDerived().AlwaysRebuild() &&
3764 Operand.get() == E->getArgument())
3765 return SemaRef.Owned(E->Retain());
3766
3767 return getDerived().RebuildCXXDeleteExpr(E->getLocStart(),
3768 E->isGlobalDelete(),
3769 E->isArrayForm(),
3770 move(Operand));
3771}
3772
3773template<typename Derived>
3774Sema::OwningExprResult
3775TreeTransform<Derived>::TransformUnresolvedFunctionNameExpr(
3776 UnresolvedFunctionNameExpr *E) {
3777 // There is no transformation we can apply to an unresolved function name.
3778 return SemaRef.Owned(E->Retain());
3779}
3780
3781template<typename Derived>
3782Sema::OwningExprResult
3783TreeTransform<Derived>::TransformUnaryTypeTraitExpr(UnaryTypeTraitExpr *E) {
3784 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
3785
3786 QualType T = getDerived().TransformType(E->getQueriedType());
3787 if (T.isNull())
3788 return SemaRef.ExprError();
3789
3790 if (!getDerived().AlwaysRebuild() &&
3791 T == E->getQueriedType())
3792 return SemaRef.Owned(E->Retain());
3793
3794 // FIXME: Bad location information
3795 SourceLocation FakeLParenLoc
3796 = SemaRef.PP.getLocForEndOfToken(E->getLocStart());
3797
3798 return getDerived().RebuildUnaryTypeTrait(E->getTrait(),
3799 E->getLocStart(),
3800 /*FIXME:*/FakeLParenLoc,
3801 T,
3802 E->getLocEnd());
3803}
3804
3805template<typename Derived>
3806Sema::OwningExprResult
3807TreeTransform<Derived>::TransformQualifiedDeclRefExpr(QualifiedDeclRefExpr *E) {
3808 NestedNameSpecifier *NNS
3809 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
3810 E->getQualifierRange());
3811 if (!NNS)
3812 return SemaRef.ExprError();
3813
3814 NamedDecl *ND
3815 = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
3816 if (!ND)
3817 return SemaRef.ExprError();
3818
3819 if (!getDerived().AlwaysRebuild() &&
3820 NNS == E->getQualifier() &&
3821 ND == E->getDecl())
3822 return SemaRef.Owned(E->Retain());
3823
3824 return getDerived().RebuildQualifiedDeclRefExpr(NNS,
3825 E->getQualifierRange(),
3826 ND,
3827 E->getLocation(),
3828 /*FIXME:*/false);
3829}
3830
3831template<typename Derived>
3832Sema::OwningExprResult
3833TreeTransform<Derived>::TransformUnresolvedDeclRefExpr(
3834 UnresolvedDeclRefExpr *E) {
3835 NestedNameSpecifier *NNS
3836 = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
3837 E->getQualifierRange());
3838 if (!NNS)
3839 return SemaRef.ExprError();
3840
3841 // FIXME: Transform the declaration name
3842 DeclarationName Name = E->getDeclName();
3843
3844 if (!getDerived().AlwaysRebuild() &&
3845 NNS == E->getQualifier() &&
3846 Name == E->getDeclName())
3847 return SemaRef.Owned(E->Retain());
3848
3849 return getDerived().RebuildUnresolvedDeclRefExpr(NNS,
3850 E->getQualifierRange(),
3851 Name,
3852 E->getLocation(),
3853 /*FIXME:*/false);
3854}
3855
3856template<typename Derived>
3857Sema::OwningExprResult
3858TreeTransform<Derived>::TransformTemplateIdRefExpr(TemplateIdRefExpr *E) {
3859 TemplateName Template
3860 = getDerived().TransformTemplateName(E->getTemplateName());
3861 if (Template.isNull())
3862 return SemaRef.ExprError();
3863
3864 llvm::SmallVector<TemplateArgument, 4> TransArgs;
3865 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
3866 TemplateArgument TransArg
3867 = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
3868 if (TransArg.isNull())
3869 return SemaRef.ExprError();
3870
3871 TransArgs.push_back(TransArg);
3872 }
3873
3874 // FIXME: Would like to avoid rebuilding if nothing changed, but we can't
3875 // compare template arguments (yet).
3876
3877 // FIXME: It's possible that we'll find out now that the template name
3878 // actually refers to a type, in which case the caller is actually dealing
3879 // with a functional cast. Give a reasonable error message!
3880 return getDerived().RebuildTemplateIdExpr(Template, E->getTemplateNameLoc(),
3881 E->getLAngleLoc(),
3882 TransArgs.data(),
3883 TransArgs.size(),
3884 E->getRAngleLoc());
3885}
3886
3887template<typename Derived>
3888Sema::OwningExprResult
3889TreeTransform<Derived>::TransformCXXConstructExpr(CXXConstructExpr *E) {
3890 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName());
3891
3892 QualType T = getDerived().TransformType(E->getType());
3893 if (T.isNull())
3894 return SemaRef.ExprError();
3895
3896 CXXConstructorDecl *Constructor
3897 = cast_or_null<CXXConstructorDecl>(
3898 getDerived().TransformDecl(E->getConstructor()));
3899 if (!Constructor)
3900 return SemaRef.ExprError();
3901
3902 bool ArgumentChanged = false;
3903 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
3904 for (CXXConstructExpr::arg_iterator Arg = E->arg_begin(),
3905 ArgEnd = E->arg_end();
3906 Arg != ArgEnd; ++Arg) {
3907 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
3908 if (TransArg.isInvalid())
3909 return SemaRef.ExprError();
3910
3911 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
3912 Args.push_back(TransArg.takeAs<Expr>());
3913 }
3914
3915 if (!getDerived().AlwaysRebuild() &&
3916 T == E->getType() &&
3917 Constructor == E->getConstructor() &&
3918 !ArgumentChanged)
3919 return SemaRef.Owned(E->Retain());
3920
3921 return getDerived().RebuildCXXConstructExpr(T, Constructor, E->isElidable(),
3922 move_arg(Args));
3923}
3924
3925/// \brief Transform a C++ temporary-binding expression.
3926///
3927/// The transformation of a temporary-binding expression always attempts to
3928/// bind a new temporary variable to its subexpression, even if the
3929/// subexpression itself did not change, because the temporary variable itself
3930/// must be unique.
3931template<typename Derived>
3932Sema::OwningExprResult
3933TreeTransform<Derived>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr *E) {
3934 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3935 if (SubExpr.isInvalid())
3936 return SemaRef.ExprError();
3937
3938 return SemaRef.MaybeBindToTemporary(SubExpr.takeAs<Expr>());
3939}
3940
3941/// \brief Transform a C++ expression that contains temporaries that should
3942/// be destroyed after the expression is evaluated.
3943///
3944/// The transformation of a full expression always attempts to build a new
3945/// CXXExprWithTemporaries expression, even if the
3946/// subexpression itself did not change, because it will need to capture the
3947/// the new temporary variables introduced in the subexpression.
3948template<typename Derived>
3949Sema::OwningExprResult
3950TreeTransform<Derived>::TransformCXXExprWithTemporaries(
3951 CXXExprWithTemporaries *E) {
3952 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr());
3953 if (SubExpr.isInvalid())
3954 return SemaRef.ExprError();
3955
3956 return SemaRef.Owned(
3957 SemaRef.MaybeCreateCXXExprWithTemporaries(SubExpr.takeAs<Expr>(),
3958 E->shouldDestroyTemporaries()));
3959}
3960
3961template<typename Derived>
3962Sema::OwningExprResult
3963TreeTransform<Derived>::TransformCXXTemporaryObjectExpr(
3964 CXXTemporaryObjectExpr *E) {
3965 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
3966 QualType T = getDerived().TransformType(E->getType());
3967 if (T.isNull())
3968 return SemaRef.ExprError();
3969
3970 CXXConstructorDecl *Constructor
3971 = cast_or_null<CXXConstructorDecl>(
3972 getDerived().TransformDecl(E->getConstructor()));
3973 if (!Constructor)
3974 return SemaRef.ExprError();
3975
3976 bool ArgumentChanged = false;
3977 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
3978 Args.reserve(E->getNumArgs());
3979 for (CXXTemporaryObjectExpr::arg_iterator Arg = E->arg_begin(),
3980 ArgEnd = E->arg_end();
3981 Arg != ArgEnd; ++Arg) {
3982 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
3983 if (TransArg.isInvalid())
3984 return SemaRef.ExprError();
3985
3986 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
3987 Args.push_back((Expr *)TransArg.release());
3988 }
3989
3990 if (!getDerived().AlwaysRebuild() &&
3991 T == E->getType() &&
3992 Constructor == E->getConstructor() &&
3993 !ArgumentChanged)
3994 return SemaRef.Owned(E->Retain());
3995
3996 // FIXME: Bogus location information
3997 SourceLocation CommaLoc;
3998 if (Args.size() > 1) {
3999 Expr *First = (Expr *)Args[0];
4000 CommaLoc
4001 = SemaRef.PP.getLocForEndOfToken(First->getSourceRange().getEnd());
4002 }
4003 return getDerived().RebuildCXXTemporaryObjectExpr(E->getTypeBeginLoc(),
4004 T,
4005 /*FIXME:*/E->getTypeBeginLoc(),
4006 move_arg(Args),
4007 &CommaLoc,
4008 E->getLocEnd());
4009}
4010
4011template<typename Derived>
4012Sema::OwningExprResult
4013TreeTransform<Derived>::TransformCXXUnresolvedConstructExpr(
4014 CXXUnresolvedConstructExpr *E) {
4015 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName());
4016 QualType T = getDerived().TransformType(E->getTypeAsWritten());
4017 if (T.isNull())
4018 return SemaRef.ExprError();
4019
4020 bool ArgumentChanged = false;
4021 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef);
4022 llvm::SmallVector<SourceLocation, 8> FakeCommaLocs;
4023 for (CXXUnresolvedConstructExpr::arg_iterator Arg = E->arg_begin(),
4024 ArgEnd = E->arg_end();
4025 Arg != ArgEnd; ++Arg) {
4026 OwningExprResult TransArg = getDerived().TransformExpr(*Arg);
4027 if (TransArg.isInvalid())
4028 return SemaRef.ExprError();
4029
4030 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg;
4031 FakeCommaLocs.push_back(
4032 SemaRef.PP.getLocForEndOfToken((*Arg)->getLocEnd()));
4033 Args.push_back(TransArg.takeAs<Expr>());
4034 }
4035
4036 if (!getDerived().AlwaysRebuild() &&
4037 T == E->getTypeAsWritten() &&
4038 !ArgumentChanged)
4039 return SemaRef.Owned(E->Retain());
4040
4041 // FIXME: we're faking the locations of the commas
4042 return getDerived().RebuildCXXUnresolvedConstructExpr(E->getTypeBeginLoc(),
4043 T,
4044 E->getLParenLoc(),
4045 move_arg(Args),
4046 FakeCommaLocs.data(),
4047 E->getRParenLoc());
4048}
Douglas Gregore399ad42009-08-26 22:36:53 +00004049
Douglas Gregor9d879762009-08-11 05:31:07 +00004050template<typename Derived>
4051Sema::OwningExprResult
4052TreeTransform<Derived>::TransformCXXUnresolvedMemberExpr(
4053 CXXUnresolvedMemberExpr *E) {
4054 // Transform the base of the expression.
4055 OwningExprResult Base = getDerived().TransformExpr(E->getBase());
4056 if (Base.isInvalid())
4057 return SemaRef.ExprError();
4058
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004059 Sema::TypeTy *ObjectType = 0;
4060 Base = SemaRef.ActOnStartCXXMemberReference(0, move(Base),
4061 E->getOperatorLoc(),
4062 E->isArrow()? tok::arrow : tok::period,
4063 ObjectType);
4064 if (Base.isInvalid())
4065 return SemaRef.ExprError();
4066
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004067 NamedDecl *FirstQualifierInScope
4068 = cast_or_null<NamedDecl>(
4069 getDerived().TransformDecl(E->getFirstQualifierFoundInScope()));
4070
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004071 NestedNameSpecifier *Qualifier = 0;
4072 if (E->getQualifier()) {
4073 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
4074 E->getQualifierRange(),
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004075 QualType::getFromOpaquePtr(ObjectType),
4076 FirstQualifierInScope);
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004077 if (!Qualifier)
4078 return SemaRef.ExprError();
4079 }
4080
Douglas Gregor9d879762009-08-11 05:31:07 +00004081 // FIXME: Transform the declaration name
4082 DeclarationName Name = E->getMember();
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004083
Douglas Gregor9d879762009-08-11 05:31:07 +00004084 if (!getDerived().AlwaysRebuild() &&
4085 Base.get() == E->getBase() &&
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004086 Qualifier == E->getQualifier() &&
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004087 Name == E->getMember() &&
4088 FirstQualifierInScope == E->getFirstQualifierFoundInScope())
Douglas Gregor9d879762009-08-11 05:31:07 +00004089 return SemaRef.Owned(E->Retain());
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004090
Douglas Gregor9d879762009-08-11 05:31:07 +00004091 return getDerived().RebuildCXXUnresolvedMemberExpr(move(Base),
4092 E->isArrow(),
4093 E->getOperatorLoc(),
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004094 Qualifier,
4095 E->getQualifierRange(),
4096 Name,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004097 E->getMemberLoc(),
4098 FirstQualifierInScope);
Douglas Gregor9d879762009-08-11 05:31:07 +00004099}
4100
4101template<typename Derived>
4102Sema::OwningExprResult
4103TreeTransform<Derived>::TransformObjCStringLiteral(ObjCStringLiteral *E) {
4104 return SemaRef.Owned(E->Retain());
4105}
4106
4107template<typename Derived>
4108Sema::OwningExprResult
4109TreeTransform<Derived>::TransformObjCEncodeExpr(ObjCEncodeExpr *E) {
4110 // FIXME: poor source location
4111 TemporaryBase Rebase(*this, E->getAtLoc(), DeclarationName());
4112 QualType EncodedType = getDerived().TransformType(E->getEncodedType());
4113 if (EncodedType.isNull())
4114 return SemaRef.ExprError();
4115
4116 if (!getDerived().AlwaysRebuild() &&
4117 EncodedType == E->getEncodedType())
4118 return SemaRef.Owned(E->Retain());
4119
4120 return getDerived().RebuildObjCEncodeExpr(E->getAtLoc(),
4121 EncodedType,
4122 E->getRParenLoc());
4123}
4124
4125template<typename Derived>
4126Sema::OwningExprResult
4127TreeTransform<Derived>::TransformObjCMessageExpr(ObjCMessageExpr *E) {
4128 // FIXME: Implement this!
4129 assert(false && "Cannot transform Objective-C expressions yet");
4130 return SemaRef.Owned(E->Retain());
4131}
4132
4133template<typename Derived>
4134Sema::OwningExprResult
4135TreeTransform<Derived>::TransformObjCSelectorExpr(ObjCSelectorExpr *E) {
4136 return SemaRef.Owned(E->Retain());
4137}
4138
4139template<typename Derived>
4140Sema::OwningExprResult
4141TreeTransform<Derived>::TransformObjCProtocolExpr(ObjCProtocolExpr *E) {
4142 ObjCProtocolDecl *Protocol
4143 = cast_or_null<ObjCProtocolDecl>(
4144 getDerived().TransformDecl(E->getProtocol()));
4145 if (!Protocol)
4146 return SemaRef.ExprError();
4147
4148 if (!getDerived().AlwaysRebuild() &&
4149 Protocol == E->getProtocol())
4150 return SemaRef.Owned(E->Retain());
4151
4152 return getDerived().RebuildObjCProtocolExpr(Protocol,
4153 E->getAtLoc(),
4154 /*FIXME:*/E->getAtLoc(),
4155 /*FIXME:*/E->getAtLoc(),
4156 E->getRParenLoc());
4157
4158}
4159
4160template<typename Derived>
4161Sema::OwningExprResult
4162TreeTransform<Derived>::TransformObjCIvarRefExpr(ObjCIvarRefExpr *E) {
4163 // FIXME: Implement this!
4164 assert(false && "Cannot transform Objective-C expressions yet");
4165 return SemaRef.Owned(E->Retain());
4166}
4167
4168template<typename Derived>
4169Sema::OwningExprResult
4170TreeTransform<Derived>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr *E) {
4171 // FIXME: Implement this!
4172 assert(false && "Cannot transform Objective-C expressions yet");
4173 return SemaRef.Owned(E->Retain());
4174}
4175
4176template<typename Derived>
4177Sema::OwningExprResult
Fariborz Jahanian128cdc52009-08-20 17:02:02 +00004178TreeTransform<Derived>::TransformObjCImplicitSetterGetterRefExpr(
4179 ObjCImplicitSetterGetterRefExpr *E) {
Douglas Gregor9d879762009-08-11 05:31:07 +00004180 // FIXME: Implement this!
4181 assert(false && "Cannot transform Objective-C expressions yet");
4182 return SemaRef.Owned(E->Retain());
4183}
4184
4185template<typename Derived>
4186Sema::OwningExprResult
4187TreeTransform<Derived>::TransformObjCSuperExpr(ObjCSuperExpr *E) {
4188 // FIXME: Implement this!
4189 assert(false && "Cannot transform Objective-C expressions yet");
4190 return SemaRef.Owned(E->Retain());
4191}
4192
4193template<typename Derived>
4194Sema::OwningExprResult
4195TreeTransform<Derived>::TransformObjCIsaExpr(ObjCIsaExpr *E) {
4196 // FIXME: Implement this!
4197 assert(false && "Cannot transform Objective-C expressions yet");
4198 return SemaRef.Owned(E->Retain());
4199}
4200
4201template<typename Derived>
4202Sema::OwningExprResult
4203TreeTransform<Derived>::TransformShuffleVectorExpr(ShuffleVectorExpr *E) {
4204 bool ArgumentChanged = false;
4205 ASTOwningVector<&ActionBase::DeleteExpr> SubExprs(SemaRef);
4206 for (unsigned I = 0, N = E->getNumSubExprs(); I != N; ++I) {
4207 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExpr(I));
4208 if (SubExpr.isInvalid())
4209 return SemaRef.ExprError();
4210
4211 ArgumentChanged = ArgumentChanged || SubExpr.get() != E->getExpr(I);
4212 SubExprs.push_back(SubExpr.takeAs<Expr>());
4213 }
4214
4215 if (!getDerived().AlwaysRebuild() &&
4216 !ArgumentChanged)
4217 return SemaRef.Owned(E->Retain());
4218
4219 return getDerived().RebuildShuffleVectorExpr(E->getBuiltinLoc(),
4220 move_arg(SubExprs),
4221 E->getRParenLoc());
4222}
4223
4224template<typename Derived>
4225Sema::OwningExprResult
4226TreeTransform<Derived>::TransformBlockExpr(BlockExpr *E) {
4227 // FIXME: Implement this!
4228 assert(false && "Cannot transform block expressions yet");
4229 return SemaRef.Owned(E->Retain());
4230}
4231
4232template<typename Derived>
4233Sema::OwningExprResult
4234TreeTransform<Derived>::TransformBlockDeclRefExpr(BlockDeclRefExpr *E) {
4235 // FIXME: Implement this!
4236 assert(false && "Cannot transform block-related expressions yet");
4237 return SemaRef.Owned(E->Retain());
4238}
4239
4240//===----------------------------------------------------------------------===//
Douglas Gregor841324a2009-08-04 16:50:30 +00004241// Type reconstruction
4242//===----------------------------------------------------------------------===//
4243
4244template<typename Derived>
4245QualType TreeTransform<Derived>::RebuildPointerType(QualType PointeeType) {
4246 return SemaRef.BuildPointerType(PointeeType, 0,
4247 getDerived().getBaseLocation(),
4248 getDerived().getBaseEntity());
4249}
4250
4251template<typename Derived>
4252QualType TreeTransform<Derived>::RebuildBlockPointerType(QualType PointeeType) {
4253 return SemaRef.BuildBlockPointerType(PointeeType, 0,
4254 getDerived().getBaseLocation(),
4255 getDerived().getBaseEntity());
4256}
4257
4258template<typename Derived>
4259QualType
4260TreeTransform<Derived>::RebuildLValueReferenceType(QualType ReferentType) {
4261 return SemaRef.BuildReferenceType(ReferentType, true, 0,
4262 getDerived().getBaseLocation(),
4263 getDerived().getBaseEntity());
4264}
4265
4266template<typename Derived>
4267QualType
4268TreeTransform<Derived>::RebuildRValueReferenceType(QualType ReferentType) {
4269 return SemaRef.BuildReferenceType(ReferentType, false, 0,
4270 getDerived().getBaseLocation(),
4271 getDerived().getBaseEntity());
4272}
4273
4274template<typename Derived>
4275QualType TreeTransform<Derived>::RebuildMemberPointerType(QualType PointeeType,
4276 QualType ClassType) {
4277 return SemaRef.BuildMemberPointerType(PointeeType, ClassType, 0,
4278 getDerived().getBaseLocation(),
4279 getDerived().getBaseEntity());
4280}
4281
4282template<typename Derived>
4283QualType
4284TreeTransform<Derived>::RebuildArrayType(QualType ElementType,
4285 ArrayType::ArraySizeModifier SizeMod,
4286 const llvm::APInt *Size,
4287 Expr *SizeExpr,
4288 unsigned IndexTypeQuals,
4289 SourceRange BracketsRange) {
4290 if (SizeExpr || !Size)
4291 return SemaRef.BuildArrayType(ElementType, SizeMod, SizeExpr,
4292 IndexTypeQuals, BracketsRange,
4293 getDerived().getBaseEntity());
4294
4295 QualType Types[] = {
4296 SemaRef.Context.UnsignedCharTy, SemaRef.Context.UnsignedShortTy,
4297 SemaRef.Context.UnsignedIntTy, SemaRef.Context.UnsignedLongTy,
4298 SemaRef.Context.UnsignedLongLongTy, SemaRef.Context.UnsignedInt128Ty
4299 };
4300 const unsigned NumTypes = sizeof(Types) / sizeof(QualType);
4301 QualType SizeType;
4302 for (unsigned I = 0; I != NumTypes; ++I)
4303 if (Size->getBitWidth() == SemaRef.Context.getIntWidth(Types[I])) {
4304 SizeType = Types[I];
4305 break;
4306 }
4307
4308 if (SizeType.isNull())
4309 SizeType = SemaRef.Context.getFixedWidthIntType(Size->getBitWidth(), false);
4310
4311 IntegerLiteral ArraySize(*Size, SizeType, /*FIXME*/BracketsRange.getBegin());
4312 return SemaRef.BuildArrayType(ElementType, SizeMod, &ArraySize,
4313 IndexTypeQuals, BracketsRange,
4314 getDerived().getBaseEntity());
4315}
4316
4317template<typename Derived>
4318QualType
4319TreeTransform<Derived>::RebuildConstantArrayType(QualType ElementType,
4320 ArrayType::ArraySizeModifier SizeMod,
4321 const llvm::APInt &Size,
4322 unsigned IndexTypeQuals) {
4323 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0,
4324 IndexTypeQuals, SourceRange());
4325}
4326
4327template<typename Derived>
4328QualType
4329TreeTransform<Derived>::RebuildConstantArrayWithExprType(QualType ElementType,
4330 ArrayType::ArraySizeModifier SizeMod,
4331 const llvm::APInt &Size,
4332 Expr *SizeExpr,
4333 unsigned IndexTypeQuals,
4334 SourceRange BracketsRange) {
4335 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, SizeExpr,
4336 IndexTypeQuals, BracketsRange);
4337}
4338
4339template<typename Derived>
4340QualType
4341TreeTransform<Derived>::RebuildConstantArrayWithoutExprType(
4342 QualType ElementType,
4343 ArrayType::ArraySizeModifier SizeMod,
4344 const llvm::APInt &Size,
4345 unsigned IndexTypeQuals) {
4346 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0,
4347 IndexTypeQuals, SourceRange());
4348}
4349
4350template<typename Derived>
4351QualType
4352TreeTransform<Derived>::RebuildIncompleteArrayType(QualType ElementType,
4353 ArrayType::ArraySizeModifier SizeMod,
4354 unsigned IndexTypeQuals) {
4355 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 0,
4356 IndexTypeQuals, SourceRange());
4357}
4358
4359template<typename Derived>
4360QualType
4361TreeTransform<Derived>::RebuildVariableArrayType(QualType ElementType,
4362 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregor9d879762009-08-11 05:31:07 +00004363 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +00004364 unsigned IndexTypeQuals,
4365 SourceRange BracketsRange) {
4366 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
4367 SizeExpr.takeAs<Expr>(),
4368 IndexTypeQuals, BracketsRange);
4369}
4370
4371template<typename Derived>
4372QualType
4373TreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType,
4374 ArrayType::ArraySizeModifier SizeMod,
Douglas Gregor9d879762009-08-11 05:31:07 +00004375 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +00004376 unsigned IndexTypeQuals,
4377 SourceRange BracketsRange) {
4378 return getDerived().RebuildArrayType(ElementType, SizeMod, 0,
4379 SizeExpr.takeAs<Expr>(),
4380 IndexTypeQuals, BracketsRange);
4381}
4382
4383template<typename Derived>
4384QualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType,
4385 unsigned NumElements) {
4386 // FIXME: semantic checking!
4387 return SemaRef.Context.getVectorType(ElementType, NumElements);
4388}
4389
4390template<typename Derived>
4391QualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType,
4392 unsigned NumElements,
4393 SourceLocation AttributeLoc) {
4394 llvm::APInt numElements(SemaRef.Context.getIntWidth(SemaRef.Context.IntTy),
4395 NumElements, true);
4396 IntegerLiteral *VectorSize
4397 = new (SemaRef.Context) IntegerLiteral(numElements, SemaRef.Context.IntTy,
4398 AttributeLoc);
4399 return SemaRef.BuildExtVectorType(ElementType, SemaRef.Owned(VectorSize),
4400 AttributeLoc);
4401}
4402
4403template<typename Derived>
4404QualType
4405TreeTransform<Derived>::RebuildDependentSizedExtVectorType(QualType ElementType,
Douglas Gregor9d879762009-08-11 05:31:07 +00004406 ExprArg SizeExpr,
Douglas Gregor841324a2009-08-04 16:50:30 +00004407 SourceLocation AttributeLoc) {
4408 return SemaRef.BuildExtVectorType(ElementType, move(SizeExpr), AttributeLoc);
4409}
4410
4411template<typename Derived>
4412QualType TreeTransform<Derived>::RebuildFunctionProtoType(QualType T,
4413 QualType *ParamTypes,
4414 unsigned NumParamTypes,
4415 bool Variadic,
4416 unsigned Quals) {
4417 return SemaRef.BuildFunctionType(T, ParamTypes, NumParamTypes, Variadic,
4418 Quals,
4419 getDerived().getBaseLocation(),
4420 getDerived().getBaseEntity());
4421}
4422
4423template<typename Derived>
Douglas Gregor9d879762009-08-11 05:31:07 +00004424QualType TreeTransform<Derived>::RebuildTypeOfExprType(ExprArg E) {
Douglas Gregor841324a2009-08-04 16:50:30 +00004425 return SemaRef.BuildTypeofExprType(E.takeAs<Expr>());
4426}
4427
4428template<typename Derived>
4429QualType TreeTransform<Derived>::RebuildTypeOfType(QualType Underlying) {
4430 return SemaRef.Context.getTypeOfType(Underlying);
4431}
4432
4433template<typename Derived>
Douglas Gregor9d879762009-08-11 05:31:07 +00004434QualType TreeTransform<Derived>::RebuildDecltypeType(ExprArg E) {
Douglas Gregor841324a2009-08-04 16:50:30 +00004435 return SemaRef.BuildDecltypeType(E.takeAs<Expr>());
4436}
4437
4438template<typename Derived>
4439QualType TreeTransform<Derived>::RebuildTemplateSpecializationType(
4440 TemplateName Template,
4441 const TemplateArgument *Args,
4442 unsigned NumArgs) {
4443 // FIXME: Missing source locations for the template name, <, >.
4444 return SemaRef.CheckTemplateIdType(Template, getDerived().getBaseLocation(),
4445 SourceLocation(), Args, NumArgs,
4446 SourceLocation());
4447}
4448
Douglas Gregor12431cb2009-08-06 05:28:30 +00004449template<typename Derived>
4450NestedNameSpecifier *
4451TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
4452 SourceRange Range,
Douglas Gregor0f927cf2009-09-03 16:14:30 +00004453 IdentifierInfo &II,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004454 QualType ObjectType,
4455 NamedDecl *FirstQualifierInScope) {
Douglas Gregor12431cb2009-08-06 05:28:30 +00004456 CXXScopeSpec SS;
4457 // FIXME: The source location information is all wrong.
4458 SS.setRange(Range);
4459 SS.setScopeRep(Prefix);
4460 return static_cast<NestedNameSpecifier *>(
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004461 SemaRef.BuildCXXNestedNameSpecifier(0, SS, Range.getEnd(),
Douglas Gregorc03d3302009-08-25 22:51:20 +00004462 Range.getEnd(), II,
Douglas Gregorbc2fb7f2009-09-03 21:38:09 +00004463 ObjectType,
4464 FirstQualifierInScope,
Douglas Gregorc03d3302009-08-25 22:51:20 +00004465 false));
Douglas Gregor12431cb2009-08-06 05:28:30 +00004466}
4467
4468template<typename Derived>
4469NestedNameSpecifier *
4470TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
4471 SourceRange Range,
4472 NamespaceDecl *NS) {
4473 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, NS);
4474}
4475
4476template<typename Derived>
4477NestedNameSpecifier *
4478TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix,
4479 SourceRange Range,
4480 bool TemplateKW,
4481 QualType T) {
4482 if (T->isDependentType() || T->isRecordType() ||
4483 (SemaRef.getLangOptions().CPlusPlus0x && T->isEnumeralType())) {
4484 assert(T.getCVRQualifiers() == 0 && "Can't get cv-qualifiers here");
4485 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, TemplateKW,
4486 T.getTypePtr());
4487 }
4488
4489 SemaRef.Diag(Range.getBegin(), diag::err_nested_name_spec_non_tag) << T;
4490 return 0;
4491}
4492
Douglas Gregor214d0462009-08-06 06:41:21 +00004493template<typename Derived>
4494TemplateName
4495TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
4496 bool TemplateKW,
4497 TemplateDecl *Template) {
4498 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW,
4499 Template);
4500}
4501
4502template<typename Derived>
4503TemplateName
4504TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
4505 bool TemplateKW,
4506 OverloadedFunctionDecl *Ovl) {
4507 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW, Ovl);
4508}
4509
4510template<typename Derived>
4511TemplateName
4512TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier,
4513 const IdentifierInfo &II) {
4514 if (Qualifier->isDependent())
4515 return SemaRef.Context.getDependentTemplateName(Qualifier, &II);
4516
4517 // Somewhat redundant with ActOnDependentTemplateName.
4518 CXXScopeSpec SS;
4519 SS.setRange(SourceRange(getDerived().getBaseLocation()));
4520 SS.setScopeRep(Qualifier);
4521 Sema::TemplateTy Template;
Douglas Gregor681d31d2009-09-02 22:59:36 +00004522 TemplateNameKind TNK = SemaRef.isTemplateName(0, II,
4523 /*FIXME:*/getDerived().getBaseLocation(),
4524 &SS,
4525 /*FIXME:ObjectType=*/0, false,
4526 Template);
Douglas Gregor214d0462009-08-06 06:41:21 +00004527 if (TNK == TNK_Non_template) {
4528 SemaRef.Diag(getDerived().getBaseLocation(),
4529 diag::err_template_kw_refers_to_non_template)
4530 << &II;
4531 return TemplateName();
4532 } else if (TNK == TNK_Function_template) {
4533 SemaRef.Diag(getDerived().getBaseLocation(),
4534 diag::err_template_kw_refers_to_non_template)
4535 << &II;
4536 return TemplateName();
4537 }
4538
4539 return Template.getAsVal<TemplateName>();
4540}
Douglas Gregor9d879762009-08-11 05:31:07 +00004541
4542template<typename Derived>
4543Sema::OwningExprResult
4544TreeTransform<Derived>::RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op,
4545 SourceLocation OpLoc,
4546 ExprArg Callee,
4547 ExprArg First,
4548 ExprArg Second) {
4549 Expr *FirstExpr = (Expr *)First.get();
4550 Expr *SecondExpr = (Expr *)Second.get();
4551 bool isPostIncDec = SecondExpr && (Op == OO_PlusPlus || Op == OO_MinusMinus);
4552
4553 // Determine whether this should be a builtin operation.
4554 if (SecondExpr == 0 || isPostIncDec) {
4555 if (!FirstExpr->getType()->isOverloadableType()) {
4556 // The argument is not of overloadable type, so try to create a
4557 // built-in unary operation.
4558 UnaryOperator::Opcode Opc
4559 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
4560
4561 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(First));
4562 }
4563 } else {
4564 if (!FirstExpr->getType()->isOverloadableType() &&
4565 !SecondExpr->getType()->isOverloadableType()) {
4566 // Neither of the arguments is an overloadable type, so try to
4567 // create a built-in binary operation.
4568 BinaryOperator::Opcode Opc = BinaryOperator::getOverloadedOpcode(Op);
4569 OwningExprResult Result
4570 = SemaRef.CreateBuiltinBinOp(OpLoc, Opc, FirstExpr, SecondExpr);
4571 if (Result.isInvalid())
4572 return SemaRef.ExprError();
4573
4574 First.release();
4575 Second.release();
4576 return move(Result);
4577 }
4578 }
4579
4580 // Compute the transformed set of functions (and function templates) to be
4581 // used during overload resolution.
4582 Sema::FunctionSet Functions;
4583
Douglas Gregor23026c82009-09-01 16:58:52 +00004584 DeclRefExpr *DRE
4585 = cast<DeclRefExpr>(((Expr *)Callee.get())->IgnoreParenCasts());
Douglas Gregor9d879762009-08-11 05:31:07 +00004586
4587 // FIXME: Do we have to check
4588 // IsAcceptableNonMemberOperatorCandidate for each of these?
Douglas Gregor23026c82009-09-01 16:58:52 +00004589 for (OverloadIterator F(DRE->getDecl()), FEnd; F != FEnd; ++F)
Douglas Gregor9d879762009-08-11 05:31:07 +00004590 Functions.insert(*F);
4591
4592 // Add any functions found via argument-dependent lookup.
4593 Expr *Args[2] = { FirstExpr, SecondExpr };
4594 unsigned NumArgs = 1 + (SecondExpr != 0);
4595 DeclarationName OpName
4596 = SemaRef.Context.DeclarationNames.getCXXOperatorName(Op);
4597 SemaRef.ArgumentDependentLookup(OpName, Args, NumArgs, Functions);
4598
4599 // Create the overloaded operator invocation for unary operators.
4600 if (NumArgs == 1 || isPostIncDec) {
4601 UnaryOperator::Opcode Opc
4602 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec);
4603 return SemaRef.CreateOverloadedUnaryOp(OpLoc, Opc, Functions, move(First));
4604 }
4605
4606 // Create the overloaded operator invocation for binary operators.
4607 BinaryOperator::Opcode Opc =
4608 BinaryOperator::getOverloadedOpcode(Op);
4609 OwningExprResult Result
4610 = SemaRef.CreateOverloadedBinOp(OpLoc, Opc, Functions, Args[0], Args[1]);
4611 if (Result.isInvalid())
4612 return SemaRef.ExprError();
4613
4614 First.release();
4615 Second.release();
4616 return move(Result);
4617}
Douglas Gregor214d0462009-08-06 06:41:21 +00004618
Douglas Gregor841324a2009-08-04 16:50:30 +00004619} // end namespace clang
4620
4621#endif // LLVM_CLANG_SEMA_TREETRANSFORM_H