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