TreeTransform.h revision 4a1d3d039af0d74537ecb4ff8f55bb881319b2af
1//===------- TreeTransform.h - Semantic Tree Transformation -----*- C++ -*-===/ 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" 17#include "Lookup.h" 18#include "clang/Sema/SemaDiagnostic.h" 19#include "clang/AST/Decl.h" 20#include "clang/AST/Expr.h" 21#include "clang/AST/ExprCXX.h" 22#include "clang/AST/ExprObjC.h" 23#include "clang/AST/Stmt.h" 24#include "clang/AST/StmtCXX.h" 25#include "clang/AST/StmtObjC.h" 26#include "clang/AST/TypeLocBuilder.h" 27#include "clang/Parse/Ownership.h" 28#include "clang/Parse/Designator.h" 29#include "clang/Lex/Preprocessor.h" 30#include "llvm/Support/ErrorHandling.h" 31#include <algorithm> 32 33namespace clang { 34 35/// \brief A semantic tree transformation that allows one to transform one 36/// abstract syntax tree into another. 37/// 38/// A new tree transformation is defined by creating a new subclass \c X of 39/// \c TreeTransform<X> and then overriding certain operations to provide 40/// behavior specific to that transformation. For example, template 41/// instantiation is implemented as a tree transformation where the 42/// transformation of TemplateTypeParmType nodes involves substituting the 43/// template arguments for their corresponding template parameters; a similar 44/// transformation is performed for non-type template parameters and 45/// template template parameters. 46/// 47/// This tree-transformation template uses static polymorphism to allow 48/// subclasses to customize any of its operations. Thus, a subclass can 49/// override any of the transformation or rebuild operators by providing an 50/// operation with the same signature as the default implementation. The 51/// overridding function should not be virtual. 52/// 53/// Semantic tree transformations are split into two stages, either of which 54/// can be replaced by a subclass. The "transform" step transforms an AST node 55/// or the parts of an AST node using the various transformation functions, 56/// then passes the pieces on to the "rebuild" step, which constructs a new AST 57/// node of the appropriate kind from the pieces. The default transformation 58/// routines recursively transform the operands to composite AST nodes (e.g., 59/// the pointee type of a PointerType node) and, if any of those operand nodes 60/// were changed by the transformation, invokes the rebuild operation to create 61/// a new AST node. 62/// 63/// Subclasses can customize the transformation at various levels. The 64/// most coarse-grained transformations involve replacing TransformType(), 65/// TransformExpr(), TransformDecl(), TransformNestedNameSpecifier(), 66/// TransformTemplateName(), or TransformTemplateArgument() with entirely 67/// new implementations. 68/// 69/// For more fine-grained transformations, subclasses can replace any of the 70/// \c TransformXXX functions (where XXX is the name of an AST node, e.g., 71/// PointerType, StmtExpr) to alter the transformation. As mentioned previously, 72/// replacing TransformTemplateTypeParmType() allows template instantiation 73/// to substitute template arguments for their corresponding template 74/// parameters. Additionally, subclasses can override the \c RebuildXXX 75/// functions to control how AST nodes are rebuilt when their operands change. 76/// By default, \c TreeTransform will invoke semantic analysis to rebuild 77/// AST nodes. However, certain other tree transformations (e.g, cloning) may 78/// be able to use more efficient rebuild steps. 79/// 80/// There are a handful of other functions that can be overridden, allowing one 81/// to avoid traversing nodes that don't need any transformation 82/// (\c AlreadyTransformed()), force rebuilding AST nodes even when their 83/// operands have not changed (\c AlwaysRebuild()), and customize the 84/// default locations and entity names used for type-checking 85/// (\c getBaseLocation(), \c getBaseEntity()). 86template<typename Derived> 87class TreeTransform { 88protected: 89 Sema &SemaRef; 90 91public: 92 typedef Sema::OwningStmtResult OwningStmtResult; 93 typedef Sema::OwningExprResult OwningExprResult; 94 typedef Sema::StmtArg StmtArg; 95 typedef Sema::ExprArg ExprArg; 96 typedef Sema::MultiExprArg MultiExprArg; 97 typedef Sema::MultiStmtArg MultiStmtArg; 98 typedef Sema::DeclPtrTy DeclPtrTy; 99 100 /// \brief Initializes a new tree transformer. 101 TreeTransform(Sema &SemaRef) : SemaRef(SemaRef) { } 102 103 /// \brief Retrieves a reference to the derived class. 104 Derived &getDerived() { return static_cast<Derived&>(*this); } 105 106 /// \brief Retrieves a reference to the derived class. 107 const Derived &getDerived() const { 108 return static_cast<const Derived&>(*this); 109 } 110 111 /// \brief Retrieves a reference to the semantic analysis object used for 112 /// this tree transform. 113 Sema &getSema() const { return SemaRef; } 114 115 /// \brief Whether the transformation should always rebuild AST nodes, even 116 /// if none of the children have changed. 117 /// 118 /// Subclasses may override this function to specify when the transformation 119 /// should rebuild all AST nodes. 120 bool AlwaysRebuild() { return false; } 121 122 /// \brief Returns the location of the entity being transformed, if that 123 /// information was not available elsewhere in the AST. 124 /// 125 /// By default, returns no source-location information. Subclasses can 126 /// provide an alternative implementation that provides better location 127 /// information. 128 SourceLocation getBaseLocation() { return SourceLocation(); } 129 130 /// \brief Returns the name of the entity being transformed, if that 131 /// information was not available elsewhere in the AST. 132 /// 133 /// By default, returns an empty name. Subclasses can provide an alternative 134 /// implementation with a more precise name. 135 DeclarationName getBaseEntity() { return DeclarationName(); } 136 137 /// \brief Sets the "base" location and entity when that 138 /// information is known based on another transformation. 139 /// 140 /// By default, the source location and entity are ignored. Subclasses can 141 /// override this function to provide a customized implementation. 142 void setBase(SourceLocation Loc, DeclarationName Entity) { } 143 144 /// \brief RAII object that temporarily sets the base location and entity 145 /// used for reporting diagnostics in types. 146 class TemporaryBase { 147 TreeTransform &Self; 148 SourceLocation OldLocation; 149 DeclarationName OldEntity; 150 151 public: 152 TemporaryBase(TreeTransform &Self, SourceLocation Location, 153 DeclarationName Entity) : Self(Self) { 154 OldLocation = Self.getDerived().getBaseLocation(); 155 OldEntity = Self.getDerived().getBaseEntity(); 156 Self.getDerived().setBase(Location, Entity); 157 } 158 159 ~TemporaryBase() { 160 Self.getDerived().setBase(OldLocation, OldEntity); 161 } 162 }; 163 164 /// \brief Determine whether the given type \p T has already been 165 /// transformed. 166 /// 167 /// Subclasses can provide an alternative implementation of this routine 168 /// to short-circuit evaluation when it is known that a given type will 169 /// not change. For example, template instantiation need not traverse 170 /// non-dependent types. 171 bool AlreadyTransformed(QualType T) { 172 return T.isNull(); 173 } 174 175 /// \brief Determine whether the given call argument should be dropped, e.g., 176 /// because it is a default argument. 177 /// 178 /// Subclasses can provide an alternative implementation of this routine to 179 /// determine which kinds of call arguments get dropped. By default, 180 /// CXXDefaultArgument nodes are dropped (prior to transformation). 181 bool DropCallArgument(Expr *E) { 182 return E->isDefaultArgument(); 183 } 184 185 /// \brief Transforms the given type into another type. 186 /// 187 /// By default, this routine transforms a type by creating a 188 /// TypeSourceInfo for it and delegating to the appropriate 189 /// function. This is expensive, but we don't mind, because 190 /// this method is deprecated anyway; all users should be 191 /// switched to storing TypeSourceInfos. 192 /// 193 /// \returns the transformed type. 194 QualType TransformType(QualType T, QualType ObjectType = QualType()); 195 196 /// \brief Transforms the given type-with-location into a new 197 /// type-with-location. 198 /// 199 /// By default, this routine transforms a type by delegating to the 200 /// appropriate TransformXXXType to build a new type. Subclasses 201 /// may override this function (to take over all type 202 /// transformations) or some set of the TransformXXXType functions 203 /// to alter the transformation. 204 TypeSourceInfo *TransformType(TypeSourceInfo *DI, 205 QualType ObjectType = QualType()); 206 207 /// \brief Transform the given type-with-location into a new 208 /// type, collecting location information in the given builder 209 /// as necessary. 210 /// 211 QualType TransformType(TypeLocBuilder &TLB, TypeLoc TL, 212 QualType ObjectType = QualType()); 213 214 /// \brief Transform the given statement. 215 /// 216 /// By default, this routine transforms a statement by delegating to the 217 /// appropriate TransformXXXStmt function to transform a specific kind of 218 /// statement or the TransformExpr() function to transform an expression. 219 /// Subclasses may override this function to transform statements using some 220 /// other mechanism. 221 /// 222 /// \returns the transformed statement. 223 OwningStmtResult TransformStmt(Stmt *S); 224 225 /// \brief Transform the given expression. 226 /// 227 /// By default, this routine transforms an expression by delegating to the 228 /// appropriate TransformXXXExpr function to build a new expression. 229 /// Subclasses may override this function to transform expressions using some 230 /// other mechanism. 231 /// 232 /// \returns the transformed expression. 233 OwningExprResult TransformExpr(Expr *E); 234 235 /// \brief Transform the given declaration, which is referenced from a type 236 /// or expression. 237 /// 238 /// By default, acts as the identity function on declarations. Subclasses 239 /// may override this function to provide alternate behavior. 240 Decl *TransformDecl(SourceLocation Loc, Decl *D) { return D; } 241 242 /// \brief Transform the definition of the given declaration. 243 /// 244 /// By default, invokes TransformDecl() to transform the declaration. 245 /// Subclasses may override this function to provide alternate behavior. 246 Decl *TransformDefinition(SourceLocation Loc, Decl *D) { 247 return getDerived().TransformDecl(Loc, D); 248 } 249 250 /// \brief Transform the given declaration, which was the first part of a 251 /// nested-name-specifier in a member access expression. 252 /// 253 /// This specific declaration transformation only applies to the first 254 /// identifier in a nested-name-specifier of a member access expression, e.g., 255 /// the \c T in \c x->T::member 256 /// 257 /// By default, invokes TransformDecl() to transform the declaration. 258 /// Subclasses may override this function to provide alternate behavior. 259 NamedDecl *TransformFirstQualifierInScope(NamedDecl *D, SourceLocation Loc) { 260 return cast_or_null<NamedDecl>(getDerived().TransformDecl(Loc, D)); 261 } 262 263 /// \brief Transform the given nested-name-specifier. 264 /// 265 /// By default, transforms all of the types and declarations within the 266 /// nested-name-specifier. Subclasses may override this function to provide 267 /// alternate behavior. 268 NestedNameSpecifier *TransformNestedNameSpecifier(NestedNameSpecifier *NNS, 269 SourceRange Range, 270 QualType ObjectType = QualType(), 271 NamedDecl *FirstQualifierInScope = 0); 272 273 /// \brief Transform the given declaration name. 274 /// 275 /// By default, transforms the types of conversion function, constructor, 276 /// and destructor names and then (if needed) rebuilds the declaration name. 277 /// Identifiers and selectors are returned unmodified. Sublcasses may 278 /// override this function to provide alternate behavior. 279 DeclarationName TransformDeclarationName(DeclarationName Name, 280 SourceLocation Loc, 281 QualType ObjectType = QualType()); 282 283 /// \brief Transform the given template name. 284 /// 285 /// By default, transforms the template name by transforming the declarations 286 /// and nested-name-specifiers that occur within the template name. 287 /// Subclasses may override this function to provide alternate behavior. 288 TemplateName TransformTemplateName(TemplateName Name, 289 QualType ObjectType = QualType()); 290 291 /// \brief Transform the given template argument. 292 /// 293 /// By default, this operation transforms the type, expression, or 294 /// declaration stored within the template argument and constructs a 295 /// new template argument from the transformed result. Subclasses may 296 /// override this function to provide alternate behavior. 297 /// 298 /// Returns true if there was an error. 299 bool TransformTemplateArgument(const TemplateArgumentLoc &Input, 300 TemplateArgumentLoc &Output); 301 302 /// \brief Fakes up a TemplateArgumentLoc for a given TemplateArgument. 303 void InventTemplateArgumentLoc(const TemplateArgument &Arg, 304 TemplateArgumentLoc &ArgLoc); 305 306 /// \brief Fakes up a TypeSourceInfo for a type. 307 TypeSourceInfo *InventTypeSourceInfo(QualType T) { 308 return SemaRef.Context.getTrivialTypeSourceInfo(T, 309 getDerived().getBaseLocation()); 310 } 311 312#define ABSTRACT_TYPELOC(CLASS, PARENT) 313#define TYPELOC(CLASS, PARENT) \ 314 QualType Transform##CLASS##Type(TypeLocBuilder &TLB, CLASS##TypeLoc T, \ 315 QualType ObjectType = QualType()); 316#include "clang/AST/TypeLocNodes.def" 317 318 /// \brief Transforms the parameters of a function type into the 319 /// given vectors. 320 /// 321 /// The result vectors should be kept in sync; null entries in the 322 /// variables vector are acceptable. 323 /// 324 /// Return true on error. 325 bool TransformFunctionTypeParams(FunctionProtoTypeLoc TL, 326 llvm::SmallVectorImpl<QualType> &PTypes, 327 llvm::SmallVectorImpl<ParmVarDecl*> &PVars); 328 329 /// \brief Transforms a single function-type parameter. Return null 330 /// on error. 331 ParmVarDecl *TransformFunctionTypeParam(ParmVarDecl *OldParm); 332 333 QualType TransformReferenceType(TypeLocBuilder &TLB, ReferenceTypeLoc TL, 334 QualType ObjectType); 335 336 QualType 337 TransformTemplateSpecializationType(const TemplateSpecializationType *T, 338 QualType ObjectType); 339 340 OwningStmtResult TransformCompoundStmt(CompoundStmt *S, bool IsStmtExpr); 341 OwningExprResult TransformCXXNamedCastExpr(CXXNamedCastExpr *E); 342 343#define STMT(Node, Parent) \ 344 OwningStmtResult Transform##Node(Node *S); 345#define EXPR(Node, Parent) \ 346 OwningExprResult Transform##Node(Node *E); 347#define ABSTRACT_EXPR(Node, Parent) 348#include "clang/AST/StmtNodes.def" 349 350 /// \brief Build a new pointer type given its pointee type. 351 /// 352 /// By default, performs semantic analysis when building the pointer type. 353 /// Subclasses may override this routine to provide different behavior. 354 QualType RebuildPointerType(QualType PointeeType, SourceLocation Sigil); 355 356 /// \brief Build a new block pointer type given its pointee type. 357 /// 358 /// By default, performs semantic analysis when building the block pointer 359 /// type. Subclasses may override this routine to provide different behavior. 360 QualType RebuildBlockPointerType(QualType PointeeType, SourceLocation Sigil); 361 362 /// \brief Build a new reference type given the type it references. 363 /// 364 /// By default, performs semantic analysis when building the 365 /// reference type. Subclasses may override this routine to provide 366 /// different behavior. 367 /// 368 /// \param LValue whether the type was written with an lvalue sigil 369 /// or an rvalue sigil. 370 QualType RebuildReferenceType(QualType ReferentType, 371 bool LValue, 372 SourceLocation Sigil); 373 374 /// \brief Build a new member pointer type given the pointee type and the 375 /// class type it refers into. 376 /// 377 /// By default, performs semantic analysis when building the member pointer 378 /// type. Subclasses may override this routine to provide different behavior. 379 QualType RebuildMemberPointerType(QualType PointeeType, QualType ClassType, 380 SourceLocation Sigil); 381 382 /// \brief Build a new array type given the element type, size 383 /// modifier, size of the array (if known), size expression, and index type 384 /// qualifiers. 385 /// 386 /// By default, performs semantic analysis when building the array type. 387 /// Subclasses may override this routine to provide different behavior. 388 /// Also by default, all of the other Rebuild*Array 389 QualType RebuildArrayType(QualType ElementType, 390 ArrayType::ArraySizeModifier SizeMod, 391 const llvm::APInt *Size, 392 Expr *SizeExpr, 393 unsigned IndexTypeQuals, 394 SourceRange BracketsRange); 395 396 /// \brief Build a new constant array type given the element type, size 397 /// modifier, (known) size of the array, and index type qualifiers. 398 /// 399 /// By default, performs semantic analysis when building the array type. 400 /// Subclasses may override this routine to provide different behavior. 401 QualType RebuildConstantArrayType(QualType ElementType, 402 ArrayType::ArraySizeModifier SizeMod, 403 const llvm::APInt &Size, 404 unsigned IndexTypeQuals, 405 SourceRange BracketsRange); 406 407 /// \brief Build a new incomplete array type given the element type, size 408 /// modifier, and index type qualifiers. 409 /// 410 /// By default, performs semantic analysis when building the array type. 411 /// Subclasses may override this routine to provide different behavior. 412 QualType RebuildIncompleteArrayType(QualType ElementType, 413 ArrayType::ArraySizeModifier SizeMod, 414 unsigned IndexTypeQuals, 415 SourceRange BracketsRange); 416 417 /// \brief Build a new variable-length array type given the element type, 418 /// size modifier, size expression, and index type qualifiers. 419 /// 420 /// By default, performs semantic analysis when building the array type. 421 /// Subclasses may override this routine to provide different behavior. 422 QualType RebuildVariableArrayType(QualType ElementType, 423 ArrayType::ArraySizeModifier SizeMod, 424 ExprArg SizeExpr, 425 unsigned IndexTypeQuals, 426 SourceRange BracketsRange); 427 428 /// \brief Build a new dependent-sized array type given the element type, 429 /// size modifier, size expression, and index type qualifiers. 430 /// 431 /// By default, performs semantic analysis when building the array type. 432 /// Subclasses may override this routine to provide different behavior. 433 QualType RebuildDependentSizedArrayType(QualType ElementType, 434 ArrayType::ArraySizeModifier SizeMod, 435 ExprArg SizeExpr, 436 unsigned IndexTypeQuals, 437 SourceRange BracketsRange); 438 439 /// \brief Build a new vector type given the element type and 440 /// number of elements. 441 /// 442 /// By default, performs semantic analysis when building the vector type. 443 /// Subclasses may override this routine to provide different behavior. 444 QualType RebuildVectorType(QualType ElementType, unsigned NumElements, 445 bool IsAltiVec, bool IsPixel); 446 447 /// \brief Build a new extended vector type given the element type and 448 /// number of elements. 449 /// 450 /// By default, performs semantic analysis when building the vector type. 451 /// Subclasses may override this routine to provide different behavior. 452 QualType RebuildExtVectorType(QualType ElementType, unsigned NumElements, 453 SourceLocation AttributeLoc); 454 455 /// \brief Build a new potentially dependently-sized extended vector type 456 /// given the element type and number of elements. 457 /// 458 /// By default, performs semantic analysis when building the vector type. 459 /// Subclasses may override this routine to provide different behavior. 460 QualType RebuildDependentSizedExtVectorType(QualType ElementType, 461 ExprArg SizeExpr, 462 SourceLocation AttributeLoc); 463 464 /// \brief Build a new function type. 465 /// 466 /// By default, performs semantic analysis when building the function type. 467 /// Subclasses may override this routine to provide different behavior. 468 QualType RebuildFunctionProtoType(QualType T, 469 QualType *ParamTypes, 470 unsigned NumParamTypes, 471 bool Variadic, unsigned Quals); 472 473 /// \brief Build a new unprototyped function type. 474 QualType RebuildFunctionNoProtoType(QualType ResultType); 475 476 /// \brief Rebuild an unresolved typename type, given the decl that 477 /// the UnresolvedUsingTypenameDecl was transformed to. 478 QualType RebuildUnresolvedUsingType(Decl *D); 479 480 /// \brief Build a new typedef type. 481 QualType RebuildTypedefType(TypedefDecl *Typedef) { 482 return SemaRef.Context.getTypeDeclType(Typedef); 483 } 484 485 /// \brief Build a new class/struct/union type. 486 QualType RebuildRecordType(RecordDecl *Record) { 487 return SemaRef.Context.getTypeDeclType(Record); 488 } 489 490 /// \brief Build a new Enum type. 491 QualType RebuildEnumType(EnumDecl *Enum) { 492 return SemaRef.Context.getTypeDeclType(Enum); 493 } 494 495 /// \brief Build a new elaborated type. 496 QualType RebuildElaboratedType(QualType T, ElaboratedType::TagKind Tag) { 497 return SemaRef.Context.getElaboratedType(T, Tag); 498 } 499 500 /// \brief Build a new typeof(expr) type. 501 /// 502 /// By default, performs semantic analysis when building the typeof type. 503 /// Subclasses may override this routine to provide different behavior. 504 QualType RebuildTypeOfExprType(ExprArg Underlying); 505 506 /// \brief Build a new typeof(type) type. 507 /// 508 /// By default, builds a new TypeOfType with the given underlying type. 509 QualType RebuildTypeOfType(QualType Underlying); 510 511 /// \brief Build a new C++0x decltype type. 512 /// 513 /// By default, performs semantic analysis when building the decltype type. 514 /// Subclasses may override this routine to provide different behavior. 515 QualType RebuildDecltypeType(ExprArg Underlying); 516 517 /// \brief Build a new template specialization type. 518 /// 519 /// By default, performs semantic analysis when building the template 520 /// specialization type. Subclasses may override this routine to provide 521 /// different behavior. 522 QualType RebuildTemplateSpecializationType(TemplateName Template, 523 SourceLocation TemplateLoc, 524 const TemplateArgumentListInfo &Args); 525 526 /// \brief Build a new qualified name type. 527 /// 528 /// By default, builds a new QualifiedNameType type from the 529 /// nested-name-specifier and the named type. Subclasses may override 530 /// this routine to provide different behavior. 531 QualType RebuildQualifiedNameType(NestedNameSpecifier *NNS, QualType Named) { 532 return SemaRef.Context.getQualifiedNameType(NNS, Named); 533 } 534 535 /// \brief Build a new typename type that refers to a template-id. 536 /// 537 /// By default, builds a new DependentNameType type from the 538 /// nested-name-specifier 539 /// and the given type. Subclasses may override this routine to provide 540 /// different behavior. 541 QualType RebuildDependentNameType(ElaboratedTypeKeyword Keyword, 542 NestedNameSpecifier *NNS, QualType T) { 543 if (NNS->isDependent()) { 544 // If the name is still dependent, just build a new dependent name type. 545 CXXScopeSpec SS; 546 SS.setScopeRep(NNS); 547 if (!SemaRef.computeDeclContext(SS)) 548 return SemaRef.Context.getDependentNameType(Keyword, NNS, 549 cast<TemplateSpecializationType>(T)); 550 } 551 552 // FIXME: Handle elaborated-type-specifiers separately. 553 return SemaRef.Context.getQualifiedNameType(NNS, T); 554 } 555 556 /// \brief Build a new typename type that refers to an identifier. 557 /// 558 /// By default, performs semantic analysis when building the typename type 559 /// (or qualified name type). Subclasses may override this routine to provide 560 /// different behavior. 561 QualType RebuildDependentNameType(ElaboratedTypeKeyword Keyword, 562 NestedNameSpecifier *NNS, 563 const IdentifierInfo *Id, 564 SourceRange SR) { 565 CXXScopeSpec SS; 566 SS.setScopeRep(NNS); 567 568 if (NNS->isDependent()) { 569 // If the name is still dependent, just build a new dependent name type. 570 if (!SemaRef.computeDeclContext(SS)) 571 return SemaRef.Context.getDependentNameType(Keyword, NNS, Id); 572 } 573 574 TagDecl::TagKind Kind = TagDecl::TK_enum; 575 switch (Keyword) { 576 case ETK_None: 577 // Fall through. 578 case ETK_Typename: 579 return SemaRef.CheckTypenameType(Keyword, NNS, *Id, SR); 580 581 case ETK_Class: Kind = TagDecl::TK_class; break; 582 case ETK_Struct: Kind = TagDecl::TK_struct; break; 583 case ETK_Union: Kind = TagDecl::TK_union; break; 584 case ETK_Enum: Kind = TagDecl::TK_enum; break; 585 } 586 587 // We had a dependent elaborated-type-specifier that as been transformed 588 // into a non-dependent elaborated-type-specifier. Find the tag we're 589 // referring to. 590 LookupResult Result(SemaRef, Id, SR.getEnd(), Sema::LookupTagName); 591 DeclContext *DC = SemaRef.computeDeclContext(SS, false); 592 if (!DC) 593 return QualType(); 594 595 TagDecl *Tag = 0; 596 SemaRef.LookupQualifiedName(Result, DC); 597 switch (Result.getResultKind()) { 598 case LookupResult::NotFound: 599 case LookupResult::NotFoundInCurrentInstantiation: 600 break; 601 602 case LookupResult::Found: 603 Tag = Result.getAsSingle<TagDecl>(); 604 break; 605 606 case LookupResult::FoundOverloaded: 607 case LookupResult::FoundUnresolvedValue: 608 llvm_unreachable("Tag lookup cannot find non-tags"); 609 return QualType(); 610 611 case LookupResult::Ambiguous: 612 // Let the LookupResult structure handle ambiguities. 613 return QualType(); 614 } 615 616 if (!Tag) { 617 // FIXME: Would be nice to highlight just the source range. 618 SemaRef.Diag(SR.getEnd(), diag::err_not_tag_in_scope) 619 << Kind << Id << DC; 620 return QualType(); 621 } 622 623 // FIXME: Terrible location information 624 if (!SemaRef.isAcceptableTagRedeclaration(Tag, Kind, SR.getEnd(), *Id)) { 625 SemaRef.Diag(SR.getBegin(), diag::err_use_with_wrong_tag) << Id; 626 SemaRef.Diag(Tag->getLocation(), diag::note_previous_use); 627 return QualType(); 628 } 629 630 // Build the elaborated-type-specifier type. 631 QualType T = SemaRef.Context.getTypeDeclType(Tag); 632 T = SemaRef.Context.getQualifiedNameType(NNS, T); 633 return SemaRef.Context.getElaboratedType(T, Kind); 634 } 635 636 /// \brief Build a new nested-name-specifier given the prefix and an 637 /// identifier that names the next step in the nested-name-specifier. 638 /// 639 /// By default, performs semantic analysis when building the new 640 /// nested-name-specifier. Subclasses may override this routine to provide 641 /// different behavior. 642 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 643 SourceRange Range, 644 IdentifierInfo &II, 645 QualType ObjectType, 646 NamedDecl *FirstQualifierInScope); 647 648 /// \brief Build a new nested-name-specifier given the prefix and the 649 /// namespace named in the next step in the nested-name-specifier. 650 /// 651 /// By default, performs semantic analysis when building the new 652 /// nested-name-specifier. Subclasses may override this routine to provide 653 /// different behavior. 654 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 655 SourceRange Range, 656 NamespaceDecl *NS); 657 658 /// \brief Build a new nested-name-specifier given the prefix and the 659 /// type named in the next step in the nested-name-specifier. 660 /// 661 /// By default, performs semantic analysis when building the new 662 /// nested-name-specifier. Subclasses may override this routine to provide 663 /// different behavior. 664 NestedNameSpecifier *RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 665 SourceRange Range, 666 bool TemplateKW, 667 QualType T); 668 669 /// \brief Build a new template name given a nested name specifier, a flag 670 /// indicating whether the "template" keyword was provided, and the template 671 /// that the template name refers to. 672 /// 673 /// By default, builds the new template name directly. Subclasses may override 674 /// this routine to provide different behavior. 675 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier, 676 bool TemplateKW, 677 TemplateDecl *Template); 678 679 /// \brief Build a new template name given a nested name specifier and the 680 /// name that is referred to as a template. 681 /// 682 /// By default, performs semantic analysis to determine whether the name can 683 /// be resolved to a specific template, then builds the appropriate kind of 684 /// template name. Subclasses may override this routine to provide different 685 /// behavior. 686 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier, 687 const IdentifierInfo &II, 688 QualType ObjectType); 689 690 /// \brief Build a new template name given a nested name specifier and the 691 /// overloaded operator name that is referred to as a template. 692 /// 693 /// By default, performs semantic analysis to determine whether the name can 694 /// be resolved to a specific template, then builds the appropriate kind of 695 /// template name. Subclasses may override this routine to provide different 696 /// behavior. 697 TemplateName RebuildTemplateName(NestedNameSpecifier *Qualifier, 698 OverloadedOperatorKind Operator, 699 QualType ObjectType); 700 701 /// \brief Build a new compound statement. 702 /// 703 /// By default, performs semantic analysis to build the new statement. 704 /// Subclasses may override this routine to provide different behavior. 705 OwningStmtResult RebuildCompoundStmt(SourceLocation LBraceLoc, 706 MultiStmtArg Statements, 707 SourceLocation RBraceLoc, 708 bool IsStmtExpr) { 709 return getSema().ActOnCompoundStmt(LBraceLoc, RBraceLoc, move(Statements), 710 IsStmtExpr); 711 } 712 713 /// \brief Build a new case statement. 714 /// 715 /// By default, performs semantic analysis to build the new statement. 716 /// Subclasses may override this routine to provide different behavior. 717 OwningStmtResult RebuildCaseStmt(SourceLocation CaseLoc, 718 ExprArg LHS, 719 SourceLocation EllipsisLoc, 720 ExprArg RHS, 721 SourceLocation ColonLoc) { 722 return getSema().ActOnCaseStmt(CaseLoc, move(LHS), EllipsisLoc, move(RHS), 723 ColonLoc); 724 } 725 726 /// \brief Attach the body to a new case statement. 727 /// 728 /// By default, performs semantic analysis to build the new statement. 729 /// Subclasses may override this routine to provide different behavior. 730 OwningStmtResult RebuildCaseStmtBody(StmtArg S, StmtArg Body) { 731 getSema().ActOnCaseStmtBody(S.get(), move(Body)); 732 return move(S); 733 } 734 735 /// \brief Build a new default statement. 736 /// 737 /// By default, performs semantic analysis to build the new statement. 738 /// Subclasses may override this routine to provide different behavior. 739 OwningStmtResult RebuildDefaultStmt(SourceLocation DefaultLoc, 740 SourceLocation ColonLoc, 741 StmtArg SubStmt) { 742 return getSema().ActOnDefaultStmt(DefaultLoc, ColonLoc, move(SubStmt), 743 /*CurScope=*/0); 744 } 745 746 /// \brief Build a new label statement. 747 /// 748 /// By default, performs semantic analysis to build the new statement. 749 /// Subclasses may override this routine to provide different behavior. 750 OwningStmtResult RebuildLabelStmt(SourceLocation IdentLoc, 751 IdentifierInfo *Id, 752 SourceLocation ColonLoc, 753 StmtArg SubStmt) { 754 return SemaRef.ActOnLabelStmt(IdentLoc, Id, ColonLoc, move(SubStmt)); 755 } 756 757 /// \brief Build a new "if" statement. 758 /// 759 /// By default, performs semantic analysis to build the new statement. 760 /// Subclasses may override this routine to provide different behavior. 761 OwningStmtResult RebuildIfStmt(SourceLocation IfLoc, Sema::FullExprArg Cond, 762 VarDecl *CondVar, StmtArg Then, 763 SourceLocation ElseLoc, StmtArg Else) { 764 return getSema().ActOnIfStmt(IfLoc, Cond, DeclPtrTy::make(CondVar), 765 move(Then), ElseLoc, move(Else)); 766 } 767 768 /// \brief Start building a new switch statement. 769 /// 770 /// By default, performs semantic analysis to build the new statement. 771 /// Subclasses may override this routine to provide different behavior. 772 OwningStmtResult RebuildSwitchStmtStart(Sema::FullExprArg Cond, 773 VarDecl *CondVar) { 774 return getSema().ActOnStartOfSwitchStmt(Cond, DeclPtrTy::make(CondVar)); 775 } 776 777 /// \brief Attach the body to the switch statement. 778 /// 779 /// By default, performs semantic analysis to build the new statement. 780 /// Subclasses may override this routine to provide different behavior. 781 OwningStmtResult RebuildSwitchStmtBody(SourceLocation SwitchLoc, 782 StmtArg Switch, StmtArg Body) { 783 return getSema().ActOnFinishSwitchStmt(SwitchLoc, move(Switch), 784 move(Body)); 785 } 786 787 /// \brief Build a new while statement. 788 /// 789 /// By default, performs semantic analysis to build the new statement. 790 /// Subclasses may override this routine to provide different behavior. 791 OwningStmtResult RebuildWhileStmt(SourceLocation WhileLoc, 792 Sema::FullExprArg Cond, 793 VarDecl *CondVar, 794 StmtArg Body) { 795 return getSema().ActOnWhileStmt(WhileLoc, Cond, DeclPtrTy::make(CondVar), 796 move(Body)); 797 } 798 799 /// \brief Build a new do-while statement. 800 /// 801 /// By default, performs semantic analysis to build the new statement. 802 /// Subclasses may override this routine to provide different behavior. 803 OwningStmtResult RebuildDoStmt(SourceLocation DoLoc, StmtArg Body, 804 SourceLocation WhileLoc, 805 SourceLocation LParenLoc, 806 ExprArg Cond, 807 SourceLocation RParenLoc) { 808 return getSema().ActOnDoStmt(DoLoc, move(Body), WhileLoc, LParenLoc, 809 move(Cond), RParenLoc); 810 } 811 812 /// \brief Build a new for statement. 813 /// 814 /// By default, performs semantic analysis to build the new statement. 815 /// Subclasses may override this routine to provide different behavior. 816 OwningStmtResult RebuildForStmt(SourceLocation ForLoc, 817 SourceLocation LParenLoc, 818 StmtArg Init, Sema::FullExprArg Cond, 819 VarDecl *CondVar, Sema::FullExprArg Inc, 820 SourceLocation RParenLoc, StmtArg Body) { 821 return getSema().ActOnForStmt(ForLoc, LParenLoc, move(Init), Cond, 822 DeclPtrTy::make(CondVar), 823 Inc, RParenLoc, move(Body)); 824 } 825 826 /// \brief Build a new goto statement. 827 /// 828 /// By default, performs semantic analysis to build the new statement. 829 /// Subclasses may override this routine to provide different behavior. 830 OwningStmtResult RebuildGotoStmt(SourceLocation GotoLoc, 831 SourceLocation LabelLoc, 832 LabelStmt *Label) { 833 return getSema().ActOnGotoStmt(GotoLoc, LabelLoc, Label->getID()); 834 } 835 836 /// \brief Build a new indirect goto statement. 837 /// 838 /// By default, performs semantic analysis to build the new statement. 839 /// Subclasses may override this routine to provide different behavior. 840 OwningStmtResult RebuildIndirectGotoStmt(SourceLocation GotoLoc, 841 SourceLocation StarLoc, 842 ExprArg Target) { 843 return getSema().ActOnIndirectGotoStmt(GotoLoc, StarLoc, move(Target)); 844 } 845 846 /// \brief Build a new return statement. 847 /// 848 /// By default, performs semantic analysis to build the new statement. 849 /// Subclasses may override this routine to provide different behavior. 850 OwningStmtResult RebuildReturnStmt(SourceLocation ReturnLoc, 851 ExprArg Result) { 852 853 return getSema().ActOnReturnStmt(ReturnLoc, move(Result)); 854 } 855 856 /// \brief Build a new declaration statement. 857 /// 858 /// By default, performs semantic analysis to build the new statement. 859 /// Subclasses may override this routine to provide different behavior. 860 OwningStmtResult RebuildDeclStmt(Decl **Decls, unsigned NumDecls, 861 SourceLocation StartLoc, 862 SourceLocation EndLoc) { 863 return getSema().Owned( 864 new (getSema().Context) DeclStmt( 865 DeclGroupRef::Create(getSema().Context, 866 Decls, NumDecls), 867 StartLoc, EndLoc)); 868 } 869 870 /// \brief Build a new inline asm statement. 871 /// 872 /// By default, performs semantic analysis to build the new statement. 873 /// Subclasses may override this routine to provide different behavior. 874 OwningStmtResult RebuildAsmStmt(SourceLocation AsmLoc, 875 bool IsSimple, 876 bool IsVolatile, 877 unsigned NumOutputs, 878 unsigned NumInputs, 879 IdentifierInfo **Names, 880 MultiExprArg Constraints, 881 MultiExprArg Exprs, 882 ExprArg AsmString, 883 MultiExprArg Clobbers, 884 SourceLocation RParenLoc, 885 bool MSAsm) { 886 return getSema().ActOnAsmStmt(AsmLoc, IsSimple, IsVolatile, NumOutputs, 887 NumInputs, Names, move(Constraints), 888 move(Exprs), move(AsmString), move(Clobbers), 889 RParenLoc, MSAsm); 890 } 891 892 /// \brief Build a new Objective-C @try statement. 893 /// 894 /// By default, performs semantic analysis to build the new statement. 895 /// Subclasses may override this routine to provide different behavior. 896 OwningStmtResult RebuildObjCAtTryStmt(SourceLocation AtLoc, 897 StmtArg TryBody, 898 MultiStmtArg CatchStmts, 899 StmtArg Finally) { 900 return getSema().ActOnObjCAtTryStmt(AtLoc, move(TryBody), move(CatchStmts), 901 move(Finally)); 902 } 903 904 /// \brief Rebuild an Objective-C exception declaration. 905 /// 906 /// By default, performs semantic analysis to build the new declaration. 907 /// Subclasses may override this routine to provide different behavior. 908 VarDecl *RebuildObjCExceptionDecl(VarDecl *ExceptionDecl, 909 TypeSourceInfo *TInfo, QualType T) { 910 return getSema().BuildObjCExceptionDecl(TInfo, T, 911 ExceptionDecl->getIdentifier(), 912 ExceptionDecl->getLocation()); 913 } 914 915 /// \brief Build a new Objective-C @catch statement. 916 /// 917 /// By default, performs semantic analysis to build the new statement. 918 /// Subclasses may override this routine to provide different behavior. 919 OwningStmtResult RebuildObjCAtCatchStmt(SourceLocation AtLoc, 920 SourceLocation RParenLoc, 921 VarDecl *Var, 922 StmtArg Body) { 923 return getSema().ActOnObjCAtCatchStmt(AtLoc, RParenLoc, 924 Sema::DeclPtrTy::make(Var), 925 move(Body)); 926 } 927 928 /// \brief Build a new Objective-C @finally statement. 929 /// 930 /// By default, performs semantic analysis to build the new statement. 931 /// Subclasses may override this routine to provide different behavior. 932 OwningStmtResult RebuildObjCAtFinallyStmt(SourceLocation AtLoc, 933 StmtArg Body) { 934 return getSema().ActOnObjCAtFinallyStmt(AtLoc, move(Body)); 935 } 936 937 /// \brief Build a new Objective-C @throw statement. 938 /// 939 /// By default, performs semantic analysis to build the new statement. 940 /// Subclasses may override this routine to provide different behavior. 941 OwningStmtResult RebuildObjCAtThrowStmt(SourceLocation AtLoc, 942 ExprArg Operand) { 943 return getSema().BuildObjCAtThrowStmt(AtLoc, move(Operand)); 944 } 945 946 /// \brief Build a new Objective-C @synchronized statement. 947 /// 948 /// By default, performs semantic analysis to build the new statement. 949 /// Subclasses may override this routine to provide different behavior. 950 OwningStmtResult RebuildObjCAtSynchronizedStmt(SourceLocation AtLoc, 951 ExprArg Object, 952 StmtArg Body) { 953 return getSema().ActOnObjCAtSynchronizedStmt(AtLoc, move(Object), 954 move(Body)); 955 } 956 957 /// \brief Build a new Objective-C fast enumeration statement. 958 /// 959 /// By default, performs semantic analysis to build the new statement. 960 /// Subclasses may override this routine to provide different behavior. 961 OwningStmtResult RebuildObjCForCollectionStmt(SourceLocation ForLoc, 962 SourceLocation LParenLoc, 963 StmtArg Element, 964 ExprArg Collection, 965 SourceLocation RParenLoc, 966 StmtArg Body) { 967 return getSema().ActOnObjCForCollectionStmt(ForLoc, LParenLoc, 968 move(Element), 969 move(Collection), 970 RParenLoc, 971 move(Body)); 972 } 973 974 /// \brief Build a new C++ exception declaration. 975 /// 976 /// By default, performs semantic analysis to build the new decaration. 977 /// Subclasses may override this routine to provide different behavior. 978 VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl, QualType T, 979 TypeSourceInfo *Declarator, 980 IdentifierInfo *Name, 981 SourceLocation Loc, 982 SourceRange TypeRange) { 983 return getSema().BuildExceptionDeclaration(0, T, Declarator, Name, Loc, 984 TypeRange); 985 } 986 987 /// \brief Build a new C++ catch statement. 988 /// 989 /// By default, performs semantic analysis to build the new statement. 990 /// Subclasses may override this routine to provide different behavior. 991 OwningStmtResult RebuildCXXCatchStmt(SourceLocation CatchLoc, 992 VarDecl *ExceptionDecl, 993 StmtArg Handler) { 994 return getSema().Owned( 995 new (getSema().Context) CXXCatchStmt(CatchLoc, ExceptionDecl, 996 Handler.takeAs<Stmt>())); 997 } 998 999 /// \brief Build a new C++ try statement. 1000 /// 1001 /// By default, performs semantic analysis to build the new statement. 1002 /// Subclasses may override this routine to provide different behavior. 1003 OwningStmtResult RebuildCXXTryStmt(SourceLocation TryLoc, 1004 StmtArg TryBlock, 1005 MultiStmtArg Handlers) { 1006 return getSema().ActOnCXXTryBlock(TryLoc, move(TryBlock), move(Handlers)); 1007 } 1008 1009 /// \brief Build a new expression that references a declaration. 1010 /// 1011 /// By default, performs semantic analysis to build the new expression. 1012 /// Subclasses may override this routine to provide different behavior. 1013 OwningExprResult RebuildDeclarationNameExpr(const CXXScopeSpec &SS, 1014 LookupResult &R, 1015 bool RequiresADL) { 1016 return getSema().BuildDeclarationNameExpr(SS, R, RequiresADL); 1017 } 1018 1019 1020 /// \brief Build a new expression that references a declaration. 1021 /// 1022 /// By default, performs semantic analysis to build the new expression. 1023 /// Subclasses may override this routine to provide different behavior. 1024 OwningExprResult RebuildDeclRefExpr(NestedNameSpecifier *Qualifier, 1025 SourceRange QualifierRange, 1026 ValueDecl *VD, SourceLocation Loc, 1027 TemplateArgumentListInfo *TemplateArgs) { 1028 CXXScopeSpec SS; 1029 SS.setScopeRep(Qualifier); 1030 SS.setRange(QualifierRange); 1031 1032 // FIXME: loses template args. 1033 1034 return getSema().BuildDeclarationNameExpr(SS, Loc, VD); 1035 } 1036 1037 /// \brief Build a new expression in parentheses. 1038 /// 1039 /// By default, performs semantic analysis to build the new expression. 1040 /// Subclasses may override this routine to provide different behavior. 1041 OwningExprResult RebuildParenExpr(ExprArg SubExpr, SourceLocation LParen, 1042 SourceLocation RParen) { 1043 return getSema().ActOnParenExpr(LParen, RParen, move(SubExpr)); 1044 } 1045 1046 /// \brief Build a new pseudo-destructor expression. 1047 /// 1048 /// By default, performs semantic analysis to build the new expression. 1049 /// Subclasses may override this routine to provide different behavior. 1050 OwningExprResult RebuildCXXPseudoDestructorExpr(ExprArg Base, 1051 SourceLocation OperatorLoc, 1052 bool isArrow, 1053 NestedNameSpecifier *Qualifier, 1054 SourceRange QualifierRange, 1055 TypeSourceInfo *ScopeType, 1056 SourceLocation CCLoc, 1057 SourceLocation TildeLoc, 1058 PseudoDestructorTypeStorage Destroyed); 1059 1060 /// \brief Build a new unary operator expression. 1061 /// 1062 /// By default, performs semantic analysis to build the new expression. 1063 /// Subclasses may override this routine to provide different behavior. 1064 OwningExprResult RebuildUnaryOperator(SourceLocation OpLoc, 1065 UnaryOperator::Opcode Opc, 1066 ExprArg SubExpr) { 1067 return getSema().BuildUnaryOp(/*Scope=*/0, OpLoc, Opc, move(SubExpr)); 1068 } 1069 1070 /// \brief Build a new sizeof or alignof expression with a type argument. 1071 /// 1072 /// By default, performs semantic analysis to build the new expression. 1073 /// Subclasses may override this routine to provide different behavior. 1074 OwningExprResult RebuildSizeOfAlignOf(TypeSourceInfo *TInfo, 1075 SourceLocation OpLoc, 1076 bool isSizeOf, SourceRange R) { 1077 return getSema().CreateSizeOfAlignOfExpr(TInfo, OpLoc, isSizeOf, R); 1078 } 1079 1080 /// \brief Build a new sizeof or alignof expression with an expression 1081 /// argument. 1082 /// 1083 /// By default, performs semantic analysis to build the new expression. 1084 /// Subclasses may override this routine to provide different behavior. 1085 OwningExprResult RebuildSizeOfAlignOf(ExprArg SubExpr, SourceLocation OpLoc, 1086 bool isSizeOf, SourceRange R) { 1087 OwningExprResult Result 1088 = getSema().CreateSizeOfAlignOfExpr((Expr *)SubExpr.get(), 1089 OpLoc, isSizeOf, R); 1090 if (Result.isInvalid()) 1091 return getSema().ExprError(); 1092 1093 SubExpr.release(); 1094 return move(Result); 1095 } 1096 1097 /// \brief Build a new array subscript expression. 1098 /// 1099 /// By default, performs semantic analysis to build the new expression. 1100 /// Subclasses may override this routine to provide different behavior. 1101 OwningExprResult RebuildArraySubscriptExpr(ExprArg LHS, 1102 SourceLocation LBracketLoc, 1103 ExprArg RHS, 1104 SourceLocation RBracketLoc) { 1105 return getSema().ActOnArraySubscriptExpr(/*Scope=*/0, move(LHS), 1106 LBracketLoc, move(RHS), 1107 RBracketLoc); 1108 } 1109 1110 /// \brief Build a new call expression. 1111 /// 1112 /// By default, performs semantic analysis to build the new expression. 1113 /// Subclasses may override this routine to provide different behavior. 1114 OwningExprResult RebuildCallExpr(ExprArg Callee, SourceLocation LParenLoc, 1115 MultiExprArg Args, 1116 SourceLocation *CommaLocs, 1117 SourceLocation RParenLoc) { 1118 return getSema().ActOnCallExpr(/*Scope=*/0, move(Callee), LParenLoc, 1119 move(Args), CommaLocs, RParenLoc); 1120 } 1121 1122 /// \brief Build a new member access expression. 1123 /// 1124 /// By default, performs semantic analysis to build the new expression. 1125 /// Subclasses may override this routine to provide different behavior. 1126 OwningExprResult RebuildMemberExpr(ExprArg Base, SourceLocation OpLoc, 1127 bool isArrow, 1128 NestedNameSpecifier *Qualifier, 1129 SourceRange QualifierRange, 1130 SourceLocation MemberLoc, 1131 ValueDecl *Member, 1132 NamedDecl *FoundDecl, 1133 const TemplateArgumentListInfo *ExplicitTemplateArgs, 1134 NamedDecl *FirstQualifierInScope) { 1135 if (!Member->getDeclName()) { 1136 // We have a reference to an unnamed field. 1137 assert(!Qualifier && "Can't have an unnamed field with a qualifier!"); 1138 1139 Expr *BaseExpr = Base.takeAs<Expr>(); 1140 if (getSema().PerformObjectMemberConversion(BaseExpr, Qualifier, 1141 FoundDecl, Member)) 1142 return getSema().ExprError(); 1143 1144 MemberExpr *ME = 1145 new (getSema().Context) MemberExpr(BaseExpr, isArrow, 1146 Member, MemberLoc, 1147 cast<FieldDecl>(Member)->getType()); 1148 return getSema().Owned(ME); 1149 } 1150 1151 CXXScopeSpec SS; 1152 if (Qualifier) { 1153 SS.setRange(QualifierRange); 1154 SS.setScopeRep(Qualifier); 1155 } 1156 1157 QualType BaseType = ((Expr*) Base.get())->getType(); 1158 1159 // FIXME: this involves duplicating earlier analysis in a lot of 1160 // cases; we should avoid this when possible. 1161 LookupResult R(getSema(), Member->getDeclName(), MemberLoc, 1162 Sema::LookupMemberName); 1163 R.addDecl(FoundDecl); 1164 R.resolveKind(); 1165 1166 return getSema().BuildMemberReferenceExpr(move(Base), BaseType, 1167 OpLoc, isArrow, 1168 SS, FirstQualifierInScope, 1169 R, ExplicitTemplateArgs); 1170 } 1171 1172 /// \brief Build a new binary operator expression. 1173 /// 1174 /// By default, performs semantic analysis to build the new expression. 1175 /// Subclasses may override this routine to provide different behavior. 1176 OwningExprResult RebuildBinaryOperator(SourceLocation OpLoc, 1177 BinaryOperator::Opcode Opc, 1178 ExprArg LHS, ExprArg RHS) { 1179 return getSema().BuildBinOp(/*Scope=*/0, OpLoc, Opc, 1180 LHS.takeAs<Expr>(), RHS.takeAs<Expr>()); 1181 } 1182 1183 /// \brief Build a new conditional operator expression. 1184 /// 1185 /// By default, performs semantic analysis to build the new expression. 1186 /// Subclasses may override this routine to provide different behavior. 1187 OwningExprResult RebuildConditionalOperator(ExprArg Cond, 1188 SourceLocation QuestionLoc, 1189 ExprArg LHS, 1190 SourceLocation ColonLoc, 1191 ExprArg RHS) { 1192 return getSema().ActOnConditionalOp(QuestionLoc, ColonLoc, move(Cond), 1193 move(LHS), move(RHS)); 1194 } 1195 1196 /// \brief Build a new C-style 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 RebuildCStyleCastExpr(SourceLocation LParenLoc, 1201 TypeSourceInfo *TInfo, 1202 SourceLocation RParenLoc, 1203 ExprArg SubExpr) { 1204 return getSema().BuildCStyleCastExpr(LParenLoc, TInfo, RParenLoc, 1205 move(SubExpr)); 1206 } 1207 1208 /// \brief Build a new compound literal expression. 1209 /// 1210 /// By default, performs semantic analysis to build the new expression. 1211 /// Subclasses may override this routine to provide different behavior. 1212 OwningExprResult RebuildCompoundLiteralExpr(SourceLocation LParenLoc, 1213 TypeSourceInfo *TInfo, 1214 SourceLocation RParenLoc, 1215 ExprArg Init) { 1216 return getSema().BuildCompoundLiteralExpr(LParenLoc, TInfo, RParenLoc, 1217 move(Init)); 1218 } 1219 1220 /// \brief Build a new extended vector element access expression. 1221 /// 1222 /// By default, performs semantic analysis to build the new expression. 1223 /// Subclasses may override this routine to provide different behavior. 1224 OwningExprResult RebuildExtVectorElementExpr(ExprArg Base, 1225 SourceLocation OpLoc, 1226 SourceLocation AccessorLoc, 1227 IdentifierInfo &Accessor) { 1228 1229 CXXScopeSpec SS; 1230 QualType BaseType = ((Expr*) Base.get())->getType(); 1231 return getSema().BuildMemberReferenceExpr(move(Base), BaseType, 1232 OpLoc, /*IsArrow*/ false, 1233 SS, /*FirstQualifierInScope*/ 0, 1234 DeclarationName(&Accessor), 1235 AccessorLoc, 1236 /* TemplateArgs */ 0); 1237 } 1238 1239 /// \brief Build a new initializer list expression. 1240 /// 1241 /// By default, performs semantic analysis to build the new expression. 1242 /// Subclasses may override this routine to provide different behavior. 1243 OwningExprResult RebuildInitList(SourceLocation LBraceLoc, 1244 MultiExprArg Inits, 1245 SourceLocation RBraceLoc, 1246 QualType ResultTy) { 1247 OwningExprResult Result 1248 = SemaRef.ActOnInitList(LBraceLoc, move(Inits), RBraceLoc); 1249 if (Result.isInvalid() || ResultTy->isDependentType()) 1250 return move(Result); 1251 1252 // Patch in the result type we were given, which may have been computed 1253 // when the initial InitListExpr was built. 1254 InitListExpr *ILE = cast<InitListExpr>((Expr *)Result.get()); 1255 ILE->setType(ResultTy); 1256 return move(Result); 1257 } 1258 1259 /// \brief Build a new designated initializer expression. 1260 /// 1261 /// By default, performs semantic analysis to build the new expression. 1262 /// Subclasses may override this routine to provide different behavior. 1263 OwningExprResult RebuildDesignatedInitExpr(Designation &Desig, 1264 MultiExprArg ArrayExprs, 1265 SourceLocation EqualOrColonLoc, 1266 bool GNUSyntax, 1267 ExprArg Init) { 1268 OwningExprResult Result 1269 = SemaRef.ActOnDesignatedInitializer(Desig, EqualOrColonLoc, GNUSyntax, 1270 move(Init)); 1271 if (Result.isInvalid()) 1272 return SemaRef.ExprError(); 1273 1274 ArrayExprs.release(); 1275 return move(Result); 1276 } 1277 1278 /// \brief Build a new value-initialized expression. 1279 /// 1280 /// By default, builds the implicit value initialization without performing 1281 /// any semantic analysis. Subclasses may override this routine to provide 1282 /// different behavior. 1283 OwningExprResult RebuildImplicitValueInitExpr(QualType T) { 1284 return SemaRef.Owned(new (SemaRef.Context) ImplicitValueInitExpr(T)); 1285 } 1286 1287 /// \brief Build a new \c va_arg 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 RebuildVAArgExpr(SourceLocation BuiltinLoc, ExprArg SubExpr, 1292 QualType T, SourceLocation RParenLoc) { 1293 return getSema().ActOnVAArg(BuiltinLoc, move(SubExpr), T.getAsOpaquePtr(), 1294 RParenLoc); 1295 } 1296 1297 /// \brief Build a new expression list in parentheses. 1298 /// 1299 /// By default, performs semantic analysis to build the new expression. 1300 /// Subclasses may override this routine to provide different behavior. 1301 OwningExprResult RebuildParenListExpr(SourceLocation LParenLoc, 1302 MultiExprArg SubExprs, 1303 SourceLocation RParenLoc) { 1304 return getSema().ActOnParenOrParenListExpr(LParenLoc, RParenLoc, 1305 move(SubExprs)); 1306 } 1307 1308 /// \brief Build a new address-of-label expression. 1309 /// 1310 /// By default, performs semantic analysis, using the name of the label 1311 /// rather than attempting to map the label statement itself. 1312 /// Subclasses may override this routine to provide different behavior. 1313 OwningExprResult RebuildAddrLabelExpr(SourceLocation AmpAmpLoc, 1314 SourceLocation LabelLoc, 1315 LabelStmt *Label) { 1316 return getSema().ActOnAddrLabel(AmpAmpLoc, LabelLoc, Label->getID()); 1317 } 1318 1319 /// \brief Build a new GNU statement expression. 1320 /// 1321 /// By default, performs semantic analysis to build the new expression. 1322 /// Subclasses may override this routine to provide different behavior. 1323 OwningExprResult RebuildStmtExpr(SourceLocation LParenLoc, 1324 StmtArg SubStmt, 1325 SourceLocation RParenLoc) { 1326 return getSema().ActOnStmtExpr(LParenLoc, move(SubStmt), RParenLoc); 1327 } 1328 1329 /// \brief Build a new __builtin_types_compatible_p expression. 1330 /// 1331 /// By default, performs semantic analysis to build the new expression. 1332 /// Subclasses may override this routine to provide different behavior. 1333 OwningExprResult RebuildTypesCompatibleExpr(SourceLocation BuiltinLoc, 1334 QualType T1, QualType T2, 1335 SourceLocation RParenLoc) { 1336 return getSema().ActOnTypesCompatibleExpr(BuiltinLoc, 1337 T1.getAsOpaquePtr(), 1338 T2.getAsOpaquePtr(), 1339 RParenLoc); 1340 } 1341 1342 /// \brief Build a new __builtin_choose_expr expression. 1343 /// 1344 /// By default, performs semantic analysis to build the new expression. 1345 /// Subclasses may override this routine to provide different behavior. 1346 OwningExprResult RebuildChooseExpr(SourceLocation BuiltinLoc, 1347 ExprArg Cond, ExprArg LHS, ExprArg RHS, 1348 SourceLocation RParenLoc) { 1349 return SemaRef.ActOnChooseExpr(BuiltinLoc, 1350 move(Cond), move(LHS), move(RHS), 1351 RParenLoc); 1352 } 1353 1354 /// \brief Build a new overloaded operator call expression. 1355 /// 1356 /// By default, performs semantic analysis to build the new expression. 1357 /// The semantic analysis provides the behavior of template instantiation, 1358 /// copying with transformations that turn what looks like an overloaded 1359 /// operator call into a use of a builtin operator, performing 1360 /// argument-dependent lookup, etc. Subclasses may override this routine to 1361 /// provide different behavior. 1362 OwningExprResult RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op, 1363 SourceLocation OpLoc, 1364 ExprArg Callee, 1365 ExprArg First, 1366 ExprArg Second); 1367 1368 /// \brief Build a new C++ "named" cast expression, such as static_cast or 1369 /// reinterpret_cast. 1370 /// 1371 /// By default, this routine dispatches to one of the more-specific routines 1372 /// for a particular named case, e.g., RebuildCXXStaticCastExpr(). 1373 /// Subclasses may override this routine to provide different behavior. 1374 OwningExprResult RebuildCXXNamedCastExpr(SourceLocation OpLoc, 1375 Stmt::StmtClass Class, 1376 SourceLocation LAngleLoc, 1377 TypeSourceInfo *TInfo, 1378 SourceLocation RAngleLoc, 1379 SourceLocation LParenLoc, 1380 ExprArg SubExpr, 1381 SourceLocation RParenLoc) { 1382 switch (Class) { 1383 case Stmt::CXXStaticCastExprClass: 1384 return getDerived().RebuildCXXStaticCastExpr(OpLoc, LAngleLoc, TInfo, 1385 RAngleLoc, LParenLoc, 1386 move(SubExpr), RParenLoc); 1387 1388 case Stmt::CXXDynamicCastExprClass: 1389 return getDerived().RebuildCXXDynamicCastExpr(OpLoc, LAngleLoc, TInfo, 1390 RAngleLoc, LParenLoc, 1391 move(SubExpr), RParenLoc); 1392 1393 case Stmt::CXXReinterpretCastExprClass: 1394 return getDerived().RebuildCXXReinterpretCastExpr(OpLoc, LAngleLoc, TInfo, 1395 RAngleLoc, LParenLoc, 1396 move(SubExpr), 1397 RParenLoc); 1398 1399 case Stmt::CXXConstCastExprClass: 1400 return getDerived().RebuildCXXConstCastExpr(OpLoc, LAngleLoc, TInfo, 1401 RAngleLoc, LParenLoc, 1402 move(SubExpr), RParenLoc); 1403 1404 default: 1405 assert(false && "Invalid C++ named cast"); 1406 break; 1407 } 1408 1409 return getSema().ExprError(); 1410 } 1411 1412 /// \brief Build a new C++ static_cast expression. 1413 /// 1414 /// By default, performs semantic analysis to build the new expression. 1415 /// Subclasses may override this routine to provide different behavior. 1416 OwningExprResult RebuildCXXStaticCastExpr(SourceLocation OpLoc, 1417 SourceLocation LAngleLoc, 1418 TypeSourceInfo *TInfo, 1419 SourceLocation RAngleLoc, 1420 SourceLocation LParenLoc, 1421 ExprArg SubExpr, 1422 SourceLocation RParenLoc) { 1423 return getSema().BuildCXXNamedCast(OpLoc, tok::kw_static_cast, 1424 TInfo, move(SubExpr), 1425 SourceRange(LAngleLoc, RAngleLoc), 1426 SourceRange(LParenLoc, RParenLoc)); 1427 } 1428 1429 /// \brief Build a new C++ dynamic_cast expression. 1430 /// 1431 /// By default, performs semantic analysis to build the new expression. 1432 /// Subclasses may override this routine to provide different behavior. 1433 OwningExprResult RebuildCXXDynamicCastExpr(SourceLocation OpLoc, 1434 SourceLocation LAngleLoc, 1435 TypeSourceInfo *TInfo, 1436 SourceLocation RAngleLoc, 1437 SourceLocation LParenLoc, 1438 ExprArg SubExpr, 1439 SourceLocation RParenLoc) { 1440 return getSema().BuildCXXNamedCast(OpLoc, tok::kw_dynamic_cast, 1441 TInfo, move(SubExpr), 1442 SourceRange(LAngleLoc, RAngleLoc), 1443 SourceRange(LParenLoc, RParenLoc)); 1444 } 1445 1446 /// \brief Build a new C++ reinterpret_cast expression. 1447 /// 1448 /// By default, performs semantic analysis to build the new expression. 1449 /// Subclasses may override this routine to provide different behavior. 1450 OwningExprResult RebuildCXXReinterpretCastExpr(SourceLocation OpLoc, 1451 SourceLocation LAngleLoc, 1452 TypeSourceInfo *TInfo, 1453 SourceLocation RAngleLoc, 1454 SourceLocation LParenLoc, 1455 ExprArg SubExpr, 1456 SourceLocation RParenLoc) { 1457 return getSema().BuildCXXNamedCast(OpLoc, tok::kw_reinterpret_cast, 1458 TInfo, move(SubExpr), 1459 SourceRange(LAngleLoc, RAngleLoc), 1460 SourceRange(LParenLoc, RParenLoc)); 1461 } 1462 1463 /// \brief Build a new C++ const_cast expression. 1464 /// 1465 /// By default, performs semantic analysis to build the new expression. 1466 /// Subclasses may override this routine to provide different behavior. 1467 OwningExprResult RebuildCXXConstCastExpr(SourceLocation OpLoc, 1468 SourceLocation LAngleLoc, 1469 TypeSourceInfo *TInfo, 1470 SourceLocation RAngleLoc, 1471 SourceLocation LParenLoc, 1472 ExprArg SubExpr, 1473 SourceLocation RParenLoc) { 1474 return getSema().BuildCXXNamedCast(OpLoc, tok::kw_const_cast, 1475 TInfo, move(SubExpr), 1476 SourceRange(LAngleLoc, RAngleLoc), 1477 SourceRange(LParenLoc, RParenLoc)); 1478 } 1479 1480 /// \brief Build a new C++ functional-style cast expression. 1481 /// 1482 /// By default, performs semantic analysis to build the new expression. 1483 /// Subclasses may override this routine to provide different behavior. 1484 OwningExprResult RebuildCXXFunctionalCastExpr(SourceRange TypeRange, 1485 TypeSourceInfo *TInfo, 1486 SourceLocation LParenLoc, 1487 ExprArg SubExpr, 1488 SourceLocation RParenLoc) { 1489 void *Sub = SubExpr.takeAs<Expr>(); 1490 return getSema().ActOnCXXTypeConstructExpr(TypeRange, 1491 TInfo->getType().getAsOpaquePtr(), 1492 LParenLoc, 1493 Sema::MultiExprArg(getSema(), &Sub, 1), 1494 /*CommaLocs=*/0, 1495 RParenLoc); 1496 } 1497 1498 /// \brief Build a new C++ typeid(type) expression. 1499 /// 1500 /// By default, performs semantic analysis to build the new expression. 1501 /// Subclasses may override this routine to provide different behavior. 1502 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc, 1503 SourceLocation LParenLoc, 1504 QualType T, 1505 SourceLocation RParenLoc) { 1506 return getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, true, 1507 T.getAsOpaquePtr(), RParenLoc); 1508 } 1509 1510 /// \brief Build a new C++ typeid(expr) expression. 1511 /// 1512 /// By default, performs semantic analysis to build the new expression. 1513 /// Subclasses may override this routine to provide different behavior. 1514 OwningExprResult RebuildCXXTypeidExpr(SourceLocation TypeidLoc, 1515 SourceLocation LParenLoc, 1516 ExprArg Operand, 1517 SourceLocation RParenLoc) { 1518 OwningExprResult Result 1519 = getSema().ActOnCXXTypeid(TypeidLoc, LParenLoc, false, Operand.get(), 1520 RParenLoc); 1521 if (Result.isInvalid()) 1522 return getSema().ExprError(); 1523 1524 Operand.release(); // FIXME: since ActOnCXXTypeid silently took ownership 1525 return move(Result); 1526 } 1527 1528 /// \brief Build a new C++ "this" expression. 1529 /// 1530 /// By default, builds a new "this" expression without performing any 1531 /// semantic analysis. Subclasses may override this routine to provide 1532 /// different behavior. 1533 OwningExprResult RebuildCXXThisExpr(SourceLocation ThisLoc, 1534 QualType ThisType, 1535 bool isImplicit) { 1536 return getSema().Owned( 1537 new (getSema().Context) CXXThisExpr(ThisLoc, ThisType, 1538 isImplicit)); 1539 } 1540 1541 /// \brief Build a new C++ throw expression. 1542 /// 1543 /// By default, performs semantic analysis to build the new expression. 1544 /// Subclasses may override this routine to provide different behavior. 1545 OwningExprResult RebuildCXXThrowExpr(SourceLocation ThrowLoc, ExprArg Sub) { 1546 return getSema().ActOnCXXThrow(ThrowLoc, move(Sub)); 1547 } 1548 1549 /// \brief Build a new C++ default-argument expression. 1550 /// 1551 /// By default, builds a new default-argument expression, which does not 1552 /// require any semantic analysis. Subclasses may override this routine to 1553 /// provide different behavior. 1554 OwningExprResult RebuildCXXDefaultArgExpr(SourceLocation Loc, 1555 ParmVarDecl *Param) { 1556 return getSema().Owned(CXXDefaultArgExpr::Create(getSema().Context, Loc, 1557 Param)); 1558 } 1559 1560 /// \brief Build a new C++ zero-initialization expression. 1561 /// 1562 /// By default, performs semantic analysis to build the new expression. 1563 /// Subclasses may override this routine to provide different behavior. 1564 OwningExprResult RebuildCXXZeroInitValueExpr(SourceLocation TypeStartLoc, 1565 SourceLocation LParenLoc, 1566 QualType T, 1567 SourceLocation RParenLoc) { 1568 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeStartLoc), 1569 T.getAsOpaquePtr(), LParenLoc, 1570 MultiExprArg(getSema(), 0, 0), 1571 0, RParenLoc); 1572 } 1573 1574 /// \brief Build a new C++ "new" expression. 1575 /// 1576 /// By default, performs semantic analysis to build the new expression. 1577 /// Subclasses may override this routine to provide different behavior. 1578 OwningExprResult RebuildCXXNewExpr(SourceLocation StartLoc, 1579 bool UseGlobal, 1580 SourceLocation PlacementLParen, 1581 MultiExprArg PlacementArgs, 1582 SourceLocation PlacementRParen, 1583 bool ParenTypeId, 1584 QualType AllocType, 1585 SourceLocation TypeLoc, 1586 SourceRange TypeRange, 1587 ExprArg ArraySize, 1588 SourceLocation ConstructorLParen, 1589 MultiExprArg ConstructorArgs, 1590 SourceLocation ConstructorRParen) { 1591 return getSema().BuildCXXNew(StartLoc, UseGlobal, 1592 PlacementLParen, 1593 move(PlacementArgs), 1594 PlacementRParen, 1595 ParenTypeId, 1596 AllocType, 1597 TypeLoc, 1598 TypeRange, 1599 move(ArraySize), 1600 ConstructorLParen, 1601 move(ConstructorArgs), 1602 ConstructorRParen); 1603 } 1604 1605 /// \brief Build a new C++ "delete" expression. 1606 /// 1607 /// By default, performs semantic analysis to build the new expression. 1608 /// Subclasses may override this routine to provide different behavior. 1609 OwningExprResult RebuildCXXDeleteExpr(SourceLocation StartLoc, 1610 bool IsGlobalDelete, 1611 bool IsArrayForm, 1612 ExprArg Operand) { 1613 return getSema().ActOnCXXDelete(StartLoc, IsGlobalDelete, IsArrayForm, 1614 move(Operand)); 1615 } 1616 1617 /// \brief Build a new unary type trait expression. 1618 /// 1619 /// By default, performs semantic analysis to build the new expression. 1620 /// Subclasses may override this routine to provide different behavior. 1621 OwningExprResult RebuildUnaryTypeTrait(UnaryTypeTrait Trait, 1622 SourceLocation StartLoc, 1623 SourceLocation LParenLoc, 1624 QualType T, 1625 SourceLocation RParenLoc) { 1626 return getSema().ActOnUnaryTypeTrait(Trait, StartLoc, LParenLoc, 1627 T.getAsOpaquePtr(), RParenLoc); 1628 } 1629 1630 /// \brief Build a new (previously unresolved) declaration reference 1631 /// expression. 1632 /// 1633 /// By default, performs semantic analysis to build the new expression. 1634 /// Subclasses may override this routine to provide different behavior. 1635 OwningExprResult RebuildDependentScopeDeclRefExpr(NestedNameSpecifier *NNS, 1636 SourceRange QualifierRange, 1637 DeclarationName Name, 1638 SourceLocation Location, 1639 const TemplateArgumentListInfo *TemplateArgs) { 1640 CXXScopeSpec SS; 1641 SS.setRange(QualifierRange); 1642 SS.setScopeRep(NNS); 1643 1644 if (TemplateArgs) 1645 return getSema().BuildQualifiedTemplateIdExpr(SS, Name, Location, 1646 *TemplateArgs); 1647 1648 return getSema().BuildQualifiedDeclarationNameExpr(SS, Name, Location); 1649 } 1650 1651 /// \brief Build a new template-id expression. 1652 /// 1653 /// By default, performs semantic analysis to build the new expression. 1654 /// Subclasses may override this routine to provide different behavior. 1655 OwningExprResult RebuildTemplateIdExpr(const CXXScopeSpec &SS, 1656 LookupResult &R, 1657 bool RequiresADL, 1658 const TemplateArgumentListInfo &TemplateArgs) { 1659 return getSema().BuildTemplateIdExpr(SS, R, RequiresADL, TemplateArgs); 1660 } 1661 1662 /// \brief Build a new object-construction expression. 1663 /// 1664 /// By default, performs semantic analysis to build the new expression. 1665 /// Subclasses may override this routine to provide different behavior. 1666 OwningExprResult RebuildCXXConstructExpr(QualType T, 1667 SourceLocation Loc, 1668 CXXConstructorDecl *Constructor, 1669 bool IsElidable, 1670 MultiExprArg Args) { 1671 ASTOwningVector<&ActionBase::DeleteExpr> ConvertedArgs(SemaRef); 1672 if (getSema().CompleteConstructorCall(Constructor, move(Args), Loc, 1673 ConvertedArgs)) 1674 return getSema().ExprError(); 1675 1676 return getSema().BuildCXXConstructExpr(Loc, T, Constructor, IsElidable, 1677 move_arg(ConvertedArgs)); 1678 } 1679 1680 /// \brief Build a new object-construction expression. 1681 /// 1682 /// By default, performs semantic analysis to build the new expression. 1683 /// Subclasses may override this routine to provide different behavior. 1684 OwningExprResult RebuildCXXTemporaryObjectExpr(SourceLocation TypeBeginLoc, 1685 QualType T, 1686 SourceLocation LParenLoc, 1687 MultiExprArg Args, 1688 SourceLocation *Commas, 1689 SourceLocation RParenLoc) { 1690 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc), 1691 T.getAsOpaquePtr(), 1692 LParenLoc, 1693 move(Args), 1694 Commas, 1695 RParenLoc); 1696 } 1697 1698 /// \brief Build a new object-construction expression. 1699 /// 1700 /// By default, performs semantic analysis to build the new expression. 1701 /// Subclasses may override this routine to provide different behavior. 1702 OwningExprResult RebuildCXXUnresolvedConstructExpr(SourceLocation TypeBeginLoc, 1703 QualType T, 1704 SourceLocation LParenLoc, 1705 MultiExprArg Args, 1706 SourceLocation *Commas, 1707 SourceLocation RParenLoc) { 1708 return getSema().ActOnCXXTypeConstructExpr(SourceRange(TypeBeginLoc, 1709 /*FIXME*/LParenLoc), 1710 T.getAsOpaquePtr(), 1711 LParenLoc, 1712 move(Args), 1713 Commas, 1714 RParenLoc); 1715 } 1716 1717 /// \brief Build a new member reference expression. 1718 /// 1719 /// By default, performs semantic analysis to build the new expression. 1720 /// Subclasses may override this routine to provide different behavior. 1721 OwningExprResult RebuildCXXDependentScopeMemberExpr(ExprArg BaseE, 1722 QualType BaseType, 1723 bool IsArrow, 1724 SourceLocation OperatorLoc, 1725 NestedNameSpecifier *Qualifier, 1726 SourceRange QualifierRange, 1727 NamedDecl *FirstQualifierInScope, 1728 DeclarationName Name, 1729 SourceLocation MemberLoc, 1730 const TemplateArgumentListInfo *TemplateArgs) { 1731 CXXScopeSpec SS; 1732 SS.setRange(QualifierRange); 1733 SS.setScopeRep(Qualifier); 1734 1735 return SemaRef.BuildMemberReferenceExpr(move(BaseE), BaseType, 1736 OperatorLoc, IsArrow, 1737 SS, FirstQualifierInScope, 1738 Name, MemberLoc, TemplateArgs); 1739 } 1740 1741 /// \brief Build a new member reference expression. 1742 /// 1743 /// By default, performs semantic analysis to build the new expression. 1744 /// Subclasses may override this routine to provide different behavior. 1745 OwningExprResult RebuildUnresolvedMemberExpr(ExprArg BaseE, 1746 QualType BaseType, 1747 SourceLocation OperatorLoc, 1748 bool IsArrow, 1749 NestedNameSpecifier *Qualifier, 1750 SourceRange QualifierRange, 1751 NamedDecl *FirstQualifierInScope, 1752 LookupResult &R, 1753 const TemplateArgumentListInfo *TemplateArgs) { 1754 CXXScopeSpec SS; 1755 SS.setRange(QualifierRange); 1756 SS.setScopeRep(Qualifier); 1757 1758 return SemaRef.BuildMemberReferenceExpr(move(BaseE), BaseType, 1759 OperatorLoc, IsArrow, 1760 SS, FirstQualifierInScope, 1761 R, TemplateArgs); 1762 } 1763 1764 /// \brief Build a new Objective-C @encode expression. 1765 /// 1766 /// By default, performs semantic analysis to build the new expression. 1767 /// Subclasses may override this routine to provide different behavior. 1768 OwningExprResult RebuildObjCEncodeExpr(SourceLocation AtLoc, 1769 TypeSourceInfo *EncodeTypeInfo, 1770 SourceLocation RParenLoc) { 1771 return SemaRef.Owned(SemaRef.BuildObjCEncodeExpression(AtLoc, EncodeTypeInfo, 1772 RParenLoc)); 1773 } 1774 1775 /// \brief Build a new Objective-C class message. 1776 OwningExprResult RebuildObjCMessageExpr(TypeSourceInfo *ReceiverTypeInfo, 1777 Selector Sel, 1778 ObjCMethodDecl *Method, 1779 SourceLocation LBracLoc, 1780 MultiExprArg Args, 1781 SourceLocation RBracLoc) { 1782 return SemaRef.BuildClassMessage(ReceiverTypeInfo, 1783 ReceiverTypeInfo->getType(), 1784 /*SuperLoc=*/SourceLocation(), 1785 Sel, Method, LBracLoc, RBracLoc, 1786 move(Args)); 1787 } 1788 1789 /// \brief Build a new Objective-C instance message. 1790 OwningExprResult RebuildObjCMessageExpr(ExprArg Receiver, 1791 Selector Sel, 1792 ObjCMethodDecl *Method, 1793 SourceLocation LBracLoc, 1794 MultiExprArg Args, 1795 SourceLocation RBracLoc) { 1796 QualType ReceiverType = static_cast<Expr *>(Receiver.get())->getType(); 1797 return SemaRef.BuildInstanceMessage(move(Receiver), 1798 ReceiverType, 1799 /*SuperLoc=*/SourceLocation(), 1800 Sel, Method, LBracLoc, RBracLoc, 1801 move(Args)); 1802 } 1803 1804 /// \brief Build a new Objective-C ivar reference expression. 1805 /// 1806 /// By default, performs semantic analysis to build the new expression. 1807 /// Subclasses may override this routine to provide different behavior. 1808 OwningExprResult RebuildObjCIvarRefExpr(ExprArg BaseArg, ObjCIvarDecl *Ivar, 1809 SourceLocation IvarLoc, 1810 bool IsArrow, bool IsFreeIvar) { 1811 // FIXME: We lose track of the IsFreeIvar bit. 1812 CXXScopeSpec SS; 1813 Expr *Base = BaseArg.takeAs<Expr>(); 1814 LookupResult R(getSema(), Ivar->getDeclName(), IvarLoc, 1815 Sema::LookupMemberName); 1816 OwningExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 1817 /*FIME:*/IvarLoc, 1818 SS, DeclPtrTy()); 1819 if (Result.isInvalid()) 1820 return getSema().ExprError(); 1821 1822 if (Result.get()) 1823 return move(Result); 1824 1825 return getSema().BuildMemberReferenceExpr(getSema().Owned(Base), 1826 Base->getType(), 1827 /*FIXME:*/IvarLoc, IsArrow, SS, 1828 /*FirstQualifierInScope=*/0, 1829 R, 1830 /*TemplateArgs=*/0); 1831 } 1832 1833 /// \brief Build a new Objective-C property reference expression. 1834 /// 1835 /// By default, performs semantic analysis to build the new expression. 1836 /// Subclasses may override this routine to provide different behavior. 1837 OwningExprResult RebuildObjCPropertyRefExpr(ExprArg BaseArg, 1838 ObjCPropertyDecl *Property, 1839 SourceLocation PropertyLoc) { 1840 CXXScopeSpec SS; 1841 Expr *Base = BaseArg.takeAs<Expr>(); 1842 LookupResult R(getSema(), Property->getDeclName(), PropertyLoc, 1843 Sema::LookupMemberName); 1844 bool IsArrow = false; 1845 OwningExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 1846 /*FIME:*/PropertyLoc, 1847 SS, DeclPtrTy()); 1848 if (Result.isInvalid()) 1849 return getSema().ExprError(); 1850 1851 if (Result.get()) 1852 return move(Result); 1853 1854 return getSema().BuildMemberReferenceExpr(getSema().Owned(Base), 1855 Base->getType(), 1856 /*FIXME:*/PropertyLoc, IsArrow, 1857 SS, 1858 /*FirstQualifierInScope=*/0, 1859 R, 1860 /*TemplateArgs=*/0); 1861 } 1862 1863 /// \brief Build a new Objective-C "isa" expression. 1864 /// 1865 /// By default, performs semantic analysis to build the new expression. 1866 /// Subclasses may override this routine to provide different behavior. 1867 OwningExprResult RebuildObjCIsaExpr(ExprArg BaseArg, SourceLocation IsaLoc, 1868 bool IsArrow) { 1869 CXXScopeSpec SS; 1870 Expr *Base = BaseArg.takeAs<Expr>(); 1871 LookupResult R(getSema(), &getSema().Context.Idents.get("isa"), IsaLoc, 1872 Sema::LookupMemberName); 1873 OwningExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 1874 /*FIME:*/IsaLoc, 1875 SS, DeclPtrTy()); 1876 if (Result.isInvalid()) 1877 return getSema().ExprError(); 1878 1879 if (Result.get()) 1880 return move(Result); 1881 1882 return getSema().BuildMemberReferenceExpr(getSema().Owned(Base), 1883 Base->getType(), 1884 /*FIXME:*/IsaLoc, IsArrow, SS, 1885 /*FirstQualifierInScope=*/0, 1886 R, 1887 /*TemplateArgs=*/0); 1888 } 1889 1890 /// \brief Build a new shuffle vector expression. 1891 /// 1892 /// By default, performs semantic analysis to build the new expression. 1893 /// Subclasses may override this routine to provide different behavior. 1894 OwningExprResult RebuildShuffleVectorExpr(SourceLocation BuiltinLoc, 1895 MultiExprArg SubExprs, 1896 SourceLocation RParenLoc) { 1897 // Find the declaration for __builtin_shufflevector 1898 const IdentifierInfo &Name 1899 = SemaRef.Context.Idents.get("__builtin_shufflevector"); 1900 TranslationUnitDecl *TUDecl = SemaRef.Context.getTranslationUnitDecl(); 1901 DeclContext::lookup_result Lookup = TUDecl->lookup(DeclarationName(&Name)); 1902 assert(Lookup.first != Lookup.second && "No __builtin_shufflevector?"); 1903 1904 // Build a reference to the __builtin_shufflevector builtin 1905 FunctionDecl *Builtin = cast<FunctionDecl>(*Lookup.first); 1906 Expr *Callee 1907 = new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(), 1908 BuiltinLoc); 1909 SemaRef.UsualUnaryConversions(Callee); 1910 1911 // Build the CallExpr 1912 unsigned NumSubExprs = SubExprs.size(); 1913 Expr **Subs = (Expr **)SubExprs.release(); 1914 CallExpr *TheCall = new (SemaRef.Context) CallExpr(SemaRef.Context, Callee, 1915 Subs, NumSubExprs, 1916 Builtin->getResultType(), 1917 RParenLoc); 1918 OwningExprResult OwnedCall(SemaRef.Owned(TheCall)); 1919 1920 // Type-check the __builtin_shufflevector expression. 1921 OwningExprResult Result = SemaRef.SemaBuiltinShuffleVector(TheCall); 1922 if (Result.isInvalid()) 1923 return SemaRef.ExprError(); 1924 1925 OwnedCall.release(); 1926 return move(Result); 1927 } 1928}; 1929 1930template<typename Derived> 1931Sema::OwningStmtResult TreeTransform<Derived>::TransformStmt(Stmt *S) { 1932 if (!S) 1933 return SemaRef.Owned(S); 1934 1935 switch (S->getStmtClass()) { 1936 case Stmt::NoStmtClass: break; 1937 1938 // Transform individual statement nodes 1939#define STMT(Node, Parent) \ 1940 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S)); 1941#define EXPR(Node, Parent) 1942#include "clang/AST/StmtNodes.def" 1943 1944 // Transform expressions by calling TransformExpr. 1945#define STMT(Node, Parent) 1946#define ABSTRACT_EXPR(Node, Parent) 1947#define EXPR(Node, Parent) case Stmt::Node##Class: 1948#include "clang/AST/StmtNodes.def" 1949 { 1950 Sema::OwningExprResult E = getDerived().TransformExpr(cast<Expr>(S)); 1951 if (E.isInvalid()) 1952 return getSema().StmtError(); 1953 1954 return getSema().ActOnExprStmt(getSema().MakeFullExpr(E)); 1955 } 1956 } 1957 1958 return SemaRef.Owned(S->Retain()); 1959} 1960 1961 1962template<typename Derived> 1963Sema::OwningExprResult TreeTransform<Derived>::TransformExpr(Expr *E) { 1964 if (!E) 1965 return SemaRef.Owned(E); 1966 1967 switch (E->getStmtClass()) { 1968 case Stmt::NoStmtClass: break; 1969#define STMT(Node, Parent) case Stmt::Node##Class: break; 1970#define ABSTRACT_EXPR(Node, Parent) 1971#define EXPR(Node, Parent) \ 1972 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E)); 1973#include "clang/AST/StmtNodes.def" 1974 } 1975 1976 return SemaRef.Owned(E->Retain()); 1977} 1978 1979template<typename Derived> 1980NestedNameSpecifier * 1981TreeTransform<Derived>::TransformNestedNameSpecifier(NestedNameSpecifier *NNS, 1982 SourceRange Range, 1983 QualType ObjectType, 1984 NamedDecl *FirstQualifierInScope) { 1985 if (!NNS) 1986 return 0; 1987 1988 // Transform the prefix of this nested name specifier. 1989 NestedNameSpecifier *Prefix = NNS->getPrefix(); 1990 if (Prefix) { 1991 Prefix = getDerived().TransformNestedNameSpecifier(Prefix, Range, 1992 ObjectType, 1993 FirstQualifierInScope); 1994 if (!Prefix) 1995 return 0; 1996 1997 // Clear out the object type and the first qualifier in scope; they only 1998 // apply to the first element in the nested-name-specifier. 1999 ObjectType = QualType(); 2000 FirstQualifierInScope = 0; 2001 } 2002 2003 switch (NNS->getKind()) { 2004 case NestedNameSpecifier::Identifier: 2005 assert((Prefix || !ObjectType.isNull()) && 2006 "Identifier nested-name-specifier with no prefix or object type"); 2007 if (!getDerived().AlwaysRebuild() && Prefix == NNS->getPrefix() && 2008 ObjectType.isNull()) 2009 return NNS; 2010 2011 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, 2012 *NNS->getAsIdentifier(), 2013 ObjectType, 2014 FirstQualifierInScope); 2015 2016 case NestedNameSpecifier::Namespace: { 2017 NamespaceDecl *NS 2018 = cast_or_null<NamespaceDecl>( 2019 getDerived().TransformDecl(Range.getBegin(), 2020 NNS->getAsNamespace())); 2021 if (!getDerived().AlwaysRebuild() && 2022 Prefix == NNS->getPrefix() && 2023 NS == NNS->getAsNamespace()) 2024 return NNS; 2025 2026 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, NS); 2027 } 2028 2029 case NestedNameSpecifier::Global: 2030 // There is no meaningful transformation that one could perform on the 2031 // global scope. 2032 return NNS; 2033 2034 case NestedNameSpecifier::TypeSpecWithTemplate: 2035 case NestedNameSpecifier::TypeSpec: { 2036 TemporaryBase Rebase(*this, Range.getBegin(), DeclarationName()); 2037 QualType T = getDerived().TransformType(QualType(NNS->getAsType(), 0), 2038 ObjectType); 2039 if (T.isNull()) 2040 return 0; 2041 2042 if (!getDerived().AlwaysRebuild() && 2043 Prefix == NNS->getPrefix() && 2044 T == QualType(NNS->getAsType(), 0)) 2045 return NNS; 2046 2047 return getDerived().RebuildNestedNameSpecifier(Prefix, Range, 2048 NNS->getKind() == NestedNameSpecifier::TypeSpecWithTemplate, 2049 T); 2050 } 2051 } 2052 2053 // Required to silence a GCC warning 2054 return 0; 2055} 2056 2057template<typename Derived> 2058DeclarationName 2059TreeTransform<Derived>::TransformDeclarationName(DeclarationName Name, 2060 SourceLocation Loc, 2061 QualType ObjectType) { 2062 if (!Name) 2063 return Name; 2064 2065 switch (Name.getNameKind()) { 2066 case DeclarationName::Identifier: 2067 case DeclarationName::ObjCZeroArgSelector: 2068 case DeclarationName::ObjCOneArgSelector: 2069 case DeclarationName::ObjCMultiArgSelector: 2070 case DeclarationName::CXXOperatorName: 2071 case DeclarationName::CXXLiteralOperatorName: 2072 case DeclarationName::CXXUsingDirective: 2073 return Name; 2074 2075 case DeclarationName::CXXConstructorName: 2076 case DeclarationName::CXXDestructorName: 2077 case DeclarationName::CXXConversionFunctionName: { 2078 TemporaryBase Rebase(*this, Loc, Name); 2079 QualType T = getDerived().TransformType(Name.getCXXNameType(), 2080 ObjectType); 2081 if (T.isNull()) 2082 return DeclarationName(); 2083 2084 return SemaRef.Context.DeclarationNames.getCXXSpecialName( 2085 Name.getNameKind(), 2086 SemaRef.Context.getCanonicalType(T)); 2087 } 2088 } 2089 2090 return DeclarationName(); 2091} 2092 2093template<typename Derived> 2094TemplateName 2095TreeTransform<Derived>::TransformTemplateName(TemplateName Name, 2096 QualType ObjectType) { 2097 SourceLocation Loc = getDerived().getBaseLocation(); 2098 2099 if (QualifiedTemplateName *QTN = Name.getAsQualifiedTemplateName()) { 2100 NestedNameSpecifier *NNS 2101 = getDerived().TransformNestedNameSpecifier(QTN->getQualifier(), 2102 /*FIXME:*/SourceRange(getDerived().getBaseLocation()), 2103 ObjectType); 2104 if (!NNS) 2105 return TemplateName(); 2106 2107 if (TemplateDecl *Template = QTN->getTemplateDecl()) { 2108 TemplateDecl *TransTemplate 2109 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Loc, Template)); 2110 if (!TransTemplate) 2111 return TemplateName(); 2112 2113 if (!getDerived().AlwaysRebuild() && 2114 NNS == QTN->getQualifier() && 2115 TransTemplate == Template) 2116 return Name; 2117 2118 return getDerived().RebuildTemplateName(NNS, QTN->hasTemplateKeyword(), 2119 TransTemplate); 2120 } 2121 2122 // These should be getting filtered out before they make it into the AST. 2123 assert(false && "overloaded template name survived to here"); 2124 } 2125 2126 if (DependentTemplateName *DTN = Name.getAsDependentTemplateName()) { 2127 NestedNameSpecifier *NNS 2128 = getDerived().TransformNestedNameSpecifier(DTN->getQualifier(), 2129 /*FIXME:*/SourceRange(getDerived().getBaseLocation()), 2130 ObjectType); 2131 if (!NNS && DTN->getQualifier()) 2132 return TemplateName(); 2133 2134 if (!getDerived().AlwaysRebuild() && 2135 NNS == DTN->getQualifier() && 2136 ObjectType.isNull()) 2137 return Name; 2138 2139 if (DTN->isIdentifier()) 2140 return getDerived().RebuildTemplateName(NNS, *DTN->getIdentifier(), 2141 ObjectType); 2142 2143 return getDerived().RebuildTemplateName(NNS, DTN->getOperator(), 2144 ObjectType); 2145 } 2146 2147 if (TemplateDecl *Template = Name.getAsTemplateDecl()) { 2148 TemplateDecl *TransTemplate 2149 = cast_or_null<TemplateDecl>(getDerived().TransformDecl(Loc, Template)); 2150 if (!TransTemplate) 2151 return TemplateName(); 2152 2153 if (!getDerived().AlwaysRebuild() && 2154 TransTemplate == Template) 2155 return Name; 2156 2157 return TemplateName(TransTemplate); 2158 } 2159 2160 // These should be getting filtered out before they reach the AST. 2161 assert(false && "overloaded function decl survived to here"); 2162 return TemplateName(); 2163} 2164 2165template<typename Derived> 2166void TreeTransform<Derived>::InventTemplateArgumentLoc( 2167 const TemplateArgument &Arg, 2168 TemplateArgumentLoc &Output) { 2169 SourceLocation Loc = getDerived().getBaseLocation(); 2170 switch (Arg.getKind()) { 2171 case TemplateArgument::Null: 2172 llvm_unreachable("null template argument in TreeTransform"); 2173 break; 2174 2175 case TemplateArgument::Type: 2176 Output = TemplateArgumentLoc(Arg, 2177 SemaRef.Context.getTrivialTypeSourceInfo(Arg.getAsType(), Loc)); 2178 2179 break; 2180 2181 case TemplateArgument::Template: 2182 Output = TemplateArgumentLoc(Arg, SourceRange(), Loc); 2183 break; 2184 2185 case TemplateArgument::Expression: 2186 Output = TemplateArgumentLoc(Arg, Arg.getAsExpr()); 2187 break; 2188 2189 case TemplateArgument::Declaration: 2190 case TemplateArgument::Integral: 2191 case TemplateArgument::Pack: 2192 Output = TemplateArgumentLoc(Arg, TemplateArgumentLocInfo()); 2193 break; 2194 } 2195} 2196 2197template<typename Derived> 2198bool TreeTransform<Derived>::TransformTemplateArgument( 2199 const TemplateArgumentLoc &Input, 2200 TemplateArgumentLoc &Output) { 2201 const TemplateArgument &Arg = Input.getArgument(); 2202 switch (Arg.getKind()) { 2203 case TemplateArgument::Null: 2204 case TemplateArgument::Integral: 2205 Output = Input; 2206 return false; 2207 2208 case TemplateArgument::Type: { 2209 TypeSourceInfo *DI = Input.getTypeSourceInfo(); 2210 if (DI == NULL) 2211 DI = InventTypeSourceInfo(Input.getArgument().getAsType()); 2212 2213 DI = getDerived().TransformType(DI); 2214 if (!DI) return true; 2215 2216 Output = TemplateArgumentLoc(TemplateArgument(DI->getType()), DI); 2217 return false; 2218 } 2219 2220 case TemplateArgument::Declaration: { 2221 // FIXME: we should never have to transform one of these. 2222 DeclarationName Name; 2223 if (NamedDecl *ND = dyn_cast<NamedDecl>(Arg.getAsDecl())) 2224 Name = ND->getDeclName(); 2225 TemporaryBase Rebase(*this, Input.getLocation(), Name); 2226 Decl *D = getDerived().TransformDecl(Input.getLocation(), Arg.getAsDecl()); 2227 if (!D) return true; 2228 2229 Expr *SourceExpr = Input.getSourceDeclExpression(); 2230 if (SourceExpr) { 2231 EnterExpressionEvaluationContext Unevaluated(getSema(), 2232 Action::Unevaluated); 2233 Sema::OwningExprResult E = getDerived().TransformExpr(SourceExpr); 2234 if (E.isInvalid()) 2235 SourceExpr = NULL; 2236 else { 2237 SourceExpr = E.takeAs<Expr>(); 2238 SourceExpr->Retain(); 2239 } 2240 } 2241 2242 Output = TemplateArgumentLoc(TemplateArgument(D), SourceExpr); 2243 return false; 2244 } 2245 2246 case TemplateArgument::Template: { 2247 TemporaryBase Rebase(*this, Input.getLocation(), DeclarationName()); 2248 TemplateName Template 2249 = getDerived().TransformTemplateName(Arg.getAsTemplate()); 2250 if (Template.isNull()) 2251 return true; 2252 2253 Output = TemplateArgumentLoc(TemplateArgument(Template), 2254 Input.getTemplateQualifierRange(), 2255 Input.getTemplateNameLoc()); 2256 return false; 2257 } 2258 2259 case TemplateArgument::Expression: { 2260 // Template argument expressions are not potentially evaluated. 2261 EnterExpressionEvaluationContext Unevaluated(getSema(), 2262 Action::Unevaluated); 2263 2264 Expr *InputExpr = Input.getSourceExpression(); 2265 if (!InputExpr) InputExpr = Input.getArgument().getAsExpr(); 2266 2267 Sema::OwningExprResult E 2268 = getDerived().TransformExpr(InputExpr); 2269 if (E.isInvalid()) return true; 2270 2271 Expr *ETaken = E.takeAs<Expr>(); 2272 ETaken->Retain(); 2273 Output = TemplateArgumentLoc(TemplateArgument(ETaken), ETaken); 2274 return false; 2275 } 2276 2277 case TemplateArgument::Pack: { 2278 llvm::SmallVector<TemplateArgument, 4> TransformedArgs; 2279 TransformedArgs.reserve(Arg.pack_size()); 2280 for (TemplateArgument::pack_iterator A = Arg.pack_begin(), 2281 AEnd = Arg.pack_end(); 2282 A != AEnd; ++A) { 2283 2284 // FIXME: preserve source information here when we start 2285 // caring about parameter packs. 2286 2287 TemplateArgumentLoc InputArg; 2288 TemplateArgumentLoc OutputArg; 2289 getDerived().InventTemplateArgumentLoc(*A, InputArg); 2290 if (getDerived().TransformTemplateArgument(InputArg, OutputArg)) 2291 return true; 2292 2293 TransformedArgs.push_back(OutputArg.getArgument()); 2294 } 2295 TemplateArgument Result; 2296 Result.setArgumentPack(TransformedArgs.data(), TransformedArgs.size(), 2297 true); 2298 Output = TemplateArgumentLoc(Result, Input.getLocInfo()); 2299 return false; 2300 } 2301 } 2302 2303 // Work around bogus GCC warning 2304 return true; 2305} 2306 2307//===----------------------------------------------------------------------===// 2308// Type transformation 2309//===----------------------------------------------------------------------===// 2310 2311template<typename Derived> 2312QualType TreeTransform<Derived>::TransformType(QualType T, 2313 QualType ObjectType) { 2314 if (getDerived().AlreadyTransformed(T)) 2315 return T; 2316 2317 // Temporary workaround. All of these transformations should 2318 // eventually turn into transformations on TypeLocs. 2319 TypeSourceInfo *DI = getSema().Context.CreateTypeSourceInfo(T); 2320 DI->getTypeLoc().initialize(getDerived().getBaseLocation()); 2321 2322 TypeSourceInfo *NewDI = getDerived().TransformType(DI, ObjectType); 2323 2324 if (!NewDI) 2325 return QualType(); 2326 2327 return NewDI->getType(); 2328} 2329 2330template<typename Derived> 2331TypeSourceInfo *TreeTransform<Derived>::TransformType(TypeSourceInfo *DI, 2332 QualType ObjectType) { 2333 if (getDerived().AlreadyTransformed(DI->getType())) 2334 return DI; 2335 2336 TypeLocBuilder TLB; 2337 2338 TypeLoc TL = DI->getTypeLoc(); 2339 TLB.reserve(TL.getFullDataSize()); 2340 2341 QualType Result = getDerived().TransformType(TLB, TL, ObjectType); 2342 if (Result.isNull()) 2343 return 0; 2344 2345 return TLB.getTypeSourceInfo(SemaRef.Context, Result); 2346} 2347 2348template<typename Derived> 2349QualType 2350TreeTransform<Derived>::TransformType(TypeLocBuilder &TLB, TypeLoc T, 2351 QualType ObjectType) { 2352 switch (T.getTypeLocClass()) { 2353#define ABSTRACT_TYPELOC(CLASS, PARENT) 2354#define TYPELOC(CLASS, PARENT) \ 2355 case TypeLoc::CLASS: \ 2356 return getDerived().Transform##CLASS##Type(TLB, cast<CLASS##TypeLoc>(T), \ 2357 ObjectType); 2358#include "clang/AST/TypeLocNodes.def" 2359 } 2360 2361 llvm_unreachable("unhandled type loc!"); 2362 return QualType(); 2363} 2364 2365/// FIXME: By default, this routine adds type qualifiers only to types 2366/// that can have qualifiers, and silently suppresses those qualifiers 2367/// that are not permitted (e.g., qualifiers on reference or function 2368/// types). This is the right thing for template instantiation, but 2369/// probably not for other clients. 2370template<typename Derived> 2371QualType 2372TreeTransform<Derived>::TransformQualifiedType(TypeLocBuilder &TLB, 2373 QualifiedTypeLoc T, 2374 QualType ObjectType) { 2375 Qualifiers Quals = T.getType().getLocalQualifiers(); 2376 2377 QualType Result = getDerived().TransformType(TLB, T.getUnqualifiedLoc(), 2378 ObjectType); 2379 if (Result.isNull()) 2380 return QualType(); 2381 2382 // Silently suppress qualifiers if the result type can't be qualified. 2383 // FIXME: this is the right thing for template instantiation, but 2384 // probably not for other clients. 2385 if (Result->isFunctionType() || Result->isReferenceType()) 2386 return Result; 2387 2388 Result = SemaRef.Context.getQualifiedType(Result, Quals); 2389 2390 TLB.push<QualifiedTypeLoc>(Result); 2391 2392 // No location information to preserve. 2393 2394 return Result; 2395} 2396 2397template <class TyLoc> static inline 2398QualType TransformTypeSpecType(TypeLocBuilder &TLB, TyLoc T) { 2399 TyLoc NewT = TLB.push<TyLoc>(T.getType()); 2400 NewT.setNameLoc(T.getNameLoc()); 2401 return T.getType(); 2402} 2403 2404template<typename Derived> 2405QualType TreeTransform<Derived>::TransformBuiltinType(TypeLocBuilder &TLB, 2406 BuiltinTypeLoc T, 2407 QualType ObjectType) { 2408 BuiltinTypeLoc NewT = TLB.push<BuiltinTypeLoc>(T.getType()); 2409 NewT.setBuiltinLoc(T.getBuiltinLoc()); 2410 if (T.needsExtraLocalData()) 2411 NewT.getWrittenBuiltinSpecs() = T.getWrittenBuiltinSpecs(); 2412 return T.getType(); 2413} 2414 2415template<typename Derived> 2416QualType TreeTransform<Derived>::TransformComplexType(TypeLocBuilder &TLB, 2417 ComplexTypeLoc T, 2418 QualType ObjectType) { 2419 // FIXME: recurse? 2420 return TransformTypeSpecType(TLB, T); 2421} 2422 2423template<typename Derived> 2424QualType TreeTransform<Derived>::TransformPointerType(TypeLocBuilder &TLB, 2425 PointerTypeLoc TL, 2426 QualType ObjectType) { 2427 QualType PointeeType 2428 = getDerived().TransformType(TLB, TL.getPointeeLoc()); 2429 if (PointeeType.isNull()) 2430 return QualType(); 2431 2432 QualType Result = TL.getType(); 2433 if (PointeeType->isObjCInterfaceType()) { 2434 // A dependent pointer type 'T *' has is being transformed such 2435 // that an Objective-C class type is being replaced for 'T'. The 2436 // resulting pointer type is an ObjCObjectPointerType, not a 2437 // PointerType. 2438 const ObjCInterfaceType *IFace = PointeeType->getAs<ObjCInterfaceType>(); 2439 Result = SemaRef.Context.getObjCObjectPointerType(PointeeType, 2440 const_cast<ObjCProtocolDecl **>( 2441 IFace->qual_begin()), 2442 IFace->getNumProtocols()); 2443 2444 ObjCObjectPointerTypeLoc NewT = TLB.push<ObjCObjectPointerTypeLoc>(Result); 2445 NewT.setStarLoc(TL.getSigilLoc()); 2446 NewT.setHasProtocolsAsWritten(false); 2447 NewT.setLAngleLoc(SourceLocation()); 2448 NewT.setRAngleLoc(SourceLocation()); 2449 NewT.setHasBaseTypeAsWritten(true); 2450 return Result; 2451 } 2452 2453 if (getDerived().AlwaysRebuild() || 2454 PointeeType != TL.getPointeeLoc().getType()) { 2455 Result = getDerived().RebuildPointerType(PointeeType, TL.getSigilLoc()); 2456 if (Result.isNull()) 2457 return QualType(); 2458 } 2459 2460 PointerTypeLoc NewT = TLB.push<PointerTypeLoc>(Result); 2461 NewT.setSigilLoc(TL.getSigilLoc()); 2462 return Result; 2463} 2464 2465template<typename Derived> 2466QualType 2467TreeTransform<Derived>::TransformBlockPointerType(TypeLocBuilder &TLB, 2468 BlockPointerTypeLoc TL, 2469 QualType ObjectType) { 2470 QualType PointeeType 2471 = getDerived().TransformType(TLB, TL.getPointeeLoc()); 2472 if (PointeeType.isNull()) 2473 return QualType(); 2474 2475 QualType Result = TL.getType(); 2476 if (getDerived().AlwaysRebuild() || 2477 PointeeType != TL.getPointeeLoc().getType()) { 2478 Result = getDerived().RebuildBlockPointerType(PointeeType, 2479 TL.getSigilLoc()); 2480 if (Result.isNull()) 2481 return QualType(); 2482 } 2483 2484 BlockPointerTypeLoc NewT = TLB.push<BlockPointerTypeLoc>(Result); 2485 NewT.setSigilLoc(TL.getSigilLoc()); 2486 return Result; 2487} 2488 2489/// Transforms a reference type. Note that somewhat paradoxically we 2490/// don't care whether the type itself is an l-value type or an r-value 2491/// type; we only care if the type was *written* as an l-value type 2492/// or an r-value type. 2493template<typename Derived> 2494QualType 2495TreeTransform<Derived>::TransformReferenceType(TypeLocBuilder &TLB, 2496 ReferenceTypeLoc TL, 2497 QualType ObjectType) { 2498 const ReferenceType *T = TL.getTypePtr(); 2499 2500 // Note that this works with the pointee-as-written. 2501 QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc()); 2502 if (PointeeType.isNull()) 2503 return QualType(); 2504 2505 QualType Result = TL.getType(); 2506 if (getDerived().AlwaysRebuild() || 2507 PointeeType != T->getPointeeTypeAsWritten()) { 2508 Result = getDerived().RebuildReferenceType(PointeeType, 2509 T->isSpelledAsLValue(), 2510 TL.getSigilLoc()); 2511 if (Result.isNull()) 2512 return QualType(); 2513 } 2514 2515 // r-value references can be rebuilt as l-value references. 2516 ReferenceTypeLoc NewTL; 2517 if (isa<LValueReferenceType>(Result)) 2518 NewTL = TLB.push<LValueReferenceTypeLoc>(Result); 2519 else 2520 NewTL = TLB.push<RValueReferenceTypeLoc>(Result); 2521 NewTL.setSigilLoc(TL.getSigilLoc()); 2522 2523 return Result; 2524} 2525 2526template<typename Derived> 2527QualType 2528TreeTransform<Derived>::TransformLValueReferenceType(TypeLocBuilder &TLB, 2529 LValueReferenceTypeLoc TL, 2530 QualType ObjectType) { 2531 return TransformReferenceType(TLB, TL, ObjectType); 2532} 2533 2534template<typename Derived> 2535QualType 2536TreeTransform<Derived>::TransformRValueReferenceType(TypeLocBuilder &TLB, 2537 RValueReferenceTypeLoc TL, 2538 QualType ObjectType) { 2539 return TransformReferenceType(TLB, TL, ObjectType); 2540} 2541 2542template<typename Derived> 2543QualType 2544TreeTransform<Derived>::TransformMemberPointerType(TypeLocBuilder &TLB, 2545 MemberPointerTypeLoc TL, 2546 QualType ObjectType) { 2547 MemberPointerType *T = TL.getTypePtr(); 2548 2549 QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc()); 2550 if (PointeeType.isNull()) 2551 return QualType(); 2552 2553 // TODO: preserve source information for this. 2554 QualType ClassType 2555 = getDerived().TransformType(QualType(T->getClass(), 0)); 2556 if (ClassType.isNull()) 2557 return QualType(); 2558 2559 QualType Result = TL.getType(); 2560 if (getDerived().AlwaysRebuild() || 2561 PointeeType != T->getPointeeType() || 2562 ClassType != QualType(T->getClass(), 0)) { 2563 Result = getDerived().RebuildMemberPointerType(PointeeType, ClassType, 2564 TL.getStarLoc()); 2565 if (Result.isNull()) 2566 return QualType(); 2567 } 2568 2569 MemberPointerTypeLoc NewTL = TLB.push<MemberPointerTypeLoc>(Result); 2570 NewTL.setSigilLoc(TL.getSigilLoc()); 2571 2572 return Result; 2573} 2574 2575template<typename Derived> 2576QualType 2577TreeTransform<Derived>::TransformConstantArrayType(TypeLocBuilder &TLB, 2578 ConstantArrayTypeLoc TL, 2579 QualType ObjectType) { 2580 ConstantArrayType *T = TL.getTypePtr(); 2581 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 2582 if (ElementType.isNull()) 2583 return QualType(); 2584 2585 QualType Result = TL.getType(); 2586 if (getDerived().AlwaysRebuild() || 2587 ElementType != T->getElementType()) { 2588 Result = getDerived().RebuildConstantArrayType(ElementType, 2589 T->getSizeModifier(), 2590 T->getSize(), 2591 T->getIndexTypeCVRQualifiers(), 2592 TL.getBracketsRange()); 2593 if (Result.isNull()) 2594 return QualType(); 2595 } 2596 2597 ConstantArrayTypeLoc NewTL = TLB.push<ConstantArrayTypeLoc>(Result); 2598 NewTL.setLBracketLoc(TL.getLBracketLoc()); 2599 NewTL.setRBracketLoc(TL.getRBracketLoc()); 2600 2601 Expr *Size = TL.getSizeExpr(); 2602 if (Size) { 2603 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 2604 Size = getDerived().TransformExpr(Size).template takeAs<Expr>(); 2605 } 2606 NewTL.setSizeExpr(Size); 2607 2608 return Result; 2609} 2610 2611template<typename Derived> 2612QualType TreeTransform<Derived>::TransformIncompleteArrayType( 2613 TypeLocBuilder &TLB, 2614 IncompleteArrayTypeLoc TL, 2615 QualType ObjectType) { 2616 IncompleteArrayType *T = TL.getTypePtr(); 2617 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 2618 if (ElementType.isNull()) 2619 return QualType(); 2620 2621 QualType Result = TL.getType(); 2622 if (getDerived().AlwaysRebuild() || 2623 ElementType != T->getElementType()) { 2624 Result = getDerived().RebuildIncompleteArrayType(ElementType, 2625 T->getSizeModifier(), 2626 T->getIndexTypeCVRQualifiers(), 2627 TL.getBracketsRange()); 2628 if (Result.isNull()) 2629 return QualType(); 2630 } 2631 2632 IncompleteArrayTypeLoc NewTL = TLB.push<IncompleteArrayTypeLoc>(Result); 2633 NewTL.setLBracketLoc(TL.getLBracketLoc()); 2634 NewTL.setRBracketLoc(TL.getRBracketLoc()); 2635 NewTL.setSizeExpr(0); 2636 2637 return Result; 2638} 2639 2640template<typename Derived> 2641QualType 2642TreeTransform<Derived>::TransformVariableArrayType(TypeLocBuilder &TLB, 2643 VariableArrayTypeLoc TL, 2644 QualType ObjectType) { 2645 VariableArrayType *T = TL.getTypePtr(); 2646 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 2647 if (ElementType.isNull()) 2648 return QualType(); 2649 2650 // Array bounds are not potentially evaluated contexts 2651 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 2652 2653 Sema::OwningExprResult SizeResult 2654 = getDerived().TransformExpr(T->getSizeExpr()); 2655 if (SizeResult.isInvalid()) 2656 return QualType(); 2657 2658 Expr *Size = static_cast<Expr*>(SizeResult.get()); 2659 2660 QualType Result = TL.getType(); 2661 if (getDerived().AlwaysRebuild() || 2662 ElementType != T->getElementType() || 2663 Size != T->getSizeExpr()) { 2664 Result = getDerived().RebuildVariableArrayType(ElementType, 2665 T->getSizeModifier(), 2666 move(SizeResult), 2667 T->getIndexTypeCVRQualifiers(), 2668 TL.getBracketsRange()); 2669 if (Result.isNull()) 2670 return QualType(); 2671 } 2672 else SizeResult.take(); 2673 2674 VariableArrayTypeLoc NewTL = TLB.push<VariableArrayTypeLoc>(Result); 2675 NewTL.setLBracketLoc(TL.getLBracketLoc()); 2676 NewTL.setRBracketLoc(TL.getRBracketLoc()); 2677 NewTL.setSizeExpr(Size); 2678 2679 return Result; 2680} 2681 2682template<typename Derived> 2683QualType 2684TreeTransform<Derived>::TransformDependentSizedArrayType(TypeLocBuilder &TLB, 2685 DependentSizedArrayTypeLoc TL, 2686 QualType ObjectType) { 2687 DependentSizedArrayType *T = TL.getTypePtr(); 2688 QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 2689 if (ElementType.isNull()) 2690 return QualType(); 2691 2692 // Array bounds are not potentially evaluated contexts 2693 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 2694 2695 Sema::OwningExprResult SizeResult 2696 = getDerived().TransformExpr(T->getSizeExpr()); 2697 if (SizeResult.isInvalid()) 2698 return QualType(); 2699 2700 Expr *Size = static_cast<Expr*>(SizeResult.get()); 2701 2702 QualType Result = TL.getType(); 2703 if (getDerived().AlwaysRebuild() || 2704 ElementType != T->getElementType() || 2705 Size != T->getSizeExpr()) { 2706 Result = getDerived().RebuildDependentSizedArrayType(ElementType, 2707 T->getSizeModifier(), 2708 move(SizeResult), 2709 T->getIndexTypeCVRQualifiers(), 2710 TL.getBracketsRange()); 2711 if (Result.isNull()) 2712 return QualType(); 2713 } 2714 else SizeResult.take(); 2715 2716 // We might have any sort of array type now, but fortunately they 2717 // all have the same location layout. 2718 ArrayTypeLoc NewTL = TLB.push<ArrayTypeLoc>(Result); 2719 NewTL.setLBracketLoc(TL.getLBracketLoc()); 2720 NewTL.setRBracketLoc(TL.getRBracketLoc()); 2721 NewTL.setSizeExpr(Size); 2722 2723 return Result; 2724} 2725 2726template<typename Derived> 2727QualType TreeTransform<Derived>::TransformDependentSizedExtVectorType( 2728 TypeLocBuilder &TLB, 2729 DependentSizedExtVectorTypeLoc TL, 2730 QualType ObjectType) { 2731 DependentSizedExtVectorType *T = TL.getTypePtr(); 2732 2733 // FIXME: ext vector locs should be nested 2734 QualType ElementType = getDerived().TransformType(T->getElementType()); 2735 if (ElementType.isNull()) 2736 return QualType(); 2737 2738 // Vector sizes are not potentially evaluated contexts 2739 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 2740 2741 Sema::OwningExprResult Size = getDerived().TransformExpr(T->getSizeExpr()); 2742 if (Size.isInvalid()) 2743 return QualType(); 2744 2745 QualType Result = TL.getType(); 2746 if (getDerived().AlwaysRebuild() || 2747 ElementType != T->getElementType() || 2748 Size.get() != T->getSizeExpr()) { 2749 Result = getDerived().RebuildDependentSizedExtVectorType(ElementType, 2750 move(Size), 2751 T->getAttributeLoc()); 2752 if (Result.isNull()) 2753 return QualType(); 2754 } 2755 else Size.take(); 2756 2757 // Result might be dependent or not. 2758 if (isa<DependentSizedExtVectorType>(Result)) { 2759 DependentSizedExtVectorTypeLoc NewTL 2760 = TLB.push<DependentSizedExtVectorTypeLoc>(Result); 2761 NewTL.setNameLoc(TL.getNameLoc()); 2762 } else { 2763 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result); 2764 NewTL.setNameLoc(TL.getNameLoc()); 2765 } 2766 2767 return Result; 2768} 2769 2770template<typename Derived> 2771QualType TreeTransform<Derived>::TransformVectorType(TypeLocBuilder &TLB, 2772 VectorTypeLoc TL, 2773 QualType ObjectType) { 2774 VectorType *T = TL.getTypePtr(); 2775 QualType ElementType = getDerived().TransformType(T->getElementType()); 2776 if (ElementType.isNull()) 2777 return QualType(); 2778 2779 QualType Result = TL.getType(); 2780 if (getDerived().AlwaysRebuild() || 2781 ElementType != T->getElementType()) { 2782 Result = getDerived().RebuildVectorType(ElementType, T->getNumElements(), 2783 T->isAltiVec(), T->isPixel()); 2784 if (Result.isNull()) 2785 return QualType(); 2786 } 2787 2788 VectorTypeLoc NewTL = TLB.push<VectorTypeLoc>(Result); 2789 NewTL.setNameLoc(TL.getNameLoc()); 2790 2791 return Result; 2792} 2793 2794template<typename Derived> 2795QualType TreeTransform<Derived>::TransformExtVectorType(TypeLocBuilder &TLB, 2796 ExtVectorTypeLoc TL, 2797 QualType ObjectType) { 2798 VectorType *T = TL.getTypePtr(); 2799 QualType ElementType = getDerived().TransformType(T->getElementType()); 2800 if (ElementType.isNull()) 2801 return QualType(); 2802 2803 QualType Result = TL.getType(); 2804 if (getDerived().AlwaysRebuild() || 2805 ElementType != T->getElementType()) { 2806 Result = getDerived().RebuildExtVectorType(ElementType, 2807 T->getNumElements(), 2808 /*FIXME*/ SourceLocation()); 2809 if (Result.isNull()) 2810 return QualType(); 2811 } 2812 2813 ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result); 2814 NewTL.setNameLoc(TL.getNameLoc()); 2815 2816 return Result; 2817} 2818 2819template<typename Derived> 2820ParmVarDecl * 2821TreeTransform<Derived>::TransformFunctionTypeParam(ParmVarDecl *OldParm) { 2822 TypeSourceInfo *OldDI = OldParm->getTypeSourceInfo(); 2823 TypeSourceInfo *NewDI = getDerived().TransformType(OldDI); 2824 if (!NewDI) 2825 return 0; 2826 2827 if (NewDI == OldDI) 2828 return OldParm; 2829 else 2830 return ParmVarDecl::Create(SemaRef.Context, 2831 OldParm->getDeclContext(), 2832 OldParm->getLocation(), 2833 OldParm->getIdentifier(), 2834 NewDI->getType(), 2835 NewDI, 2836 OldParm->getStorageClass(), 2837 OldParm->getStorageClassAsWritten(), 2838 /* DefArg */ NULL); 2839} 2840 2841template<typename Derived> 2842bool TreeTransform<Derived>:: 2843 TransformFunctionTypeParams(FunctionProtoTypeLoc TL, 2844 llvm::SmallVectorImpl<QualType> &PTypes, 2845 llvm::SmallVectorImpl<ParmVarDecl*> &PVars) { 2846 FunctionProtoType *T = TL.getTypePtr(); 2847 2848 for (unsigned i = 0, e = TL.getNumArgs(); i != e; ++i) { 2849 ParmVarDecl *OldParm = TL.getArg(i); 2850 2851 QualType NewType; 2852 ParmVarDecl *NewParm; 2853 2854 if (OldParm) { 2855 NewParm = getDerived().TransformFunctionTypeParam(OldParm); 2856 if (!NewParm) 2857 return true; 2858 NewType = NewParm->getType(); 2859 2860 // Deal with the possibility that we don't have a parameter 2861 // declaration for this parameter. 2862 } else { 2863 NewParm = 0; 2864 2865 QualType OldType = T->getArgType(i); 2866 NewType = getDerived().TransformType(OldType); 2867 if (NewType.isNull()) 2868 return true; 2869 } 2870 2871 PTypes.push_back(NewType); 2872 PVars.push_back(NewParm); 2873 } 2874 2875 return false; 2876} 2877 2878template<typename Derived> 2879QualType 2880TreeTransform<Derived>::TransformFunctionProtoType(TypeLocBuilder &TLB, 2881 FunctionProtoTypeLoc TL, 2882 QualType ObjectType) { 2883 FunctionProtoType *T = TL.getTypePtr(); 2884 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc()); 2885 if (ResultType.isNull()) 2886 return QualType(); 2887 2888 // Transform the parameters. 2889 llvm::SmallVector<QualType, 4> ParamTypes; 2890 llvm::SmallVector<ParmVarDecl*, 4> ParamDecls; 2891 if (getDerived().TransformFunctionTypeParams(TL, ParamTypes, ParamDecls)) 2892 return QualType(); 2893 2894 QualType Result = TL.getType(); 2895 if (getDerived().AlwaysRebuild() || 2896 ResultType != T->getResultType() || 2897 !std::equal(T->arg_type_begin(), T->arg_type_end(), ParamTypes.begin())) { 2898 Result = getDerived().RebuildFunctionProtoType(ResultType, 2899 ParamTypes.data(), 2900 ParamTypes.size(), 2901 T->isVariadic(), 2902 T->getTypeQuals()); 2903 if (Result.isNull()) 2904 return QualType(); 2905 } 2906 2907 FunctionProtoTypeLoc NewTL = TLB.push<FunctionProtoTypeLoc>(Result); 2908 NewTL.setLParenLoc(TL.getLParenLoc()); 2909 NewTL.setRParenLoc(TL.getRParenLoc()); 2910 for (unsigned i = 0, e = NewTL.getNumArgs(); i != e; ++i) 2911 NewTL.setArg(i, ParamDecls[i]); 2912 2913 return Result; 2914} 2915 2916template<typename Derived> 2917QualType TreeTransform<Derived>::TransformFunctionNoProtoType( 2918 TypeLocBuilder &TLB, 2919 FunctionNoProtoTypeLoc TL, 2920 QualType ObjectType) { 2921 FunctionNoProtoType *T = TL.getTypePtr(); 2922 QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc()); 2923 if (ResultType.isNull()) 2924 return QualType(); 2925 2926 QualType Result = TL.getType(); 2927 if (getDerived().AlwaysRebuild() || 2928 ResultType != T->getResultType()) 2929 Result = getDerived().RebuildFunctionNoProtoType(ResultType); 2930 2931 FunctionNoProtoTypeLoc NewTL = TLB.push<FunctionNoProtoTypeLoc>(Result); 2932 NewTL.setLParenLoc(TL.getLParenLoc()); 2933 NewTL.setRParenLoc(TL.getRParenLoc()); 2934 2935 return Result; 2936} 2937 2938template<typename Derived> QualType 2939TreeTransform<Derived>::TransformUnresolvedUsingType(TypeLocBuilder &TLB, 2940 UnresolvedUsingTypeLoc TL, 2941 QualType ObjectType) { 2942 UnresolvedUsingType *T = TL.getTypePtr(); 2943 Decl *D = getDerived().TransformDecl(TL.getNameLoc(), T->getDecl()); 2944 if (!D) 2945 return QualType(); 2946 2947 QualType Result = TL.getType(); 2948 if (getDerived().AlwaysRebuild() || D != T->getDecl()) { 2949 Result = getDerived().RebuildUnresolvedUsingType(D); 2950 if (Result.isNull()) 2951 return QualType(); 2952 } 2953 2954 // We might get an arbitrary type spec type back. We should at 2955 // least always get a type spec type, though. 2956 TypeSpecTypeLoc NewTL = TLB.pushTypeSpec(Result); 2957 NewTL.setNameLoc(TL.getNameLoc()); 2958 2959 return Result; 2960} 2961 2962template<typename Derived> 2963QualType TreeTransform<Derived>::TransformTypedefType(TypeLocBuilder &TLB, 2964 TypedefTypeLoc TL, 2965 QualType ObjectType) { 2966 TypedefType *T = TL.getTypePtr(); 2967 TypedefDecl *Typedef 2968 = cast_or_null<TypedefDecl>(getDerived().TransformDecl(TL.getNameLoc(), 2969 T->getDecl())); 2970 if (!Typedef) 2971 return QualType(); 2972 2973 QualType Result = TL.getType(); 2974 if (getDerived().AlwaysRebuild() || 2975 Typedef != T->getDecl()) { 2976 Result = getDerived().RebuildTypedefType(Typedef); 2977 if (Result.isNull()) 2978 return QualType(); 2979 } 2980 2981 TypedefTypeLoc NewTL = TLB.push<TypedefTypeLoc>(Result); 2982 NewTL.setNameLoc(TL.getNameLoc()); 2983 2984 return Result; 2985} 2986 2987template<typename Derived> 2988QualType TreeTransform<Derived>::TransformTypeOfExprType(TypeLocBuilder &TLB, 2989 TypeOfExprTypeLoc TL, 2990 QualType ObjectType) { 2991 // typeof expressions are not potentially evaluated contexts 2992 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 2993 2994 Sema::OwningExprResult E = getDerived().TransformExpr(TL.getUnderlyingExpr()); 2995 if (E.isInvalid()) 2996 return QualType(); 2997 2998 QualType Result = TL.getType(); 2999 if (getDerived().AlwaysRebuild() || 3000 E.get() != TL.getUnderlyingExpr()) { 3001 Result = getDerived().RebuildTypeOfExprType(move(E)); 3002 if (Result.isNull()) 3003 return QualType(); 3004 } 3005 else E.take(); 3006 3007 TypeOfExprTypeLoc NewTL = TLB.push<TypeOfExprTypeLoc>(Result); 3008 NewTL.setTypeofLoc(TL.getTypeofLoc()); 3009 NewTL.setLParenLoc(TL.getLParenLoc()); 3010 NewTL.setRParenLoc(TL.getRParenLoc()); 3011 3012 return Result; 3013} 3014 3015template<typename Derived> 3016QualType TreeTransform<Derived>::TransformTypeOfType(TypeLocBuilder &TLB, 3017 TypeOfTypeLoc TL, 3018 QualType ObjectType) { 3019 TypeSourceInfo* Old_Under_TI = TL.getUnderlyingTInfo(); 3020 TypeSourceInfo* New_Under_TI = getDerived().TransformType(Old_Under_TI); 3021 if (!New_Under_TI) 3022 return QualType(); 3023 3024 QualType Result = TL.getType(); 3025 if (getDerived().AlwaysRebuild() || New_Under_TI != Old_Under_TI) { 3026 Result = getDerived().RebuildTypeOfType(New_Under_TI->getType()); 3027 if (Result.isNull()) 3028 return QualType(); 3029 } 3030 3031 TypeOfTypeLoc NewTL = TLB.push<TypeOfTypeLoc>(Result); 3032 NewTL.setTypeofLoc(TL.getTypeofLoc()); 3033 NewTL.setLParenLoc(TL.getLParenLoc()); 3034 NewTL.setRParenLoc(TL.getRParenLoc()); 3035 NewTL.setUnderlyingTInfo(New_Under_TI); 3036 3037 return Result; 3038} 3039 3040template<typename Derived> 3041QualType TreeTransform<Derived>::TransformDecltypeType(TypeLocBuilder &TLB, 3042 DecltypeTypeLoc TL, 3043 QualType ObjectType) { 3044 DecltypeType *T = TL.getTypePtr(); 3045 3046 // decltype expressions are not potentially evaluated contexts 3047 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 3048 3049 Sema::OwningExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr()); 3050 if (E.isInvalid()) 3051 return QualType(); 3052 3053 QualType Result = TL.getType(); 3054 if (getDerived().AlwaysRebuild() || 3055 E.get() != T->getUnderlyingExpr()) { 3056 Result = getDerived().RebuildDecltypeType(move(E)); 3057 if (Result.isNull()) 3058 return QualType(); 3059 } 3060 else E.take(); 3061 3062 DecltypeTypeLoc NewTL = TLB.push<DecltypeTypeLoc>(Result); 3063 NewTL.setNameLoc(TL.getNameLoc()); 3064 3065 return Result; 3066} 3067 3068template<typename Derived> 3069QualType TreeTransform<Derived>::TransformRecordType(TypeLocBuilder &TLB, 3070 RecordTypeLoc TL, 3071 QualType ObjectType) { 3072 RecordType *T = TL.getTypePtr(); 3073 RecordDecl *Record 3074 = cast_or_null<RecordDecl>(getDerived().TransformDecl(TL.getNameLoc(), 3075 T->getDecl())); 3076 if (!Record) 3077 return QualType(); 3078 3079 QualType Result = TL.getType(); 3080 if (getDerived().AlwaysRebuild() || 3081 Record != T->getDecl()) { 3082 Result = getDerived().RebuildRecordType(Record); 3083 if (Result.isNull()) 3084 return QualType(); 3085 } 3086 3087 RecordTypeLoc NewTL = TLB.push<RecordTypeLoc>(Result); 3088 NewTL.setNameLoc(TL.getNameLoc()); 3089 3090 return Result; 3091} 3092 3093template<typename Derived> 3094QualType TreeTransform<Derived>::TransformEnumType(TypeLocBuilder &TLB, 3095 EnumTypeLoc TL, 3096 QualType ObjectType) { 3097 EnumType *T = TL.getTypePtr(); 3098 EnumDecl *Enum 3099 = cast_or_null<EnumDecl>(getDerived().TransformDecl(TL.getNameLoc(), 3100 T->getDecl())); 3101 if (!Enum) 3102 return QualType(); 3103 3104 QualType Result = TL.getType(); 3105 if (getDerived().AlwaysRebuild() || 3106 Enum != T->getDecl()) { 3107 Result = getDerived().RebuildEnumType(Enum); 3108 if (Result.isNull()) 3109 return QualType(); 3110 } 3111 3112 EnumTypeLoc NewTL = TLB.push<EnumTypeLoc>(Result); 3113 NewTL.setNameLoc(TL.getNameLoc()); 3114 3115 return Result; 3116} 3117 3118template <typename Derived> 3119QualType TreeTransform<Derived>::TransformElaboratedType(TypeLocBuilder &TLB, 3120 ElaboratedTypeLoc TL, 3121 QualType ObjectType) { 3122 ElaboratedType *T = TL.getTypePtr(); 3123 3124 // FIXME: this should be a nested type. 3125 QualType Underlying = getDerived().TransformType(T->getUnderlyingType()); 3126 if (Underlying.isNull()) 3127 return QualType(); 3128 3129 QualType Result = TL.getType(); 3130 if (getDerived().AlwaysRebuild() || 3131 Underlying != T->getUnderlyingType()) { 3132 Result = getDerived().RebuildElaboratedType(Underlying, T->getTagKind()); 3133 if (Result.isNull()) 3134 return QualType(); 3135 } 3136 3137 ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result); 3138 NewTL.setNameLoc(TL.getNameLoc()); 3139 3140 return Result; 3141} 3142 3143template<typename Derived> 3144QualType TreeTransform<Derived>::TransformInjectedClassNameType( 3145 TypeLocBuilder &TLB, 3146 InjectedClassNameTypeLoc TL, 3147 QualType ObjectType) { 3148 Decl *D = getDerived().TransformDecl(TL.getNameLoc(), 3149 TL.getTypePtr()->getDecl()); 3150 if (!D) return QualType(); 3151 3152 QualType T = SemaRef.Context.getTypeDeclType(cast<TypeDecl>(D)); 3153 TLB.pushTypeSpec(T).setNameLoc(TL.getNameLoc()); 3154 return T; 3155} 3156 3157 3158template<typename Derived> 3159QualType TreeTransform<Derived>::TransformTemplateTypeParmType( 3160 TypeLocBuilder &TLB, 3161 TemplateTypeParmTypeLoc TL, 3162 QualType ObjectType) { 3163 return TransformTypeSpecType(TLB, TL); 3164} 3165 3166template<typename Derived> 3167QualType TreeTransform<Derived>::TransformSubstTemplateTypeParmType( 3168 TypeLocBuilder &TLB, 3169 SubstTemplateTypeParmTypeLoc TL, 3170 QualType ObjectType) { 3171 return TransformTypeSpecType(TLB, TL); 3172} 3173 3174template<typename Derived> 3175QualType TreeTransform<Derived>::TransformTemplateSpecializationType( 3176 const TemplateSpecializationType *TST, 3177 QualType ObjectType) { 3178 // FIXME: this entire method is a temporary workaround; callers 3179 // should be rewritten to provide real type locs. 3180 3181 // Fake up a TemplateSpecializationTypeLoc. 3182 TypeLocBuilder TLB; 3183 TemplateSpecializationTypeLoc TL 3184 = TLB.push<TemplateSpecializationTypeLoc>(QualType(TST, 0)); 3185 3186 SourceLocation BaseLoc = getDerived().getBaseLocation(); 3187 3188 TL.setTemplateNameLoc(BaseLoc); 3189 TL.setLAngleLoc(BaseLoc); 3190 TL.setRAngleLoc(BaseLoc); 3191 for (unsigned i = 0, e = TL.getNumArgs(); i != e; ++i) { 3192 const TemplateArgument &TA = TST->getArg(i); 3193 TemplateArgumentLoc TAL; 3194 getDerived().InventTemplateArgumentLoc(TA, TAL); 3195 TL.setArgLocInfo(i, TAL.getLocInfo()); 3196 } 3197 3198 TypeLocBuilder IgnoredTLB; 3199 return TransformTemplateSpecializationType(IgnoredTLB, TL, ObjectType); 3200} 3201 3202template<typename Derived> 3203QualType TreeTransform<Derived>::TransformTemplateSpecializationType( 3204 TypeLocBuilder &TLB, 3205 TemplateSpecializationTypeLoc TL, 3206 QualType ObjectType) { 3207 const TemplateSpecializationType *T = TL.getTypePtr(); 3208 3209 TemplateName Template 3210 = getDerived().TransformTemplateName(T->getTemplateName(), ObjectType); 3211 if (Template.isNull()) 3212 return QualType(); 3213 3214 TemplateArgumentListInfo NewTemplateArgs; 3215 NewTemplateArgs.setLAngleLoc(TL.getLAngleLoc()); 3216 NewTemplateArgs.setRAngleLoc(TL.getRAngleLoc()); 3217 3218 for (unsigned i = 0, e = T->getNumArgs(); i != e; ++i) { 3219 TemplateArgumentLoc Loc; 3220 if (getDerived().TransformTemplateArgument(TL.getArgLoc(i), Loc)) 3221 return QualType(); 3222 NewTemplateArgs.addArgument(Loc); 3223 } 3224 3225 // FIXME: maybe don't rebuild if all the template arguments are the same. 3226 3227 QualType Result = 3228 getDerived().RebuildTemplateSpecializationType(Template, 3229 TL.getTemplateNameLoc(), 3230 NewTemplateArgs); 3231 3232 if (!Result.isNull()) { 3233 TemplateSpecializationTypeLoc NewTL 3234 = TLB.push<TemplateSpecializationTypeLoc>(Result); 3235 NewTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 3236 NewTL.setLAngleLoc(TL.getLAngleLoc()); 3237 NewTL.setRAngleLoc(TL.getRAngleLoc()); 3238 for (unsigned i = 0, e = NewTemplateArgs.size(); i != e; ++i) 3239 NewTL.setArgLocInfo(i, NewTemplateArgs[i].getLocInfo()); 3240 } 3241 3242 return Result; 3243} 3244 3245template<typename Derived> 3246QualType 3247TreeTransform<Derived>::TransformQualifiedNameType(TypeLocBuilder &TLB, 3248 QualifiedNameTypeLoc TL, 3249 QualType ObjectType) { 3250 QualifiedNameType *T = TL.getTypePtr(); 3251 NestedNameSpecifier *NNS 3252 = getDerived().TransformNestedNameSpecifier(T->getQualifier(), 3253 SourceRange(), 3254 ObjectType); 3255 if (!NNS) 3256 return QualType(); 3257 3258 QualType Named = getDerived().TransformType(T->getNamedType()); 3259 if (Named.isNull()) 3260 return QualType(); 3261 3262 QualType Result = TL.getType(); 3263 if (getDerived().AlwaysRebuild() || 3264 NNS != T->getQualifier() || 3265 Named != T->getNamedType()) { 3266 Result = getDerived().RebuildQualifiedNameType(NNS, Named); 3267 if (Result.isNull()) 3268 return QualType(); 3269 } 3270 3271 QualifiedNameTypeLoc NewTL = TLB.push<QualifiedNameTypeLoc>(Result); 3272 NewTL.setNameLoc(TL.getNameLoc()); 3273 3274 return Result; 3275} 3276 3277template<typename Derived> 3278QualType TreeTransform<Derived>::TransformDependentNameType(TypeLocBuilder &TLB, 3279 DependentNameTypeLoc TL, 3280 QualType ObjectType) { 3281 DependentNameType *T = TL.getTypePtr(); 3282 3283 /* FIXME: preserve source information better than this */ 3284 SourceRange SR(TL.getNameLoc()); 3285 3286 NestedNameSpecifier *NNS 3287 = getDerived().TransformNestedNameSpecifier(T->getQualifier(), SR, 3288 ObjectType); 3289 if (!NNS) 3290 return QualType(); 3291 3292 QualType Result; 3293 3294 if (const TemplateSpecializationType *TemplateId = T->getTemplateId()) { 3295 QualType NewTemplateId 3296 = getDerived().TransformType(QualType(TemplateId, 0)); 3297 if (NewTemplateId.isNull()) 3298 return QualType(); 3299 3300 if (!getDerived().AlwaysRebuild() && 3301 NNS == T->getQualifier() && 3302 NewTemplateId == QualType(TemplateId, 0)) 3303 return QualType(T, 0); 3304 3305 Result = getDerived().RebuildDependentNameType(T->getKeyword(), NNS, 3306 NewTemplateId); 3307 } else { 3308 Result = getDerived().RebuildDependentNameType(T->getKeyword(), NNS, 3309 T->getIdentifier(), SR); 3310 } 3311 if (Result.isNull()) 3312 return QualType(); 3313 3314 DependentNameTypeLoc NewTL = TLB.push<DependentNameTypeLoc>(Result); 3315 NewTL.setNameLoc(TL.getNameLoc()); 3316 3317 return Result; 3318} 3319 3320template<typename Derived> 3321QualType 3322TreeTransform<Derived>::TransformObjCInterfaceType(TypeLocBuilder &TLB, 3323 ObjCInterfaceTypeLoc TL, 3324 QualType ObjectType) { 3325 // ObjCInterfaceType is never dependent. 3326 return TL.getType(); 3327} 3328 3329template<typename Derived> 3330QualType 3331TreeTransform<Derived>::TransformObjCObjectPointerType(TypeLocBuilder &TLB, 3332 ObjCObjectPointerTypeLoc TL, 3333 QualType ObjectType) { 3334 // ObjCObjectPointerType is never dependent. 3335 return TL.getType(); 3336} 3337 3338//===----------------------------------------------------------------------===// 3339// Statement transformation 3340//===----------------------------------------------------------------------===// 3341template<typename Derived> 3342Sema::OwningStmtResult 3343TreeTransform<Derived>::TransformNullStmt(NullStmt *S) { 3344 return SemaRef.Owned(S->Retain()); 3345} 3346 3347template<typename Derived> 3348Sema::OwningStmtResult 3349TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S) { 3350 return getDerived().TransformCompoundStmt(S, false); 3351} 3352 3353template<typename Derived> 3354Sema::OwningStmtResult 3355TreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S, 3356 bool IsStmtExpr) { 3357 bool SubStmtChanged = false; 3358 ASTOwningVector<&ActionBase::DeleteStmt> Statements(getSema()); 3359 for (CompoundStmt::body_iterator B = S->body_begin(), BEnd = S->body_end(); 3360 B != BEnd; ++B) { 3361 OwningStmtResult Result = getDerived().TransformStmt(*B); 3362 if (Result.isInvalid()) 3363 return getSema().StmtError(); 3364 3365 SubStmtChanged = SubStmtChanged || Result.get() != *B; 3366 Statements.push_back(Result.takeAs<Stmt>()); 3367 } 3368 3369 if (!getDerived().AlwaysRebuild() && 3370 !SubStmtChanged) 3371 return SemaRef.Owned(S->Retain()); 3372 3373 return getDerived().RebuildCompoundStmt(S->getLBracLoc(), 3374 move_arg(Statements), 3375 S->getRBracLoc(), 3376 IsStmtExpr); 3377} 3378 3379template<typename Derived> 3380Sema::OwningStmtResult 3381TreeTransform<Derived>::TransformCaseStmt(CaseStmt *S) { 3382 OwningExprResult LHS(SemaRef), RHS(SemaRef); 3383 { 3384 // The case value expressions are not potentially evaluated. 3385 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 3386 3387 // Transform the left-hand case value. 3388 LHS = getDerived().TransformExpr(S->getLHS()); 3389 if (LHS.isInvalid()) 3390 return SemaRef.StmtError(); 3391 3392 // Transform the right-hand case value (for the GNU case-range extension). 3393 RHS = getDerived().TransformExpr(S->getRHS()); 3394 if (RHS.isInvalid()) 3395 return SemaRef.StmtError(); 3396 } 3397 3398 // Build the case statement. 3399 // Case statements are always rebuilt so that they will attached to their 3400 // transformed switch statement. 3401 OwningStmtResult Case = getDerived().RebuildCaseStmt(S->getCaseLoc(), 3402 move(LHS), 3403 S->getEllipsisLoc(), 3404 move(RHS), 3405 S->getColonLoc()); 3406 if (Case.isInvalid()) 3407 return SemaRef.StmtError(); 3408 3409 // Transform the statement following the case 3410 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 3411 if (SubStmt.isInvalid()) 3412 return SemaRef.StmtError(); 3413 3414 // Attach the body to the case statement 3415 return getDerived().RebuildCaseStmtBody(move(Case), move(SubStmt)); 3416} 3417 3418template<typename Derived> 3419Sema::OwningStmtResult 3420TreeTransform<Derived>::TransformDefaultStmt(DefaultStmt *S) { 3421 // Transform the statement following the default case 3422 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 3423 if (SubStmt.isInvalid()) 3424 return SemaRef.StmtError(); 3425 3426 // Default statements are always rebuilt 3427 return getDerived().RebuildDefaultStmt(S->getDefaultLoc(), S->getColonLoc(), 3428 move(SubStmt)); 3429} 3430 3431template<typename Derived> 3432Sema::OwningStmtResult 3433TreeTransform<Derived>::TransformLabelStmt(LabelStmt *S) { 3434 OwningStmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 3435 if (SubStmt.isInvalid()) 3436 return SemaRef.StmtError(); 3437 3438 // FIXME: Pass the real colon location in. 3439 SourceLocation ColonLoc = SemaRef.PP.getLocForEndOfToken(S->getIdentLoc()); 3440 return getDerived().RebuildLabelStmt(S->getIdentLoc(), S->getID(), ColonLoc, 3441 move(SubStmt)); 3442} 3443 3444template<typename Derived> 3445Sema::OwningStmtResult 3446TreeTransform<Derived>::TransformIfStmt(IfStmt *S) { 3447 // Transform the condition 3448 OwningExprResult Cond(SemaRef); 3449 VarDecl *ConditionVar = 0; 3450 if (S->getConditionVariable()) { 3451 ConditionVar 3452 = cast_or_null<VarDecl>( 3453 getDerived().TransformDefinition( 3454 S->getConditionVariable()->getLocation(), 3455 S->getConditionVariable())); 3456 if (!ConditionVar) 3457 return SemaRef.StmtError(); 3458 } else { 3459 Cond = getDerived().TransformExpr(S->getCond()); 3460 3461 if (Cond.isInvalid()) 3462 return SemaRef.StmtError(); 3463 } 3464 3465 Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond)); 3466 3467 // Transform the "then" branch. 3468 OwningStmtResult Then = getDerived().TransformStmt(S->getThen()); 3469 if (Then.isInvalid()) 3470 return SemaRef.StmtError(); 3471 3472 // Transform the "else" branch. 3473 OwningStmtResult Else = getDerived().TransformStmt(S->getElse()); 3474 if (Else.isInvalid()) 3475 return SemaRef.StmtError(); 3476 3477 if (!getDerived().AlwaysRebuild() && 3478 FullCond->get() == S->getCond() && 3479 ConditionVar == S->getConditionVariable() && 3480 Then.get() == S->getThen() && 3481 Else.get() == S->getElse()) 3482 return SemaRef.Owned(S->Retain()); 3483 3484 return getDerived().RebuildIfStmt(S->getIfLoc(), FullCond, ConditionVar, 3485 move(Then), 3486 S->getElseLoc(), move(Else)); 3487} 3488 3489template<typename Derived> 3490Sema::OwningStmtResult 3491TreeTransform<Derived>::TransformSwitchStmt(SwitchStmt *S) { 3492 // Transform the condition. 3493 OwningExprResult Cond(SemaRef); 3494 VarDecl *ConditionVar = 0; 3495 if (S->getConditionVariable()) { 3496 ConditionVar 3497 = cast_or_null<VarDecl>( 3498 getDerived().TransformDefinition( 3499 S->getConditionVariable()->getLocation(), 3500 S->getConditionVariable())); 3501 if (!ConditionVar) 3502 return SemaRef.StmtError(); 3503 } else { 3504 Cond = getDerived().TransformExpr(S->getCond()); 3505 3506 if (Cond.isInvalid()) 3507 return SemaRef.StmtError(); 3508 } 3509 3510 Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond)); 3511 3512 // Rebuild the switch statement. 3513 OwningStmtResult Switch = getDerived().RebuildSwitchStmtStart(FullCond, 3514 ConditionVar); 3515 if (Switch.isInvalid()) 3516 return SemaRef.StmtError(); 3517 3518 // Transform the body of the switch statement. 3519 OwningStmtResult Body = getDerived().TransformStmt(S->getBody()); 3520 if (Body.isInvalid()) 3521 return SemaRef.StmtError(); 3522 3523 // Complete the switch statement. 3524 return getDerived().RebuildSwitchStmtBody(S->getSwitchLoc(), move(Switch), 3525 move(Body)); 3526} 3527 3528template<typename Derived> 3529Sema::OwningStmtResult 3530TreeTransform<Derived>::TransformWhileStmt(WhileStmt *S) { 3531 // Transform the condition 3532 OwningExprResult Cond(SemaRef); 3533 VarDecl *ConditionVar = 0; 3534 if (S->getConditionVariable()) { 3535 ConditionVar 3536 = cast_or_null<VarDecl>( 3537 getDerived().TransformDefinition( 3538 S->getConditionVariable()->getLocation(), 3539 S->getConditionVariable())); 3540 if (!ConditionVar) 3541 return SemaRef.StmtError(); 3542 } else { 3543 Cond = getDerived().TransformExpr(S->getCond()); 3544 3545 if (Cond.isInvalid()) 3546 return SemaRef.StmtError(); 3547 } 3548 3549 Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond)); 3550 3551 // Transform the body 3552 OwningStmtResult Body = getDerived().TransformStmt(S->getBody()); 3553 if (Body.isInvalid()) 3554 return SemaRef.StmtError(); 3555 3556 if (!getDerived().AlwaysRebuild() && 3557 FullCond->get() == S->getCond() && 3558 ConditionVar == S->getConditionVariable() && 3559 Body.get() == S->getBody()) 3560 return SemaRef.Owned(S->Retain()); 3561 3562 return getDerived().RebuildWhileStmt(S->getWhileLoc(), FullCond, ConditionVar, 3563 move(Body)); 3564} 3565 3566template<typename Derived> 3567Sema::OwningStmtResult 3568TreeTransform<Derived>::TransformDoStmt(DoStmt *S) { 3569 // Transform the condition 3570 OwningExprResult Cond = getDerived().TransformExpr(S->getCond()); 3571 if (Cond.isInvalid()) 3572 return SemaRef.StmtError(); 3573 3574 // Transform the body 3575 OwningStmtResult Body = getDerived().TransformStmt(S->getBody()); 3576 if (Body.isInvalid()) 3577 return SemaRef.StmtError(); 3578 3579 if (!getDerived().AlwaysRebuild() && 3580 Cond.get() == S->getCond() && 3581 Body.get() == S->getBody()) 3582 return SemaRef.Owned(S->Retain()); 3583 3584 return getDerived().RebuildDoStmt(S->getDoLoc(), move(Body), S->getWhileLoc(), 3585 /*FIXME:*/S->getWhileLoc(), move(Cond), 3586 S->getRParenLoc()); 3587} 3588 3589template<typename Derived> 3590Sema::OwningStmtResult 3591TreeTransform<Derived>::TransformForStmt(ForStmt *S) { 3592 // Transform the initialization statement 3593 OwningStmtResult Init = getDerived().TransformStmt(S->getInit()); 3594 if (Init.isInvalid()) 3595 return SemaRef.StmtError(); 3596 3597 // Transform the condition 3598 OwningExprResult Cond(SemaRef); 3599 VarDecl *ConditionVar = 0; 3600 if (S->getConditionVariable()) { 3601 ConditionVar 3602 = cast_or_null<VarDecl>( 3603 getDerived().TransformDefinition( 3604 S->getConditionVariable()->getLocation(), 3605 S->getConditionVariable())); 3606 if (!ConditionVar) 3607 return SemaRef.StmtError(); 3608 } else { 3609 Cond = getDerived().TransformExpr(S->getCond()); 3610 3611 if (Cond.isInvalid()) 3612 return SemaRef.StmtError(); 3613 } 3614 3615 // Transform the increment 3616 OwningExprResult Inc = getDerived().TransformExpr(S->getInc()); 3617 if (Inc.isInvalid()) 3618 return SemaRef.StmtError(); 3619 3620 // Transform the body 3621 OwningStmtResult Body = getDerived().TransformStmt(S->getBody()); 3622 if (Body.isInvalid()) 3623 return SemaRef.StmtError(); 3624 3625 if (!getDerived().AlwaysRebuild() && 3626 Init.get() == S->getInit() && 3627 Cond.get() == S->getCond() && 3628 Inc.get() == S->getInc() && 3629 Body.get() == S->getBody()) 3630 return SemaRef.Owned(S->Retain()); 3631 3632 return getDerived().RebuildForStmt(S->getForLoc(), S->getLParenLoc(), 3633 move(Init), getSema().MakeFullExpr(Cond), 3634 ConditionVar, 3635 getSema().MakeFullExpr(Inc), 3636 S->getRParenLoc(), move(Body)); 3637} 3638 3639template<typename Derived> 3640Sema::OwningStmtResult 3641TreeTransform<Derived>::TransformGotoStmt(GotoStmt *S) { 3642 // Goto statements must always be rebuilt, to resolve the label. 3643 return getDerived().RebuildGotoStmt(S->getGotoLoc(), S->getLabelLoc(), 3644 S->getLabel()); 3645} 3646 3647template<typename Derived> 3648Sema::OwningStmtResult 3649TreeTransform<Derived>::TransformIndirectGotoStmt(IndirectGotoStmt *S) { 3650 OwningExprResult Target = getDerived().TransformExpr(S->getTarget()); 3651 if (Target.isInvalid()) 3652 return SemaRef.StmtError(); 3653 3654 if (!getDerived().AlwaysRebuild() && 3655 Target.get() == S->getTarget()) 3656 return SemaRef.Owned(S->Retain()); 3657 3658 return getDerived().RebuildIndirectGotoStmt(S->getGotoLoc(), S->getStarLoc(), 3659 move(Target)); 3660} 3661 3662template<typename Derived> 3663Sema::OwningStmtResult 3664TreeTransform<Derived>::TransformContinueStmt(ContinueStmt *S) { 3665 return SemaRef.Owned(S->Retain()); 3666} 3667 3668template<typename Derived> 3669Sema::OwningStmtResult 3670TreeTransform<Derived>::TransformBreakStmt(BreakStmt *S) { 3671 return SemaRef.Owned(S->Retain()); 3672} 3673 3674template<typename Derived> 3675Sema::OwningStmtResult 3676TreeTransform<Derived>::TransformReturnStmt(ReturnStmt *S) { 3677 Sema::OwningExprResult Result = getDerived().TransformExpr(S->getRetValue()); 3678 if (Result.isInvalid()) 3679 return SemaRef.StmtError(); 3680 3681 // FIXME: We always rebuild the return statement because there is no way 3682 // to tell whether the return type of the function has changed. 3683 return getDerived().RebuildReturnStmt(S->getReturnLoc(), move(Result)); 3684} 3685 3686template<typename Derived> 3687Sema::OwningStmtResult 3688TreeTransform<Derived>::TransformDeclStmt(DeclStmt *S) { 3689 bool DeclChanged = false; 3690 llvm::SmallVector<Decl *, 4> Decls; 3691 for (DeclStmt::decl_iterator D = S->decl_begin(), DEnd = S->decl_end(); 3692 D != DEnd; ++D) { 3693 Decl *Transformed = getDerived().TransformDefinition((*D)->getLocation(), 3694 *D); 3695 if (!Transformed) 3696 return SemaRef.StmtError(); 3697 3698 if (Transformed != *D) 3699 DeclChanged = true; 3700 3701 Decls.push_back(Transformed); 3702 } 3703 3704 if (!getDerived().AlwaysRebuild() && !DeclChanged) 3705 return SemaRef.Owned(S->Retain()); 3706 3707 return getDerived().RebuildDeclStmt(Decls.data(), Decls.size(), 3708 S->getStartLoc(), S->getEndLoc()); 3709} 3710 3711template<typename Derived> 3712Sema::OwningStmtResult 3713TreeTransform<Derived>::TransformSwitchCase(SwitchCase *S) { 3714 assert(false && "SwitchCase is abstract and cannot be transformed"); 3715 return SemaRef.Owned(S->Retain()); 3716} 3717 3718template<typename Derived> 3719Sema::OwningStmtResult 3720TreeTransform<Derived>::TransformAsmStmt(AsmStmt *S) { 3721 3722 ASTOwningVector<&ActionBase::DeleteExpr> Constraints(getSema()); 3723 ASTOwningVector<&ActionBase::DeleteExpr> Exprs(getSema()); 3724 llvm::SmallVector<IdentifierInfo *, 4> Names; 3725 3726 OwningExprResult AsmString(SemaRef); 3727 ASTOwningVector<&ActionBase::DeleteExpr> Clobbers(getSema()); 3728 3729 bool ExprsChanged = false; 3730 3731 // Go through the outputs. 3732 for (unsigned I = 0, E = S->getNumOutputs(); I != E; ++I) { 3733 Names.push_back(S->getOutputIdentifier(I)); 3734 3735 // No need to transform the constraint literal. 3736 Constraints.push_back(S->getOutputConstraintLiteral(I)->Retain()); 3737 3738 // Transform the output expr. 3739 Expr *OutputExpr = S->getOutputExpr(I); 3740 OwningExprResult Result = getDerived().TransformExpr(OutputExpr); 3741 if (Result.isInvalid()) 3742 return SemaRef.StmtError(); 3743 3744 ExprsChanged |= Result.get() != OutputExpr; 3745 3746 Exprs.push_back(Result.takeAs<Expr>()); 3747 } 3748 3749 // Go through the inputs. 3750 for (unsigned I = 0, E = S->getNumInputs(); I != E; ++I) { 3751 Names.push_back(S->getInputIdentifier(I)); 3752 3753 // No need to transform the constraint literal. 3754 Constraints.push_back(S->getInputConstraintLiteral(I)->Retain()); 3755 3756 // Transform the input expr. 3757 Expr *InputExpr = S->getInputExpr(I); 3758 OwningExprResult Result = getDerived().TransformExpr(InputExpr); 3759 if (Result.isInvalid()) 3760 return SemaRef.StmtError(); 3761 3762 ExprsChanged |= Result.get() != InputExpr; 3763 3764 Exprs.push_back(Result.takeAs<Expr>()); 3765 } 3766 3767 if (!getDerived().AlwaysRebuild() && !ExprsChanged) 3768 return SemaRef.Owned(S->Retain()); 3769 3770 // Go through the clobbers. 3771 for (unsigned I = 0, E = S->getNumClobbers(); I != E; ++I) 3772 Clobbers.push_back(S->getClobber(I)->Retain()); 3773 3774 // No need to transform the asm string literal. 3775 AsmString = SemaRef.Owned(S->getAsmString()); 3776 3777 return getDerived().RebuildAsmStmt(S->getAsmLoc(), 3778 S->isSimple(), 3779 S->isVolatile(), 3780 S->getNumOutputs(), 3781 S->getNumInputs(), 3782 Names.data(), 3783 move_arg(Constraints), 3784 move_arg(Exprs), 3785 move(AsmString), 3786 move_arg(Clobbers), 3787 S->getRParenLoc(), 3788 S->isMSAsm()); 3789} 3790 3791 3792template<typename Derived> 3793Sema::OwningStmtResult 3794TreeTransform<Derived>::TransformObjCAtTryStmt(ObjCAtTryStmt *S) { 3795 // Transform the body of the @try. 3796 OwningStmtResult TryBody = getDerived().TransformStmt(S->getTryBody()); 3797 if (TryBody.isInvalid()) 3798 return SemaRef.StmtError(); 3799 3800 // Transform the @catch statements (if present). 3801 bool AnyCatchChanged = false; 3802 ASTOwningVector<&ActionBase::DeleteStmt> CatchStmts(SemaRef); 3803 for (unsigned I = 0, N = S->getNumCatchStmts(); I != N; ++I) { 3804 OwningStmtResult Catch = getDerived().TransformStmt(S->getCatchStmt(I)); 3805 if (Catch.isInvalid()) 3806 return SemaRef.StmtError(); 3807 if (Catch.get() != S->getCatchStmt(I)) 3808 AnyCatchChanged = true; 3809 CatchStmts.push_back(Catch.release()); 3810 } 3811 3812 // Transform the @finally statement (if present). 3813 OwningStmtResult Finally(SemaRef); 3814 if (S->getFinallyStmt()) { 3815 Finally = getDerived().TransformStmt(S->getFinallyStmt()); 3816 if (Finally.isInvalid()) 3817 return SemaRef.StmtError(); 3818 } 3819 3820 // If nothing changed, just retain this statement. 3821 if (!getDerived().AlwaysRebuild() && 3822 TryBody.get() == S->getTryBody() && 3823 !AnyCatchChanged && 3824 Finally.get() == S->getFinallyStmt()) 3825 return SemaRef.Owned(S->Retain()); 3826 3827 // Build a new statement. 3828 return getDerived().RebuildObjCAtTryStmt(S->getAtTryLoc(), move(TryBody), 3829 move_arg(CatchStmts), move(Finally)); 3830} 3831 3832template<typename Derived> 3833Sema::OwningStmtResult 3834TreeTransform<Derived>::TransformObjCAtCatchStmt(ObjCAtCatchStmt *S) { 3835 // Transform the @catch parameter, if there is one. 3836 VarDecl *Var = 0; 3837 if (VarDecl *FromVar = S->getCatchParamDecl()) { 3838 TypeSourceInfo *TSInfo = 0; 3839 if (FromVar->getTypeSourceInfo()) { 3840 TSInfo = getDerived().TransformType(FromVar->getTypeSourceInfo()); 3841 if (!TSInfo) 3842 return SemaRef.StmtError(); 3843 } 3844 3845 QualType T; 3846 if (TSInfo) 3847 T = TSInfo->getType(); 3848 else { 3849 T = getDerived().TransformType(FromVar->getType()); 3850 if (T.isNull()) 3851 return SemaRef.StmtError(); 3852 } 3853 3854 Var = getDerived().RebuildObjCExceptionDecl(FromVar, TSInfo, T); 3855 if (!Var) 3856 return SemaRef.StmtError(); 3857 } 3858 3859 OwningStmtResult Body = getDerived().TransformStmt(S->getCatchBody()); 3860 if (Body.isInvalid()) 3861 return SemaRef.StmtError(); 3862 3863 return getDerived().RebuildObjCAtCatchStmt(S->getAtCatchLoc(), 3864 S->getRParenLoc(), 3865 Var, move(Body)); 3866} 3867 3868template<typename Derived> 3869Sema::OwningStmtResult 3870TreeTransform<Derived>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt *S) { 3871 // Transform the body. 3872 OwningStmtResult Body = getDerived().TransformStmt(S->getFinallyBody()); 3873 if (Body.isInvalid()) 3874 return SemaRef.StmtError(); 3875 3876 // If nothing changed, just retain this statement. 3877 if (!getDerived().AlwaysRebuild() && 3878 Body.get() == S->getFinallyBody()) 3879 return SemaRef.Owned(S->Retain()); 3880 3881 // Build a new statement. 3882 return getDerived().RebuildObjCAtFinallyStmt(S->getAtFinallyLoc(), 3883 move(Body)); 3884} 3885 3886template<typename Derived> 3887Sema::OwningStmtResult 3888TreeTransform<Derived>::TransformObjCAtThrowStmt(ObjCAtThrowStmt *S) { 3889 OwningExprResult Operand(SemaRef); 3890 if (S->getThrowExpr()) { 3891 Operand = getDerived().TransformExpr(S->getThrowExpr()); 3892 if (Operand.isInvalid()) 3893 return getSema().StmtError(); 3894 } 3895 3896 if (!getDerived().AlwaysRebuild() && 3897 Operand.get() == S->getThrowExpr()) 3898 return getSema().Owned(S->Retain()); 3899 3900 return getDerived().RebuildObjCAtThrowStmt(S->getThrowLoc(), move(Operand)); 3901} 3902 3903template<typename Derived> 3904Sema::OwningStmtResult 3905TreeTransform<Derived>::TransformObjCAtSynchronizedStmt( 3906 ObjCAtSynchronizedStmt *S) { 3907 // Transform the object we are locking. 3908 OwningExprResult Object = getDerived().TransformExpr(S->getSynchExpr()); 3909 if (Object.isInvalid()) 3910 return SemaRef.StmtError(); 3911 3912 // Transform the body. 3913 OwningStmtResult Body = getDerived().TransformStmt(S->getSynchBody()); 3914 if (Body.isInvalid()) 3915 return SemaRef.StmtError(); 3916 3917 // If nothing change, just retain the current statement. 3918 if (!getDerived().AlwaysRebuild() && 3919 Object.get() == S->getSynchExpr() && 3920 Body.get() == S->getSynchBody()) 3921 return SemaRef.Owned(S->Retain()); 3922 3923 // Build a new statement. 3924 return getDerived().RebuildObjCAtSynchronizedStmt(S->getAtSynchronizedLoc(), 3925 move(Object), move(Body)); 3926} 3927 3928template<typename Derived> 3929Sema::OwningStmtResult 3930TreeTransform<Derived>::TransformObjCForCollectionStmt( 3931 ObjCForCollectionStmt *S) { 3932 // Transform the element statement. 3933 OwningStmtResult Element = getDerived().TransformStmt(S->getElement()); 3934 if (Element.isInvalid()) 3935 return SemaRef.StmtError(); 3936 3937 // Transform the collection expression. 3938 OwningExprResult Collection = getDerived().TransformExpr(S->getCollection()); 3939 if (Collection.isInvalid()) 3940 return SemaRef.StmtError(); 3941 3942 // Transform the body. 3943 OwningStmtResult Body = getDerived().TransformStmt(S->getBody()); 3944 if (Body.isInvalid()) 3945 return SemaRef.StmtError(); 3946 3947 // If nothing changed, just retain this statement. 3948 if (!getDerived().AlwaysRebuild() && 3949 Element.get() == S->getElement() && 3950 Collection.get() == S->getCollection() && 3951 Body.get() == S->getBody()) 3952 return SemaRef.Owned(S->Retain()); 3953 3954 // Build a new statement. 3955 return getDerived().RebuildObjCForCollectionStmt(S->getForLoc(), 3956 /*FIXME:*/S->getForLoc(), 3957 move(Element), 3958 move(Collection), 3959 S->getRParenLoc(), 3960 move(Body)); 3961} 3962 3963 3964template<typename Derived> 3965Sema::OwningStmtResult 3966TreeTransform<Derived>::TransformCXXCatchStmt(CXXCatchStmt *S) { 3967 // Transform the exception declaration, if any. 3968 VarDecl *Var = 0; 3969 if (S->getExceptionDecl()) { 3970 VarDecl *ExceptionDecl = S->getExceptionDecl(); 3971 TemporaryBase Rebase(*this, ExceptionDecl->getLocation(), 3972 ExceptionDecl->getDeclName()); 3973 3974 QualType T = getDerived().TransformType(ExceptionDecl->getType()); 3975 if (T.isNull()) 3976 return SemaRef.StmtError(); 3977 3978 Var = getDerived().RebuildExceptionDecl(ExceptionDecl, 3979 T, 3980 ExceptionDecl->getTypeSourceInfo(), 3981 ExceptionDecl->getIdentifier(), 3982 ExceptionDecl->getLocation(), 3983 /*FIXME: Inaccurate*/ 3984 SourceRange(ExceptionDecl->getLocation())); 3985 if (!Var || Var->isInvalidDecl()) { 3986 if (Var) 3987 Var->Destroy(SemaRef.Context); 3988 return SemaRef.StmtError(); 3989 } 3990 } 3991 3992 // Transform the actual exception handler. 3993 OwningStmtResult Handler = getDerived().TransformStmt(S->getHandlerBlock()); 3994 if (Handler.isInvalid()) { 3995 if (Var) 3996 Var->Destroy(SemaRef.Context); 3997 return SemaRef.StmtError(); 3998 } 3999 4000 if (!getDerived().AlwaysRebuild() && 4001 !Var && 4002 Handler.get() == S->getHandlerBlock()) 4003 return SemaRef.Owned(S->Retain()); 4004 4005 return getDerived().RebuildCXXCatchStmt(S->getCatchLoc(), 4006 Var, 4007 move(Handler)); 4008} 4009 4010template<typename Derived> 4011Sema::OwningStmtResult 4012TreeTransform<Derived>::TransformCXXTryStmt(CXXTryStmt *S) { 4013 // Transform the try block itself. 4014 OwningStmtResult TryBlock 4015 = getDerived().TransformCompoundStmt(S->getTryBlock()); 4016 if (TryBlock.isInvalid()) 4017 return SemaRef.StmtError(); 4018 4019 // Transform the handlers. 4020 bool HandlerChanged = false; 4021 ASTOwningVector<&ActionBase::DeleteStmt> Handlers(SemaRef); 4022 for (unsigned I = 0, N = S->getNumHandlers(); I != N; ++I) { 4023 OwningStmtResult Handler 4024 = getDerived().TransformCXXCatchStmt(S->getHandler(I)); 4025 if (Handler.isInvalid()) 4026 return SemaRef.StmtError(); 4027 4028 HandlerChanged = HandlerChanged || Handler.get() != S->getHandler(I); 4029 Handlers.push_back(Handler.takeAs<Stmt>()); 4030 } 4031 4032 if (!getDerived().AlwaysRebuild() && 4033 TryBlock.get() == S->getTryBlock() && 4034 !HandlerChanged) 4035 return SemaRef.Owned(S->Retain()); 4036 4037 return getDerived().RebuildCXXTryStmt(S->getTryLoc(), move(TryBlock), 4038 move_arg(Handlers)); 4039} 4040 4041//===----------------------------------------------------------------------===// 4042// Expression transformation 4043//===----------------------------------------------------------------------===// 4044template<typename Derived> 4045Sema::OwningExprResult 4046TreeTransform<Derived>::TransformPredefinedExpr(PredefinedExpr *E) { 4047 return SemaRef.Owned(E->Retain()); 4048} 4049 4050template<typename Derived> 4051Sema::OwningExprResult 4052TreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) { 4053 NestedNameSpecifier *Qualifier = 0; 4054 if (E->getQualifier()) { 4055 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(), 4056 E->getQualifierRange()); 4057 if (!Qualifier) 4058 return SemaRef.ExprError(); 4059 } 4060 4061 ValueDecl *ND 4062 = cast_or_null<ValueDecl>(getDerived().TransformDecl(E->getLocation(), 4063 E->getDecl())); 4064 if (!ND) 4065 return SemaRef.ExprError(); 4066 4067 if (!getDerived().AlwaysRebuild() && 4068 Qualifier == E->getQualifier() && 4069 ND == E->getDecl() && 4070 !E->hasExplicitTemplateArgumentList()) { 4071 4072 // Mark it referenced in the new context regardless. 4073 // FIXME: this is a bit instantiation-specific. 4074 SemaRef.MarkDeclarationReferenced(E->getLocation(), ND); 4075 4076 return SemaRef.Owned(E->Retain()); 4077 } 4078 4079 TemplateArgumentListInfo TransArgs, *TemplateArgs = 0; 4080 if (E->hasExplicitTemplateArgumentList()) { 4081 TemplateArgs = &TransArgs; 4082 TransArgs.setLAngleLoc(E->getLAngleLoc()); 4083 TransArgs.setRAngleLoc(E->getRAngleLoc()); 4084 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) { 4085 TemplateArgumentLoc Loc; 4086 if (getDerived().TransformTemplateArgument(E->getTemplateArgs()[I], Loc)) 4087 return SemaRef.ExprError(); 4088 TransArgs.addArgument(Loc); 4089 } 4090 } 4091 4092 return getDerived().RebuildDeclRefExpr(Qualifier, E->getQualifierRange(), 4093 ND, E->getLocation(), TemplateArgs); 4094} 4095 4096template<typename Derived> 4097Sema::OwningExprResult 4098TreeTransform<Derived>::TransformIntegerLiteral(IntegerLiteral *E) { 4099 return SemaRef.Owned(E->Retain()); 4100} 4101 4102template<typename Derived> 4103Sema::OwningExprResult 4104TreeTransform<Derived>::TransformFloatingLiteral(FloatingLiteral *E) { 4105 return SemaRef.Owned(E->Retain()); 4106} 4107 4108template<typename Derived> 4109Sema::OwningExprResult 4110TreeTransform<Derived>::TransformImaginaryLiteral(ImaginaryLiteral *E) { 4111 return SemaRef.Owned(E->Retain()); 4112} 4113 4114template<typename Derived> 4115Sema::OwningExprResult 4116TreeTransform<Derived>::TransformStringLiteral(StringLiteral *E) { 4117 return SemaRef.Owned(E->Retain()); 4118} 4119 4120template<typename Derived> 4121Sema::OwningExprResult 4122TreeTransform<Derived>::TransformCharacterLiteral(CharacterLiteral *E) { 4123 return SemaRef.Owned(E->Retain()); 4124} 4125 4126template<typename Derived> 4127Sema::OwningExprResult 4128TreeTransform<Derived>::TransformParenExpr(ParenExpr *E) { 4129 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 4130 if (SubExpr.isInvalid()) 4131 return SemaRef.ExprError(); 4132 4133 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr()) 4134 return SemaRef.Owned(E->Retain()); 4135 4136 return getDerived().RebuildParenExpr(move(SubExpr), E->getLParen(), 4137 E->getRParen()); 4138} 4139 4140template<typename Derived> 4141Sema::OwningExprResult 4142TreeTransform<Derived>::TransformUnaryOperator(UnaryOperator *E) { 4143 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 4144 if (SubExpr.isInvalid()) 4145 return SemaRef.ExprError(); 4146 4147 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr()) 4148 return SemaRef.Owned(E->Retain()); 4149 4150 return getDerived().RebuildUnaryOperator(E->getOperatorLoc(), 4151 E->getOpcode(), 4152 move(SubExpr)); 4153} 4154 4155template<typename Derived> 4156Sema::OwningExprResult 4157TreeTransform<Derived>::TransformSizeOfAlignOfExpr(SizeOfAlignOfExpr *E) { 4158 if (E->isArgumentType()) { 4159 TypeSourceInfo *OldT = E->getArgumentTypeInfo(); 4160 4161 TypeSourceInfo *NewT = getDerived().TransformType(OldT); 4162 if (!NewT) 4163 return SemaRef.ExprError(); 4164 4165 if (!getDerived().AlwaysRebuild() && OldT == NewT) 4166 return SemaRef.Owned(E->Retain()); 4167 4168 return getDerived().RebuildSizeOfAlignOf(NewT, E->getOperatorLoc(), 4169 E->isSizeOf(), 4170 E->getSourceRange()); 4171 } 4172 4173 Sema::OwningExprResult SubExpr(SemaRef); 4174 { 4175 // C++0x [expr.sizeof]p1: 4176 // The operand is either an expression, which is an unevaluated operand 4177 // [...] 4178 EnterExpressionEvaluationContext Unevaluated(SemaRef, Action::Unevaluated); 4179 4180 SubExpr = getDerived().TransformExpr(E->getArgumentExpr()); 4181 if (SubExpr.isInvalid()) 4182 return SemaRef.ExprError(); 4183 4184 if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr()) 4185 return SemaRef.Owned(E->Retain()); 4186 } 4187 4188 return getDerived().RebuildSizeOfAlignOf(move(SubExpr), E->getOperatorLoc(), 4189 E->isSizeOf(), 4190 E->getSourceRange()); 4191} 4192 4193template<typename Derived> 4194Sema::OwningExprResult 4195TreeTransform<Derived>::TransformArraySubscriptExpr(ArraySubscriptExpr *E) { 4196 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS()); 4197 if (LHS.isInvalid()) 4198 return SemaRef.ExprError(); 4199 4200 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS()); 4201 if (RHS.isInvalid()) 4202 return SemaRef.ExprError(); 4203 4204 4205 if (!getDerived().AlwaysRebuild() && 4206 LHS.get() == E->getLHS() && 4207 RHS.get() == E->getRHS()) 4208 return SemaRef.Owned(E->Retain()); 4209 4210 return getDerived().RebuildArraySubscriptExpr(move(LHS), 4211 /*FIXME:*/E->getLHS()->getLocStart(), 4212 move(RHS), 4213 E->getRBracketLoc()); 4214} 4215 4216template<typename Derived> 4217Sema::OwningExprResult 4218TreeTransform<Derived>::TransformCallExpr(CallExpr *E) { 4219 // Transform the callee. 4220 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee()); 4221 if (Callee.isInvalid()) 4222 return SemaRef.ExprError(); 4223 4224 // Transform arguments. 4225 bool ArgChanged = false; 4226 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 4227 llvm::SmallVector<SourceLocation, 4> FakeCommaLocs; 4228 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) { 4229 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I)); 4230 if (Arg.isInvalid()) 4231 return SemaRef.ExprError(); 4232 4233 // FIXME: Wrong source location information for the ','. 4234 FakeCommaLocs.push_back( 4235 SemaRef.PP.getLocForEndOfToken(E->getArg(I)->getSourceRange().getEnd())); 4236 4237 ArgChanged = ArgChanged || Arg.get() != E->getArg(I); 4238 Args.push_back(Arg.takeAs<Expr>()); 4239 } 4240 4241 if (!getDerived().AlwaysRebuild() && 4242 Callee.get() == E->getCallee() && 4243 !ArgChanged) 4244 return SemaRef.Owned(E->Retain()); 4245 4246 // FIXME: Wrong source location information for the '('. 4247 SourceLocation FakeLParenLoc 4248 = ((Expr *)Callee.get())->getSourceRange().getBegin(); 4249 return getDerived().RebuildCallExpr(move(Callee), FakeLParenLoc, 4250 move_arg(Args), 4251 FakeCommaLocs.data(), 4252 E->getRParenLoc()); 4253} 4254 4255template<typename Derived> 4256Sema::OwningExprResult 4257TreeTransform<Derived>::TransformMemberExpr(MemberExpr *E) { 4258 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 4259 if (Base.isInvalid()) 4260 return SemaRef.ExprError(); 4261 4262 NestedNameSpecifier *Qualifier = 0; 4263 if (E->hasQualifier()) { 4264 Qualifier 4265 = getDerived().TransformNestedNameSpecifier(E->getQualifier(), 4266 E->getQualifierRange()); 4267 if (Qualifier == 0) 4268 return SemaRef.ExprError(); 4269 } 4270 4271 ValueDecl *Member 4272 = cast_or_null<ValueDecl>(getDerived().TransformDecl(E->getMemberLoc(), 4273 E->getMemberDecl())); 4274 if (!Member) 4275 return SemaRef.ExprError(); 4276 4277 NamedDecl *FoundDecl = E->getFoundDecl(); 4278 if (FoundDecl == E->getMemberDecl()) { 4279 FoundDecl = Member; 4280 } else { 4281 FoundDecl = cast_or_null<NamedDecl>( 4282 getDerived().TransformDecl(E->getMemberLoc(), FoundDecl)); 4283 if (!FoundDecl) 4284 return SemaRef.ExprError(); 4285 } 4286 4287 if (!getDerived().AlwaysRebuild() && 4288 Base.get() == E->getBase() && 4289 Qualifier == E->getQualifier() && 4290 Member == E->getMemberDecl() && 4291 FoundDecl == E->getFoundDecl() && 4292 !E->hasExplicitTemplateArgumentList()) { 4293 4294 // Mark it referenced in the new context regardless. 4295 // FIXME: this is a bit instantiation-specific. 4296 SemaRef.MarkDeclarationReferenced(E->getMemberLoc(), Member); 4297 return SemaRef.Owned(E->Retain()); 4298 } 4299 4300 TemplateArgumentListInfo TransArgs; 4301 if (E->hasExplicitTemplateArgumentList()) { 4302 TransArgs.setLAngleLoc(E->getLAngleLoc()); 4303 TransArgs.setRAngleLoc(E->getRAngleLoc()); 4304 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) { 4305 TemplateArgumentLoc Loc; 4306 if (getDerived().TransformTemplateArgument(E->getTemplateArgs()[I], Loc)) 4307 return SemaRef.ExprError(); 4308 TransArgs.addArgument(Loc); 4309 } 4310 } 4311 4312 // FIXME: Bogus source location for the operator 4313 SourceLocation FakeOperatorLoc 4314 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getSourceRange().getEnd()); 4315 4316 // FIXME: to do this check properly, we will need to preserve the 4317 // first-qualifier-in-scope here, just in case we had a dependent 4318 // base (and therefore couldn't do the check) and a 4319 // nested-name-qualifier (and therefore could do the lookup). 4320 NamedDecl *FirstQualifierInScope = 0; 4321 4322 return getDerived().RebuildMemberExpr(move(Base), FakeOperatorLoc, 4323 E->isArrow(), 4324 Qualifier, 4325 E->getQualifierRange(), 4326 E->getMemberLoc(), 4327 Member, 4328 FoundDecl, 4329 (E->hasExplicitTemplateArgumentList() 4330 ? &TransArgs : 0), 4331 FirstQualifierInScope); 4332} 4333 4334template<typename Derived> 4335Sema::OwningExprResult 4336TreeTransform<Derived>::TransformBinaryOperator(BinaryOperator *E) { 4337 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS()); 4338 if (LHS.isInvalid()) 4339 return SemaRef.ExprError(); 4340 4341 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS()); 4342 if (RHS.isInvalid()) 4343 return SemaRef.ExprError(); 4344 4345 if (!getDerived().AlwaysRebuild() && 4346 LHS.get() == E->getLHS() && 4347 RHS.get() == E->getRHS()) 4348 return SemaRef.Owned(E->Retain()); 4349 4350 return getDerived().RebuildBinaryOperator(E->getOperatorLoc(), E->getOpcode(), 4351 move(LHS), move(RHS)); 4352} 4353 4354template<typename Derived> 4355Sema::OwningExprResult 4356TreeTransform<Derived>::TransformCompoundAssignOperator( 4357 CompoundAssignOperator *E) { 4358 return getDerived().TransformBinaryOperator(E); 4359} 4360 4361template<typename Derived> 4362Sema::OwningExprResult 4363TreeTransform<Derived>::TransformConditionalOperator(ConditionalOperator *E) { 4364 OwningExprResult Cond = getDerived().TransformExpr(E->getCond()); 4365 if (Cond.isInvalid()) 4366 return SemaRef.ExprError(); 4367 4368 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS()); 4369 if (LHS.isInvalid()) 4370 return SemaRef.ExprError(); 4371 4372 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS()); 4373 if (RHS.isInvalid()) 4374 return SemaRef.ExprError(); 4375 4376 if (!getDerived().AlwaysRebuild() && 4377 Cond.get() == E->getCond() && 4378 LHS.get() == E->getLHS() && 4379 RHS.get() == E->getRHS()) 4380 return SemaRef.Owned(E->Retain()); 4381 4382 return getDerived().RebuildConditionalOperator(move(Cond), 4383 E->getQuestionLoc(), 4384 move(LHS), 4385 E->getColonLoc(), 4386 move(RHS)); 4387} 4388 4389template<typename Derived> 4390Sema::OwningExprResult 4391TreeTransform<Derived>::TransformImplicitCastExpr(ImplicitCastExpr *E) { 4392 // Implicit casts are eliminated during transformation, since they 4393 // will be recomputed by semantic analysis after transformation. 4394 return getDerived().TransformExpr(E->getSubExprAsWritten()); 4395} 4396 4397template<typename Derived> 4398Sema::OwningExprResult 4399TreeTransform<Derived>::TransformCStyleCastExpr(CStyleCastExpr *E) { 4400 TypeSourceInfo *OldT; 4401 TypeSourceInfo *NewT; 4402 { 4403 // FIXME: Source location isn't quite accurate. 4404 SourceLocation TypeStartLoc 4405 = SemaRef.PP.getLocForEndOfToken(E->getLParenLoc()); 4406 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName()); 4407 4408 OldT = E->getTypeInfoAsWritten(); 4409 NewT = getDerived().TransformType(OldT); 4410 if (!NewT) 4411 return SemaRef.ExprError(); 4412 } 4413 4414 OwningExprResult SubExpr 4415 = getDerived().TransformExpr(E->getSubExprAsWritten()); 4416 if (SubExpr.isInvalid()) 4417 return SemaRef.ExprError(); 4418 4419 if (!getDerived().AlwaysRebuild() && 4420 OldT == NewT && 4421 SubExpr.get() == E->getSubExpr()) 4422 return SemaRef.Owned(E->Retain()); 4423 4424 return getDerived().RebuildCStyleCastExpr(E->getLParenLoc(), 4425 NewT, 4426 E->getRParenLoc(), 4427 move(SubExpr)); 4428} 4429 4430template<typename Derived> 4431Sema::OwningExprResult 4432TreeTransform<Derived>::TransformCompoundLiteralExpr(CompoundLiteralExpr *E) { 4433 TypeSourceInfo *OldT = E->getTypeSourceInfo(); 4434 TypeSourceInfo *NewT = getDerived().TransformType(OldT); 4435 if (!NewT) 4436 return SemaRef.ExprError(); 4437 4438 OwningExprResult Init = getDerived().TransformExpr(E->getInitializer()); 4439 if (Init.isInvalid()) 4440 return SemaRef.ExprError(); 4441 4442 if (!getDerived().AlwaysRebuild() && 4443 OldT == NewT && 4444 Init.get() == E->getInitializer()) 4445 return SemaRef.Owned(E->Retain()); 4446 4447 // Note: the expression type doesn't necessarily match the 4448 // type-as-written, but that's okay, because it should always be 4449 // derivable from the initializer. 4450 4451 return getDerived().RebuildCompoundLiteralExpr(E->getLParenLoc(), NewT, 4452 /*FIXME:*/E->getInitializer()->getLocEnd(), 4453 move(Init)); 4454} 4455 4456template<typename Derived> 4457Sema::OwningExprResult 4458TreeTransform<Derived>::TransformExtVectorElementExpr(ExtVectorElementExpr *E) { 4459 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 4460 if (Base.isInvalid()) 4461 return SemaRef.ExprError(); 4462 4463 if (!getDerived().AlwaysRebuild() && 4464 Base.get() == E->getBase()) 4465 return SemaRef.Owned(E->Retain()); 4466 4467 // FIXME: Bad source location 4468 SourceLocation FakeOperatorLoc 4469 = SemaRef.PP.getLocForEndOfToken(E->getBase()->getLocEnd()); 4470 return getDerived().RebuildExtVectorElementExpr(move(Base), FakeOperatorLoc, 4471 E->getAccessorLoc(), 4472 E->getAccessor()); 4473} 4474 4475template<typename Derived> 4476Sema::OwningExprResult 4477TreeTransform<Derived>::TransformInitListExpr(InitListExpr *E) { 4478 bool InitChanged = false; 4479 4480 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef); 4481 for (unsigned I = 0, N = E->getNumInits(); I != N; ++I) { 4482 OwningExprResult Init = getDerived().TransformExpr(E->getInit(I)); 4483 if (Init.isInvalid()) 4484 return SemaRef.ExprError(); 4485 4486 InitChanged = InitChanged || Init.get() != E->getInit(I); 4487 Inits.push_back(Init.takeAs<Expr>()); 4488 } 4489 4490 if (!getDerived().AlwaysRebuild() && !InitChanged) 4491 return SemaRef.Owned(E->Retain()); 4492 4493 return getDerived().RebuildInitList(E->getLBraceLoc(), move_arg(Inits), 4494 E->getRBraceLoc(), E->getType()); 4495} 4496 4497template<typename Derived> 4498Sema::OwningExprResult 4499TreeTransform<Derived>::TransformDesignatedInitExpr(DesignatedInitExpr *E) { 4500 Designation Desig; 4501 4502 // transform the initializer value 4503 OwningExprResult Init = getDerived().TransformExpr(E->getInit()); 4504 if (Init.isInvalid()) 4505 return SemaRef.ExprError(); 4506 4507 // transform the designators. 4508 ASTOwningVector<&ActionBase::DeleteExpr, 4> ArrayExprs(SemaRef); 4509 bool ExprChanged = false; 4510 for (DesignatedInitExpr::designators_iterator D = E->designators_begin(), 4511 DEnd = E->designators_end(); 4512 D != DEnd; ++D) { 4513 if (D->isFieldDesignator()) { 4514 Desig.AddDesignator(Designator::getField(D->getFieldName(), 4515 D->getDotLoc(), 4516 D->getFieldLoc())); 4517 continue; 4518 } 4519 4520 if (D->isArrayDesignator()) { 4521 OwningExprResult Index = getDerived().TransformExpr(E->getArrayIndex(*D)); 4522 if (Index.isInvalid()) 4523 return SemaRef.ExprError(); 4524 4525 Desig.AddDesignator(Designator::getArray(Index.get(), 4526 D->getLBracketLoc())); 4527 4528 ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(*D); 4529 ArrayExprs.push_back(Index.release()); 4530 continue; 4531 } 4532 4533 assert(D->isArrayRangeDesignator() && "New kind of designator?"); 4534 OwningExprResult Start 4535 = getDerived().TransformExpr(E->getArrayRangeStart(*D)); 4536 if (Start.isInvalid()) 4537 return SemaRef.ExprError(); 4538 4539 OwningExprResult End = getDerived().TransformExpr(E->getArrayRangeEnd(*D)); 4540 if (End.isInvalid()) 4541 return SemaRef.ExprError(); 4542 4543 Desig.AddDesignator(Designator::getArrayRange(Start.get(), 4544 End.get(), 4545 D->getLBracketLoc(), 4546 D->getEllipsisLoc())); 4547 4548 ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(*D) || 4549 End.get() != E->getArrayRangeEnd(*D); 4550 4551 ArrayExprs.push_back(Start.release()); 4552 ArrayExprs.push_back(End.release()); 4553 } 4554 4555 if (!getDerived().AlwaysRebuild() && 4556 Init.get() == E->getInit() && 4557 !ExprChanged) 4558 return SemaRef.Owned(E->Retain()); 4559 4560 return getDerived().RebuildDesignatedInitExpr(Desig, move_arg(ArrayExprs), 4561 E->getEqualOrColonLoc(), 4562 E->usesGNUSyntax(), move(Init)); 4563} 4564 4565template<typename Derived> 4566Sema::OwningExprResult 4567TreeTransform<Derived>::TransformImplicitValueInitExpr( 4568 ImplicitValueInitExpr *E) { 4569 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName()); 4570 4571 // FIXME: Will we ever have proper type location here? Will we actually 4572 // need to transform the type? 4573 QualType T = getDerived().TransformType(E->getType()); 4574 if (T.isNull()) 4575 return SemaRef.ExprError(); 4576 4577 if (!getDerived().AlwaysRebuild() && 4578 T == E->getType()) 4579 return SemaRef.Owned(E->Retain()); 4580 4581 return getDerived().RebuildImplicitValueInitExpr(T); 4582} 4583 4584template<typename Derived> 4585Sema::OwningExprResult 4586TreeTransform<Derived>::TransformVAArgExpr(VAArgExpr *E) { 4587 // FIXME: Do we want the type as written? 4588 QualType T; 4589 4590 { 4591 // FIXME: Source location isn't quite accurate. 4592 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName()); 4593 T = getDerived().TransformType(E->getType()); 4594 if (T.isNull()) 4595 return SemaRef.ExprError(); 4596 } 4597 4598 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 4599 if (SubExpr.isInvalid()) 4600 return SemaRef.ExprError(); 4601 4602 if (!getDerived().AlwaysRebuild() && 4603 T == E->getType() && 4604 SubExpr.get() == E->getSubExpr()) 4605 return SemaRef.Owned(E->Retain()); 4606 4607 return getDerived().RebuildVAArgExpr(E->getBuiltinLoc(), move(SubExpr), 4608 T, E->getRParenLoc()); 4609} 4610 4611template<typename Derived> 4612Sema::OwningExprResult 4613TreeTransform<Derived>::TransformParenListExpr(ParenListExpr *E) { 4614 bool ArgumentChanged = false; 4615 ASTOwningVector<&ActionBase::DeleteExpr, 4> Inits(SemaRef); 4616 for (unsigned I = 0, N = E->getNumExprs(); I != N; ++I) { 4617 OwningExprResult Init = getDerived().TransformExpr(E->getExpr(I)); 4618 if (Init.isInvalid()) 4619 return SemaRef.ExprError(); 4620 4621 ArgumentChanged = ArgumentChanged || Init.get() != E->getExpr(I); 4622 Inits.push_back(Init.takeAs<Expr>()); 4623 } 4624 4625 return getDerived().RebuildParenListExpr(E->getLParenLoc(), 4626 move_arg(Inits), 4627 E->getRParenLoc()); 4628} 4629 4630/// \brief Transform an address-of-label expression. 4631/// 4632/// By default, the transformation of an address-of-label expression always 4633/// rebuilds the expression, so that the label identifier can be resolved to 4634/// the corresponding label statement by semantic analysis. 4635template<typename Derived> 4636Sema::OwningExprResult 4637TreeTransform<Derived>::TransformAddrLabelExpr(AddrLabelExpr *E) { 4638 return getDerived().RebuildAddrLabelExpr(E->getAmpAmpLoc(), E->getLabelLoc(), 4639 E->getLabel()); 4640} 4641 4642template<typename Derived> 4643Sema::OwningExprResult 4644TreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) { 4645 OwningStmtResult SubStmt 4646 = getDerived().TransformCompoundStmt(E->getSubStmt(), true); 4647 if (SubStmt.isInvalid()) 4648 return SemaRef.ExprError(); 4649 4650 if (!getDerived().AlwaysRebuild() && 4651 SubStmt.get() == E->getSubStmt()) 4652 return SemaRef.Owned(E->Retain()); 4653 4654 return getDerived().RebuildStmtExpr(E->getLParenLoc(), 4655 move(SubStmt), 4656 E->getRParenLoc()); 4657} 4658 4659template<typename Derived> 4660Sema::OwningExprResult 4661TreeTransform<Derived>::TransformTypesCompatibleExpr(TypesCompatibleExpr *E) { 4662 QualType T1, T2; 4663 { 4664 // FIXME: Source location isn't quite accurate. 4665 TemporaryBase Rebase(*this, E->getBuiltinLoc(), DeclarationName()); 4666 4667 T1 = getDerived().TransformType(E->getArgType1()); 4668 if (T1.isNull()) 4669 return SemaRef.ExprError(); 4670 4671 T2 = getDerived().TransformType(E->getArgType2()); 4672 if (T2.isNull()) 4673 return SemaRef.ExprError(); 4674 } 4675 4676 if (!getDerived().AlwaysRebuild() && 4677 T1 == E->getArgType1() && 4678 T2 == E->getArgType2()) 4679 return SemaRef.Owned(E->Retain()); 4680 4681 return getDerived().RebuildTypesCompatibleExpr(E->getBuiltinLoc(), 4682 T1, T2, E->getRParenLoc()); 4683} 4684 4685template<typename Derived> 4686Sema::OwningExprResult 4687TreeTransform<Derived>::TransformChooseExpr(ChooseExpr *E) { 4688 OwningExprResult Cond = getDerived().TransformExpr(E->getCond()); 4689 if (Cond.isInvalid()) 4690 return SemaRef.ExprError(); 4691 4692 OwningExprResult LHS = getDerived().TransformExpr(E->getLHS()); 4693 if (LHS.isInvalid()) 4694 return SemaRef.ExprError(); 4695 4696 OwningExprResult RHS = getDerived().TransformExpr(E->getRHS()); 4697 if (RHS.isInvalid()) 4698 return SemaRef.ExprError(); 4699 4700 if (!getDerived().AlwaysRebuild() && 4701 Cond.get() == E->getCond() && 4702 LHS.get() == E->getLHS() && 4703 RHS.get() == E->getRHS()) 4704 return SemaRef.Owned(E->Retain()); 4705 4706 return getDerived().RebuildChooseExpr(E->getBuiltinLoc(), 4707 move(Cond), move(LHS), move(RHS), 4708 E->getRParenLoc()); 4709} 4710 4711template<typename Derived> 4712Sema::OwningExprResult 4713TreeTransform<Derived>::TransformGNUNullExpr(GNUNullExpr *E) { 4714 return SemaRef.Owned(E->Retain()); 4715} 4716 4717template<typename Derived> 4718Sema::OwningExprResult 4719TreeTransform<Derived>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr *E) { 4720 switch (E->getOperator()) { 4721 case OO_New: 4722 case OO_Delete: 4723 case OO_Array_New: 4724 case OO_Array_Delete: 4725 llvm_unreachable("new and delete operators cannot use CXXOperatorCallExpr"); 4726 return SemaRef.ExprError(); 4727 4728 case OO_Call: { 4729 // This is a call to an object's operator(). 4730 assert(E->getNumArgs() >= 1 && "Object call is missing arguments"); 4731 4732 // Transform the object itself. 4733 OwningExprResult Object = getDerived().TransformExpr(E->getArg(0)); 4734 if (Object.isInvalid()) 4735 return SemaRef.ExprError(); 4736 4737 // FIXME: Poor location information 4738 SourceLocation FakeLParenLoc 4739 = SemaRef.PP.getLocForEndOfToken( 4740 static_cast<Expr *>(Object.get())->getLocEnd()); 4741 4742 // Transform the call arguments. 4743 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 4744 llvm::SmallVector<SourceLocation, 4> FakeCommaLocs; 4745 for (unsigned I = 1, N = E->getNumArgs(); I != N; ++I) { 4746 if (getDerived().DropCallArgument(E->getArg(I))) 4747 break; 4748 4749 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I)); 4750 if (Arg.isInvalid()) 4751 return SemaRef.ExprError(); 4752 4753 // FIXME: Poor source location information. 4754 SourceLocation FakeCommaLoc 4755 = SemaRef.PP.getLocForEndOfToken( 4756 static_cast<Expr *>(Arg.get())->getLocEnd()); 4757 FakeCommaLocs.push_back(FakeCommaLoc); 4758 Args.push_back(Arg.release()); 4759 } 4760 4761 return getDerived().RebuildCallExpr(move(Object), FakeLParenLoc, 4762 move_arg(Args), 4763 FakeCommaLocs.data(), 4764 E->getLocEnd()); 4765 } 4766 4767#define OVERLOADED_OPERATOR(Name,Spelling,Token,Unary,Binary,MemberOnly) \ 4768 case OO_##Name: 4769#define OVERLOADED_OPERATOR_MULTI(Name,Spelling,Unary,Binary,MemberOnly) 4770#include "clang/Basic/OperatorKinds.def" 4771 case OO_Subscript: 4772 // Handled below. 4773 break; 4774 4775 case OO_Conditional: 4776 llvm_unreachable("conditional operator is not actually overloadable"); 4777 return SemaRef.ExprError(); 4778 4779 case OO_None: 4780 case NUM_OVERLOADED_OPERATORS: 4781 llvm_unreachable("not an overloaded operator?"); 4782 return SemaRef.ExprError(); 4783 } 4784 4785 OwningExprResult Callee = getDerived().TransformExpr(E->getCallee()); 4786 if (Callee.isInvalid()) 4787 return SemaRef.ExprError(); 4788 4789 OwningExprResult First = getDerived().TransformExpr(E->getArg(0)); 4790 if (First.isInvalid()) 4791 return SemaRef.ExprError(); 4792 4793 OwningExprResult Second(SemaRef); 4794 if (E->getNumArgs() == 2) { 4795 Second = getDerived().TransformExpr(E->getArg(1)); 4796 if (Second.isInvalid()) 4797 return SemaRef.ExprError(); 4798 } 4799 4800 if (!getDerived().AlwaysRebuild() && 4801 Callee.get() == E->getCallee() && 4802 First.get() == E->getArg(0) && 4803 (E->getNumArgs() != 2 || Second.get() == E->getArg(1))) 4804 return SemaRef.Owned(E->Retain()); 4805 4806 return getDerived().RebuildCXXOperatorCallExpr(E->getOperator(), 4807 E->getOperatorLoc(), 4808 move(Callee), 4809 move(First), 4810 move(Second)); 4811} 4812 4813template<typename Derived> 4814Sema::OwningExprResult 4815TreeTransform<Derived>::TransformCXXMemberCallExpr(CXXMemberCallExpr *E) { 4816 return getDerived().TransformCallExpr(E); 4817} 4818 4819template<typename Derived> 4820Sema::OwningExprResult 4821TreeTransform<Derived>::TransformCXXNamedCastExpr(CXXNamedCastExpr *E) { 4822 TypeSourceInfo *OldT; 4823 TypeSourceInfo *NewT; 4824 { 4825 // FIXME: Source location isn't quite accurate. 4826 SourceLocation TypeStartLoc 4827 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc()); 4828 TemporaryBase Rebase(*this, TypeStartLoc, DeclarationName()); 4829 4830 OldT = E->getTypeInfoAsWritten(); 4831 NewT = getDerived().TransformType(OldT); 4832 if (!NewT) 4833 return SemaRef.ExprError(); 4834 } 4835 4836 OwningExprResult SubExpr 4837 = getDerived().TransformExpr(E->getSubExprAsWritten()); 4838 if (SubExpr.isInvalid()) 4839 return SemaRef.ExprError(); 4840 4841 if (!getDerived().AlwaysRebuild() && 4842 OldT == NewT && 4843 SubExpr.get() == E->getSubExpr()) 4844 return SemaRef.Owned(E->Retain()); 4845 4846 // FIXME: Poor source location information here. 4847 SourceLocation FakeLAngleLoc 4848 = SemaRef.PP.getLocForEndOfToken(E->getOperatorLoc()); 4849 SourceLocation FakeRAngleLoc = E->getSubExpr()->getSourceRange().getBegin(); 4850 SourceLocation FakeRParenLoc 4851 = SemaRef.PP.getLocForEndOfToken( 4852 E->getSubExpr()->getSourceRange().getEnd()); 4853 return getDerived().RebuildCXXNamedCastExpr(E->getOperatorLoc(), 4854 E->getStmtClass(), 4855 FakeLAngleLoc, 4856 NewT, 4857 FakeRAngleLoc, 4858 FakeRAngleLoc, 4859 move(SubExpr), 4860 FakeRParenLoc); 4861} 4862 4863template<typename Derived> 4864Sema::OwningExprResult 4865TreeTransform<Derived>::TransformCXXStaticCastExpr(CXXStaticCastExpr *E) { 4866 return getDerived().TransformCXXNamedCastExpr(E); 4867} 4868 4869template<typename Derived> 4870Sema::OwningExprResult 4871TreeTransform<Derived>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr *E) { 4872 return getDerived().TransformCXXNamedCastExpr(E); 4873} 4874 4875template<typename Derived> 4876Sema::OwningExprResult 4877TreeTransform<Derived>::TransformCXXReinterpretCastExpr( 4878 CXXReinterpretCastExpr *E) { 4879 return getDerived().TransformCXXNamedCastExpr(E); 4880} 4881 4882template<typename Derived> 4883Sema::OwningExprResult 4884TreeTransform<Derived>::TransformCXXConstCastExpr(CXXConstCastExpr *E) { 4885 return getDerived().TransformCXXNamedCastExpr(E); 4886} 4887 4888template<typename Derived> 4889Sema::OwningExprResult 4890TreeTransform<Derived>::TransformCXXFunctionalCastExpr( 4891 CXXFunctionalCastExpr *E) { 4892 TypeSourceInfo *OldT; 4893 TypeSourceInfo *NewT; 4894 { 4895 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName()); 4896 4897 OldT = E->getTypeInfoAsWritten(); 4898 NewT = getDerived().TransformType(OldT); 4899 if (!NewT) 4900 return SemaRef.ExprError(); 4901 } 4902 4903 OwningExprResult SubExpr 4904 = getDerived().TransformExpr(E->getSubExprAsWritten()); 4905 if (SubExpr.isInvalid()) 4906 return SemaRef.ExprError(); 4907 4908 if (!getDerived().AlwaysRebuild() && 4909 OldT == NewT && 4910 SubExpr.get() == E->getSubExpr()) 4911 return SemaRef.Owned(E->Retain()); 4912 4913 // FIXME: The end of the type's source range is wrong 4914 return getDerived().RebuildCXXFunctionalCastExpr( 4915 /*FIXME:*/SourceRange(E->getTypeBeginLoc()), 4916 NewT, 4917 /*FIXME:*/E->getSubExpr()->getLocStart(), 4918 move(SubExpr), 4919 E->getRParenLoc()); 4920} 4921 4922template<typename Derived> 4923Sema::OwningExprResult 4924TreeTransform<Derived>::TransformCXXTypeidExpr(CXXTypeidExpr *E) { 4925 if (E->isTypeOperand()) { 4926 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName()); 4927 4928 QualType T = getDerived().TransformType(E->getTypeOperand()); 4929 if (T.isNull()) 4930 return SemaRef.ExprError(); 4931 4932 if (!getDerived().AlwaysRebuild() && 4933 T == E->getTypeOperand()) 4934 return SemaRef.Owned(E->Retain()); 4935 4936 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(), 4937 /*FIXME:*/E->getLocStart(), 4938 T, 4939 E->getLocEnd()); 4940 } 4941 4942 // We don't know whether the expression is potentially evaluated until 4943 // after we perform semantic analysis, so the expression is potentially 4944 // potentially evaluated. 4945 EnterExpressionEvaluationContext Unevaluated(SemaRef, 4946 Action::PotentiallyPotentiallyEvaluated); 4947 4948 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand()); 4949 if (SubExpr.isInvalid()) 4950 return SemaRef.ExprError(); 4951 4952 if (!getDerived().AlwaysRebuild() && 4953 SubExpr.get() == E->getExprOperand()) 4954 return SemaRef.Owned(E->Retain()); 4955 4956 return getDerived().RebuildCXXTypeidExpr(E->getLocStart(), 4957 /*FIXME:*/E->getLocStart(), 4958 move(SubExpr), 4959 E->getLocEnd()); 4960} 4961 4962template<typename Derived> 4963Sema::OwningExprResult 4964TreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) { 4965 return SemaRef.Owned(E->Retain()); 4966} 4967 4968template<typename Derived> 4969Sema::OwningExprResult 4970TreeTransform<Derived>::TransformCXXNullPtrLiteralExpr( 4971 CXXNullPtrLiteralExpr *E) { 4972 return SemaRef.Owned(E->Retain()); 4973} 4974 4975template<typename Derived> 4976Sema::OwningExprResult 4977TreeTransform<Derived>::TransformCXXThisExpr(CXXThisExpr *E) { 4978 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName()); 4979 4980 QualType T = getDerived().TransformType(E->getType()); 4981 if (T.isNull()) 4982 return SemaRef.ExprError(); 4983 4984 if (!getDerived().AlwaysRebuild() && 4985 T == E->getType()) 4986 return SemaRef.Owned(E->Retain()); 4987 4988 return getDerived().RebuildCXXThisExpr(E->getLocStart(), T, E->isImplicit()); 4989} 4990 4991template<typename Derived> 4992Sema::OwningExprResult 4993TreeTransform<Derived>::TransformCXXThrowExpr(CXXThrowExpr *E) { 4994 OwningExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 4995 if (SubExpr.isInvalid()) 4996 return SemaRef.ExprError(); 4997 4998 if (!getDerived().AlwaysRebuild() && 4999 SubExpr.get() == E->getSubExpr()) 5000 return SemaRef.Owned(E->Retain()); 5001 5002 return getDerived().RebuildCXXThrowExpr(E->getThrowLoc(), move(SubExpr)); 5003} 5004 5005template<typename Derived> 5006Sema::OwningExprResult 5007TreeTransform<Derived>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E) { 5008 ParmVarDecl *Param 5009 = cast_or_null<ParmVarDecl>(getDerived().TransformDecl(E->getLocStart(), 5010 E->getParam())); 5011 if (!Param) 5012 return SemaRef.ExprError(); 5013 5014 if (!getDerived().AlwaysRebuild() && 5015 Param == E->getParam()) 5016 return SemaRef.Owned(E->Retain()); 5017 5018 return getDerived().RebuildCXXDefaultArgExpr(E->getUsedLocation(), Param); 5019} 5020 5021template<typename Derived> 5022Sema::OwningExprResult 5023TreeTransform<Derived>::TransformCXXZeroInitValueExpr(CXXZeroInitValueExpr *E) { 5024 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName()); 5025 5026 QualType T = getDerived().TransformType(E->getType()); 5027 if (T.isNull()) 5028 return SemaRef.ExprError(); 5029 5030 if (!getDerived().AlwaysRebuild() && 5031 T == E->getType()) 5032 return SemaRef.Owned(E->Retain()); 5033 5034 return getDerived().RebuildCXXZeroInitValueExpr(E->getTypeBeginLoc(), 5035 /*FIXME:*/E->getTypeBeginLoc(), 5036 T, 5037 E->getRParenLoc()); 5038} 5039 5040template<typename Derived> 5041Sema::OwningExprResult 5042TreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) { 5043 // Transform the type that we're allocating 5044 TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName()); 5045 QualType AllocType = getDerived().TransformType(E->getAllocatedType()); 5046 if (AllocType.isNull()) 5047 return SemaRef.ExprError(); 5048 5049 // Transform the size of the array we're allocating (if any). 5050 OwningExprResult ArraySize = getDerived().TransformExpr(E->getArraySize()); 5051 if (ArraySize.isInvalid()) 5052 return SemaRef.ExprError(); 5053 5054 // Transform the placement arguments (if any). 5055 bool ArgumentChanged = false; 5056 ASTOwningVector<&ActionBase::DeleteExpr> PlacementArgs(SemaRef); 5057 for (unsigned I = 0, N = E->getNumPlacementArgs(); I != N; ++I) { 5058 OwningExprResult Arg = getDerived().TransformExpr(E->getPlacementArg(I)); 5059 if (Arg.isInvalid()) 5060 return SemaRef.ExprError(); 5061 5062 ArgumentChanged = ArgumentChanged || Arg.get() != E->getPlacementArg(I); 5063 PlacementArgs.push_back(Arg.take()); 5064 } 5065 5066 // transform the constructor arguments (if any). 5067 ASTOwningVector<&ActionBase::DeleteExpr> ConstructorArgs(SemaRef); 5068 for (unsigned I = 0, N = E->getNumConstructorArgs(); I != N; ++I) { 5069 OwningExprResult Arg = getDerived().TransformExpr(E->getConstructorArg(I)); 5070 if (Arg.isInvalid()) 5071 return SemaRef.ExprError(); 5072 5073 ArgumentChanged = ArgumentChanged || Arg.get() != E->getConstructorArg(I); 5074 ConstructorArgs.push_back(Arg.take()); 5075 } 5076 5077 // Transform constructor, new operator, and delete operator. 5078 CXXConstructorDecl *Constructor = 0; 5079 if (E->getConstructor()) { 5080 Constructor = cast_or_null<CXXConstructorDecl>( 5081 getDerived().TransformDecl(E->getLocStart(), 5082 E->getConstructor())); 5083 if (!Constructor) 5084 return SemaRef.ExprError(); 5085 } 5086 5087 FunctionDecl *OperatorNew = 0; 5088 if (E->getOperatorNew()) { 5089 OperatorNew = cast_or_null<FunctionDecl>( 5090 getDerived().TransformDecl(E->getLocStart(), 5091 E->getOperatorNew())); 5092 if (!OperatorNew) 5093 return SemaRef.ExprError(); 5094 } 5095 5096 FunctionDecl *OperatorDelete = 0; 5097 if (E->getOperatorDelete()) { 5098 OperatorDelete = cast_or_null<FunctionDecl>( 5099 getDerived().TransformDecl(E->getLocStart(), 5100 E->getOperatorDelete())); 5101 if (!OperatorDelete) 5102 return SemaRef.ExprError(); 5103 } 5104 5105 if (!getDerived().AlwaysRebuild() && 5106 AllocType == E->getAllocatedType() && 5107 ArraySize.get() == E->getArraySize() && 5108 Constructor == E->getConstructor() && 5109 OperatorNew == E->getOperatorNew() && 5110 OperatorDelete == E->getOperatorDelete() && 5111 !ArgumentChanged) { 5112 // Mark any declarations we need as referenced. 5113 // FIXME: instantiation-specific. 5114 if (Constructor) 5115 SemaRef.MarkDeclarationReferenced(E->getLocStart(), Constructor); 5116 if (OperatorNew) 5117 SemaRef.MarkDeclarationReferenced(E->getLocStart(), OperatorNew); 5118 if (OperatorDelete) 5119 SemaRef.MarkDeclarationReferenced(E->getLocStart(), OperatorDelete); 5120 return SemaRef.Owned(E->Retain()); 5121 } 5122 5123 if (!ArraySize.get()) { 5124 // If no array size was specified, but the new expression was 5125 // instantiated with an array type (e.g., "new T" where T is 5126 // instantiated with "int[4]"), extract the outer bound from the 5127 // array type as our array size. We do this with constant and 5128 // dependently-sized array types. 5129 const ArrayType *ArrayT = SemaRef.Context.getAsArrayType(AllocType); 5130 if (!ArrayT) { 5131 // Do nothing 5132 } else if (const ConstantArrayType *ConsArrayT 5133 = dyn_cast<ConstantArrayType>(ArrayT)) { 5134 ArraySize 5135 = SemaRef.Owned(new (SemaRef.Context) IntegerLiteral( 5136 ConsArrayT->getSize(), 5137 SemaRef.Context.getSizeType(), 5138 /*FIXME:*/E->getLocStart())); 5139 AllocType = ConsArrayT->getElementType(); 5140 } else if (const DependentSizedArrayType *DepArrayT 5141 = dyn_cast<DependentSizedArrayType>(ArrayT)) { 5142 if (DepArrayT->getSizeExpr()) { 5143 ArraySize = SemaRef.Owned(DepArrayT->getSizeExpr()->Retain()); 5144 AllocType = DepArrayT->getElementType(); 5145 } 5146 } 5147 } 5148 return getDerived().RebuildCXXNewExpr(E->getLocStart(), 5149 E->isGlobalNew(), 5150 /*FIXME:*/E->getLocStart(), 5151 move_arg(PlacementArgs), 5152 /*FIXME:*/E->getLocStart(), 5153 E->isParenTypeId(), 5154 AllocType, 5155 /*FIXME:*/E->getLocStart(), 5156 /*FIXME:*/SourceRange(), 5157 move(ArraySize), 5158 /*FIXME:*/E->getLocStart(), 5159 move_arg(ConstructorArgs), 5160 E->getLocEnd()); 5161} 5162 5163template<typename Derived> 5164Sema::OwningExprResult 5165TreeTransform<Derived>::TransformCXXDeleteExpr(CXXDeleteExpr *E) { 5166 OwningExprResult Operand = getDerived().TransformExpr(E->getArgument()); 5167 if (Operand.isInvalid()) 5168 return SemaRef.ExprError(); 5169 5170 // Transform the delete operator, if known. 5171 FunctionDecl *OperatorDelete = 0; 5172 if (E->getOperatorDelete()) { 5173 OperatorDelete = cast_or_null<FunctionDecl>( 5174 getDerived().TransformDecl(E->getLocStart(), 5175 E->getOperatorDelete())); 5176 if (!OperatorDelete) 5177 return SemaRef.ExprError(); 5178 } 5179 5180 if (!getDerived().AlwaysRebuild() && 5181 Operand.get() == E->getArgument() && 5182 OperatorDelete == E->getOperatorDelete()) { 5183 // Mark any declarations we need as referenced. 5184 // FIXME: instantiation-specific. 5185 if (OperatorDelete) 5186 SemaRef.MarkDeclarationReferenced(E->getLocStart(), OperatorDelete); 5187 return SemaRef.Owned(E->Retain()); 5188 } 5189 5190 return getDerived().RebuildCXXDeleteExpr(E->getLocStart(), 5191 E->isGlobalDelete(), 5192 E->isArrayForm(), 5193 move(Operand)); 5194} 5195 5196template<typename Derived> 5197Sema::OwningExprResult 5198TreeTransform<Derived>::TransformCXXPseudoDestructorExpr( 5199 CXXPseudoDestructorExpr *E) { 5200 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 5201 if (Base.isInvalid()) 5202 return SemaRef.ExprError(); 5203 5204 Sema::TypeTy *ObjectTypePtr = 0; 5205 bool MayBePseudoDestructor = false; 5206 Base = SemaRef.ActOnStartCXXMemberReference(0, move(Base), 5207 E->getOperatorLoc(), 5208 E->isArrow()? tok::arrow : tok::period, 5209 ObjectTypePtr, 5210 MayBePseudoDestructor); 5211 if (Base.isInvalid()) 5212 return SemaRef.ExprError(); 5213 5214 QualType ObjectType = QualType::getFromOpaquePtr(ObjectTypePtr); 5215 NestedNameSpecifier *Qualifier 5216 = getDerived().TransformNestedNameSpecifier(E->getQualifier(), 5217 E->getQualifierRange(), 5218 ObjectType); 5219 if (E->getQualifier() && !Qualifier) 5220 return SemaRef.ExprError(); 5221 5222 PseudoDestructorTypeStorage Destroyed; 5223 if (E->getDestroyedTypeInfo()) { 5224 TypeSourceInfo *DestroyedTypeInfo 5225 = getDerived().TransformType(E->getDestroyedTypeInfo(), ObjectType); 5226 if (!DestroyedTypeInfo) 5227 return SemaRef.ExprError(); 5228 Destroyed = DestroyedTypeInfo; 5229 } else if (ObjectType->isDependentType()) { 5230 // We aren't likely to be able to resolve the identifier down to a type 5231 // now anyway, so just retain the identifier. 5232 Destroyed = PseudoDestructorTypeStorage(E->getDestroyedTypeIdentifier(), 5233 E->getDestroyedTypeLoc()); 5234 } else { 5235 // Look for a destructor known with the given name. 5236 CXXScopeSpec SS; 5237 if (Qualifier) { 5238 SS.setScopeRep(Qualifier); 5239 SS.setRange(E->getQualifierRange()); 5240 } 5241 5242 Sema::TypeTy *T = SemaRef.getDestructorName(E->getTildeLoc(), 5243 *E->getDestroyedTypeIdentifier(), 5244 E->getDestroyedTypeLoc(), 5245 /*Scope=*/0, 5246 SS, ObjectTypePtr, 5247 false); 5248 if (!T) 5249 return SemaRef.ExprError(); 5250 5251 Destroyed 5252 = SemaRef.Context.getTrivialTypeSourceInfo(SemaRef.GetTypeFromParser(T), 5253 E->getDestroyedTypeLoc()); 5254 } 5255 5256 TypeSourceInfo *ScopeTypeInfo = 0; 5257 if (E->getScopeTypeInfo()) { 5258 ScopeTypeInfo = getDerived().TransformType(E->getScopeTypeInfo(), 5259 ObjectType); 5260 if (!ScopeTypeInfo) 5261 return SemaRef.ExprError(); 5262 } 5263 5264 return getDerived().RebuildCXXPseudoDestructorExpr(move(Base), 5265 E->getOperatorLoc(), 5266 E->isArrow(), 5267 Qualifier, 5268 E->getQualifierRange(), 5269 ScopeTypeInfo, 5270 E->getColonColonLoc(), 5271 E->getTildeLoc(), 5272 Destroyed); 5273} 5274 5275template<typename Derived> 5276Sema::OwningExprResult 5277TreeTransform<Derived>::TransformUnresolvedLookupExpr( 5278 UnresolvedLookupExpr *Old) { 5279 TemporaryBase Rebase(*this, Old->getNameLoc(), DeclarationName()); 5280 5281 LookupResult R(SemaRef, Old->getName(), Old->getNameLoc(), 5282 Sema::LookupOrdinaryName); 5283 5284 // Transform all the decls. 5285 for (UnresolvedLookupExpr::decls_iterator I = Old->decls_begin(), 5286 E = Old->decls_end(); I != E; ++I) { 5287 NamedDecl *InstD = static_cast<NamedDecl*>( 5288 getDerived().TransformDecl(Old->getNameLoc(), 5289 *I)); 5290 if (!InstD) { 5291 // Silently ignore these if a UsingShadowDecl instantiated to nothing. 5292 // This can happen because of dependent hiding. 5293 if (isa<UsingShadowDecl>(*I)) 5294 continue; 5295 else 5296 return SemaRef.ExprError(); 5297 } 5298 5299 // Expand using declarations. 5300 if (isa<UsingDecl>(InstD)) { 5301 UsingDecl *UD = cast<UsingDecl>(InstD); 5302 for (UsingDecl::shadow_iterator I = UD->shadow_begin(), 5303 E = UD->shadow_end(); I != E; ++I) 5304 R.addDecl(*I); 5305 continue; 5306 } 5307 5308 R.addDecl(InstD); 5309 } 5310 5311 // Resolve a kind, but don't do any further analysis. If it's 5312 // ambiguous, the callee needs to deal with it. 5313 R.resolveKind(); 5314 5315 // Rebuild the nested-name qualifier, if present. 5316 CXXScopeSpec SS; 5317 NestedNameSpecifier *Qualifier = 0; 5318 if (Old->getQualifier()) { 5319 Qualifier = getDerived().TransformNestedNameSpecifier(Old->getQualifier(), 5320 Old->getQualifierRange()); 5321 if (!Qualifier) 5322 return SemaRef.ExprError(); 5323 5324 SS.setScopeRep(Qualifier); 5325 SS.setRange(Old->getQualifierRange()); 5326 } 5327 5328 // If we have no template arguments, it's a normal declaration name. 5329 if (!Old->hasExplicitTemplateArgs()) 5330 return getDerived().RebuildDeclarationNameExpr(SS, R, Old->requiresADL()); 5331 5332 // If we have template arguments, rebuild them, then rebuild the 5333 // templateid expression. 5334 TemplateArgumentListInfo TransArgs(Old->getLAngleLoc(), Old->getRAngleLoc()); 5335 for (unsigned I = 0, N = Old->getNumTemplateArgs(); I != N; ++I) { 5336 TemplateArgumentLoc Loc; 5337 if (getDerived().TransformTemplateArgument(Old->getTemplateArgs()[I], Loc)) 5338 return SemaRef.ExprError(); 5339 TransArgs.addArgument(Loc); 5340 } 5341 5342 return getDerived().RebuildTemplateIdExpr(SS, R, Old->requiresADL(), 5343 TransArgs); 5344} 5345 5346template<typename Derived> 5347Sema::OwningExprResult 5348TreeTransform<Derived>::TransformUnaryTypeTraitExpr(UnaryTypeTraitExpr *E) { 5349 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName()); 5350 5351 QualType T = getDerived().TransformType(E->getQueriedType()); 5352 if (T.isNull()) 5353 return SemaRef.ExprError(); 5354 5355 if (!getDerived().AlwaysRebuild() && 5356 T == E->getQueriedType()) 5357 return SemaRef.Owned(E->Retain()); 5358 5359 // FIXME: Bad location information 5360 SourceLocation FakeLParenLoc 5361 = SemaRef.PP.getLocForEndOfToken(E->getLocStart()); 5362 5363 return getDerived().RebuildUnaryTypeTrait(E->getTrait(), 5364 E->getLocStart(), 5365 /*FIXME:*/FakeLParenLoc, 5366 T, 5367 E->getLocEnd()); 5368} 5369 5370template<typename Derived> 5371Sema::OwningExprResult 5372TreeTransform<Derived>::TransformDependentScopeDeclRefExpr( 5373 DependentScopeDeclRefExpr *E) { 5374 NestedNameSpecifier *NNS 5375 = getDerived().TransformNestedNameSpecifier(E->getQualifier(), 5376 E->getQualifierRange()); 5377 if (!NNS) 5378 return SemaRef.ExprError(); 5379 5380 DeclarationName Name 5381 = getDerived().TransformDeclarationName(E->getDeclName(), E->getLocation()); 5382 if (!Name) 5383 return SemaRef.ExprError(); 5384 5385 if (!E->hasExplicitTemplateArgs()) { 5386 if (!getDerived().AlwaysRebuild() && 5387 NNS == E->getQualifier() && 5388 Name == E->getDeclName()) 5389 return SemaRef.Owned(E->Retain()); 5390 5391 return getDerived().RebuildDependentScopeDeclRefExpr(NNS, 5392 E->getQualifierRange(), 5393 Name, E->getLocation(), 5394 /*TemplateArgs*/ 0); 5395 } 5396 5397 TemplateArgumentListInfo TransArgs(E->getLAngleLoc(), E->getRAngleLoc()); 5398 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) { 5399 TemplateArgumentLoc Loc; 5400 if (getDerived().TransformTemplateArgument(E->getTemplateArgs()[I], Loc)) 5401 return SemaRef.ExprError(); 5402 TransArgs.addArgument(Loc); 5403 } 5404 5405 return getDerived().RebuildDependentScopeDeclRefExpr(NNS, 5406 E->getQualifierRange(), 5407 Name, E->getLocation(), 5408 &TransArgs); 5409} 5410 5411template<typename Derived> 5412Sema::OwningExprResult 5413TreeTransform<Derived>::TransformCXXConstructExpr(CXXConstructExpr *E) { 5414 // CXXConstructExprs are always implicit, so when we have a 5415 // 1-argument construction we just transform that argument. 5416 if (E->getNumArgs() == 1 || 5417 (E->getNumArgs() > 1 && getDerived().DropCallArgument(E->getArg(1)))) 5418 return getDerived().TransformExpr(E->getArg(0)); 5419 5420 TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName()); 5421 5422 QualType T = getDerived().TransformType(E->getType()); 5423 if (T.isNull()) 5424 return SemaRef.ExprError(); 5425 5426 CXXConstructorDecl *Constructor 5427 = cast_or_null<CXXConstructorDecl>( 5428 getDerived().TransformDecl(E->getLocStart(), 5429 E->getConstructor())); 5430 if (!Constructor) 5431 return SemaRef.ExprError(); 5432 5433 bool ArgumentChanged = false; 5434 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 5435 for (CXXConstructExpr::arg_iterator Arg = E->arg_begin(), 5436 ArgEnd = E->arg_end(); 5437 Arg != ArgEnd; ++Arg) { 5438 if (getDerived().DropCallArgument(*Arg)) { 5439 ArgumentChanged = true; 5440 break; 5441 } 5442 5443 OwningExprResult TransArg = getDerived().TransformExpr(*Arg); 5444 if (TransArg.isInvalid()) 5445 return SemaRef.ExprError(); 5446 5447 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg; 5448 Args.push_back(TransArg.takeAs<Expr>()); 5449 } 5450 5451 if (!getDerived().AlwaysRebuild() && 5452 T == E->getType() && 5453 Constructor == E->getConstructor() && 5454 !ArgumentChanged) { 5455 // Mark the constructor as referenced. 5456 // FIXME: Instantiation-specific 5457 SemaRef.MarkDeclarationReferenced(E->getLocStart(), Constructor); 5458 return SemaRef.Owned(E->Retain()); 5459 } 5460 5461 return getDerived().RebuildCXXConstructExpr(T, /*FIXME:*/E->getLocStart(), 5462 Constructor, E->isElidable(), 5463 move_arg(Args)); 5464} 5465 5466/// \brief Transform a C++ temporary-binding expression. 5467/// 5468/// Since CXXBindTemporaryExpr nodes are implicitly generated, we just 5469/// transform the subexpression and return that. 5470template<typename Derived> 5471Sema::OwningExprResult 5472TreeTransform<Derived>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr *E) { 5473 return getDerived().TransformExpr(E->getSubExpr()); 5474} 5475 5476/// \brief Transform a C++ reference-binding expression. 5477/// 5478/// Since CXXBindReferenceExpr nodes are implicitly generated, we just 5479/// transform the subexpression and return that. 5480template<typename Derived> 5481Sema::OwningExprResult 5482TreeTransform<Derived>::TransformCXXBindReferenceExpr(CXXBindReferenceExpr *E) { 5483 return getDerived().TransformExpr(E->getSubExpr()); 5484} 5485 5486/// \brief Transform a C++ expression that contains temporaries that should 5487/// be destroyed after the expression is evaluated. 5488/// 5489/// Since CXXExprWithTemporaries nodes are implicitly generated, we 5490/// just transform the subexpression and return that. 5491template<typename Derived> 5492Sema::OwningExprResult 5493TreeTransform<Derived>::TransformCXXExprWithTemporaries( 5494 CXXExprWithTemporaries *E) { 5495 return getDerived().TransformExpr(E->getSubExpr()); 5496} 5497 5498template<typename Derived> 5499Sema::OwningExprResult 5500TreeTransform<Derived>::TransformCXXTemporaryObjectExpr( 5501 CXXTemporaryObjectExpr *E) { 5502 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName()); 5503 QualType T = getDerived().TransformType(E->getType()); 5504 if (T.isNull()) 5505 return SemaRef.ExprError(); 5506 5507 CXXConstructorDecl *Constructor 5508 = cast_or_null<CXXConstructorDecl>( 5509 getDerived().TransformDecl(E->getLocStart(), 5510 E->getConstructor())); 5511 if (!Constructor) 5512 return SemaRef.ExprError(); 5513 5514 bool ArgumentChanged = false; 5515 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 5516 Args.reserve(E->getNumArgs()); 5517 for (CXXTemporaryObjectExpr::arg_iterator Arg = E->arg_begin(), 5518 ArgEnd = E->arg_end(); 5519 Arg != ArgEnd; ++Arg) { 5520 if (getDerived().DropCallArgument(*Arg)) { 5521 ArgumentChanged = true; 5522 break; 5523 } 5524 5525 OwningExprResult TransArg = getDerived().TransformExpr(*Arg); 5526 if (TransArg.isInvalid()) 5527 return SemaRef.ExprError(); 5528 5529 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg; 5530 Args.push_back((Expr *)TransArg.release()); 5531 } 5532 5533 if (!getDerived().AlwaysRebuild() && 5534 T == E->getType() && 5535 Constructor == E->getConstructor() && 5536 !ArgumentChanged) { 5537 // FIXME: Instantiation-specific 5538 SemaRef.MarkDeclarationReferenced(E->getTypeBeginLoc(), Constructor); 5539 return SemaRef.MaybeBindToTemporary(E->Retain()); 5540 } 5541 5542 // FIXME: Bogus location information 5543 SourceLocation CommaLoc; 5544 if (Args.size() > 1) { 5545 Expr *First = (Expr *)Args[0]; 5546 CommaLoc 5547 = SemaRef.PP.getLocForEndOfToken(First->getSourceRange().getEnd()); 5548 } 5549 return getDerived().RebuildCXXTemporaryObjectExpr(E->getTypeBeginLoc(), 5550 T, 5551 /*FIXME:*/E->getTypeBeginLoc(), 5552 move_arg(Args), 5553 &CommaLoc, 5554 E->getLocEnd()); 5555} 5556 5557template<typename Derived> 5558Sema::OwningExprResult 5559TreeTransform<Derived>::TransformCXXUnresolvedConstructExpr( 5560 CXXUnresolvedConstructExpr *E) { 5561 TemporaryBase Rebase(*this, E->getTypeBeginLoc(), DeclarationName()); 5562 QualType T = getDerived().TransformType(E->getTypeAsWritten()); 5563 if (T.isNull()) 5564 return SemaRef.ExprError(); 5565 5566 bool ArgumentChanged = false; 5567 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 5568 llvm::SmallVector<SourceLocation, 8> FakeCommaLocs; 5569 for (CXXUnresolvedConstructExpr::arg_iterator Arg = E->arg_begin(), 5570 ArgEnd = E->arg_end(); 5571 Arg != ArgEnd; ++Arg) { 5572 OwningExprResult TransArg = getDerived().TransformExpr(*Arg); 5573 if (TransArg.isInvalid()) 5574 return SemaRef.ExprError(); 5575 5576 ArgumentChanged = ArgumentChanged || TransArg.get() != *Arg; 5577 FakeCommaLocs.push_back( 5578 SemaRef.PP.getLocForEndOfToken((*Arg)->getLocEnd())); 5579 Args.push_back(TransArg.takeAs<Expr>()); 5580 } 5581 5582 if (!getDerived().AlwaysRebuild() && 5583 T == E->getTypeAsWritten() && 5584 !ArgumentChanged) 5585 return SemaRef.Owned(E->Retain()); 5586 5587 // FIXME: we're faking the locations of the commas 5588 return getDerived().RebuildCXXUnresolvedConstructExpr(E->getTypeBeginLoc(), 5589 T, 5590 E->getLParenLoc(), 5591 move_arg(Args), 5592 FakeCommaLocs.data(), 5593 E->getRParenLoc()); 5594} 5595 5596template<typename Derived> 5597Sema::OwningExprResult 5598TreeTransform<Derived>::TransformCXXDependentScopeMemberExpr( 5599 CXXDependentScopeMemberExpr *E) { 5600 // Transform the base of the expression. 5601 OwningExprResult Base(SemaRef, (Expr*) 0); 5602 Expr *OldBase; 5603 QualType BaseType; 5604 QualType ObjectType; 5605 if (!E->isImplicitAccess()) { 5606 OldBase = E->getBase(); 5607 Base = getDerived().TransformExpr(OldBase); 5608 if (Base.isInvalid()) 5609 return SemaRef.ExprError(); 5610 5611 // Start the member reference and compute the object's type. 5612 Sema::TypeTy *ObjectTy = 0; 5613 bool MayBePseudoDestructor = false; 5614 Base = SemaRef.ActOnStartCXXMemberReference(0, move(Base), 5615 E->getOperatorLoc(), 5616 E->isArrow()? tok::arrow : tok::period, 5617 ObjectTy, 5618 MayBePseudoDestructor); 5619 if (Base.isInvalid()) 5620 return SemaRef.ExprError(); 5621 5622 ObjectType = QualType::getFromOpaquePtr(ObjectTy); 5623 BaseType = ((Expr*) Base.get())->getType(); 5624 } else { 5625 OldBase = 0; 5626 BaseType = getDerived().TransformType(E->getBaseType()); 5627 ObjectType = BaseType->getAs<PointerType>()->getPointeeType(); 5628 } 5629 5630 // Transform the first part of the nested-name-specifier that qualifies 5631 // the member name. 5632 NamedDecl *FirstQualifierInScope 5633 = getDerived().TransformFirstQualifierInScope( 5634 E->getFirstQualifierFoundInScope(), 5635 E->getQualifierRange().getBegin()); 5636 5637 NestedNameSpecifier *Qualifier = 0; 5638 if (E->getQualifier()) { 5639 Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(), 5640 E->getQualifierRange(), 5641 ObjectType, 5642 FirstQualifierInScope); 5643 if (!Qualifier) 5644 return SemaRef.ExprError(); 5645 } 5646 5647 DeclarationName Name 5648 = getDerived().TransformDeclarationName(E->getMember(), E->getMemberLoc(), 5649 ObjectType); 5650 if (!Name) 5651 return SemaRef.ExprError(); 5652 5653 if (!E->hasExplicitTemplateArgs()) { 5654 // This is a reference to a member without an explicitly-specified 5655 // template argument list. Optimize for this common case. 5656 if (!getDerived().AlwaysRebuild() && 5657 Base.get() == OldBase && 5658 BaseType == E->getBaseType() && 5659 Qualifier == E->getQualifier() && 5660 Name == E->getMember() && 5661 FirstQualifierInScope == E->getFirstQualifierFoundInScope()) 5662 return SemaRef.Owned(E->Retain()); 5663 5664 return getDerived().RebuildCXXDependentScopeMemberExpr(move(Base), 5665 BaseType, 5666 E->isArrow(), 5667 E->getOperatorLoc(), 5668 Qualifier, 5669 E->getQualifierRange(), 5670 FirstQualifierInScope, 5671 Name, 5672 E->getMemberLoc(), 5673 /*TemplateArgs*/ 0); 5674 } 5675 5676 TemplateArgumentListInfo TransArgs(E->getLAngleLoc(), E->getRAngleLoc()); 5677 for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) { 5678 TemplateArgumentLoc Loc; 5679 if (getDerived().TransformTemplateArgument(E->getTemplateArgs()[I], Loc)) 5680 return SemaRef.ExprError(); 5681 TransArgs.addArgument(Loc); 5682 } 5683 5684 return getDerived().RebuildCXXDependentScopeMemberExpr(move(Base), 5685 BaseType, 5686 E->isArrow(), 5687 E->getOperatorLoc(), 5688 Qualifier, 5689 E->getQualifierRange(), 5690 FirstQualifierInScope, 5691 Name, 5692 E->getMemberLoc(), 5693 &TransArgs); 5694} 5695 5696template<typename Derived> 5697Sema::OwningExprResult 5698TreeTransform<Derived>::TransformUnresolvedMemberExpr(UnresolvedMemberExpr *Old) { 5699 // Transform the base of the expression. 5700 OwningExprResult Base(SemaRef, (Expr*) 0); 5701 QualType BaseType; 5702 if (!Old->isImplicitAccess()) { 5703 Base = getDerived().TransformExpr(Old->getBase()); 5704 if (Base.isInvalid()) 5705 return SemaRef.ExprError(); 5706 BaseType = ((Expr*) Base.get())->getType(); 5707 } else { 5708 BaseType = getDerived().TransformType(Old->getBaseType()); 5709 } 5710 5711 NestedNameSpecifier *Qualifier = 0; 5712 if (Old->getQualifier()) { 5713 Qualifier 5714 = getDerived().TransformNestedNameSpecifier(Old->getQualifier(), 5715 Old->getQualifierRange()); 5716 if (Qualifier == 0) 5717 return SemaRef.ExprError(); 5718 } 5719 5720 LookupResult R(SemaRef, Old->getMemberName(), Old->getMemberLoc(), 5721 Sema::LookupOrdinaryName); 5722 5723 // Transform all the decls. 5724 for (UnresolvedMemberExpr::decls_iterator I = Old->decls_begin(), 5725 E = Old->decls_end(); I != E; ++I) { 5726 NamedDecl *InstD = static_cast<NamedDecl*>( 5727 getDerived().TransformDecl(Old->getMemberLoc(), 5728 *I)); 5729 if (!InstD) { 5730 // Silently ignore these if a UsingShadowDecl instantiated to nothing. 5731 // This can happen because of dependent hiding. 5732 if (isa<UsingShadowDecl>(*I)) 5733 continue; 5734 else 5735 return SemaRef.ExprError(); 5736 } 5737 5738 // Expand using declarations. 5739 if (isa<UsingDecl>(InstD)) { 5740 UsingDecl *UD = cast<UsingDecl>(InstD); 5741 for (UsingDecl::shadow_iterator I = UD->shadow_begin(), 5742 E = UD->shadow_end(); I != E; ++I) 5743 R.addDecl(*I); 5744 continue; 5745 } 5746 5747 R.addDecl(InstD); 5748 } 5749 5750 R.resolveKind(); 5751 5752 TemplateArgumentListInfo TransArgs; 5753 if (Old->hasExplicitTemplateArgs()) { 5754 TransArgs.setLAngleLoc(Old->getLAngleLoc()); 5755 TransArgs.setRAngleLoc(Old->getRAngleLoc()); 5756 for (unsigned I = 0, N = Old->getNumTemplateArgs(); I != N; ++I) { 5757 TemplateArgumentLoc Loc; 5758 if (getDerived().TransformTemplateArgument(Old->getTemplateArgs()[I], 5759 Loc)) 5760 return SemaRef.ExprError(); 5761 TransArgs.addArgument(Loc); 5762 } 5763 } 5764 5765 // FIXME: to do this check properly, we will need to preserve the 5766 // first-qualifier-in-scope here, just in case we had a dependent 5767 // base (and therefore couldn't do the check) and a 5768 // nested-name-qualifier (and therefore could do the lookup). 5769 NamedDecl *FirstQualifierInScope = 0; 5770 5771 return getDerived().RebuildUnresolvedMemberExpr(move(Base), 5772 BaseType, 5773 Old->getOperatorLoc(), 5774 Old->isArrow(), 5775 Qualifier, 5776 Old->getQualifierRange(), 5777 FirstQualifierInScope, 5778 R, 5779 (Old->hasExplicitTemplateArgs() 5780 ? &TransArgs : 0)); 5781} 5782 5783template<typename Derived> 5784Sema::OwningExprResult 5785TreeTransform<Derived>::TransformObjCStringLiteral(ObjCStringLiteral *E) { 5786 return SemaRef.Owned(E->Retain()); 5787} 5788 5789template<typename Derived> 5790Sema::OwningExprResult 5791TreeTransform<Derived>::TransformObjCEncodeExpr(ObjCEncodeExpr *E) { 5792 TypeSourceInfo *EncodedTypeInfo 5793 = getDerived().TransformType(E->getEncodedTypeSourceInfo()); 5794 if (!EncodedTypeInfo) 5795 return SemaRef.ExprError(); 5796 5797 if (!getDerived().AlwaysRebuild() && 5798 EncodedTypeInfo == E->getEncodedTypeSourceInfo()) 5799 return SemaRef.Owned(E->Retain()); 5800 5801 return getDerived().RebuildObjCEncodeExpr(E->getAtLoc(), 5802 EncodedTypeInfo, 5803 E->getRParenLoc()); 5804} 5805 5806template<typename Derived> 5807Sema::OwningExprResult 5808TreeTransform<Derived>::TransformObjCMessageExpr(ObjCMessageExpr *E) { 5809 // Transform arguments. 5810 bool ArgChanged = false; 5811 ASTOwningVector<&ActionBase::DeleteExpr> Args(SemaRef); 5812 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) { 5813 OwningExprResult Arg = getDerived().TransformExpr(E->getArg(I)); 5814 if (Arg.isInvalid()) 5815 return SemaRef.ExprError(); 5816 5817 ArgChanged = ArgChanged || Arg.get() != E->getArg(I); 5818 Args.push_back(Arg.takeAs<Expr>()); 5819 } 5820 5821 if (E->getReceiverKind() == ObjCMessageExpr::Class) { 5822 // Class message: transform the receiver type. 5823 TypeSourceInfo *ReceiverTypeInfo 5824 = getDerived().TransformType(E->getClassReceiverTypeInfo()); 5825 if (!ReceiverTypeInfo) 5826 return SemaRef.ExprError(); 5827 5828 // If nothing changed, just retain the existing message send. 5829 if (!getDerived().AlwaysRebuild() && 5830 ReceiverTypeInfo == E->getClassReceiverTypeInfo() && !ArgChanged) 5831 return SemaRef.Owned(E->Retain()); 5832 5833 // Build a new class message send. 5834 return getDerived().RebuildObjCMessageExpr(ReceiverTypeInfo, 5835 E->getSelector(), 5836 E->getMethodDecl(), 5837 E->getLeftLoc(), 5838 move_arg(Args), 5839 E->getRightLoc()); 5840 } 5841 5842 // Instance message: transform the receiver 5843 assert(E->getReceiverKind() == ObjCMessageExpr::Instance && 5844 "Only class and instance messages may be instantiated"); 5845 OwningExprResult Receiver 5846 = getDerived().TransformExpr(E->getInstanceReceiver()); 5847 if (Receiver.isInvalid()) 5848 return SemaRef.ExprError(); 5849 5850 // If nothing changed, just retain the existing message send. 5851 if (!getDerived().AlwaysRebuild() && 5852 Receiver.get() == E->getInstanceReceiver() && !ArgChanged) 5853 return SemaRef.Owned(E->Retain()); 5854 5855 // Build a new instance message send. 5856 return getDerived().RebuildObjCMessageExpr(move(Receiver), 5857 E->getSelector(), 5858 E->getMethodDecl(), 5859 E->getLeftLoc(), 5860 move_arg(Args), 5861 E->getRightLoc()); 5862} 5863 5864template<typename Derived> 5865Sema::OwningExprResult 5866TreeTransform<Derived>::TransformObjCSelectorExpr(ObjCSelectorExpr *E) { 5867 return SemaRef.Owned(E->Retain()); 5868} 5869 5870template<typename Derived> 5871Sema::OwningExprResult 5872TreeTransform<Derived>::TransformObjCProtocolExpr(ObjCProtocolExpr *E) { 5873 return SemaRef.Owned(E->Retain()); 5874} 5875 5876template<typename Derived> 5877Sema::OwningExprResult 5878TreeTransform<Derived>::TransformObjCIvarRefExpr(ObjCIvarRefExpr *E) { 5879 // Transform the base expression. 5880 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 5881 if (Base.isInvalid()) 5882 return SemaRef.ExprError(); 5883 5884 // We don't need to transform the ivar; it will never change. 5885 5886 // If nothing changed, just retain the existing expression. 5887 if (!getDerived().AlwaysRebuild() && 5888 Base.get() == E->getBase()) 5889 return SemaRef.Owned(E->Retain()); 5890 5891 return getDerived().RebuildObjCIvarRefExpr(move(Base), E->getDecl(), 5892 E->getLocation(), 5893 E->isArrow(), E->isFreeIvar()); 5894} 5895 5896template<typename Derived> 5897Sema::OwningExprResult 5898TreeTransform<Derived>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr *E) { 5899 // Transform the base expression. 5900 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 5901 if (Base.isInvalid()) 5902 return SemaRef.ExprError(); 5903 5904 // We don't need to transform the property; it will never change. 5905 5906 // If nothing changed, just retain the existing expression. 5907 if (!getDerived().AlwaysRebuild() && 5908 Base.get() == E->getBase()) 5909 return SemaRef.Owned(E->Retain()); 5910 5911 return getDerived().RebuildObjCPropertyRefExpr(move(Base), E->getProperty(), 5912 E->getLocation()); 5913} 5914 5915template<typename Derived> 5916Sema::OwningExprResult 5917TreeTransform<Derived>::TransformObjCImplicitSetterGetterRefExpr( 5918 ObjCImplicitSetterGetterRefExpr *E) { 5919 // FIXME: Implement this! 5920 assert(false && "Cannot transform Objective-C expressions yet"); 5921 return SemaRef.Owned(E->Retain()); 5922} 5923 5924template<typename Derived> 5925Sema::OwningExprResult 5926TreeTransform<Derived>::TransformObjCSuperExpr(ObjCSuperExpr *E) { 5927 // Can never occur in a dependent context. 5928 return SemaRef.Owned(E->Retain()); 5929} 5930 5931template<typename Derived> 5932Sema::OwningExprResult 5933TreeTransform<Derived>::TransformObjCIsaExpr(ObjCIsaExpr *E) { 5934 // Transform the base expression. 5935 OwningExprResult Base = getDerived().TransformExpr(E->getBase()); 5936 if (Base.isInvalid()) 5937 return SemaRef.ExprError(); 5938 5939 // If nothing changed, just retain the existing expression. 5940 if (!getDerived().AlwaysRebuild() && 5941 Base.get() == E->getBase()) 5942 return SemaRef.Owned(E->Retain()); 5943 5944 return getDerived().RebuildObjCIsaExpr(move(Base), E->getIsaMemberLoc(), 5945 E->isArrow()); 5946} 5947 5948template<typename Derived> 5949Sema::OwningExprResult 5950TreeTransform<Derived>::TransformShuffleVectorExpr(ShuffleVectorExpr *E) { 5951 bool ArgumentChanged = false; 5952 ASTOwningVector<&ActionBase::DeleteExpr> SubExprs(SemaRef); 5953 for (unsigned I = 0, N = E->getNumSubExprs(); I != N; ++I) { 5954 OwningExprResult SubExpr = getDerived().TransformExpr(E->getExpr(I)); 5955 if (SubExpr.isInvalid()) 5956 return SemaRef.ExprError(); 5957 5958 ArgumentChanged = ArgumentChanged || SubExpr.get() != E->getExpr(I); 5959 SubExprs.push_back(SubExpr.takeAs<Expr>()); 5960 } 5961 5962 if (!getDerived().AlwaysRebuild() && 5963 !ArgumentChanged) 5964 return SemaRef.Owned(E->Retain()); 5965 5966 return getDerived().RebuildShuffleVectorExpr(E->getBuiltinLoc(), 5967 move_arg(SubExprs), 5968 E->getRParenLoc()); 5969} 5970 5971template<typename Derived> 5972Sema::OwningExprResult 5973TreeTransform<Derived>::TransformBlockExpr(BlockExpr *E) { 5974 // FIXME: Implement this! 5975 assert(false && "Cannot transform block expressions yet"); 5976 return SemaRef.Owned(E->Retain()); 5977} 5978 5979template<typename Derived> 5980Sema::OwningExprResult 5981TreeTransform<Derived>::TransformBlockDeclRefExpr(BlockDeclRefExpr *E) { 5982 // FIXME: Implement this! 5983 assert(false && "Cannot transform block-related expressions yet"); 5984 return SemaRef.Owned(E->Retain()); 5985} 5986 5987//===----------------------------------------------------------------------===// 5988// Type reconstruction 5989//===----------------------------------------------------------------------===// 5990 5991template<typename Derived> 5992QualType TreeTransform<Derived>::RebuildPointerType(QualType PointeeType, 5993 SourceLocation Star) { 5994 return SemaRef.BuildPointerType(PointeeType, Qualifiers(), Star, 5995 getDerived().getBaseEntity()); 5996} 5997 5998template<typename Derived> 5999QualType TreeTransform<Derived>::RebuildBlockPointerType(QualType PointeeType, 6000 SourceLocation Star) { 6001 return SemaRef.BuildBlockPointerType(PointeeType, Qualifiers(), Star, 6002 getDerived().getBaseEntity()); 6003} 6004 6005template<typename Derived> 6006QualType 6007TreeTransform<Derived>::RebuildReferenceType(QualType ReferentType, 6008 bool WrittenAsLValue, 6009 SourceLocation Sigil) { 6010 return SemaRef.BuildReferenceType(ReferentType, WrittenAsLValue, Qualifiers(), 6011 Sigil, getDerived().getBaseEntity()); 6012} 6013 6014template<typename Derived> 6015QualType 6016TreeTransform<Derived>::RebuildMemberPointerType(QualType PointeeType, 6017 QualType ClassType, 6018 SourceLocation Sigil) { 6019 return SemaRef.BuildMemberPointerType(PointeeType, ClassType, Qualifiers(), 6020 Sigil, getDerived().getBaseEntity()); 6021} 6022 6023template<typename Derived> 6024QualType 6025TreeTransform<Derived>::RebuildArrayType(QualType ElementType, 6026 ArrayType::ArraySizeModifier SizeMod, 6027 const llvm::APInt *Size, 6028 Expr *SizeExpr, 6029 unsigned IndexTypeQuals, 6030 SourceRange BracketsRange) { 6031 if (SizeExpr || !Size) 6032 return SemaRef.BuildArrayType(ElementType, SizeMod, SizeExpr, 6033 IndexTypeQuals, BracketsRange, 6034 getDerived().getBaseEntity()); 6035 6036 QualType Types[] = { 6037 SemaRef.Context.UnsignedCharTy, SemaRef.Context.UnsignedShortTy, 6038 SemaRef.Context.UnsignedIntTy, SemaRef.Context.UnsignedLongTy, 6039 SemaRef.Context.UnsignedLongLongTy, SemaRef.Context.UnsignedInt128Ty 6040 }; 6041 const unsigned NumTypes = sizeof(Types) / sizeof(QualType); 6042 QualType SizeType; 6043 for (unsigned I = 0; I != NumTypes; ++I) 6044 if (Size->getBitWidth() == SemaRef.Context.getIntWidth(Types[I])) { 6045 SizeType = Types[I]; 6046 break; 6047 } 6048 6049 IntegerLiteral ArraySize(*Size, SizeType, /*FIXME*/BracketsRange.getBegin()); 6050 return SemaRef.BuildArrayType(ElementType, SizeMod, &ArraySize, 6051 IndexTypeQuals, BracketsRange, 6052 getDerived().getBaseEntity()); 6053} 6054 6055template<typename Derived> 6056QualType 6057TreeTransform<Derived>::RebuildConstantArrayType(QualType ElementType, 6058 ArrayType::ArraySizeModifier SizeMod, 6059 const llvm::APInt &Size, 6060 unsigned IndexTypeQuals, 6061 SourceRange BracketsRange) { 6062 return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0, 6063 IndexTypeQuals, BracketsRange); 6064} 6065 6066template<typename Derived> 6067QualType 6068TreeTransform<Derived>::RebuildIncompleteArrayType(QualType ElementType, 6069 ArrayType::ArraySizeModifier SizeMod, 6070 unsigned IndexTypeQuals, 6071 SourceRange BracketsRange) { 6072 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 0, 6073 IndexTypeQuals, BracketsRange); 6074} 6075 6076template<typename Derived> 6077QualType 6078TreeTransform<Derived>::RebuildVariableArrayType(QualType ElementType, 6079 ArrayType::ArraySizeModifier SizeMod, 6080 ExprArg SizeExpr, 6081 unsigned IndexTypeQuals, 6082 SourceRange BracketsRange) { 6083 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 6084 SizeExpr.takeAs<Expr>(), 6085 IndexTypeQuals, BracketsRange); 6086} 6087 6088template<typename Derived> 6089QualType 6090TreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType, 6091 ArrayType::ArraySizeModifier SizeMod, 6092 ExprArg SizeExpr, 6093 unsigned IndexTypeQuals, 6094 SourceRange BracketsRange) { 6095 return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 6096 SizeExpr.takeAs<Expr>(), 6097 IndexTypeQuals, BracketsRange); 6098} 6099 6100template<typename Derived> 6101QualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType, 6102 unsigned NumElements, 6103 bool IsAltiVec, bool IsPixel) { 6104 // FIXME: semantic checking! 6105 return SemaRef.Context.getVectorType(ElementType, NumElements, 6106 IsAltiVec, IsPixel); 6107} 6108 6109template<typename Derived> 6110QualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType, 6111 unsigned NumElements, 6112 SourceLocation AttributeLoc) { 6113 llvm::APInt numElements(SemaRef.Context.getIntWidth(SemaRef.Context.IntTy), 6114 NumElements, true); 6115 IntegerLiteral *VectorSize 6116 = new (SemaRef.Context) IntegerLiteral(numElements, SemaRef.Context.IntTy, 6117 AttributeLoc); 6118 return SemaRef.BuildExtVectorType(ElementType, SemaRef.Owned(VectorSize), 6119 AttributeLoc); 6120} 6121 6122template<typename Derived> 6123QualType 6124TreeTransform<Derived>::RebuildDependentSizedExtVectorType(QualType ElementType, 6125 ExprArg SizeExpr, 6126 SourceLocation AttributeLoc) { 6127 return SemaRef.BuildExtVectorType(ElementType, move(SizeExpr), AttributeLoc); 6128} 6129 6130template<typename Derived> 6131QualType TreeTransform<Derived>::RebuildFunctionProtoType(QualType T, 6132 QualType *ParamTypes, 6133 unsigned NumParamTypes, 6134 bool Variadic, 6135 unsigned Quals) { 6136 return SemaRef.BuildFunctionType(T, ParamTypes, NumParamTypes, Variadic, 6137 Quals, 6138 getDerived().getBaseLocation(), 6139 getDerived().getBaseEntity()); 6140} 6141 6142template<typename Derived> 6143QualType TreeTransform<Derived>::RebuildFunctionNoProtoType(QualType T) { 6144 return SemaRef.Context.getFunctionNoProtoType(T); 6145} 6146 6147template<typename Derived> 6148QualType TreeTransform<Derived>::RebuildUnresolvedUsingType(Decl *D) { 6149 assert(D && "no decl found"); 6150 if (D->isInvalidDecl()) return QualType(); 6151 6152 // FIXME: Doesn't account for ObjCInterfaceDecl! 6153 TypeDecl *Ty; 6154 if (isa<UsingDecl>(D)) { 6155 UsingDecl *Using = cast<UsingDecl>(D); 6156 assert(Using->isTypeName() && 6157 "UnresolvedUsingTypenameDecl transformed to non-typename using"); 6158 6159 // A valid resolved using typename decl points to exactly one type decl. 6160 assert(++Using->shadow_begin() == Using->shadow_end()); 6161 Ty = cast<TypeDecl>((*Using->shadow_begin())->getTargetDecl()); 6162 6163 } else { 6164 assert(isa<UnresolvedUsingTypenameDecl>(D) && 6165 "UnresolvedUsingTypenameDecl transformed to non-using decl"); 6166 Ty = cast<UnresolvedUsingTypenameDecl>(D); 6167 } 6168 6169 return SemaRef.Context.getTypeDeclType(Ty); 6170} 6171 6172template<typename Derived> 6173QualType TreeTransform<Derived>::RebuildTypeOfExprType(ExprArg E) { 6174 return SemaRef.BuildTypeofExprType(E.takeAs<Expr>()); 6175} 6176 6177template<typename Derived> 6178QualType TreeTransform<Derived>::RebuildTypeOfType(QualType Underlying) { 6179 return SemaRef.Context.getTypeOfType(Underlying); 6180} 6181 6182template<typename Derived> 6183QualType TreeTransform<Derived>::RebuildDecltypeType(ExprArg E) { 6184 return SemaRef.BuildDecltypeType(E.takeAs<Expr>()); 6185} 6186 6187template<typename Derived> 6188QualType TreeTransform<Derived>::RebuildTemplateSpecializationType( 6189 TemplateName Template, 6190 SourceLocation TemplateNameLoc, 6191 const TemplateArgumentListInfo &TemplateArgs) { 6192 return SemaRef.CheckTemplateIdType(Template, TemplateNameLoc, TemplateArgs); 6193} 6194 6195template<typename Derived> 6196NestedNameSpecifier * 6197TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 6198 SourceRange Range, 6199 IdentifierInfo &II, 6200 QualType ObjectType, 6201 NamedDecl *FirstQualifierInScope) { 6202 CXXScopeSpec SS; 6203 // FIXME: The source location information is all wrong. 6204 SS.setRange(Range); 6205 SS.setScopeRep(Prefix); 6206 return static_cast<NestedNameSpecifier *>( 6207 SemaRef.BuildCXXNestedNameSpecifier(0, SS, Range.getEnd(), 6208 Range.getEnd(), II, 6209 ObjectType, 6210 FirstQualifierInScope, 6211 false, false)); 6212} 6213 6214template<typename Derived> 6215NestedNameSpecifier * 6216TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 6217 SourceRange Range, 6218 NamespaceDecl *NS) { 6219 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, NS); 6220} 6221 6222template<typename Derived> 6223NestedNameSpecifier * 6224TreeTransform<Derived>::RebuildNestedNameSpecifier(NestedNameSpecifier *Prefix, 6225 SourceRange Range, 6226 bool TemplateKW, 6227 QualType T) { 6228 if (T->isDependentType() || T->isRecordType() || 6229 (SemaRef.getLangOptions().CPlusPlus0x && T->isEnumeralType())) { 6230 assert(!T.hasLocalQualifiers() && "Can't get cv-qualifiers here"); 6231 return NestedNameSpecifier::Create(SemaRef.Context, Prefix, TemplateKW, 6232 T.getTypePtr()); 6233 } 6234 6235 SemaRef.Diag(Range.getBegin(), diag::err_nested_name_spec_non_tag) << T; 6236 return 0; 6237} 6238 6239template<typename Derived> 6240TemplateName 6241TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier, 6242 bool TemplateKW, 6243 TemplateDecl *Template) { 6244 return SemaRef.Context.getQualifiedTemplateName(Qualifier, TemplateKW, 6245 Template); 6246} 6247 6248template<typename Derived> 6249TemplateName 6250TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier, 6251 const IdentifierInfo &II, 6252 QualType ObjectType) { 6253 CXXScopeSpec SS; 6254 SS.setRange(SourceRange(getDerived().getBaseLocation())); 6255 SS.setScopeRep(Qualifier); 6256 UnqualifiedId Name; 6257 Name.setIdentifier(&II, /*FIXME:*/getDerived().getBaseLocation()); 6258 return getSema().ActOnDependentTemplateName( 6259 /*FIXME:*/getDerived().getBaseLocation(), 6260 SS, 6261 Name, 6262 ObjectType.getAsOpaquePtr(), 6263 /*EnteringContext=*/false) 6264 .template getAsVal<TemplateName>(); 6265} 6266 6267template<typename Derived> 6268TemplateName 6269TreeTransform<Derived>::RebuildTemplateName(NestedNameSpecifier *Qualifier, 6270 OverloadedOperatorKind Operator, 6271 QualType ObjectType) { 6272 CXXScopeSpec SS; 6273 SS.setRange(SourceRange(getDerived().getBaseLocation())); 6274 SS.setScopeRep(Qualifier); 6275 UnqualifiedId Name; 6276 SourceLocation SymbolLocations[3]; // FIXME: Bogus location information. 6277 Name.setOperatorFunctionId(/*FIXME:*/getDerived().getBaseLocation(), 6278 Operator, SymbolLocations); 6279 return getSema().ActOnDependentTemplateName( 6280 /*FIXME:*/getDerived().getBaseLocation(), 6281 SS, 6282 Name, 6283 ObjectType.getAsOpaquePtr(), 6284 /*EnteringContext=*/false) 6285 .template getAsVal<TemplateName>(); 6286} 6287 6288template<typename Derived> 6289Sema::OwningExprResult 6290TreeTransform<Derived>::RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op, 6291 SourceLocation OpLoc, 6292 ExprArg Callee, 6293 ExprArg First, 6294 ExprArg Second) { 6295 Expr *FirstExpr = (Expr *)First.get(); 6296 Expr *SecondExpr = (Expr *)Second.get(); 6297 Expr *CalleeExpr = ((Expr *)Callee.get())->IgnoreParenCasts(); 6298 bool isPostIncDec = SecondExpr && (Op == OO_PlusPlus || Op == OO_MinusMinus); 6299 6300 // Determine whether this should be a builtin operation. 6301 if (Op == OO_Subscript) { 6302 if (!FirstExpr->getType()->isOverloadableType() && 6303 !SecondExpr->getType()->isOverloadableType()) 6304 return getSema().CreateBuiltinArraySubscriptExpr(move(First), 6305 CalleeExpr->getLocStart(), 6306 move(Second), OpLoc); 6307 } else if (Op == OO_Arrow) { 6308 // -> is never a builtin operation. 6309 return SemaRef.BuildOverloadedArrowExpr(0, move(First), OpLoc); 6310 } else if (SecondExpr == 0 || isPostIncDec) { 6311 if (!FirstExpr->getType()->isOverloadableType()) { 6312 // The argument is not of overloadable type, so try to create a 6313 // built-in unary operation. 6314 UnaryOperator::Opcode Opc 6315 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec); 6316 6317 return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, move(First)); 6318 } 6319 } else { 6320 if (!FirstExpr->getType()->isOverloadableType() && 6321 !SecondExpr->getType()->isOverloadableType()) { 6322 // Neither of the arguments is an overloadable type, so try to 6323 // create a built-in binary operation. 6324 BinaryOperator::Opcode Opc = BinaryOperator::getOverloadedOpcode(Op); 6325 OwningExprResult Result 6326 = SemaRef.CreateBuiltinBinOp(OpLoc, Opc, FirstExpr, SecondExpr); 6327 if (Result.isInvalid()) 6328 return SemaRef.ExprError(); 6329 6330 First.release(); 6331 Second.release(); 6332 return move(Result); 6333 } 6334 } 6335 6336 // Compute the transformed set of functions (and function templates) to be 6337 // used during overload resolution. 6338 UnresolvedSet<16> Functions; 6339 6340 if (UnresolvedLookupExpr *ULE = dyn_cast<UnresolvedLookupExpr>(CalleeExpr)) { 6341 assert(ULE->requiresADL()); 6342 6343 // FIXME: Do we have to check 6344 // IsAcceptableNonMemberOperatorCandidate for each of these? 6345 Functions.append(ULE->decls_begin(), ULE->decls_end()); 6346 } else { 6347 Functions.addDecl(cast<DeclRefExpr>(CalleeExpr)->getDecl()); 6348 } 6349 6350 // Add any functions found via argument-dependent lookup. 6351 Expr *Args[2] = { FirstExpr, SecondExpr }; 6352 unsigned NumArgs = 1 + (SecondExpr != 0); 6353 6354 // Create the overloaded operator invocation for unary operators. 6355 if (NumArgs == 1 || isPostIncDec) { 6356 UnaryOperator::Opcode Opc 6357 = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec); 6358 return SemaRef.CreateOverloadedUnaryOp(OpLoc, Opc, Functions, move(First)); 6359 } 6360 6361 if (Op == OO_Subscript) 6362 return SemaRef.CreateOverloadedArraySubscriptExpr(CalleeExpr->getLocStart(), 6363 OpLoc, 6364 move(First), 6365 move(Second)); 6366 6367 // Create the overloaded operator invocation for binary operators. 6368 BinaryOperator::Opcode Opc = 6369 BinaryOperator::getOverloadedOpcode(Op); 6370 OwningExprResult Result 6371 = SemaRef.CreateOverloadedBinOp(OpLoc, Opc, Functions, Args[0], Args[1]); 6372 if (Result.isInvalid()) 6373 return SemaRef.ExprError(); 6374 6375 First.release(); 6376 Second.release(); 6377 return move(Result); 6378} 6379 6380template<typename Derived> 6381Sema::OwningExprResult 6382TreeTransform<Derived>::RebuildCXXPseudoDestructorExpr(ExprArg Base, 6383 SourceLocation OperatorLoc, 6384 bool isArrow, 6385 NestedNameSpecifier *Qualifier, 6386 SourceRange QualifierRange, 6387 TypeSourceInfo *ScopeType, 6388 SourceLocation CCLoc, 6389 SourceLocation TildeLoc, 6390 PseudoDestructorTypeStorage Destroyed) { 6391 CXXScopeSpec SS; 6392 if (Qualifier) { 6393 SS.setRange(QualifierRange); 6394 SS.setScopeRep(Qualifier); 6395 } 6396 6397 Expr *BaseE = (Expr *)Base.get(); 6398 QualType BaseType = BaseE->getType(); 6399 if (BaseE->isTypeDependent() || Destroyed.getIdentifier() || 6400 (!isArrow && !BaseType->getAs<RecordType>()) || 6401 (isArrow && BaseType->getAs<PointerType>() && 6402 !BaseType->getAs<PointerType>()->getPointeeType() 6403 ->template getAs<RecordType>())){ 6404 // This pseudo-destructor expression is still a pseudo-destructor. 6405 return SemaRef.BuildPseudoDestructorExpr(move(Base), OperatorLoc, 6406 isArrow? tok::arrow : tok::period, 6407 SS, ScopeType, CCLoc, TildeLoc, 6408 Destroyed, 6409 /*FIXME?*/true); 6410 } 6411 6412 TypeSourceInfo *DestroyedType = Destroyed.getTypeSourceInfo(); 6413 DeclarationName Name 6414 = SemaRef.Context.DeclarationNames.getCXXDestructorName( 6415 SemaRef.Context.getCanonicalType(DestroyedType->getType())); 6416 6417 // FIXME: the ScopeType should be tacked onto SS. 6418 6419 return getSema().BuildMemberReferenceExpr(move(Base), BaseType, 6420 OperatorLoc, isArrow, 6421 SS, /*FIXME: FirstQualifier*/ 0, 6422 Name, Destroyed.getLocation(), 6423 /*TemplateArgs*/ 0); 6424} 6425 6426} // end namespace clang 6427 6428#endif // LLVM_CLANG_SEMA_TREETRANSFORM_H 6429