1218893Sdim//===------- TreeTransform.h - Semantic Tree Transformation -----*- C++ -*-===// 2198092Srdivacky// 3198092Srdivacky// The LLVM Compiler Infrastructure 4198092Srdivacky// 5198092Srdivacky// This file is distributed under the University of Illinois Open Source 6198092Srdivacky// License. See LICENSE.TXT for details. 7218893Sdim//===----------------------------------------------------------------------===// 8198092Srdivacky// 9198092Srdivacky// This file implements a semantic tree transformation that takes a given 10198092Srdivacky// AST and rebuilds it, possibly transforming some nodes in the process. 11198092Srdivacky// 12218893Sdim//===----------------------------------------------------------------------===// 13218893Sdim 14198092Srdivacky#ifndef LLVM_CLANG_SEMA_TREETRANSFORM_H 15198092Srdivacky#define LLVM_CLANG_SEMA_TREETRANSFORM_H 16198092Srdivacky 17249423Sdim#include "TypeLocBuilder.h" 18198092Srdivacky#include "clang/AST/Decl.h" 19212904Sdim#include "clang/AST/DeclObjC.h" 20223017Sdim#include "clang/AST/DeclTemplate.h" 21198092Srdivacky#include "clang/AST/Expr.h" 22198092Srdivacky#include "clang/AST/ExprCXX.h" 23198092Srdivacky#include "clang/AST/ExprObjC.h" 24198092Srdivacky#include "clang/AST/Stmt.h" 25198092Srdivacky#include "clang/AST/StmtCXX.h" 26198092Srdivacky#include "clang/AST/StmtObjC.h" 27249423Sdim#include "clang/Lex/Preprocessor.h" 28249423Sdim#include "clang/Sema/Designator.h" 29249423Sdim#include "clang/Sema/Lookup.h" 30212904Sdim#include "clang/Sema/Ownership.h" 31249423Sdim#include "clang/Sema/ParsedTemplate.h" 32249423Sdim#include "clang/Sema/ScopeInfo.h" 33249423Sdim#include "clang/Sema/SemaDiagnostic.h" 34249423Sdim#include "clang/Sema/SemaInternal.h" 35226633Sdim#include "llvm/ADT/ArrayRef.h" 36198398Srdivacky#include "llvm/Support/ErrorHandling.h" 37198092Srdivacky#include <algorithm> 38198092Srdivacky 39198092Srdivackynamespace clang { 40212904Sdimusing namespace sema; 41198092Srdivacky 42198092Srdivacky/// \brief A semantic tree transformation that allows one to transform one 43198092Srdivacky/// abstract syntax tree into another. 44198092Srdivacky/// 45198092Srdivacky/// A new tree transformation is defined by creating a new subclass \c X of 46198092Srdivacky/// \c TreeTransform<X> and then overriding certain operations to provide 47198092Srdivacky/// behavior specific to that transformation. For example, template 48198092Srdivacky/// instantiation is implemented as a tree transformation where the 49198092Srdivacky/// transformation of TemplateTypeParmType nodes involves substituting the 50198092Srdivacky/// template arguments for their corresponding template parameters; a similar 51198092Srdivacky/// transformation is performed for non-type template parameters and 52198092Srdivacky/// template template parameters. 53198092Srdivacky/// 54198092Srdivacky/// This tree-transformation template uses static polymorphism to allow 55198092Srdivacky/// subclasses to customize any of its operations. Thus, a subclass can 56198092Srdivacky/// override any of the transformation or rebuild operators by providing an 57198092Srdivacky/// operation with the same signature as the default implementation. The 58198092Srdivacky/// overridding function should not be virtual. 59198092Srdivacky/// 60198092Srdivacky/// Semantic tree transformations are split into two stages, either of which 61198092Srdivacky/// can be replaced by a subclass. The "transform" step transforms an AST node 62198092Srdivacky/// or the parts of an AST node using the various transformation functions, 63198092Srdivacky/// then passes the pieces on to the "rebuild" step, which constructs a new AST 64198092Srdivacky/// node of the appropriate kind from the pieces. The default transformation 65198092Srdivacky/// routines recursively transform the operands to composite AST nodes (e.g., 66198092Srdivacky/// the pointee type of a PointerType node) and, if any of those operand nodes 67198092Srdivacky/// were changed by the transformation, invokes the rebuild operation to create 68198092Srdivacky/// a new AST node. 69198092Srdivacky/// 70198092Srdivacky/// Subclasses can customize the transformation at various levels. The 71198092Srdivacky/// most coarse-grained transformations involve replacing TransformType(), 72221345Sdim/// TransformExpr(), TransformDecl(), TransformNestedNameSpecifierLoc(), 73198092Srdivacky/// TransformTemplateName(), or TransformTemplateArgument() with entirely 74198092Srdivacky/// new implementations. 75198092Srdivacky/// 76198092Srdivacky/// For more fine-grained transformations, subclasses can replace any of the 77198092Srdivacky/// \c TransformXXX functions (where XXX is the name of an AST node, e.g., 78198092Srdivacky/// PointerType, StmtExpr) to alter the transformation. As mentioned previously, 79198092Srdivacky/// replacing TransformTemplateTypeParmType() allows template instantiation 80198092Srdivacky/// to substitute template arguments for their corresponding template 81198092Srdivacky/// parameters. Additionally, subclasses can override the \c RebuildXXX 82198092Srdivacky/// functions to control how AST nodes are rebuilt when their operands change. 83198092Srdivacky/// By default, \c TreeTransform will invoke semantic analysis to rebuild 84198092Srdivacky/// AST nodes. However, certain other tree transformations (e.g, cloning) may 85198092Srdivacky/// be able to use more efficient rebuild steps. 86198092Srdivacky/// 87198092Srdivacky/// There are a handful of other functions that can be overridden, allowing one 88198092Srdivacky/// to avoid traversing nodes that don't need any transformation 89198092Srdivacky/// (\c AlreadyTransformed()), force rebuilding AST nodes even when their 90198092Srdivacky/// operands have not changed (\c AlwaysRebuild()), and customize the 91198092Srdivacky/// default locations and entity names used for type-checking 92198092Srdivacky/// (\c getBaseLocation(), \c getBaseEntity()). 93198092Srdivackytemplate<typename Derived> 94198092Srdivackyclass TreeTransform { 95218893Sdim /// \brief Private RAII object that helps us forget and then re-remember 96218893Sdim /// the template argument corresponding to a partially-substituted parameter 97218893Sdim /// pack. 98218893Sdim class ForgetPartiallySubstitutedPackRAII { 99218893Sdim Derived &Self; 100218893Sdim TemplateArgument Old; 101239462Sdim 102218893Sdim public: 103218893Sdim ForgetPartiallySubstitutedPackRAII(Derived &Self) : Self(Self) { 104218893Sdim Old = Self.ForgetPartiallySubstitutedPack(); 105218893Sdim } 106239462Sdim 107218893Sdim ~ForgetPartiallySubstitutedPackRAII() { 108218893Sdim Self.RememberPartiallySubstitutedPack(Old); 109218893Sdim } 110218893Sdim }; 111239462Sdim 112198092Srdivackyprotected: 113198092Srdivacky Sema &SemaRef; 114239462Sdim 115234353Sdim /// \brief The set of local declarations that have been transformed, for 116234353Sdim /// cases where we are forced to build new declarations within the transformer 117234353Sdim /// rather than in the subclass (e.g., lambda closure types). 118234353Sdim llvm::DenseMap<Decl *, Decl *> TransformedLocalDecls; 119239462Sdim 120198092Srdivackypublic: 121198092Srdivacky /// \brief Initializes a new tree transformer. 122198092Srdivacky TreeTransform(Sema &SemaRef) : SemaRef(SemaRef) { } 123198092Srdivacky 124198092Srdivacky /// \brief Retrieves a reference to the derived class. 125198092Srdivacky Derived &getDerived() { return static_cast<Derived&>(*this); } 126198092Srdivacky 127198092Srdivacky /// \brief Retrieves a reference to the derived class. 128198092Srdivacky const Derived &getDerived() const { 129198092Srdivacky return static_cast<const Derived&>(*this); 130198092Srdivacky } 131198092Srdivacky 132212904Sdim static inline ExprResult Owned(Expr *E) { return E; } 133212904Sdim static inline StmtResult Owned(Stmt *S) { return S; } 134212904Sdim 135198092Srdivacky /// \brief Retrieves a reference to the semantic analysis object used for 136198092Srdivacky /// this tree transform. 137198092Srdivacky Sema &getSema() const { return SemaRef; } 138198092Srdivacky 139198092Srdivacky /// \brief Whether the transformation should always rebuild AST nodes, even 140198092Srdivacky /// if none of the children have changed. 141198092Srdivacky /// 142198092Srdivacky /// Subclasses may override this function to specify when the transformation 143198092Srdivacky /// should rebuild all AST nodes. 144198092Srdivacky bool AlwaysRebuild() { return false; } 145198092Srdivacky 146198092Srdivacky /// \brief Returns the location of the entity being transformed, if that 147198092Srdivacky /// information was not available elsewhere in the AST. 148198092Srdivacky /// 149198092Srdivacky /// By default, returns no source-location information. Subclasses can 150198092Srdivacky /// provide an alternative implementation that provides better location 151198092Srdivacky /// information. 152198092Srdivacky SourceLocation getBaseLocation() { return SourceLocation(); } 153198092Srdivacky 154198092Srdivacky /// \brief Returns the name of the entity being transformed, if that 155198092Srdivacky /// information was not available elsewhere in the AST. 156198092Srdivacky /// 157198092Srdivacky /// By default, returns an empty name. Subclasses can provide an alternative 158198092Srdivacky /// implementation with a more precise name. 159198092Srdivacky DeclarationName getBaseEntity() { return DeclarationName(); } 160198092Srdivacky 161198092Srdivacky /// \brief Sets the "base" location and entity when that 162198092Srdivacky /// information is known based on another transformation. 163198092Srdivacky /// 164198092Srdivacky /// By default, the source location and entity are ignored. Subclasses can 165198092Srdivacky /// override this function to provide a customized implementation. 166198092Srdivacky void setBase(SourceLocation Loc, DeclarationName Entity) { } 167198092Srdivacky 168198092Srdivacky /// \brief RAII object that temporarily sets the base location and entity 169198092Srdivacky /// used for reporting diagnostics in types. 170198092Srdivacky class TemporaryBase { 171198092Srdivacky TreeTransform &Self; 172198092Srdivacky SourceLocation OldLocation; 173198092Srdivacky DeclarationName OldEntity; 174198092Srdivacky 175198092Srdivacky public: 176198092Srdivacky TemporaryBase(TreeTransform &Self, SourceLocation Location, 177198092Srdivacky DeclarationName Entity) : Self(Self) { 178198092Srdivacky OldLocation = Self.getDerived().getBaseLocation(); 179198092Srdivacky OldEntity = Self.getDerived().getBaseEntity(); 180239462Sdim 181218893Sdim if (Location.isValid()) 182218893Sdim Self.getDerived().setBase(Location, Entity); 183198092Srdivacky } 184198092Srdivacky 185198092Srdivacky ~TemporaryBase() { 186198092Srdivacky Self.getDerived().setBase(OldLocation, OldEntity); 187198092Srdivacky } 188198092Srdivacky }; 189198092Srdivacky 190198092Srdivacky /// \brief Determine whether the given type \p T has already been 191198092Srdivacky /// transformed. 192198092Srdivacky /// 193198092Srdivacky /// Subclasses can provide an alternative implementation of this routine 194198092Srdivacky /// to short-circuit evaluation when it is known that a given type will 195198092Srdivacky /// not change. For example, template instantiation need not traverse 196198092Srdivacky /// non-dependent types. 197198092Srdivacky bool AlreadyTransformed(QualType T) { 198198092Srdivacky return T.isNull(); 199198092Srdivacky } 200198092Srdivacky 201200583Srdivacky /// \brief Determine whether the given call argument should be dropped, e.g., 202200583Srdivacky /// because it is a default argument. 203200583Srdivacky /// 204200583Srdivacky /// Subclasses can provide an alternative implementation of this routine to 205200583Srdivacky /// determine which kinds of call arguments get dropped. By default, 206200583Srdivacky /// CXXDefaultArgument nodes are dropped (prior to transformation). 207200583Srdivacky bool DropCallArgument(Expr *E) { 208200583Srdivacky return E->isDefaultArgument(); 209200583Srdivacky } 210239462Sdim 211218893Sdim /// \brief Determine whether we should expand a pack expansion with the 212218893Sdim /// given set of parameter packs into separate arguments by repeatedly 213218893Sdim /// transforming the pattern. 214218893Sdim /// 215218893Sdim /// By default, the transformer never tries to expand pack expansions. 216218893Sdim /// Subclasses can override this routine to provide different behavior. 217218893Sdim /// 218218893Sdim /// \param EllipsisLoc The location of the ellipsis that identifies the 219218893Sdim /// pack expansion. 220218893Sdim /// 221218893Sdim /// \param PatternRange The source range that covers the entire pattern of 222218893Sdim /// the pack expansion. 223218893Sdim /// 224239462Sdim /// \param Unexpanded The set of unexpanded parameter packs within the 225218893Sdim /// pattern. 226218893Sdim /// 227218893Sdim /// \param ShouldExpand Will be set to \c true if the transformer should 228218893Sdim /// expand the corresponding pack expansions into separate arguments. When 229218893Sdim /// set, \c NumExpansions must also be set. 230218893Sdim /// 231218893Sdim /// \param RetainExpansion Whether the caller should add an unexpanded 232218893Sdim /// pack expansion after all of the expanded arguments. This is used 233218893Sdim /// when extending explicitly-specified template argument packs per 234218893Sdim /// C++0x [temp.arg.explicit]p9. 235218893Sdim /// 236218893Sdim /// \param NumExpansions The number of separate arguments that will be in 237218893Sdim /// the expanded form of the corresponding pack expansion. This is both an 238218893Sdim /// input and an output parameter, which can be set by the caller if the 239218893Sdim /// number of expansions is known a priori (e.g., due to a prior substitution) 240218893Sdim /// and will be set by the callee when the number of expansions is known. 241218893Sdim /// The callee must set this value when \c ShouldExpand is \c true; it may 242218893Sdim /// set this value in other cases. 243218893Sdim /// 244239462Sdim /// \returns true if an error occurred (e.g., because the parameter packs 245239462Sdim /// are to be instantiated with arguments of different lengths), false 246239462Sdim /// otherwise. If false, \c ShouldExpand (and possibly \c NumExpansions) 247218893Sdim /// must be set. 248218893Sdim bool TryExpandParameterPacks(SourceLocation EllipsisLoc, 249218893Sdim SourceRange PatternRange, 250249423Sdim ArrayRef<UnexpandedParameterPack> Unexpanded, 251218893Sdim bool &ShouldExpand, 252218893Sdim bool &RetainExpansion, 253249423Sdim Optional<unsigned> &NumExpansions) { 254218893Sdim ShouldExpand = false; 255218893Sdim return false; 256218893Sdim } 257239462Sdim 258218893Sdim /// \brief "Forget" about the partially-substituted pack template argument, 259218893Sdim /// when performing an instantiation that must preserve the parameter pack 260218893Sdim /// use. 261218893Sdim /// 262218893Sdim /// This routine is meant to be overridden by the template instantiator. 263218893Sdim TemplateArgument ForgetPartiallySubstitutedPack() { 264218893Sdim return TemplateArgument(); 265218893Sdim } 266239462Sdim 267218893Sdim /// \brief "Remember" the partially-substituted pack template argument 268218893Sdim /// after performing an instantiation that must preserve the parameter pack 269218893Sdim /// use. 270218893Sdim /// 271218893Sdim /// This routine is meant to be overridden by the template instantiator. 272218893Sdim void RememberPartiallySubstitutedPack(TemplateArgument Arg) { } 273239462Sdim 274218893Sdim /// \brief Note to the derived class when a function parameter pack is 275218893Sdim /// being expanded. 276218893Sdim void ExpandingFunctionParameterPack(ParmVarDecl *Pack) { } 277239462Sdim 278198092Srdivacky /// \brief Transforms the given type into another type. 279198092Srdivacky /// 280198398Srdivacky /// By default, this routine transforms a type by creating a 281200583Srdivacky /// TypeSourceInfo for it and delegating to the appropriate 282198398Srdivacky /// function. This is expensive, but we don't mind, because 283198398Srdivacky /// this method is deprecated anyway; all users should be 284200583Srdivacky /// switched to storing TypeSourceInfos. 285198092Srdivacky /// 286198092Srdivacky /// \returns the transformed type. 287218893Sdim QualType TransformType(QualType T); 288198092Srdivacky 289198398Srdivacky /// \brief Transforms the given type-with-location into a new 290198398Srdivacky /// type-with-location. 291198092Srdivacky /// 292198398Srdivacky /// By default, this routine transforms a type by delegating to the 293198398Srdivacky /// appropriate TransformXXXType to build a new type. Subclasses 294198398Srdivacky /// may override this function (to take over all type 295198398Srdivacky /// transformations) or some set of the TransformXXXType functions 296198398Srdivacky /// to alter the transformation. 297218893Sdim TypeSourceInfo *TransformType(TypeSourceInfo *DI); 298198092Srdivacky 299198398Srdivacky /// \brief Transform the given type-with-location into a new 300198398Srdivacky /// type, collecting location information in the given builder 301198398Srdivacky /// as necessary. 302198398Srdivacky /// 303218893Sdim QualType TransformType(TypeLocBuilder &TLB, TypeLoc TL); 304198398Srdivacky 305198092Srdivacky /// \brief Transform the given statement. 306198092Srdivacky /// 307198092Srdivacky /// By default, this routine transforms a statement by delegating to the 308198092Srdivacky /// appropriate TransformXXXStmt function to transform a specific kind of 309198092Srdivacky /// statement or the TransformExpr() function to transform an expression. 310198092Srdivacky /// Subclasses may override this function to transform statements using some 311198092Srdivacky /// other mechanism. 312198092Srdivacky /// 313198092Srdivacky /// \returns the transformed statement. 314212904Sdim StmtResult TransformStmt(Stmt *S); 315198092Srdivacky 316198092Srdivacky /// \brief Transform the given expression. 317198092Srdivacky /// 318198092Srdivacky /// By default, this routine transforms an expression by delegating to the 319198092Srdivacky /// appropriate TransformXXXExpr function to build a new expression. 320198092Srdivacky /// Subclasses may override this function to transform expressions using some 321198092Srdivacky /// other mechanism. 322198092Srdivacky /// 323198092Srdivacky /// \returns the transformed expression. 324212904Sdim ExprResult TransformExpr(Expr *E); 325198092Srdivacky 326249423Sdim /// \brief Transform the given initializer. 327249423Sdim /// 328249423Sdim /// By default, this routine transforms an initializer by stripping off the 329249423Sdim /// semantic nodes added by initialization, then passing the result to 330249423Sdim /// TransformExpr or TransformExprs. 331249423Sdim /// 332249423Sdim /// \returns the transformed initializer. 333249423Sdim ExprResult TransformInitializer(Expr *Init, bool CXXDirectInit); 334249423Sdim 335218893Sdim /// \brief Transform the given list of expressions. 336218893Sdim /// 337239462Sdim /// This routine transforms a list of expressions by invoking 338239462Sdim /// \c TransformExpr() for each subexpression. However, it also provides 339218893Sdim /// support for variadic templates by expanding any pack expansions (if the 340218893Sdim /// derived class permits such expansion) along the way. When pack expansions 341218893Sdim /// are present, the number of outputs may not equal the number of inputs. 342218893Sdim /// 343218893Sdim /// \param Inputs The set of expressions to be transformed. 344218893Sdim /// 345218893Sdim /// \param NumInputs The number of expressions in \c Inputs. 346218893Sdim /// 347218893Sdim /// \param IsCall If \c true, then this transform is being performed on 348239462Sdim /// function-call arguments, and any arguments that should be dropped, will 349218893Sdim /// be. 350218893Sdim /// 351218893Sdim /// \param Outputs The transformed input expressions will be added to this 352218893Sdim /// vector. 353218893Sdim /// 354218893Sdim /// \param ArgChanged If non-NULL, will be set \c true if any argument changed 355218893Sdim /// due to transformation. 356218893Sdim /// 357218893Sdim /// \returns true if an error occurred, false otherwise. 358218893Sdim bool TransformExprs(Expr **Inputs, unsigned NumInputs, bool IsCall, 359226633Sdim SmallVectorImpl<Expr *> &Outputs, 360218893Sdim bool *ArgChanged = 0); 361239462Sdim 362198092Srdivacky /// \brief Transform the given declaration, which is referenced from a type 363198092Srdivacky /// or expression. 364198092Srdivacky /// 365234353Sdim /// By default, acts as the identity function on declarations, unless the 366234353Sdim /// transformer has had to transform the declaration itself. Subclasses 367198092Srdivacky /// may override this function to provide alternate behavior. 368239462Sdim Decl *TransformDecl(SourceLocation Loc, Decl *D) { 369234353Sdim llvm::DenseMap<Decl *, Decl *>::iterator Known 370234353Sdim = TransformedLocalDecls.find(D); 371234353Sdim if (Known != TransformedLocalDecls.end()) 372234353Sdim return Known->second; 373239462Sdim 374239462Sdim return D; 375234353Sdim } 376198092Srdivacky 377239462Sdim /// \brief Transform the attributes associated with the given declaration and 378234353Sdim /// place them on the new declaration. 379234353Sdim /// 380234353Sdim /// By default, this operation does nothing. Subclasses may override this 381234353Sdim /// behavior to transform attributes. 382234353Sdim void transformAttrs(Decl *Old, Decl *New) { } 383239462Sdim 384234353Sdim /// \brief Note that a local declaration has been transformed by this 385234353Sdim /// transformer. 386234353Sdim /// 387239462Sdim /// Local declarations are typically transformed via a call to 388234353Sdim /// TransformDefinition. However, in some cases (e.g., lambda expressions), 389234353Sdim /// the transformer itself has to transform the declarations. This routine 390234353Sdim /// can be overridden by a subclass that keeps track of such mappings. 391234353Sdim void transformedLocalDecl(Decl *Old, Decl *New) { 392234353Sdim TransformedLocalDecls[Old] = New; 393234353Sdim } 394239462Sdim 395198092Srdivacky /// \brief Transform the definition of the given declaration. 396198092Srdivacky /// 397198092Srdivacky /// By default, invokes TransformDecl() to transform the declaration. 398198092Srdivacky /// Subclasses may override this function to provide alternate behavior. 399239462Sdim Decl *TransformDefinition(SourceLocation Loc, Decl *D) { 400239462Sdim return getDerived().TransformDecl(Loc, D); 401204643Srdivacky } 402198092Srdivacky 403198398Srdivacky /// \brief Transform the given declaration, which was the first part of a 404198398Srdivacky /// nested-name-specifier in a member access expression. 405198398Srdivacky /// 406239462Sdim /// This specific declaration transformation only applies to the first 407198398Srdivacky /// identifier in a nested-name-specifier of a member access expression, e.g., 408198398Srdivacky /// the \c T in \c x->T::member 409198398Srdivacky /// 410198398Srdivacky /// By default, invokes TransformDecl() to transform the declaration. 411198398Srdivacky /// Subclasses may override this function to provide alternate behavior. 412239462Sdim NamedDecl *TransformFirstQualifierInScope(NamedDecl *D, SourceLocation Loc) { 413239462Sdim return cast_or_null<NamedDecl>(getDerived().TransformDecl(Loc, D)); 414198398Srdivacky } 415239462Sdim 416219077Sdim /// \brief Transform the given nested-name-specifier with source-location 417219077Sdim /// information. 418219077Sdim /// 419219077Sdim /// By default, transforms all of the types and declarations within the 420219077Sdim /// nested-name-specifier. Subclasses may override this function to provide 421219077Sdim /// alternate behavior. 422219077Sdim NestedNameSpecifierLoc TransformNestedNameSpecifierLoc( 423219077Sdim NestedNameSpecifierLoc NNS, 424219077Sdim QualType ObjectType = QualType(), 425219077Sdim NamedDecl *FirstQualifierInScope = 0); 426219077Sdim 427198092Srdivacky /// \brief Transform the given declaration name. 428198092Srdivacky /// 429198092Srdivacky /// By default, transforms the types of conversion function, constructor, 430198092Srdivacky /// and destructor names and then (if needed) rebuilds the declaration name. 431198092Srdivacky /// Identifiers and selectors are returned unmodified. Sublcasses may 432198092Srdivacky /// override this function to provide alternate behavior. 433212904Sdim DeclarationNameInfo 434218893Sdim TransformDeclarationNameInfo(const DeclarationNameInfo &NameInfo); 435198092Srdivacky 436198092Srdivacky /// \brief Transform the given template name. 437198092Srdivacky /// 438221345Sdim /// \param SS The nested-name-specifier that qualifies the template 439221345Sdim /// name. This nested-name-specifier must already have been transformed. 440221345Sdim /// 441221345Sdim /// \param Name The template name to transform. 442221345Sdim /// 443221345Sdim /// \param NameLoc The source location of the template name. 444221345Sdim /// 445239462Sdim /// \param ObjectType If we're translating a template name within a member 446221345Sdim /// access expression, this is the type of the object whose member template 447221345Sdim /// is being referenced. 448221345Sdim /// 449221345Sdim /// \param FirstQualifierInScope If the first part of a nested-name-specifier 450221345Sdim /// also refers to a name within the current (lexical) scope, this is the 451221345Sdim /// declaration it refers to. 452221345Sdim /// 453198092Srdivacky /// By default, transforms the template name by transforming the declarations 454198092Srdivacky /// and nested-name-specifiers that occur within the template name. 455198092Srdivacky /// Subclasses may override this function to provide alternate behavior. 456221345Sdim TemplateName TransformTemplateName(CXXScopeSpec &SS, 457221345Sdim TemplateName Name, 458234353Sdim SourceLocation NameLoc, 459218893Sdim QualType ObjectType = QualType(), 460218893Sdim NamedDecl *FirstQualifierInScope = 0); 461198092Srdivacky 462198092Srdivacky /// \brief Transform the given template argument. 463198092Srdivacky /// 464198092Srdivacky /// By default, this operation transforms the type, expression, or 465198092Srdivacky /// declaration stored within the template argument and constructs a 466198092Srdivacky /// new template argument from the transformed result. Subclasses may 467198092Srdivacky /// override this function to provide alternate behavior. 468198893Srdivacky /// 469198893Srdivacky /// Returns true if there was an error. 470198893Srdivacky bool TransformTemplateArgument(const TemplateArgumentLoc &Input, 471198893Srdivacky TemplateArgumentLoc &Output); 472198092Srdivacky 473218893Sdim /// \brief Transform the given set of template arguments. 474218893Sdim /// 475239462Sdim /// By default, this operation transforms all of the template arguments 476218893Sdim /// in the input set using \c TransformTemplateArgument(), and appends 477218893Sdim /// the transformed arguments to the output list. 478218893Sdim /// 479218893Sdim /// Note that this overload of \c TransformTemplateArguments() is merely 480218893Sdim /// a convenience function. Subclasses that wish to override this behavior 481218893Sdim /// should override the iterator-based member template version. 482218893Sdim /// 483218893Sdim /// \param Inputs The set of template arguments to be transformed. 484218893Sdim /// 485218893Sdim /// \param NumInputs The number of template arguments in \p Inputs. 486218893Sdim /// 487218893Sdim /// \param Outputs The set of transformed template arguments output by this 488218893Sdim /// routine. 489218893Sdim /// 490218893Sdim /// Returns true if an error occurred. 491218893Sdim bool TransformTemplateArguments(const TemplateArgumentLoc *Inputs, 492218893Sdim unsigned NumInputs, 493218893Sdim TemplateArgumentListInfo &Outputs) { 494218893Sdim return TransformTemplateArguments(Inputs, Inputs + NumInputs, Outputs); 495218893Sdim } 496218893Sdim 497218893Sdim /// \brief Transform the given set of template arguments. 498218893Sdim /// 499239462Sdim /// By default, this operation transforms all of the template arguments 500218893Sdim /// in the input set using \c TransformTemplateArgument(), and appends 501239462Sdim /// the transformed arguments to the output list. 502218893Sdim /// 503218893Sdim /// \param First An iterator to the first template argument. 504218893Sdim /// 505218893Sdim /// \param Last An iterator one step past the last template argument. 506218893Sdim /// 507218893Sdim /// \param Outputs The set of transformed template arguments output by this 508218893Sdim /// routine. 509218893Sdim /// 510218893Sdim /// Returns true if an error occurred. 511218893Sdim template<typename InputIterator> 512218893Sdim bool TransformTemplateArguments(InputIterator First, 513218893Sdim InputIterator Last, 514218893Sdim TemplateArgumentListInfo &Outputs); 515218893Sdim 516198893Srdivacky /// \brief Fakes up a TemplateArgumentLoc for a given TemplateArgument. 517198893Srdivacky void InventTemplateArgumentLoc(const TemplateArgument &Arg, 518198893Srdivacky TemplateArgumentLoc &ArgLoc); 519198893Srdivacky 520200583Srdivacky /// \brief Fakes up a TypeSourceInfo for a type. 521200583Srdivacky TypeSourceInfo *InventTypeSourceInfo(QualType T) { 522200583Srdivacky return SemaRef.Context.getTrivialTypeSourceInfo(T, 523198893Srdivacky getDerived().getBaseLocation()); 524198893Srdivacky } 525198893Srdivacky 526198398Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 527198398Srdivacky#define TYPELOC(CLASS, PARENT) \ 528218893Sdim QualType Transform##CLASS##Type(TypeLocBuilder &TLB, CLASS##TypeLoc T); 529198398Srdivacky#include "clang/AST/TypeLocNodes.def" 530198092Srdivacky 531234982Sdim QualType TransformFunctionProtoType(TypeLocBuilder &TLB, 532234982Sdim FunctionProtoTypeLoc TL, 533234982Sdim CXXRecordDecl *ThisContext, 534234982Sdim unsigned ThisTypeQuals); 535234982Sdim 536221345Sdim StmtResult 537221345Sdim TransformSEHHandler(Stmt *Handler); 538221345Sdim 539239462Sdim QualType 540218893Sdim TransformTemplateSpecializationType(TypeLocBuilder &TLB, 541218893Sdim TemplateSpecializationTypeLoc TL, 542218893Sdim TemplateName Template); 543218893Sdim 544239462Sdim QualType 545218893Sdim TransformDependentTemplateSpecializationType(TypeLocBuilder &TLB, 546218893Sdim DependentTemplateSpecializationTypeLoc TL, 547221345Sdim TemplateName Template, 548221345Sdim CXXScopeSpec &SS); 549218893Sdim 550239462Sdim QualType 551221345Sdim TransformDependentTemplateSpecializationType(TypeLocBuilder &TLB, 552221345Sdim DependentTemplateSpecializationTypeLoc TL, 553221345Sdim NestedNameSpecifierLoc QualifierLoc); 554221345Sdim 555205219Srdivacky /// \brief Transforms the parameters of a function type into the 556205219Srdivacky /// given vectors. 557205219Srdivacky /// 558205219Srdivacky /// The result vectors should be kept in sync; null entries in the 559205219Srdivacky /// variables vector are acceptable. 560205219Srdivacky /// 561205219Srdivacky /// Return true on error. 562218893Sdim bool TransformFunctionTypeParams(SourceLocation Loc, 563218893Sdim ParmVarDecl **Params, unsigned NumParams, 564218893Sdim const QualType *ParamTypes, 565226633Sdim SmallVectorImpl<QualType> &PTypes, 566226633Sdim SmallVectorImpl<ParmVarDecl*> *PVars); 567205219Srdivacky 568205219Srdivacky /// \brief Transforms a single function-type parameter. Return null 569205219Srdivacky /// on error. 570221345Sdim /// 571221345Sdim /// \param indexAdjustment - A number to add to the parameter's 572221345Sdim /// scope index; can be negative 573218893Sdim ParmVarDecl *TransformFunctionTypeParam(ParmVarDecl *OldParm, 574221345Sdim int indexAdjustment, 575249423Sdim Optional<unsigned> NumExpansions, 576234353Sdim bool ExpectParameterPack); 577205219Srdivacky 578218893Sdim QualType TransformReferenceType(TypeLocBuilder &TLB, ReferenceTypeLoc TL); 579198893Srdivacky 580212904Sdim StmtResult TransformCompoundStmt(CompoundStmt *S, bool IsStmtExpr); 581212904Sdim ExprResult TransformCXXNamedCastExpr(CXXNamedCastExpr *E); 582198092Srdivacky 583239462Sdim /// \brief Transform the captures and body of a lambda expression. 584239462Sdim ExprResult TransformLambdaScope(LambdaExpr *E, CXXMethodDecl *CallOperator); 585239462Sdim 586243830Sdim ExprResult TransformAddressOfOperand(Expr *E); 587243830Sdim ExprResult TransformDependentScopeDeclRefExpr(DependentScopeDeclRefExpr *E, 588243830Sdim bool IsAddressOfOperand); 589243830Sdim 590198092Srdivacky#define STMT(Node, Parent) \ 591212904Sdim StmtResult Transform##Node(Node *S); 592198092Srdivacky#define EXPR(Node, Parent) \ 593212904Sdim ExprResult Transform##Node(Node *E); 594208600Srdivacky#define ABSTRACT_STMT(Stmt) 595208600Srdivacky#include "clang/AST/StmtNodes.inc" 596198092Srdivacky 597198092Srdivacky /// \brief Build a new pointer type given its pointee type. 598198092Srdivacky /// 599198092Srdivacky /// By default, performs semantic analysis when building the pointer type. 600198092Srdivacky /// Subclasses may override this routine to provide different behavior. 601198893Srdivacky QualType RebuildPointerType(QualType PointeeType, SourceLocation Sigil); 602198092Srdivacky 603198092Srdivacky /// \brief Build a new block pointer type given its pointee type. 604198092Srdivacky /// 605198092Srdivacky /// By default, performs semantic analysis when building the block pointer 606198092Srdivacky /// type. Subclasses may override this routine to provide different behavior. 607198893Srdivacky QualType RebuildBlockPointerType(QualType PointeeType, SourceLocation Sigil); 608198092Srdivacky 609198893Srdivacky /// \brief Build a new reference type given the type it references. 610198092Srdivacky /// 611198893Srdivacky /// By default, performs semantic analysis when building the 612198893Srdivacky /// reference type. Subclasses may override this routine to provide 613198893Srdivacky /// different behavior. 614198092Srdivacky /// 615198893Srdivacky /// \param LValue whether the type was written with an lvalue sigil 616198893Srdivacky /// or an rvalue sigil. 617198893Srdivacky QualType RebuildReferenceType(QualType ReferentType, 618198893Srdivacky bool LValue, 619198893Srdivacky SourceLocation Sigil); 620198092Srdivacky 621198092Srdivacky /// \brief Build a new member pointer type given the pointee type and the 622198092Srdivacky /// class type it refers into. 623198092Srdivacky /// 624198092Srdivacky /// By default, performs semantic analysis when building the member pointer 625198092Srdivacky /// type. Subclasses may override this routine to provide different behavior. 626198893Srdivacky QualType RebuildMemberPointerType(QualType PointeeType, QualType ClassType, 627198893Srdivacky SourceLocation Sigil); 628198092Srdivacky 629198092Srdivacky /// \brief Build a new array type given the element type, size 630198092Srdivacky /// modifier, size of the array (if known), size expression, and index type 631198092Srdivacky /// qualifiers. 632198092Srdivacky /// 633198092Srdivacky /// By default, performs semantic analysis when building the array type. 634198092Srdivacky /// Subclasses may override this routine to provide different behavior. 635198092Srdivacky /// Also by default, all of the other Rebuild*Array 636198092Srdivacky QualType RebuildArrayType(QualType ElementType, 637198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 638198092Srdivacky const llvm::APInt *Size, 639198092Srdivacky Expr *SizeExpr, 640198092Srdivacky unsigned IndexTypeQuals, 641198092Srdivacky SourceRange BracketsRange); 642198092Srdivacky 643198092Srdivacky /// \brief Build a new constant array type given the element type, size 644198092Srdivacky /// modifier, (known) size of the array, and index type qualifiers. 645198092Srdivacky /// 646198092Srdivacky /// By default, performs semantic analysis when building the array type. 647198092Srdivacky /// Subclasses may override this routine to provide different behavior. 648198092Srdivacky QualType RebuildConstantArrayType(QualType ElementType, 649198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 650198092Srdivacky const llvm::APInt &Size, 651198893Srdivacky unsigned IndexTypeQuals, 652198893Srdivacky SourceRange BracketsRange); 653198092Srdivacky 654198092Srdivacky /// \brief Build a new incomplete array type given the element type, size 655198092Srdivacky /// modifier, and index type qualifiers. 656198092Srdivacky /// 657198092Srdivacky /// By default, performs semantic analysis when building the array type. 658198092Srdivacky /// Subclasses may override this routine to provide different behavior. 659198092Srdivacky QualType RebuildIncompleteArrayType(QualType ElementType, 660198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 661198893Srdivacky unsigned IndexTypeQuals, 662198893Srdivacky SourceRange BracketsRange); 663198092Srdivacky 664198092Srdivacky /// \brief Build a new variable-length array type given the element type, 665198092Srdivacky /// size modifier, size expression, and index type qualifiers. 666198092Srdivacky /// 667198092Srdivacky /// By default, performs semantic analysis when building the array type. 668198092Srdivacky /// Subclasses may override this routine to provide different behavior. 669198092Srdivacky QualType RebuildVariableArrayType(QualType ElementType, 670198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 671212904Sdim Expr *SizeExpr, 672198092Srdivacky unsigned IndexTypeQuals, 673198092Srdivacky SourceRange BracketsRange); 674198092Srdivacky 675198092Srdivacky /// \brief Build a new dependent-sized array type given the element type, 676198092Srdivacky /// size modifier, size expression, and index type qualifiers. 677198092Srdivacky /// 678198092Srdivacky /// By default, performs semantic analysis when building the array type. 679198092Srdivacky /// Subclasses may override this routine to provide different behavior. 680198092Srdivacky QualType RebuildDependentSizedArrayType(QualType ElementType, 681198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 682212904Sdim Expr *SizeExpr, 683198092Srdivacky unsigned IndexTypeQuals, 684198092Srdivacky SourceRange BracketsRange); 685198092Srdivacky 686198092Srdivacky /// \brief Build a new vector type given the element type and 687198092Srdivacky /// number of elements. 688198092Srdivacky /// 689198092Srdivacky /// By default, performs semantic analysis when building the vector type. 690198092Srdivacky /// Subclasses may override this routine to provide different behavior. 691203955Srdivacky QualType RebuildVectorType(QualType ElementType, unsigned NumElements, 692218893Sdim VectorType::VectorKind VecKind); 693198092Srdivacky 694198092Srdivacky /// \brief Build a new extended vector type given the element type and 695198092Srdivacky /// number of elements. 696198092Srdivacky /// 697198092Srdivacky /// By default, performs semantic analysis when building the vector type. 698198092Srdivacky /// Subclasses may override this routine to provide different behavior. 699198092Srdivacky QualType RebuildExtVectorType(QualType ElementType, unsigned NumElements, 700198092Srdivacky SourceLocation AttributeLoc); 701198092Srdivacky 702198092Srdivacky /// \brief Build a new potentially dependently-sized extended vector type 703198092Srdivacky /// given the element type and number of elements. 704198092Srdivacky /// 705198092Srdivacky /// By default, performs semantic analysis when building the vector type. 706198092Srdivacky /// Subclasses may override this routine to provide different behavior. 707198092Srdivacky QualType RebuildDependentSizedExtVectorType(QualType ElementType, 708212904Sdim Expr *SizeExpr, 709198092Srdivacky SourceLocation AttributeLoc); 710198092Srdivacky 711198092Srdivacky /// \brief Build a new function type. 712198092Srdivacky /// 713198092Srdivacky /// By default, performs semantic analysis when building the function type. 714198092Srdivacky /// Subclasses may override this routine to provide different behavior. 715198092Srdivacky QualType RebuildFunctionProtoType(QualType T, 716249423Sdim llvm::MutableArrayRef<QualType> ParamTypes, 717249423Sdim const FunctionProtoType::ExtProtoInfo &EPI); 718198092Srdivacky 719198398Srdivacky /// \brief Build a new unprototyped function type. 720198398Srdivacky QualType RebuildFunctionNoProtoType(QualType ResultType); 721198398Srdivacky 722200583Srdivacky /// \brief Rebuild an unresolved typename type, given the decl that 723200583Srdivacky /// the UnresolvedUsingTypenameDecl was transformed to. 724200583Srdivacky QualType RebuildUnresolvedUsingType(Decl *D); 725200583Srdivacky 726198092Srdivacky /// \brief Build a new typedef type. 727221345Sdim QualType RebuildTypedefType(TypedefNameDecl *Typedef) { 728198092Srdivacky return SemaRef.Context.getTypeDeclType(Typedef); 729198092Srdivacky } 730198092Srdivacky 731198092Srdivacky /// \brief Build a new class/struct/union type. 732198092Srdivacky QualType RebuildRecordType(RecordDecl *Record) { 733198092Srdivacky return SemaRef.Context.getTypeDeclType(Record); 734198092Srdivacky } 735198092Srdivacky 736198092Srdivacky /// \brief Build a new Enum type. 737198092Srdivacky QualType RebuildEnumType(EnumDecl *Enum) { 738198092Srdivacky return SemaRef.Context.getTypeDeclType(Enum); 739198092Srdivacky } 740198092Srdivacky 741198092Srdivacky /// \brief Build a new typeof(expr) type. 742198092Srdivacky /// 743198092Srdivacky /// By default, performs semantic analysis when building the typeof type. 744198092Srdivacky /// Subclasses may override this routine to provide different behavior. 745218893Sdim QualType RebuildTypeOfExprType(Expr *Underlying, SourceLocation Loc); 746198092Srdivacky 747198092Srdivacky /// \brief Build a new typeof(type) type. 748198092Srdivacky /// 749198092Srdivacky /// By default, builds a new TypeOfType with the given underlying type. 750198092Srdivacky QualType RebuildTypeOfType(QualType Underlying); 751198092Srdivacky 752223017Sdim /// \brief Build a new unary transform type. 753223017Sdim QualType RebuildUnaryTransformType(QualType BaseType, 754223017Sdim UnaryTransformType::UTTKind UKind, 755223017Sdim SourceLocation Loc); 756223017Sdim 757251662Sdim /// \brief Build a new C++11 decltype type. 758198092Srdivacky /// 759198092Srdivacky /// By default, performs semantic analysis when building the decltype type. 760198092Srdivacky /// Subclasses may override this routine to provide different behavior. 761218893Sdim QualType RebuildDecltypeType(Expr *Underlying, SourceLocation Loc); 762198092Srdivacky 763251662Sdim /// \brief Build a new C++11 auto type. 764218893Sdim /// 765218893Sdim /// By default, builds a new AutoType with the given deduced type. 766251662Sdim QualType RebuildAutoType(QualType Deduced, bool IsDecltypeAuto) { 767251662Sdim // Note, IsDependent is always false here: we implicitly convert an 'auto' 768251662Sdim // which has been deduced to a dependent type into an undeduced 'auto', so 769251662Sdim // that we'll retry deduction after the transformation. 770251662Sdim return SemaRef.Context.getAutoType(Deduced, IsDecltypeAuto); 771218893Sdim } 772218893Sdim 773198092Srdivacky /// \brief Build a new template specialization type. 774198092Srdivacky /// 775198092Srdivacky /// By default, performs semantic analysis when building the template 776198092Srdivacky /// specialization type. Subclasses may override this routine to provide 777198092Srdivacky /// different behavior. 778198092Srdivacky QualType RebuildTemplateSpecializationType(TemplateName Template, 779198893Srdivacky SourceLocation TemplateLoc, 780221345Sdim TemplateArgumentListInfo &Args); 781198092Srdivacky 782218893Sdim /// \brief Build a new parenthesized type. 783218893Sdim /// 784218893Sdim /// By default, builds a new ParenType type from the inner type. 785218893Sdim /// Subclasses may override this routine to provide different behavior. 786218893Sdim QualType RebuildParenType(QualType InnerType) { 787218893Sdim return SemaRef.Context.getParenType(InnerType); 788218893Sdim } 789218893Sdim 790198092Srdivacky /// \brief Build a new qualified name type. 791198092Srdivacky /// 792208600Srdivacky /// By default, builds a new ElaboratedType type from the keyword, 793208600Srdivacky /// the nested-name-specifier and the named type. 794208600Srdivacky /// Subclasses may override this routine to provide different behavior. 795218893Sdim QualType RebuildElaboratedType(SourceLocation KeywordLoc, 796218893Sdim ElaboratedTypeKeyword Keyword, 797221345Sdim NestedNameSpecifierLoc QualifierLoc, 798221345Sdim QualType Named) { 799239462Sdim return SemaRef.Context.getElaboratedType(Keyword, 800239462Sdim QualifierLoc.getNestedNameSpecifier(), 801221345Sdim Named); 802198092Srdivacky } 803198092Srdivacky 804198092Srdivacky /// \brief Build a new typename type that refers to a template-id. 805198092Srdivacky /// 806208600Srdivacky /// By default, builds a new DependentNameType type from the 807208600Srdivacky /// nested-name-specifier and the given type. Subclasses may override 808208600Srdivacky /// this routine to provide different behavior. 809210299Sed QualType RebuildDependentTemplateSpecializationType( 810221345Sdim ElaboratedTypeKeyword Keyword, 811221345Sdim NestedNameSpecifierLoc QualifierLoc, 812221345Sdim const IdentifierInfo *Name, 813221345Sdim SourceLocation NameLoc, 814221345Sdim TemplateArgumentListInfo &Args) { 815210299Sed // Rebuild the template name. 816210299Sed // TODO: avoid TemplateName abstraction 817221345Sdim CXXScopeSpec SS; 818221345Sdim SS.Adopt(QualifierLoc); 819239462Sdim TemplateName InstName 820221345Sdim = getDerived().RebuildTemplateName(SS, *Name, NameLoc, QualType(), 0); 821239462Sdim 822210299Sed if (InstName.isNull()) 823210299Sed return QualType(); 824239462Sdim 825210299Sed // If it's still dependent, make a dependent specialization. 826210299Sed if (InstName.getAsDependentTemplateName()) 827239462Sdim return SemaRef.Context.getDependentTemplateSpecializationType(Keyword, 828239462Sdim QualifierLoc.getNestedNameSpecifier(), 829239462Sdim Name, 830221345Sdim Args); 831239462Sdim 832210299Sed // Otherwise, make an elaborated type wrapping a non-dependent 833210299Sed // specialization. 834210299Sed QualType T = 835221345Sdim getDerived().RebuildTemplateSpecializationType(InstName, NameLoc, Args); 836210299Sed if (T.isNull()) return QualType(); 837239462Sdim 838221345Sdim if (Keyword == ETK_None && QualifierLoc.getNestedNameSpecifier() == 0) 839221345Sdim return T; 840239462Sdim 841239462Sdim return SemaRef.Context.getElaboratedType(Keyword, 842239462Sdim QualifierLoc.getNestedNameSpecifier(), 843221345Sdim T); 844198092Srdivacky } 845198092Srdivacky 846198092Srdivacky /// \brief Build a new typename type that refers to an identifier. 847198092Srdivacky /// 848198092Srdivacky /// By default, performs semantic analysis when building the typename type 849208600Srdivacky /// (or elaborated type). Subclasses may override this routine to provide 850198092Srdivacky /// different behavior. 851208600Srdivacky QualType RebuildDependentNameType(ElaboratedTypeKeyword Keyword, 852221345Sdim SourceLocation KeywordLoc, 853221345Sdim NestedNameSpecifierLoc QualifierLoc, 854206084Srdivacky const IdentifierInfo *Id, 855208600Srdivacky SourceLocation IdLoc) { 856206084Srdivacky CXXScopeSpec SS; 857221345Sdim SS.Adopt(QualifierLoc); 858208600Srdivacky 859221345Sdim if (QualifierLoc.getNestedNameSpecifier()->isDependent()) { 860206084Srdivacky // If the name is still dependent, just build a new dependent name type. 861206084Srdivacky if (!SemaRef.computeDeclContext(SS)) 862239462Sdim return SemaRef.Context.getDependentNameType(Keyword, 863239462Sdim QualifierLoc.getNestedNameSpecifier(), 864221345Sdim Id); 865206084Srdivacky } 866206084Srdivacky 867208600Srdivacky if (Keyword == ETK_None || Keyword == ETK_Typename) 868221345Sdim return SemaRef.CheckTypenameType(Keyword, KeywordLoc, QualifierLoc, 869221345Sdim *Id, IdLoc); 870208600Srdivacky 871208600Srdivacky TagTypeKind Kind = TypeWithKeyword::getTagTypeKindForKeyword(Keyword); 872208600Srdivacky 873208600Srdivacky // We had a dependent elaborated-type-specifier that has been transformed 874206084Srdivacky // into a non-dependent elaborated-type-specifier. Find the tag we're 875206084Srdivacky // referring to. 876208600Srdivacky LookupResult Result(SemaRef, Id, IdLoc, Sema::LookupTagName); 877206084Srdivacky DeclContext *DC = SemaRef.computeDeclContext(SS, false); 878206084Srdivacky if (!DC) 879206084Srdivacky return QualType(); 880206084Srdivacky 881208600Srdivacky if (SemaRef.RequireCompleteDeclContext(SS, DC)) 882208600Srdivacky return QualType(); 883208600Srdivacky 884206084Srdivacky TagDecl *Tag = 0; 885206084Srdivacky SemaRef.LookupQualifiedName(Result, DC); 886206084Srdivacky switch (Result.getResultKind()) { 887206084Srdivacky case LookupResult::NotFound: 888206084Srdivacky case LookupResult::NotFoundInCurrentInstantiation: 889206084Srdivacky break; 890239462Sdim 891206084Srdivacky case LookupResult::Found: 892206084Srdivacky Tag = Result.getAsSingle<TagDecl>(); 893206084Srdivacky break; 894239462Sdim 895206084Srdivacky case LookupResult::FoundOverloaded: 896206084Srdivacky case LookupResult::FoundUnresolvedValue: 897206084Srdivacky llvm_unreachable("Tag lookup cannot find non-tags"); 898239462Sdim 899206084Srdivacky case LookupResult::Ambiguous: 900206084Srdivacky // Let the LookupResult structure handle ambiguities. 901206084Srdivacky return QualType(); 902206084Srdivacky } 903206084Srdivacky 904206084Srdivacky if (!Tag) { 905218893Sdim // Check where the name exists but isn't a tag type and use that to emit 906218893Sdim // better diagnostics. 907218893Sdim LookupResult Result(SemaRef, Id, IdLoc, Sema::LookupTagName); 908218893Sdim SemaRef.LookupQualifiedName(Result, DC); 909218893Sdim switch (Result.getResultKind()) { 910218893Sdim case LookupResult::Found: 911218893Sdim case LookupResult::FoundOverloaded: 912218893Sdim case LookupResult::FoundUnresolvedValue: { 913223017Sdim NamedDecl *SomeDecl = Result.getRepresentativeDecl(); 914218893Sdim unsigned Kind = 0; 915218893Sdim if (isa<TypedefDecl>(SomeDecl)) Kind = 1; 916221345Sdim else if (isa<TypeAliasDecl>(SomeDecl)) Kind = 2; 917221345Sdim else if (isa<ClassTemplateDecl>(SomeDecl)) Kind = 3; 918218893Sdim SemaRef.Diag(IdLoc, diag::err_tag_reference_non_tag) << Kind; 919218893Sdim SemaRef.Diag(SomeDecl->getLocation(), diag::note_declared_at); 920218893Sdim break; 921223017Sdim } 922218893Sdim default: 923218893Sdim // FIXME: Would be nice to highlight just the source range. 924218893Sdim SemaRef.Diag(IdLoc, diag::err_not_tag_in_scope) 925218893Sdim << Kind << Id << DC; 926218893Sdim break; 927218893Sdim } 928206084Srdivacky return QualType(); 929206084Srdivacky } 930208600Srdivacky 931223017Sdim if (!SemaRef.isAcceptableTagRedeclaration(Tag, Kind, /*isDefinition*/false, 932223017Sdim IdLoc, *Id)) { 933208600Srdivacky SemaRef.Diag(KeywordLoc, diag::err_use_with_wrong_tag) << Id; 934206084Srdivacky SemaRef.Diag(Tag->getLocation(), diag::note_previous_use); 935206084Srdivacky return QualType(); 936206084Srdivacky } 937206084Srdivacky 938206084Srdivacky // Build the elaborated-type-specifier type. 939206084Srdivacky QualType T = SemaRef.Context.getTypeDeclType(Tag); 940239462Sdim return SemaRef.Context.getElaboratedType(Keyword, 941239462Sdim QualifierLoc.getNestedNameSpecifier(), 942221345Sdim T); 943198092Srdivacky } 944198092Srdivacky 945218893Sdim /// \brief Build a new pack expansion type. 946218893Sdim /// 947218893Sdim /// By default, builds a new PackExpansionType type from the given pattern. 948218893Sdim /// Subclasses may override this routine to provide different behavior. 949239462Sdim QualType RebuildPackExpansionType(QualType Pattern, 950218893Sdim SourceRange PatternRange, 951218893Sdim SourceLocation EllipsisLoc, 952249423Sdim Optional<unsigned> NumExpansions) { 953218893Sdim return getSema().CheckPackExpansion(Pattern, PatternRange, EllipsisLoc, 954218893Sdim NumExpansions); 955218893Sdim } 956218893Sdim 957226633Sdim /// \brief Build a new atomic type given its value type. 958226633Sdim /// 959226633Sdim /// By default, performs semantic analysis when building the atomic type. 960226633Sdim /// Subclasses may override this routine to provide different behavior. 961226633Sdim QualType RebuildAtomicType(QualType ValueType, SourceLocation KWLoc); 962226633Sdim 963198092Srdivacky /// \brief Build a new template name given a nested name specifier, a flag 964198092Srdivacky /// indicating whether the "template" keyword was provided, and the template 965198092Srdivacky /// that the template name refers to. 966198092Srdivacky /// 967198092Srdivacky /// By default, builds the new template name directly. Subclasses may override 968198092Srdivacky /// this routine to provide different behavior. 969221345Sdim TemplateName RebuildTemplateName(CXXScopeSpec &SS, 970198092Srdivacky bool TemplateKW, 971198092Srdivacky TemplateDecl *Template); 972198092Srdivacky 973198092Srdivacky /// \brief Build a new template name given a nested name specifier and the 974198092Srdivacky /// name that is referred to as a template. 975198092Srdivacky /// 976198092Srdivacky /// By default, performs semantic analysis to determine whether the name can 977198092Srdivacky /// be resolved to a specific template, then builds the appropriate kind of 978198092Srdivacky /// template name. Subclasses may override this routine to provide different 979198092Srdivacky /// behavior. 980221345Sdim TemplateName RebuildTemplateName(CXXScopeSpec &SS, 981221345Sdim const IdentifierInfo &Name, 982221345Sdim SourceLocation NameLoc, 983218893Sdim QualType ObjectType, 984218893Sdim NamedDecl *FirstQualifierInScope); 985198092Srdivacky 986198893Srdivacky /// \brief Build a new template name given a nested name specifier and the 987198893Srdivacky /// overloaded operator name that is referred to as a template. 988198893Srdivacky /// 989198893Srdivacky /// By default, performs semantic analysis to determine whether the name can 990198893Srdivacky /// be resolved to a specific template, then builds the appropriate kind of 991198893Srdivacky /// template name. Subclasses may override this routine to provide different 992198893Srdivacky /// behavior. 993221345Sdim TemplateName RebuildTemplateName(CXXScopeSpec &SS, 994198893Srdivacky OverloadedOperatorKind Operator, 995221345Sdim SourceLocation NameLoc, 996198893Srdivacky QualType ObjectType); 997218893Sdim 998218893Sdim /// \brief Build a new template name given a template template parameter pack 999239462Sdim /// and the 1000218893Sdim /// 1001218893Sdim /// By default, performs semantic analysis to determine whether the name can 1002218893Sdim /// be resolved to a specific template, then builds the appropriate kind of 1003218893Sdim /// template name. Subclasses may override this routine to provide different 1004218893Sdim /// behavior. 1005218893Sdim TemplateName RebuildTemplateName(TemplateTemplateParmDecl *Param, 1006218893Sdim const TemplateArgument &ArgPack) { 1007218893Sdim return getSema().Context.getSubstTemplateTemplateParmPack(Param, ArgPack); 1008218893Sdim } 1009218893Sdim 1010198092Srdivacky /// \brief Build a new compound statement. 1011198092Srdivacky /// 1012198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1013198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1014212904Sdim StmtResult RebuildCompoundStmt(SourceLocation LBraceLoc, 1015198092Srdivacky MultiStmtArg Statements, 1016198092Srdivacky SourceLocation RBraceLoc, 1017198092Srdivacky bool IsStmtExpr) { 1018212904Sdim return getSema().ActOnCompoundStmt(LBraceLoc, RBraceLoc, Statements, 1019198092Srdivacky IsStmtExpr); 1020198092Srdivacky } 1021198092Srdivacky 1022198092Srdivacky /// \brief Build a new case statement. 1023198092Srdivacky /// 1024198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1025198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1026212904Sdim StmtResult RebuildCaseStmt(SourceLocation CaseLoc, 1027212904Sdim Expr *LHS, 1028198092Srdivacky SourceLocation EllipsisLoc, 1029212904Sdim Expr *RHS, 1030198092Srdivacky SourceLocation ColonLoc) { 1031212904Sdim return getSema().ActOnCaseStmt(CaseLoc, LHS, EllipsisLoc, RHS, 1032198092Srdivacky ColonLoc); 1033198092Srdivacky } 1034198092Srdivacky 1035198092Srdivacky /// \brief Attach the body to a new case statement. 1036198092Srdivacky /// 1037198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1038198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1039212904Sdim StmtResult RebuildCaseStmtBody(Stmt *S, Stmt *Body) { 1040212904Sdim getSema().ActOnCaseStmtBody(S, Body); 1041212904Sdim return S; 1042198092Srdivacky } 1043198092Srdivacky 1044198092Srdivacky /// \brief Build a new default statement. 1045198092Srdivacky /// 1046198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1047198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1048212904Sdim StmtResult RebuildDefaultStmt(SourceLocation DefaultLoc, 1049198092Srdivacky SourceLocation ColonLoc, 1050212904Sdim Stmt *SubStmt) { 1051212904Sdim return getSema().ActOnDefaultStmt(DefaultLoc, ColonLoc, SubStmt, 1052198092Srdivacky /*CurScope=*/0); 1053198092Srdivacky } 1054198092Srdivacky 1055198092Srdivacky /// \brief Build a new label statement. 1056198092Srdivacky /// 1057198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1058198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1059218893Sdim StmtResult RebuildLabelStmt(SourceLocation IdentLoc, LabelDecl *L, 1060218893Sdim SourceLocation ColonLoc, Stmt *SubStmt) { 1061218893Sdim return SemaRef.ActOnLabelStmt(IdentLoc, L, ColonLoc, SubStmt); 1062198092Srdivacky } 1063198092Srdivacky 1064234982Sdim /// \brief Build a new label statement. 1065234982Sdim /// 1066234982Sdim /// By default, performs semantic analysis to build the new statement. 1067234982Sdim /// Subclasses may override this routine to provide different behavior. 1068239462Sdim StmtResult RebuildAttributedStmt(SourceLocation AttrLoc, 1069239462Sdim ArrayRef<const Attr*> Attrs, 1070234982Sdim Stmt *SubStmt) { 1071234982Sdim return SemaRef.ActOnAttributedStmt(AttrLoc, Attrs, SubStmt); 1072234982Sdim } 1073234982Sdim 1074198092Srdivacky /// \brief Build a new "if" statement. 1075198092Srdivacky /// 1076198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1077198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1078212904Sdim StmtResult RebuildIfStmt(SourceLocation IfLoc, Sema::FullExprArg Cond, 1079239462Sdim VarDecl *CondVar, Stmt *Then, 1080218893Sdim SourceLocation ElseLoc, Stmt *Else) { 1081212904Sdim return getSema().ActOnIfStmt(IfLoc, Cond, CondVar, Then, ElseLoc, Else); 1082198092Srdivacky } 1083198092Srdivacky 1084198092Srdivacky /// \brief Start building a new switch statement. 1085198092Srdivacky /// 1086198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1087198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1088212904Sdim StmtResult RebuildSwitchStmtStart(SourceLocation SwitchLoc, 1089218893Sdim Expr *Cond, VarDecl *CondVar) { 1090239462Sdim return getSema().ActOnStartOfSwitchStmt(SwitchLoc, Cond, 1091212904Sdim CondVar); 1092198092Srdivacky } 1093198092Srdivacky 1094198092Srdivacky /// \brief Attach the body to the switch statement. 1095198092Srdivacky /// 1096198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1097198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1098212904Sdim StmtResult RebuildSwitchStmtBody(SourceLocation SwitchLoc, 1099218893Sdim Stmt *Switch, Stmt *Body) { 1100212904Sdim return getSema().ActOnFinishSwitchStmt(SwitchLoc, Switch, Body); 1101198092Srdivacky } 1102198092Srdivacky 1103198092Srdivacky /// \brief Build a new while statement. 1104198092Srdivacky /// 1105198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1106198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1107218893Sdim StmtResult RebuildWhileStmt(SourceLocation WhileLoc, Sema::FullExprArg Cond, 1108218893Sdim VarDecl *CondVar, Stmt *Body) { 1109212904Sdim return getSema().ActOnWhileStmt(WhileLoc, Cond, CondVar, Body); 1110198092Srdivacky } 1111198092Srdivacky 1112198092Srdivacky /// \brief Build a new do-while statement. 1113198092Srdivacky /// 1114198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1115198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1116212904Sdim StmtResult RebuildDoStmt(SourceLocation DoLoc, Stmt *Body, 1117218893Sdim SourceLocation WhileLoc, SourceLocation LParenLoc, 1118218893Sdim Expr *Cond, SourceLocation RParenLoc) { 1119212904Sdim return getSema().ActOnDoStmt(DoLoc, Body, WhileLoc, LParenLoc, 1120212904Sdim Cond, RParenLoc); 1121198092Srdivacky } 1122198092Srdivacky 1123198092Srdivacky /// \brief Build a new for statement. 1124198092Srdivacky /// 1125198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1126198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1127218893Sdim StmtResult RebuildForStmt(SourceLocation ForLoc, SourceLocation LParenLoc, 1128239462Sdim Stmt *Init, Sema::FullExprArg Cond, 1129218893Sdim VarDecl *CondVar, Sema::FullExprArg Inc, 1130218893Sdim SourceLocation RParenLoc, Stmt *Body) { 1131239462Sdim return getSema().ActOnForStmt(ForLoc, LParenLoc, Init, Cond, 1132218893Sdim CondVar, Inc, RParenLoc, Body); 1133198092Srdivacky } 1134198092Srdivacky 1135198092Srdivacky /// \brief Build a new goto statement. 1136198092Srdivacky /// 1137198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1138198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1139218893Sdim StmtResult RebuildGotoStmt(SourceLocation GotoLoc, SourceLocation LabelLoc, 1140218893Sdim LabelDecl *Label) { 1141218893Sdim return getSema().ActOnGotoStmt(GotoLoc, LabelLoc, Label); 1142198092Srdivacky } 1143198092Srdivacky 1144198092Srdivacky /// \brief Build a new indirect goto statement. 1145198092Srdivacky /// 1146198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1147198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1148212904Sdim StmtResult RebuildIndirectGotoStmt(SourceLocation GotoLoc, 1149218893Sdim SourceLocation StarLoc, 1150218893Sdim Expr *Target) { 1151212904Sdim return getSema().ActOnIndirectGotoStmt(GotoLoc, StarLoc, Target); 1152198092Srdivacky } 1153198092Srdivacky 1154198092Srdivacky /// \brief Build a new return statement. 1155198092Srdivacky /// 1156198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1157198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1158218893Sdim StmtResult RebuildReturnStmt(SourceLocation ReturnLoc, Expr *Result) { 1159212904Sdim return getSema().ActOnReturnStmt(ReturnLoc, Result); 1160198092Srdivacky } 1161198092Srdivacky 1162198092Srdivacky /// \brief Build a new declaration statement. 1163198092Srdivacky /// 1164198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1165198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1166212904Sdim StmtResult RebuildDeclStmt(Decl **Decls, unsigned NumDecls, 1167198092Srdivacky SourceLocation StartLoc, 1168198092Srdivacky SourceLocation EndLoc) { 1169219077Sdim Sema::DeclGroupPtrTy DG = getSema().BuildDeclaratorGroup(Decls, NumDecls); 1170219077Sdim return getSema().ActOnDeclStmt(DG, StartLoc, EndLoc); 1171198092Srdivacky } 1172198092Srdivacky 1173203955Srdivacky /// \brief Build a new inline asm statement. 1174203955Srdivacky /// 1175203955Srdivacky /// By default, performs semantic analysis to build the new statement. 1176203955Srdivacky /// Subclasses may override this routine to provide different behavior. 1177243830Sdim StmtResult RebuildGCCAsmStmt(SourceLocation AsmLoc, bool IsSimple, 1178243830Sdim bool IsVolatile, unsigned NumOutputs, 1179243830Sdim unsigned NumInputs, IdentifierInfo **Names, 1180243830Sdim MultiExprArg Constraints, MultiExprArg Exprs, 1181243830Sdim Expr *AsmString, MultiExprArg Clobbers, 1182243830Sdim SourceLocation RParenLoc) { 1183243830Sdim return getSema().ActOnGCCAsmStmt(AsmLoc, IsSimple, IsVolatile, NumOutputs, 1184243830Sdim NumInputs, Names, Constraints, Exprs, 1185243830Sdim AsmString, Clobbers, RParenLoc); 1186203955Srdivacky } 1187207619Srdivacky 1188239462Sdim /// \brief Build a new MS style inline asm statement. 1189207619Srdivacky /// 1190207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1191207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1192243830Sdim StmtResult RebuildMSAsmStmt(SourceLocation AsmLoc, SourceLocation LBraceLoc, 1193251662Sdim ArrayRef<Token> AsmToks, 1194251662Sdim StringRef AsmString, 1195251662Sdim unsigned NumOutputs, unsigned NumInputs, 1196251662Sdim ArrayRef<StringRef> Constraints, 1197251662Sdim ArrayRef<StringRef> Clobbers, 1198251662Sdim ArrayRef<Expr*> Exprs, 1199251662Sdim SourceLocation EndLoc) { 1200251662Sdim return getSema().ActOnMSAsmStmt(AsmLoc, LBraceLoc, AsmToks, AsmString, 1201251662Sdim NumOutputs, NumInputs, 1202251662Sdim Constraints, Clobbers, Exprs, EndLoc); 1203239462Sdim } 1204239462Sdim 1205239462Sdim /// \brief Build a new Objective-C \@try statement. 1206239462Sdim /// 1207239462Sdim /// By default, performs semantic analysis to build the new statement. 1208239462Sdim /// Subclasses may override this routine to provide different behavior. 1209212904Sdim StmtResult RebuildObjCAtTryStmt(SourceLocation AtLoc, 1210212904Sdim Stmt *TryBody, 1211207619Srdivacky MultiStmtArg CatchStmts, 1212212904Sdim Stmt *Finally) { 1213243830Sdim return getSema().ActOnObjCAtTryStmt(AtLoc, TryBody, CatchStmts, 1214212904Sdim Finally); 1215207619Srdivacky } 1216207619Srdivacky 1217207619Srdivacky /// \brief Rebuild an Objective-C exception declaration. 1218207619Srdivacky /// 1219207619Srdivacky /// By default, performs semantic analysis to build the new declaration. 1220207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1221207619Srdivacky VarDecl *RebuildObjCExceptionDecl(VarDecl *ExceptionDecl, 1222207619Srdivacky TypeSourceInfo *TInfo, QualType T) { 1223221345Sdim return getSema().BuildObjCExceptionDecl(TInfo, T, 1224221345Sdim ExceptionDecl->getInnerLocStart(), 1225221345Sdim ExceptionDecl->getLocation(), 1226221345Sdim ExceptionDecl->getIdentifier()); 1227207619Srdivacky } 1228239462Sdim 1229239462Sdim /// \brief Build a new Objective-C \@catch statement. 1230207619Srdivacky /// 1231207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1232207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1233212904Sdim StmtResult RebuildObjCAtCatchStmt(SourceLocation AtLoc, 1234207619Srdivacky SourceLocation RParenLoc, 1235207619Srdivacky VarDecl *Var, 1236212904Sdim Stmt *Body) { 1237207619Srdivacky return getSema().ActOnObjCAtCatchStmt(AtLoc, RParenLoc, 1238212904Sdim Var, Body); 1239207619Srdivacky } 1240239462Sdim 1241239462Sdim /// \brief Build a new Objective-C \@finally statement. 1242207619Srdivacky /// 1243207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1244207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1245212904Sdim StmtResult RebuildObjCAtFinallyStmt(SourceLocation AtLoc, 1246212904Sdim Stmt *Body) { 1247212904Sdim return getSema().ActOnObjCAtFinallyStmt(AtLoc, Body); 1248207619Srdivacky } 1249239462Sdim 1250239462Sdim /// \brief Build a new Objective-C \@throw statement. 1251207619Srdivacky /// 1252207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1253207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1254212904Sdim StmtResult RebuildObjCAtThrowStmt(SourceLocation AtLoc, 1255212904Sdim Expr *Operand) { 1256212904Sdim return getSema().BuildObjCAtThrowStmt(AtLoc, Operand); 1257207619Srdivacky } 1258239462Sdim 1259239462Sdim /// \brief Rebuild the operand to an Objective-C \@synchronized statement. 1260226633Sdim /// 1261226633Sdim /// By default, performs semantic analysis to build the new statement. 1262226633Sdim /// Subclasses may override this routine to provide different behavior. 1263226633Sdim ExprResult RebuildObjCAtSynchronizedOperand(SourceLocation atLoc, 1264226633Sdim Expr *object) { 1265226633Sdim return getSema().ActOnObjCAtSynchronizedOperand(atLoc, object); 1266226633Sdim } 1267226633Sdim 1268239462Sdim /// \brief Build a new Objective-C \@synchronized statement. 1269207619Srdivacky /// 1270207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1271207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1272212904Sdim StmtResult RebuildObjCAtSynchronizedStmt(SourceLocation AtLoc, 1273226633Sdim Expr *Object, Stmt *Body) { 1274226633Sdim return getSema().ActOnObjCAtSynchronizedStmt(AtLoc, Object, Body); 1275207619Srdivacky } 1276207619Srdivacky 1277239462Sdim /// \brief Build a new Objective-C \@autoreleasepool statement. 1278224145Sdim /// 1279224145Sdim /// By default, performs semantic analysis to build the new statement. 1280224145Sdim /// Subclasses may override this routine to provide different behavior. 1281224145Sdim StmtResult RebuildObjCAutoreleasePoolStmt(SourceLocation AtLoc, 1282224145Sdim Stmt *Body) { 1283224145Sdim return getSema().ActOnObjCAutoreleasePoolStmt(AtLoc, Body); 1284224145Sdim } 1285224145Sdim 1286207619Srdivacky /// \brief Build a new Objective-C fast enumeration statement. 1287207619Srdivacky /// 1288207619Srdivacky /// By default, performs semantic analysis to build the new statement. 1289207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1290212904Sdim StmtResult RebuildObjCForCollectionStmt(SourceLocation ForLoc, 1291212904Sdim Stmt *Element, 1292212904Sdim Expr *Collection, 1293212904Sdim SourceLocation RParenLoc, 1294212904Sdim Stmt *Body) { 1295239462Sdim StmtResult ForEachStmt = getSema().ActOnObjCForCollectionStmt(ForLoc, 1296239462Sdim Element, 1297212904Sdim Collection, 1298239462Sdim RParenLoc); 1299239462Sdim if (ForEachStmt.isInvalid()) 1300239462Sdim return StmtError(); 1301239462Sdim 1302239462Sdim return getSema().FinishObjCForCollectionStmt(ForEachStmt.take(), Body); 1303207619Srdivacky } 1304239462Sdim 1305198092Srdivacky /// \brief Build a new C++ exception declaration. 1306198092Srdivacky /// 1307198092Srdivacky /// By default, performs semantic analysis to build the new decaration. 1308198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1309221345Sdim VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl, 1310200583Srdivacky TypeSourceInfo *Declarator, 1311221345Sdim SourceLocation StartLoc, 1312221345Sdim SourceLocation IdLoc, 1313221345Sdim IdentifierInfo *Id) { 1314221345Sdim VarDecl *Var = getSema().BuildExceptionDeclaration(0, Declarator, 1315221345Sdim StartLoc, IdLoc, Id); 1316221345Sdim if (Var) 1317221345Sdim getSema().CurContext->addDecl(Var); 1318221345Sdim return Var; 1319198092Srdivacky } 1320198092Srdivacky 1321198092Srdivacky /// \brief Build a new C++ catch statement. 1322198092Srdivacky /// 1323198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1324198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1325212904Sdim StmtResult RebuildCXXCatchStmt(SourceLocation CatchLoc, 1326212904Sdim VarDecl *ExceptionDecl, 1327212904Sdim Stmt *Handler) { 1328212904Sdim return Owned(new (getSema().Context) CXXCatchStmt(CatchLoc, ExceptionDecl, 1329212904Sdim Handler)); 1330198092Srdivacky } 1331198092Srdivacky 1332198092Srdivacky /// \brief Build a new C++ try statement. 1333198092Srdivacky /// 1334198092Srdivacky /// By default, performs semantic analysis to build the new statement. 1335198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1336212904Sdim StmtResult RebuildCXXTryStmt(SourceLocation TryLoc, 1337212904Sdim Stmt *TryBlock, 1338212904Sdim MultiStmtArg Handlers) { 1339243830Sdim return getSema().ActOnCXXTryBlock(TryLoc, TryBlock, Handlers); 1340198092Srdivacky } 1341198092Srdivacky 1342221345Sdim /// \brief Build a new C++0x range-based for statement. 1343221345Sdim /// 1344221345Sdim /// By default, performs semantic analysis to build the new statement. 1345221345Sdim /// Subclasses may override this routine to provide different behavior. 1346221345Sdim StmtResult RebuildCXXForRangeStmt(SourceLocation ForLoc, 1347221345Sdim SourceLocation ColonLoc, 1348221345Sdim Stmt *Range, Stmt *BeginEnd, 1349221345Sdim Expr *Cond, Expr *Inc, 1350221345Sdim Stmt *LoopVar, 1351221345Sdim SourceLocation RParenLoc) { 1352251662Sdim // If we've just learned that the range is actually an Objective-C 1353251662Sdim // collection, treat this as an Objective-C fast enumeration loop. 1354251662Sdim if (DeclStmt *RangeStmt = dyn_cast<DeclStmt>(Range)) { 1355251662Sdim if (RangeStmt->isSingleDecl()) { 1356251662Sdim if (VarDecl *RangeVar = dyn_cast<VarDecl>(RangeStmt->getSingleDecl())) { 1357251662Sdim if (RangeVar->isInvalidDecl()) 1358251662Sdim return StmtError(); 1359251662Sdim 1360251662Sdim Expr *RangeExpr = RangeVar->getInit(); 1361251662Sdim if (!RangeExpr->isTypeDependent() && 1362251662Sdim RangeExpr->getType()->isObjCObjectPointerType()) 1363251662Sdim return getSema().ActOnObjCForCollectionStmt(ForLoc, LoopVar, RangeExpr, 1364251662Sdim RParenLoc); 1365251662Sdim } 1366251662Sdim } 1367251662Sdim } 1368251662Sdim 1369221345Sdim return getSema().BuildCXXForRangeStmt(ForLoc, ColonLoc, Range, BeginEnd, 1370243830Sdim Cond, Inc, LoopVar, RParenLoc, 1371243830Sdim Sema::BFRK_Rebuild); 1372221345Sdim } 1373234353Sdim 1374234353Sdim /// \brief Build a new C++0x range-based for statement. 1375234353Sdim /// 1376234353Sdim /// By default, performs semantic analysis to build the new statement. 1377234353Sdim /// Subclasses may override this routine to provide different behavior. 1378239462Sdim StmtResult RebuildMSDependentExistsStmt(SourceLocation KeywordLoc, 1379234353Sdim bool IsIfExists, 1380234353Sdim NestedNameSpecifierLoc QualifierLoc, 1381234353Sdim DeclarationNameInfo NameInfo, 1382234353Sdim Stmt *Nested) { 1383234353Sdim return getSema().BuildMSDependentExistsStmt(KeywordLoc, IsIfExists, 1384234353Sdim QualifierLoc, NameInfo, Nested); 1385234353Sdim } 1386234353Sdim 1387221345Sdim /// \brief Attach body to a C++0x range-based for statement. 1388221345Sdim /// 1389221345Sdim /// By default, performs semantic analysis to finish the new statement. 1390221345Sdim /// Subclasses may override this routine to provide different behavior. 1391221345Sdim StmtResult FinishCXXForRangeStmt(Stmt *ForRange, Stmt *Body) { 1392221345Sdim return getSema().FinishCXXForRangeStmt(ForRange, Body); 1393221345Sdim } 1394239462Sdim 1395221345Sdim StmtResult RebuildSEHTryStmt(bool IsCXXTry, 1396221345Sdim SourceLocation TryLoc, 1397221345Sdim Stmt *TryBlock, 1398221345Sdim Stmt *Handler) { 1399221345Sdim return getSema().ActOnSEHTryBlock(IsCXXTry,TryLoc,TryBlock,Handler); 1400221345Sdim } 1401221345Sdim 1402221345Sdim StmtResult RebuildSEHExceptStmt(SourceLocation Loc, 1403221345Sdim Expr *FilterExpr, 1404221345Sdim Stmt *Block) { 1405221345Sdim return getSema().ActOnSEHExceptBlock(Loc,FilterExpr,Block); 1406221345Sdim } 1407221345Sdim 1408221345Sdim StmtResult RebuildSEHFinallyStmt(SourceLocation Loc, 1409221345Sdim Stmt *Block) { 1410221345Sdim return getSema().ActOnSEHFinallyBlock(Loc,Block); 1411221345Sdim } 1412221345Sdim 1413198092Srdivacky /// \brief Build a new expression that references a declaration. 1414198092Srdivacky /// 1415198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1416198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1417212904Sdim ExprResult RebuildDeclarationNameExpr(const CXXScopeSpec &SS, 1418212904Sdim LookupResult &R, 1419212904Sdim bool RequiresADL) { 1420199990Srdivacky return getSema().BuildDeclarationNameExpr(SS, R, RequiresADL); 1421199990Srdivacky } 1422199990Srdivacky 1423199990Srdivacky 1424199990Srdivacky /// \brief Build a new expression that references a declaration. 1425199990Srdivacky /// 1426199990Srdivacky /// By default, performs semantic analysis to build the new expression. 1427199990Srdivacky /// Subclasses may override this routine to provide different behavior. 1428221345Sdim ExprResult RebuildDeclRefExpr(NestedNameSpecifierLoc QualifierLoc, 1429212904Sdim ValueDecl *VD, 1430212904Sdim const DeclarationNameInfo &NameInfo, 1431212904Sdim TemplateArgumentListInfo *TemplateArgs) { 1432198893Srdivacky CXXScopeSpec SS; 1433221345Sdim SS.Adopt(QualifierLoc); 1434200583Srdivacky 1435200583Srdivacky // FIXME: loses template args. 1436212904Sdim 1437212904Sdim return getSema().BuildDeclarationNameExpr(SS, NameInfo, VD); 1438198092Srdivacky } 1439198092Srdivacky 1440198092Srdivacky /// \brief Build a new expression in parentheses. 1441198092Srdivacky /// 1442198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1443198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1444212904Sdim ExprResult RebuildParenExpr(Expr *SubExpr, SourceLocation LParen, 1445198092Srdivacky SourceLocation RParen) { 1446212904Sdim return getSema().ActOnParenExpr(LParen, RParen, SubExpr); 1447198092Srdivacky } 1448198092Srdivacky 1449198092Srdivacky /// \brief Build a new pseudo-destructor expression. 1450198092Srdivacky /// 1451198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1452198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1453212904Sdim ExprResult RebuildCXXPseudoDestructorExpr(Expr *Base, 1454219077Sdim SourceLocation OperatorLoc, 1455219077Sdim bool isArrow, 1456219077Sdim CXXScopeSpec &SS, 1457219077Sdim TypeSourceInfo *ScopeType, 1458219077Sdim SourceLocation CCLoc, 1459219077Sdim SourceLocation TildeLoc, 1460204643Srdivacky PseudoDestructorTypeStorage Destroyed); 1461198092Srdivacky 1462198092Srdivacky /// \brief Build a new unary operator expression. 1463198092Srdivacky /// 1464198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1465198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1466212904Sdim ExprResult RebuildUnaryOperator(SourceLocation OpLoc, 1467212904Sdim UnaryOperatorKind Opc, 1468212904Sdim Expr *SubExpr) { 1469212904Sdim return getSema().BuildUnaryOp(/*Scope=*/0, OpLoc, Opc, SubExpr); 1470198092Srdivacky } 1471198092Srdivacky 1472207619Srdivacky /// \brief Build a new builtin offsetof expression. 1473207619Srdivacky /// 1474207619Srdivacky /// By default, performs semantic analysis to build the new expression. 1475207619Srdivacky /// Subclasses may override this routine to provide different behavior. 1476212904Sdim ExprResult RebuildOffsetOfExpr(SourceLocation OperatorLoc, 1477207619Srdivacky TypeSourceInfo *Type, 1478212904Sdim Sema::OffsetOfComponent *Components, 1479207619Srdivacky unsigned NumComponents, 1480207619Srdivacky SourceLocation RParenLoc) { 1481207619Srdivacky return getSema().BuildBuiltinOffsetOf(OperatorLoc, Type, Components, 1482207619Srdivacky NumComponents, RParenLoc); 1483207619Srdivacky } 1484239462Sdim 1485239462Sdim /// \brief Build a new sizeof, alignof or vec_step expression with a 1486221345Sdim /// type argument. 1487198092Srdivacky /// 1488198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1489198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1490221345Sdim ExprResult RebuildUnaryExprOrTypeTrait(TypeSourceInfo *TInfo, 1491221345Sdim SourceLocation OpLoc, 1492221345Sdim UnaryExprOrTypeTrait ExprKind, 1493221345Sdim SourceRange R) { 1494221345Sdim return getSema().CreateUnaryExprOrTypeTraitExpr(TInfo, OpLoc, ExprKind, R); 1495198092Srdivacky } 1496198092Srdivacky 1497221345Sdim /// \brief Build a new sizeof, alignof or vec step expression with an 1498221345Sdim /// expression argument. 1499198092Srdivacky /// 1500198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1501198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1502221345Sdim ExprResult RebuildUnaryExprOrTypeTrait(Expr *SubExpr, SourceLocation OpLoc, 1503221345Sdim UnaryExprOrTypeTrait ExprKind, 1504221345Sdim SourceRange R) { 1505212904Sdim ExprResult Result 1506223017Sdim = getSema().CreateUnaryExprOrTypeTraitExpr(SubExpr, OpLoc, ExprKind); 1507198092Srdivacky if (Result.isInvalid()) 1508212904Sdim return ExprError(); 1509198092Srdivacky 1510243830Sdim return Result; 1511198092Srdivacky } 1512198092Srdivacky 1513198092Srdivacky /// \brief Build a new array subscript expression. 1514198092Srdivacky /// 1515198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1516198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1517212904Sdim ExprResult RebuildArraySubscriptExpr(Expr *LHS, 1518198092Srdivacky SourceLocation LBracketLoc, 1519212904Sdim Expr *RHS, 1520198092Srdivacky SourceLocation RBracketLoc) { 1521212904Sdim return getSema().ActOnArraySubscriptExpr(/*Scope=*/0, LHS, 1522212904Sdim LBracketLoc, RHS, 1523198092Srdivacky RBracketLoc); 1524198092Srdivacky } 1525198092Srdivacky 1526198092Srdivacky /// \brief Build a new call expression. 1527198092Srdivacky /// 1528198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1529198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1530212904Sdim ExprResult RebuildCallExpr(Expr *Callee, SourceLocation LParenLoc, 1531198092Srdivacky MultiExprArg Args, 1532218893Sdim SourceLocation RParenLoc, 1533218893Sdim Expr *ExecConfig = 0) { 1534212904Sdim return getSema().ActOnCallExpr(/*Scope=*/0, Callee, LParenLoc, 1535243830Sdim Args, RParenLoc, ExecConfig); 1536198092Srdivacky } 1537198092Srdivacky 1538198092Srdivacky /// \brief Build a new member access expression. 1539198092Srdivacky /// 1540198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1541198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1542212904Sdim ExprResult RebuildMemberExpr(Expr *Base, SourceLocation OpLoc, 1543218893Sdim bool isArrow, 1544221345Sdim NestedNameSpecifierLoc QualifierLoc, 1545234353Sdim SourceLocation TemplateKWLoc, 1546218893Sdim const DeclarationNameInfo &MemberNameInfo, 1547218893Sdim ValueDecl *Member, 1548218893Sdim NamedDecl *FoundDecl, 1549199990Srdivacky const TemplateArgumentListInfo *ExplicitTemplateArgs, 1550218893Sdim NamedDecl *FirstQualifierInScope) { 1551234353Sdim ExprResult BaseResult = getSema().PerformMemberExprBaseConversion(Base, 1552234353Sdim isArrow); 1553198092Srdivacky if (!Member->getDeclName()) { 1554218893Sdim // We have a reference to an unnamed field. This is always the 1555218893Sdim // base of an anonymous struct/union member access, i.e. the 1556218893Sdim // field is always of record type. 1557221345Sdim assert(!QualifierLoc && "Can't have an unnamed field with a qualifier!"); 1558218893Sdim assert(Member->getType()->isRecordType() && 1559218893Sdim "unnamed member not of record type?"); 1560198092Srdivacky 1561234353Sdim BaseResult = 1562234353Sdim getSema().PerformObjectMemberConversion(BaseResult.take(), 1563221345Sdim QualifierLoc.getNestedNameSpecifier(), 1564221345Sdim FoundDecl, Member); 1565221345Sdim if (BaseResult.isInvalid()) 1566212904Sdim return ExprError(); 1567221345Sdim Base = BaseResult.take(); 1568218893Sdim ExprValueKind VK = isArrow ? VK_LValue : Base->getValueKind(); 1569198092Srdivacky MemberExpr *ME = 1570212904Sdim new (getSema().Context) MemberExpr(Base, isArrow, 1571212904Sdim Member, MemberNameInfo, 1572218893Sdim cast<FieldDecl>(Member)->getType(), 1573218893Sdim VK, OK_Ordinary); 1574198092Srdivacky return getSema().Owned(ME); 1575198092Srdivacky } 1576198092Srdivacky 1577198092Srdivacky CXXScopeSpec SS; 1578221345Sdim SS.Adopt(QualifierLoc); 1579198092Srdivacky 1580221345Sdim Base = BaseResult.take(); 1581212904Sdim QualType BaseType = Base->getType(); 1582200583Srdivacky 1583206084Srdivacky // FIXME: this involves duplicating earlier analysis in a lot of 1584206084Srdivacky // cases; we should avoid this when possible. 1585212904Sdim LookupResult R(getSema(), MemberNameInfo, Sema::LookupMemberName); 1586206084Srdivacky R.addDecl(FoundDecl); 1587202379Srdivacky R.resolveKind(); 1588202379Srdivacky 1589212904Sdim return getSema().BuildMemberReferenceExpr(Base, BaseType, OpLoc, isArrow, 1590234353Sdim SS, TemplateKWLoc, 1591234353Sdim FirstQualifierInScope, 1592202379Srdivacky R, ExplicitTemplateArgs); 1593198092Srdivacky } 1594198092Srdivacky 1595198092Srdivacky /// \brief Build a new binary operator expression. 1596198092Srdivacky /// 1597198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1598198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1599212904Sdim ExprResult RebuildBinaryOperator(SourceLocation OpLoc, 1600212904Sdim BinaryOperatorKind Opc, 1601212904Sdim Expr *LHS, Expr *RHS) { 1602212904Sdim return getSema().BuildBinOp(/*Scope=*/0, OpLoc, Opc, LHS, RHS); 1603198092Srdivacky } 1604198092Srdivacky 1605198092Srdivacky /// \brief Build a new conditional operator expression. 1606198092Srdivacky /// 1607198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1608198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1609212904Sdim ExprResult RebuildConditionalOperator(Expr *Cond, 1610218893Sdim SourceLocation QuestionLoc, 1611218893Sdim Expr *LHS, 1612218893Sdim SourceLocation ColonLoc, 1613218893Sdim Expr *RHS) { 1614212904Sdim return getSema().ActOnConditionalOp(QuestionLoc, ColonLoc, Cond, 1615212904Sdim LHS, RHS); 1616198092Srdivacky } 1617198092Srdivacky 1618198092Srdivacky /// \brief Build a new C-style cast expression. 1619198092Srdivacky /// 1620198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1621198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1622212904Sdim ExprResult RebuildCStyleCastExpr(SourceLocation LParenLoc, 1623202879Srdivacky TypeSourceInfo *TInfo, 1624198092Srdivacky SourceLocation RParenLoc, 1625212904Sdim Expr *SubExpr) { 1626202879Srdivacky return getSema().BuildCStyleCastExpr(LParenLoc, TInfo, RParenLoc, 1627212904Sdim SubExpr); 1628198092Srdivacky } 1629198092Srdivacky 1630198092Srdivacky /// \brief Build a new compound literal expression. 1631198092Srdivacky /// 1632198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1633198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1634212904Sdim ExprResult RebuildCompoundLiteralExpr(SourceLocation LParenLoc, 1635202879Srdivacky TypeSourceInfo *TInfo, 1636198092Srdivacky SourceLocation RParenLoc, 1637212904Sdim Expr *Init) { 1638202879Srdivacky return getSema().BuildCompoundLiteralExpr(LParenLoc, TInfo, RParenLoc, 1639212904Sdim Init); 1640198092Srdivacky } 1641198092Srdivacky 1642198092Srdivacky /// \brief Build a new extended vector element access expression. 1643198092Srdivacky /// 1644198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1645198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1646212904Sdim ExprResult RebuildExtVectorElementExpr(Expr *Base, 1647198092Srdivacky SourceLocation OpLoc, 1648198092Srdivacky SourceLocation AccessorLoc, 1649198092Srdivacky IdentifierInfo &Accessor) { 1650200583Srdivacky 1651199990Srdivacky CXXScopeSpec SS; 1652212904Sdim DeclarationNameInfo NameInfo(&Accessor, AccessorLoc); 1653212904Sdim return getSema().BuildMemberReferenceExpr(Base, Base->getType(), 1654199990Srdivacky OpLoc, /*IsArrow*/ false, 1655234353Sdim SS, SourceLocation(), 1656234353Sdim /*FirstQualifierInScope*/ 0, 1657212904Sdim NameInfo, 1658199990Srdivacky /* TemplateArgs */ 0); 1659198092Srdivacky } 1660198092Srdivacky 1661198092Srdivacky /// \brief Build a new initializer list expression. 1662198092Srdivacky /// 1663198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1664198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1665212904Sdim ExprResult RebuildInitList(SourceLocation LBraceLoc, 1666224145Sdim MultiExprArg Inits, 1667224145Sdim SourceLocation RBraceLoc, 1668224145Sdim QualType ResultTy) { 1669212904Sdim ExprResult Result 1670243830Sdim = SemaRef.ActOnInitList(LBraceLoc, Inits, RBraceLoc); 1671199482Srdivacky if (Result.isInvalid() || ResultTy->isDependentType()) 1672243830Sdim return Result; 1673239462Sdim 1674199482Srdivacky // Patch in the result type we were given, which may have been computed 1675199482Srdivacky // when the initial InitListExpr was built. 1676199482Srdivacky InitListExpr *ILE = cast<InitListExpr>((Expr *)Result.get()); 1677199482Srdivacky ILE->setType(ResultTy); 1678243830Sdim return Result; 1679198092Srdivacky } 1680198092Srdivacky 1681198092Srdivacky /// \brief Build a new designated initializer expression. 1682198092Srdivacky /// 1683198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1684198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1685212904Sdim ExprResult RebuildDesignatedInitExpr(Designation &Desig, 1686198092Srdivacky MultiExprArg ArrayExprs, 1687198092Srdivacky SourceLocation EqualOrColonLoc, 1688198092Srdivacky bool GNUSyntax, 1689212904Sdim Expr *Init) { 1690212904Sdim ExprResult Result 1691198092Srdivacky = SemaRef.ActOnDesignatedInitializer(Desig, EqualOrColonLoc, GNUSyntax, 1692212904Sdim Init); 1693198092Srdivacky if (Result.isInvalid()) 1694212904Sdim return ExprError(); 1695198092Srdivacky 1696243830Sdim return Result; 1697198092Srdivacky } 1698198092Srdivacky 1699198092Srdivacky /// \brief Build a new value-initialized expression. 1700198092Srdivacky /// 1701198092Srdivacky /// By default, builds the implicit value initialization without performing 1702198092Srdivacky /// any semantic analysis. Subclasses may override this routine to provide 1703198092Srdivacky /// different behavior. 1704212904Sdim ExprResult RebuildImplicitValueInitExpr(QualType T) { 1705198092Srdivacky return SemaRef.Owned(new (SemaRef.Context) ImplicitValueInitExpr(T)); 1706198092Srdivacky } 1707198092Srdivacky 1708198092Srdivacky /// \brief Build a new \c va_arg expression. 1709198092Srdivacky /// 1710198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1711198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1712212904Sdim ExprResult RebuildVAArgExpr(SourceLocation BuiltinLoc, 1713212904Sdim Expr *SubExpr, TypeSourceInfo *TInfo, 1714212904Sdim SourceLocation RParenLoc) { 1715212904Sdim return getSema().BuildVAArgExpr(BuiltinLoc, 1716212904Sdim SubExpr, TInfo, 1717212904Sdim RParenLoc); 1718198092Srdivacky } 1719198092Srdivacky 1720198092Srdivacky /// \brief Build a new expression list in parentheses. 1721198092Srdivacky /// 1722198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1723198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1724212904Sdim ExprResult RebuildParenListExpr(SourceLocation LParenLoc, 1725234353Sdim MultiExprArg SubExprs, 1726234353Sdim SourceLocation RParenLoc) { 1727243830Sdim return getSema().ActOnParenListExpr(LParenLoc, RParenLoc, SubExprs); 1728198092Srdivacky } 1729198092Srdivacky 1730198092Srdivacky /// \brief Build a new address-of-label expression. 1731198092Srdivacky /// 1732198092Srdivacky /// By default, performs semantic analysis, using the name of the label 1733198092Srdivacky /// rather than attempting to map the label statement itself. 1734198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1735212904Sdim ExprResult RebuildAddrLabelExpr(SourceLocation AmpAmpLoc, 1736218893Sdim SourceLocation LabelLoc, LabelDecl *Label) { 1737218893Sdim return getSema().ActOnAddrLabel(AmpAmpLoc, LabelLoc, Label); 1738198092Srdivacky } 1739198092Srdivacky 1740198092Srdivacky /// \brief Build a new GNU statement expression. 1741198092Srdivacky /// 1742198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1743198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1744212904Sdim ExprResult RebuildStmtExpr(SourceLocation LParenLoc, 1745212904Sdim Stmt *SubStmt, 1746198092Srdivacky SourceLocation RParenLoc) { 1747212904Sdim return getSema().ActOnStmtExpr(LParenLoc, SubStmt, RParenLoc); 1748198092Srdivacky } 1749198092Srdivacky 1750198092Srdivacky /// \brief Build a new __builtin_choose_expr expression. 1751198092Srdivacky /// 1752198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1753198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1754212904Sdim ExprResult RebuildChooseExpr(SourceLocation BuiltinLoc, 1755212904Sdim Expr *Cond, Expr *LHS, Expr *RHS, 1756198092Srdivacky SourceLocation RParenLoc) { 1757198092Srdivacky return SemaRef.ActOnChooseExpr(BuiltinLoc, 1758212904Sdim Cond, LHS, RHS, 1759198092Srdivacky RParenLoc); 1760198092Srdivacky } 1761198092Srdivacky 1762221345Sdim /// \brief Build a new generic selection expression. 1763221345Sdim /// 1764221345Sdim /// By default, performs semantic analysis to build the new expression. 1765221345Sdim /// Subclasses may override this routine to provide different behavior. 1766221345Sdim ExprResult RebuildGenericSelectionExpr(SourceLocation KeyLoc, 1767221345Sdim SourceLocation DefaultLoc, 1768221345Sdim SourceLocation RParenLoc, 1769221345Sdim Expr *ControllingExpr, 1770221345Sdim TypeSourceInfo **Types, 1771221345Sdim Expr **Exprs, 1772221345Sdim unsigned NumAssocs) { 1773221345Sdim return getSema().CreateGenericSelectionExpr(KeyLoc, DefaultLoc, RParenLoc, 1774221345Sdim ControllingExpr, Types, Exprs, 1775221345Sdim NumAssocs); 1776221345Sdim } 1777221345Sdim 1778198092Srdivacky /// \brief Build a new overloaded operator call expression. 1779198092Srdivacky /// 1780198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1781198092Srdivacky /// The semantic analysis provides the behavior of template instantiation, 1782198092Srdivacky /// copying with transformations that turn what looks like an overloaded 1783198092Srdivacky /// operator call into a use of a builtin operator, performing 1784198092Srdivacky /// argument-dependent lookup, etc. Subclasses may override this routine to 1785198092Srdivacky /// provide different behavior. 1786212904Sdim ExprResult RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op, 1787198092Srdivacky SourceLocation OpLoc, 1788212904Sdim Expr *Callee, 1789212904Sdim Expr *First, 1790212904Sdim Expr *Second); 1791198092Srdivacky 1792198092Srdivacky /// \brief Build a new C++ "named" cast expression, such as static_cast or 1793198092Srdivacky /// reinterpret_cast. 1794198092Srdivacky /// 1795198092Srdivacky /// By default, this routine dispatches to one of the more-specific routines 1796198092Srdivacky /// for a particular named case, e.g., RebuildCXXStaticCastExpr(). 1797198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1798212904Sdim ExprResult RebuildCXXNamedCastExpr(SourceLocation OpLoc, 1799198092Srdivacky Stmt::StmtClass Class, 1800198092Srdivacky SourceLocation LAngleLoc, 1801202879Srdivacky TypeSourceInfo *TInfo, 1802198092Srdivacky SourceLocation RAngleLoc, 1803198092Srdivacky SourceLocation LParenLoc, 1804212904Sdim Expr *SubExpr, 1805198092Srdivacky SourceLocation RParenLoc) { 1806198092Srdivacky switch (Class) { 1807198092Srdivacky case Stmt::CXXStaticCastExprClass: 1808202879Srdivacky return getDerived().RebuildCXXStaticCastExpr(OpLoc, LAngleLoc, TInfo, 1809198092Srdivacky RAngleLoc, LParenLoc, 1810212904Sdim SubExpr, RParenLoc); 1811198092Srdivacky 1812198092Srdivacky case Stmt::CXXDynamicCastExprClass: 1813202879Srdivacky return getDerived().RebuildCXXDynamicCastExpr(OpLoc, LAngleLoc, TInfo, 1814198092Srdivacky RAngleLoc, LParenLoc, 1815212904Sdim SubExpr, RParenLoc); 1816198092Srdivacky 1817198092Srdivacky case Stmt::CXXReinterpretCastExprClass: 1818202879Srdivacky return getDerived().RebuildCXXReinterpretCastExpr(OpLoc, LAngleLoc, TInfo, 1819198092Srdivacky RAngleLoc, LParenLoc, 1820212904Sdim SubExpr, 1821198092Srdivacky RParenLoc); 1822198092Srdivacky 1823198092Srdivacky case Stmt::CXXConstCastExprClass: 1824202879Srdivacky return getDerived().RebuildCXXConstCastExpr(OpLoc, LAngleLoc, TInfo, 1825198092Srdivacky RAngleLoc, LParenLoc, 1826212904Sdim SubExpr, RParenLoc); 1827198092Srdivacky 1828198092Srdivacky default: 1829226633Sdim llvm_unreachable("Invalid C++ named cast"); 1830198092Srdivacky } 1831198092Srdivacky } 1832198092Srdivacky 1833198092Srdivacky /// \brief Build a new C++ static_cast expression. 1834198092Srdivacky /// 1835198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1836198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1837212904Sdim ExprResult RebuildCXXStaticCastExpr(SourceLocation OpLoc, 1838198092Srdivacky SourceLocation LAngleLoc, 1839202879Srdivacky TypeSourceInfo *TInfo, 1840198092Srdivacky SourceLocation RAngleLoc, 1841198092Srdivacky SourceLocation LParenLoc, 1842212904Sdim Expr *SubExpr, 1843198092Srdivacky SourceLocation RParenLoc) { 1844202879Srdivacky return getSema().BuildCXXNamedCast(OpLoc, tok::kw_static_cast, 1845212904Sdim TInfo, SubExpr, 1846202879Srdivacky SourceRange(LAngleLoc, RAngleLoc), 1847202879Srdivacky SourceRange(LParenLoc, RParenLoc)); 1848198092Srdivacky } 1849198092Srdivacky 1850198092Srdivacky /// \brief Build a new C++ dynamic_cast expression. 1851198092Srdivacky /// 1852198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1853198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1854212904Sdim ExprResult RebuildCXXDynamicCastExpr(SourceLocation OpLoc, 1855198092Srdivacky SourceLocation LAngleLoc, 1856202879Srdivacky TypeSourceInfo *TInfo, 1857198092Srdivacky SourceLocation RAngleLoc, 1858198092Srdivacky SourceLocation LParenLoc, 1859212904Sdim Expr *SubExpr, 1860198092Srdivacky SourceLocation RParenLoc) { 1861202879Srdivacky return getSema().BuildCXXNamedCast(OpLoc, tok::kw_dynamic_cast, 1862212904Sdim TInfo, SubExpr, 1863202879Srdivacky SourceRange(LAngleLoc, RAngleLoc), 1864202879Srdivacky SourceRange(LParenLoc, RParenLoc)); 1865198092Srdivacky } 1866198092Srdivacky 1867198092Srdivacky /// \brief Build a new C++ reinterpret_cast expression. 1868198092Srdivacky /// 1869198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1870198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1871212904Sdim ExprResult RebuildCXXReinterpretCastExpr(SourceLocation OpLoc, 1872198092Srdivacky SourceLocation LAngleLoc, 1873202879Srdivacky TypeSourceInfo *TInfo, 1874198092Srdivacky SourceLocation RAngleLoc, 1875198092Srdivacky SourceLocation LParenLoc, 1876212904Sdim Expr *SubExpr, 1877198092Srdivacky SourceLocation RParenLoc) { 1878202879Srdivacky return getSema().BuildCXXNamedCast(OpLoc, tok::kw_reinterpret_cast, 1879212904Sdim TInfo, SubExpr, 1880202879Srdivacky SourceRange(LAngleLoc, RAngleLoc), 1881202879Srdivacky SourceRange(LParenLoc, RParenLoc)); 1882198092Srdivacky } 1883198092Srdivacky 1884198092Srdivacky /// \brief Build a new C++ const_cast expression. 1885198092Srdivacky /// 1886198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1887198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1888212904Sdim ExprResult RebuildCXXConstCastExpr(SourceLocation OpLoc, 1889198092Srdivacky SourceLocation LAngleLoc, 1890202879Srdivacky TypeSourceInfo *TInfo, 1891198092Srdivacky SourceLocation RAngleLoc, 1892198092Srdivacky SourceLocation LParenLoc, 1893212904Sdim Expr *SubExpr, 1894198092Srdivacky SourceLocation RParenLoc) { 1895202879Srdivacky return getSema().BuildCXXNamedCast(OpLoc, tok::kw_const_cast, 1896212904Sdim TInfo, SubExpr, 1897202879Srdivacky SourceRange(LAngleLoc, RAngleLoc), 1898202879Srdivacky SourceRange(LParenLoc, RParenLoc)); 1899198092Srdivacky } 1900198092Srdivacky 1901198092Srdivacky /// \brief Build a new C++ functional-style cast expression. 1902198092Srdivacky /// 1903198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1904198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1905218893Sdim ExprResult RebuildCXXFunctionalCastExpr(TypeSourceInfo *TInfo, 1906218893Sdim SourceLocation LParenLoc, 1907218893Sdim Expr *Sub, 1908218893Sdim SourceLocation RParenLoc) { 1909218893Sdim return getSema().BuildCXXTypeConstructExpr(TInfo, LParenLoc, 1910212904Sdim MultiExprArg(&Sub, 1), 1911198092Srdivacky RParenLoc); 1912198092Srdivacky } 1913198092Srdivacky 1914198092Srdivacky /// \brief Build a new C++ typeid(type) expression. 1915198092Srdivacky /// 1916198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1917198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1918212904Sdim ExprResult RebuildCXXTypeidExpr(QualType TypeInfoType, 1919207619Srdivacky SourceLocation TypeidLoc, 1920207619Srdivacky TypeSourceInfo *Operand, 1921198092Srdivacky SourceLocation RParenLoc) { 1922239462Sdim return getSema().BuildCXXTypeId(TypeInfoType, TypeidLoc, Operand, 1923207619Srdivacky RParenLoc); 1924198092Srdivacky } 1925198092Srdivacky 1926218893Sdim 1927198092Srdivacky /// \brief Build a new C++ typeid(expr) expression. 1928198092Srdivacky /// 1929198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1930198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1931212904Sdim ExprResult RebuildCXXTypeidExpr(QualType TypeInfoType, 1932207619Srdivacky SourceLocation TypeidLoc, 1933212904Sdim Expr *Operand, 1934198092Srdivacky SourceLocation RParenLoc) { 1935212904Sdim return getSema().BuildCXXTypeId(TypeInfoType, TypeidLoc, Operand, 1936207619Srdivacky RParenLoc); 1937198092Srdivacky } 1938198092Srdivacky 1939218893Sdim /// \brief Build a new C++ __uuidof(type) expression. 1940218893Sdim /// 1941218893Sdim /// By default, performs semantic analysis to build the new expression. 1942218893Sdim /// Subclasses may override this routine to provide different behavior. 1943218893Sdim ExprResult RebuildCXXUuidofExpr(QualType TypeInfoType, 1944218893Sdim SourceLocation TypeidLoc, 1945218893Sdim TypeSourceInfo *Operand, 1946218893Sdim SourceLocation RParenLoc) { 1947239462Sdim return getSema().BuildCXXUuidof(TypeInfoType, TypeidLoc, Operand, 1948218893Sdim RParenLoc); 1949218893Sdim } 1950218893Sdim 1951218893Sdim /// \brief Build a new C++ __uuidof(expr) expression. 1952218893Sdim /// 1953218893Sdim /// By default, performs semantic analysis to build the new expression. 1954218893Sdim /// Subclasses may override this routine to provide different behavior. 1955218893Sdim ExprResult RebuildCXXUuidofExpr(QualType TypeInfoType, 1956218893Sdim SourceLocation TypeidLoc, 1957218893Sdim Expr *Operand, 1958218893Sdim SourceLocation RParenLoc) { 1959218893Sdim return getSema().BuildCXXUuidof(TypeInfoType, TypeidLoc, Operand, 1960218893Sdim RParenLoc); 1961218893Sdim } 1962218893Sdim 1963198092Srdivacky /// \brief Build a new C++ "this" expression. 1964198092Srdivacky /// 1965198092Srdivacky /// By default, builds a new "this" expression without performing any 1966198092Srdivacky /// semantic analysis. Subclasses may override this routine to provide 1967198092Srdivacky /// different behavior. 1968212904Sdim ExprResult RebuildCXXThisExpr(SourceLocation ThisLoc, 1969218893Sdim QualType ThisType, 1970218893Sdim bool isImplicit) { 1971234353Sdim getSema().CheckCXXThisCapture(ThisLoc); 1972198092Srdivacky return getSema().Owned( 1973202379Srdivacky new (getSema().Context) CXXThisExpr(ThisLoc, ThisType, 1974202379Srdivacky isImplicit)); 1975198092Srdivacky } 1976198092Srdivacky 1977198092Srdivacky /// \brief Build a new C++ throw expression. 1978198092Srdivacky /// 1979198092Srdivacky /// By default, performs semantic analysis to build the new expression. 1980198092Srdivacky /// Subclasses may override this routine to provide different behavior. 1981224145Sdim ExprResult RebuildCXXThrowExpr(SourceLocation ThrowLoc, Expr *Sub, 1982224145Sdim bool IsThrownVariableInScope) { 1983224145Sdim return getSema().BuildCXXThrow(ThrowLoc, Sub, IsThrownVariableInScope); 1984198092Srdivacky } 1985198092Srdivacky 1986198092Srdivacky /// \brief Build a new C++ default-argument expression. 1987198092Srdivacky /// 1988198092Srdivacky /// By default, builds a new default-argument expression, which does not 1989198092Srdivacky /// require any semantic analysis. Subclasses may override this routine to 1990198092Srdivacky /// provide different behavior. 1991239462Sdim ExprResult RebuildCXXDefaultArgExpr(SourceLocation Loc, 1992201361Srdivacky ParmVarDecl *Param) { 1993201361Srdivacky return getSema().Owned(CXXDefaultArgExpr::Create(getSema().Context, Loc, 1994201361Srdivacky Param)); 1995198092Srdivacky } 1996198092Srdivacky 1997251662Sdim /// \brief Build a new C++11 default-initialization expression. 1998251662Sdim /// 1999251662Sdim /// By default, builds a new default field initialization expression, which 2000251662Sdim /// does not require any semantic analysis. Subclasses may override this 2001251662Sdim /// routine to provide different behavior. 2002251662Sdim ExprResult RebuildCXXDefaultInitExpr(SourceLocation Loc, 2003251662Sdim FieldDecl *Field) { 2004251662Sdim return getSema().Owned(CXXDefaultInitExpr::Create(getSema().Context, Loc, 2005251662Sdim Field)); 2006251662Sdim } 2007251662Sdim 2008198092Srdivacky /// \brief Build a new C++ zero-initialization expression. 2009198092Srdivacky /// 2010198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2011198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2012218893Sdim ExprResult RebuildCXXScalarValueInitExpr(TypeSourceInfo *TSInfo, 2013218893Sdim SourceLocation LParenLoc, 2014218893Sdim SourceLocation RParenLoc) { 2015218893Sdim return getSema().BuildCXXTypeConstructExpr(TSInfo, LParenLoc, 2016251662Sdim None, RParenLoc); 2017198092Srdivacky } 2018198092Srdivacky 2019198092Srdivacky /// \brief Build a new C++ "new" expression. 2020198092Srdivacky /// 2021198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2022198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2023212904Sdim ExprResult RebuildCXXNewExpr(SourceLocation StartLoc, 2024218893Sdim bool UseGlobal, 2025218893Sdim SourceLocation PlacementLParen, 2026218893Sdim MultiExprArg PlacementArgs, 2027218893Sdim SourceLocation PlacementRParen, 2028218893Sdim SourceRange TypeIdParens, 2029218893Sdim QualType AllocatedType, 2030218893Sdim TypeSourceInfo *AllocatedTypeInfo, 2031218893Sdim Expr *ArraySize, 2032234353Sdim SourceRange DirectInitRange, 2033234353Sdim Expr *Initializer) { 2034198092Srdivacky return getSema().BuildCXXNew(StartLoc, UseGlobal, 2035198092Srdivacky PlacementLParen, 2036243830Sdim PlacementArgs, 2037198092Srdivacky PlacementRParen, 2038210299Sed TypeIdParens, 2039218893Sdim AllocatedType, 2040218893Sdim AllocatedTypeInfo, 2041212904Sdim ArraySize, 2042234353Sdim DirectInitRange, 2043234353Sdim Initializer); 2044198092Srdivacky } 2045198092Srdivacky 2046198092Srdivacky /// \brief Build a new C++ "delete" expression. 2047198092Srdivacky /// 2048198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2049198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2050212904Sdim ExprResult RebuildCXXDeleteExpr(SourceLocation StartLoc, 2051198092Srdivacky bool IsGlobalDelete, 2052198092Srdivacky bool IsArrayForm, 2053212904Sdim Expr *Operand) { 2054198092Srdivacky return getSema().ActOnCXXDelete(StartLoc, IsGlobalDelete, IsArrayForm, 2055212904Sdim Operand); 2056198092Srdivacky } 2057198092Srdivacky 2058198092Srdivacky /// \brief Build a new unary type trait expression. 2059198092Srdivacky /// 2060198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2061198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2062212904Sdim ExprResult RebuildUnaryTypeTrait(UnaryTypeTrait Trait, 2063218893Sdim SourceLocation StartLoc, 2064218893Sdim TypeSourceInfo *T, 2065218893Sdim SourceLocation RParenLoc) { 2066218893Sdim return getSema().BuildUnaryTypeTrait(Trait, StartLoc, T, RParenLoc); 2067198092Srdivacky } 2068198092Srdivacky 2069218893Sdim /// \brief Build a new binary type trait expression. 2070218893Sdim /// 2071218893Sdim /// By default, performs semantic analysis to build the new expression. 2072218893Sdim /// Subclasses may override this routine to provide different behavior. 2073218893Sdim ExprResult RebuildBinaryTypeTrait(BinaryTypeTrait Trait, 2074218893Sdim SourceLocation StartLoc, 2075218893Sdim TypeSourceInfo *LhsT, 2076218893Sdim TypeSourceInfo *RhsT, 2077218893Sdim SourceLocation RParenLoc) { 2078218893Sdim return getSema().BuildBinaryTypeTrait(Trait, StartLoc, LhsT, RhsT, RParenLoc); 2079218893Sdim } 2080218893Sdim 2081234353Sdim /// \brief Build a new type trait expression. 2082234353Sdim /// 2083234353Sdim /// By default, performs semantic analysis to build the new expression. 2084234353Sdim /// Subclasses may override this routine to provide different behavior. 2085234353Sdim ExprResult RebuildTypeTrait(TypeTrait Trait, 2086234353Sdim SourceLocation StartLoc, 2087234353Sdim ArrayRef<TypeSourceInfo *> Args, 2088234353Sdim SourceLocation RParenLoc) { 2089234353Sdim return getSema().BuildTypeTrait(Trait, StartLoc, Args, RParenLoc); 2090234353Sdim } 2091239462Sdim 2092221345Sdim /// \brief Build a new array type trait expression. 2093221345Sdim /// 2094221345Sdim /// By default, performs semantic analysis to build the new expression. 2095221345Sdim /// Subclasses may override this routine to provide different behavior. 2096221345Sdim ExprResult RebuildArrayTypeTrait(ArrayTypeTrait Trait, 2097221345Sdim SourceLocation StartLoc, 2098221345Sdim TypeSourceInfo *TSInfo, 2099221345Sdim Expr *DimExpr, 2100221345Sdim SourceLocation RParenLoc) { 2101221345Sdim return getSema().BuildArrayTypeTrait(Trait, StartLoc, TSInfo, DimExpr, RParenLoc); 2102221345Sdim } 2103221345Sdim 2104221345Sdim /// \brief Build a new expression trait expression. 2105221345Sdim /// 2106221345Sdim /// By default, performs semantic analysis to build the new expression. 2107221345Sdim /// Subclasses may override this routine to provide different behavior. 2108221345Sdim ExprResult RebuildExpressionTrait(ExpressionTrait Trait, 2109221345Sdim SourceLocation StartLoc, 2110221345Sdim Expr *Queried, 2111221345Sdim SourceLocation RParenLoc) { 2112221345Sdim return getSema().BuildExpressionTrait(Trait, StartLoc, Queried, RParenLoc); 2113221345Sdim } 2114221345Sdim 2115198092Srdivacky /// \brief Build a new (previously unresolved) declaration reference 2116198092Srdivacky /// expression. 2117198092Srdivacky /// 2118198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2119198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2120219077Sdim ExprResult RebuildDependentScopeDeclRefExpr( 2121219077Sdim NestedNameSpecifierLoc QualifierLoc, 2122234353Sdim SourceLocation TemplateKWLoc, 2123212904Sdim const DeclarationNameInfo &NameInfo, 2124243830Sdim const TemplateArgumentListInfo *TemplateArgs, 2125243830Sdim bool IsAddressOfOperand) { 2126198092Srdivacky CXXScopeSpec SS; 2127219077Sdim SS.Adopt(QualifierLoc); 2128199990Srdivacky 2129234353Sdim if (TemplateArgs || TemplateKWLoc.isValid()) 2130234353Sdim return getSema().BuildQualifiedTemplateIdExpr(SS, TemplateKWLoc, 2131234353Sdim NameInfo, TemplateArgs); 2132199990Srdivacky 2133243830Sdim return getSema().BuildQualifiedDeclarationNameExpr(SS, NameInfo, 2134243830Sdim IsAddressOfOperand); 2135198092Srdivacky } 2136198092Srdivacky 2137198092Srdivacky /// \brief Build a new template-id expression. 2138198092Srdivacky /// 2139198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2140198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2141212904Sdim ExprResult RebuildTemplateIdExpr(const CXXScopeSpec &SS, 2142234353Sdim SourceLocation TemplateKWLoc, 2143234353Sdim LookupResult &R, 2144234353Sdim bool RequiresADL, 2145234353Sdim const TemplateArgumentListInfo *TemplateArgs) { 2146234353Sdim return getSema().BuildTemplateIdExpr(SS, TemplateKWLoc, R, RequiresADL, 2147234353Sdim TemplateArgs); 2148198092Srdivacky } 2149198092Srdivacky 2150198092Srdivacky /// \brief Build a new object-construction expression. 2151198092Srdivacky /// 2152198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2153198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2154212904Sdim ExprResult RebuildCXXConstructExpr(QualType T, 2155226633Sdim SourceLocation Loc, 2156226633Sdim CXXConstructorDecl *Constructor, 2157226633Sdim bool IsElidable, 2158226633Sdim MultiExprArg Args, 2159226633Sdim bool HadMultipleCandidates, 2160249423Sdim bool ListInitialization, 2161226633Sdim bool RequiresZeroInit, 2162218893Sdim CXXConstructExpr::ConstructionKind ConstructKind, 2163226633Sdim SourceRange ParenRange) { 2164243830Sdim SmallVector<Expr*, 8> ConvertedArgs; 2165243830Sdim if (getSema().CompleteConstructorCall(Constructor, Args, Loc, 2166200583Srdivacky ConvertedArgs)) 2167212904Sdim return ExprError(); 2168239462Sdim 2169200583Srdivacky return getSema().BuildCXXConstructExpr(Loc, T, Constructor, IsElidable, 2170243830Sdim ConvertedArgs, 2171226633Sdim HadMultipleCandidates, 2172249423Sdim ListInitialization, 2173218893Sdim RequiresZeroInit, ConstructKind, 2174218893Sdim ParenRange); 2175198092Srdivacky } 2176198092Srdivacky 2177198092Srdivacky /// \brief Build a new object-construction expression. 2178198092Srdivacky /// 2179198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2180198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2181218893Sdim ExprResult RebuildCXXTemporaryObjectExpr(TypeSourceInfo *TSInfo, 2182218893Sdim SourceLocation LParenLoc, 2183218893Sdim MultiExprArg Args, 2184218893Sdim SourceLocation RParenLoc) { 2185218893Sdim return getSema().BuildCXXTypeConstructExpr(TSInfo, 2186198092Srdivacky LParenLoc, 2187243830Sdim Args, 2188198092Srdivacky RParenLoc); 2189198092Srdivacky } 2190198092Srdivacky 2191198092Srdivacky /// \brief Build a new object-construction expression. 2192198092Srdivacky /// 2193198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2194198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2195218893Sdim ExprResult RebuildCXXUnresolvedConstructExpr(TypeSourceInfo *TSInfo, 2196218893Sdim SourceLocation LParenLoc, 2197218893Sdim MultiExprArg Args, 2198218893Sdim SourceLocation RParenLoc) { 2199218893Sdim return getSema().BuildCXXTypeConstructExpr(TSInfo, 2200198092Srdivacky LParenLoc, 2201243830Sdim Args, 2202198092Srdivacky RParenLoc); 2203198092Srdivacky } 2204198092Srdivacky 2205198092Srdivacky /// \brief Build a new member reference expression. 2206198092Srdivacky /// 2207198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2208198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2209212904Sdim ExprResult RebuildCXXDependentScopeMemberExpr(Expr *BaseE, 2210221345Sdim QualType BaseType, 2211221345Sdim bool IsArrow, 2212221345Sdim SourceLocation OperatorLoc, 2213221345Sdim NestedNameSpecifierLoc QualifierLoc, 2214234353Sdim SourceLocation TemplateKWLoc, 2215199990Srdivacky NamedDecl *FirstQualifierInScope, 2216212904Sdim const DeclarationNameInfo &MemberNameInfo, 2217199990Srdivacky const TemplateArgumentListInfo *TemplateArgs) { 2218198092Srdivacky CXXScopeSpec SS; 2219221345Sdim SS.Adopt(QualifierLoc); 2220198092Srdivacky 2221212904Sdim return SemaRef.BuildMemberReferenceExpr(BaseE, BaseType, 2222200583Srdivacky OperatorLoc, IsArrow, 2223234353Sdim SS, TemplateKWLoc, 2224234353Sdim FirstQualifierInScope, 2225212904Sdim MemberNameInfo, 2226212904Sdim TemplateArgs); 2227198092Srdivacky } 2228198092Srdivacky 2229199990Srdivacky /// \brief Build a new member reference expression. 2230198092Srdivacky /// 2231198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2232198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2233234353Sdim ExprResult RebuildUnresolvedMemberExpr(Expr *BaseE, QualType BaseType, 2234234353Sdim SourceLocation OperatorLoc, 2235234353Sdim bool IsArrow, 2236234353Sdim NestedNameSpecifierLoc QualifierLoc, 2237234353Sdim SourceLocation TemplateKWLoc, 2238234353Sdim NamedDecl *FirstQualifierInScope, 2239234353Sdim LookupResult &R, 2240199990Srdivacky const TemplateArgumentListInfo *TemplateArgs) { 2241198092Srdivacky CXXScopeSpec SS; 2242221345Sdim SS.Adopt(QualifierLoc); 2243198092Srdivacky 2244212904Sdim return SemaRef.BuildMemberReferenceExpr(BaseE, BaseType, 2245200583Srdivacky OperatorLoc, IsArrow, 2246234353Sdim SS, TemplateKWLoc, 2247234353Sdim FirstQualifierInScope, 2248202379Srdivacky R, TemplateArgs); 2249198092Srdivacky } 2250198092Srdivacky 2251218893Sdim /// \brief Build a new noexcept expression. 2252218893Sdim /// 2253218893Sdim /// By default, performs semantic analysis to build the new expression. 2254218893Sdim /// Subclasses may override this routine to provide different behavior. 2255218893Sdim ExprResult RebuildCXXNoexceptExpr(SourceRange Range, Expr *Arg) { 2256218893Sdim return SemaRef.BuildCXXNoexceptExpr(Range.getBegin(), Arg, Range.getEnd()); 2257218893Sdim } 2258218893Sdim 2259218893Sdim /// \brief Build a new expression to compute the length of a parameter pack. 2260239462Sdim ExprResult RebuildSizeOfPackExpr(SourceLocation OperatorLoc, NamedDecl *Pack, 2261239462Sdim SourceLocation PackLoc, 2262218893Sdim SourceLocation RParenLoc, 2263249423Sdim Optional<unsigned> Length) { 2264226633Sdim if (Length) 2265239462Sdim return new (SemaRef.Context) SizeOfPackExpr(SemaRef.Context.getSizeType(), 2266239462Sdim OperatorLoc, Pack, PackLoc, 2267226633Sdim RParenLoc, *Length); 2268239462Sdim 2269239462Sdim return new (SemaRef.Context) SizeOfPackExpr(SemaRef.Context.getSizeType(), 2270239462Sdim OperatorLoc, Pack, PackLoc, 2271226633Sdim RParenLoc); 2272218893Sdim } 2273234353Sdim 2274239462Sdim /// \brief Build a new Objective-C boxed expression. 2275239462Sdim /// 2276239462Sdim /// By default, performs semantic analysis to build the new expression. 2277239462Sdim /// Subclasses may override this routine to provide different behavior. 2278239462Sdim ExprResult RebuildObjCBoxedExpr(SourceRange SR, Expr *ValueExpr) { 2279239462Sdim return getSema().BuildObjCBoxedExpr(SR, ValueExpr); 2280239462Sdim } 2281239462Sdim 2282234353Sdim /// \brief Build a new Objective-C array literal. 2283234353Sdim /// 2284234353Sdim /// By default, performs semantic analysis to build the new expression. 2285234353Sdim /// Subclasses may override this routine to provide different behavior. 2286234353Sdim ExprResult RebuildObjCArrayLiteral(SourceRange Range, 2287234353Sdim Expr **Elements, unsigned NumElements) { 2288239462Sdim return getSema().BuildObjCArrayLiteral(Range, 2289234353Sdim MultiExprArg(Elements, NumElements)); 2290234353Sdim } 2291239462Sdim 2292239462Sdim ExprResult RebuildObjCSubscriptRefExpr(SourceLocation RB, 2293234353Sdim Expr *Base, Expr *Key, 2294234353Sdim ObjCMethodDecl *getterMethod, 2295234353Sdim ObjCMethodDecl *setterMethod) { 2296234353Sdim return getSema().BuildObjCSubscriptExpression(RB, Base, Key, 2297234353Sdim getterMethod, setterMethod); 2298234353Sdim } 2299234353Sdim 2300234353Sdim /// \brief Build a new Objective-C dictionary literal. 2301234353Sdim /// 2302234353Sdim /// By default, performs semantic analysis to build the new expression. 2303234353Sdim /// Subclasses may override this routine to provide different behavior. 2304234353Sdim ExprResult RebuildObjCDictionaryLiteral(SourceRange Range, 2305234353Sdim ObjCDictionaryElement *Elements, 2306234353Sdim unsigned NumElements) { 2307234353Sdim return getSema().BuildObjCDictionaryLiteral(Range, Elements, NumElements); 2308234353Sdim } 2309239462Sdim 2310239462Sdim /// \brief Build a new Objective-C \@encode expression. 2311198092Srdivacky /// 2312198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2313198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2314212904Sdim ExprResult RebuildObjCEncodeExpr(SourceLocation AtLoc, 2315207619Srdivacky TypeSourceInfo *EncodeTypeInfo, 2316198092Srdivacky SourceLocation RParenLoc) { 2317207619Srdivacky return SemaRef.Owned(SemaRef.BuildObjCEncodeExpression(AtLoc, EncodeTypeInfo, 2318198092Srdivacky RParenLoc)); 2319198092Srdivacky } 2320198092Srdivacky 2321207619Srdivacky /// \brief Build a new Objective-C class message. 2322212904Sdim ExprResult RebuildObjCMessageExpr(TypeSourceInfo *ReceiverTypeInfo, 2323207619Srdivacky Selector Sel, 2324226633Sdim ArrayRef<SourceLocation> SelectorLocs, 2325207619Srdivacky ObjCMethodDecl *Method, 2326239462Sdim SourceLocation LBracLoc, 2327207619Srdivacky MultiExprArg Args, 2328207619Srdivacky SourceLocation RBracLoc) { 2329207619Srdivacky return SemaRef.BuildClassMessage(ReceiverTypeInfo, 2330207619Srdivacky ReceiverTypeInfo->getType(), 2331207619Srdivacky /*SuperLoc=*/SourceLocation(), 2332226633Sdim Sel, Method, LBracLoc, SelectorLocs, 2333243830Sdim RBracLoc, Args); 2334207619Srdivacky } 2335207619Srdivacky 2336207619Srdivacky /// \brief Build a new Objective-C instance message. 2337212904Sdim ExprResult RebuildObjCMessageExpr(Expr *Receiver, 2338207619Srdivacky Selector Sel, 2339226633Sdim ArrayRef<SourceLocation> SelectorLocs, 2340207619Srdivacky ObjCMethodDecl *Method, 2341239462Sdim SourceLocation LBracLoc, 2342207619Srdivacky MultiExprArg Args, 2343207619Srdivacky SourceLocation RBracLoc) { 2344212904Sdim return SemaRef.BuildInstanceMessage(Receiver, 2345212904Sdim Receiver->getType(), 2346207619Srdivacky /*SuperLoc=*/SourceLocation(), 2347226633Sdim Sel, Method, LBracLoc, SelectorLocs, 2348243830Sdim RBracLoc, Args); 2349207619Srdivacky } 2350207619Srdivacky 2351207619Srdivacky /// \brief Build a new Objective-C ivar reference expression. 2352198092Srdivacky /// 2353198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2354198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2355212904Sdim ExprResult RebuildObjCIvarRefExpr(Expr *BaseArg, ObjCIvarDecl *Ivar, 2356207619Srdivacky SourceLocation IvarLoc, 2357207619Srdivacky bool IsArrow, bool IsFreeIvar) { 2358207619Srdivacky // FIXME: We lose track of the IsFreeIvar bit. 2359207619Srdivacky CXXScopeSpec SS; 2360221345Sdim ExprResult Base = getSema().Owned(BaseArg); 2361207619Srdivacky LookupResult R(getSema(), Ivar->getDeclName(), IvarLoc, 2362207619Srdivacky Sema::LookupMemberName); 2363212904Sdim ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 2364207619Srdivacky /*FIME:*/IvarLoc, 2365212904Sdim SS, 0, 2366210299Sed false); 2367221345Sdim if (Result.isInvalid() || Base.isInvalid()) 2368212904Sdim return ExprError(); 2369239462Sdim 2370207619Srdivacky if (Result.get()) 2371243830Sdim return Result; 2372239462Sdim 2373221345Sdim return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), 2374234353Sdim /*FIXME:*/IvarLoc, IsArrow, 2375234353Sdim SS, SourceLocation(), 2376207619Srdivacky /*FirstQualifierInScope=*/0, 2377239462Sdim R, 2378207619Srdivacky /*TemplateArgs=*/0); 2379198092Srdivacky } 2380198092Srdivacky 2381207619Srdivacky /// \brief Build a new Objective-C property reference expression. 2382207619Srdivacky /// 2383207619Srdivacky /// By default, performs semantic analysis to build the new expression. 2384207619Srdivacky /// Subclasses may override this routine to provide different behavior. 2385239462Sdim ExprResult RebuildObjCPropertyRefExpr(Expr *BaseArg, 2386234353Sdim ObjCPropertyDecl *Property, 2387234353Sdim SourceLocation PropertyLoc) { 2388207619Srdivacky CXXScopeSpec SS; 2389221345Sdim ExprResult Base = getSema().Owned(BaseArg); 2390207619Srdivacky LookupResult R(getSema(), Property->getDeclName(), PropertyLoc, 2391207619Srdivacky Sema::LookupMemberName); 2392207619Srdivacky bool IsArrow = false; 2393212904Sdim ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 2394207619Srdivacky /*FIME:*/PropertyLoc, 2395212904Sdim SS, 0, false); 2396221345Sdim if (Result.isInvalid() || Base.isInvalid()) 2397212904Sdim return ExprError(); 2398239462Sdim 2399207619Srdivacky if (Result.get()) 2400243830Sdim return Result; 2401239462Sdim 2402221345Sdim return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), 2403239462Sdim /*FIXME:*/PropertyLoc, IsArrow, 2404234353Sdim SS, SourceLocation(), 2405207619Srdivacky /*FirstQualifierInScope=*/0, 2406239462Sdim R, 2407207619Srdivacky /*TemplateArgs=*/0); 2408207619Srdivacky } 2409239462Sdim 2410218893Sdim /// \brief Build a new Objective-C property reference expression. 2411207619Srdivacky /// 2412207619Srdivacky /// By default, performs semantic analysis to build the new expression. 2413218893Sdim /// Subclasses may override this routine to provide different behavior. 2414218893Sdim ExprResult RebuildObjCPropertyRefExpr(Expr *Base, QualType T, 2415218893Sdim ObjCMethodDecl *Getter, 2416218893Sdim ObjCMethodDecl *Setter, 2417218893Sdim SourceLocation PropertyLoc) { 2418218893Sdim // Since these expressions can only be value-dependent, we do not 2419218893Sdim // need to perform semantic analysis again. 2420212904Sdim return Owned( 2421218893Sdim new (getSema().Context) ObjCPropertyRefExpr(Getter, Setter, T, 2422218893Sdim VK_LValue, OK_ObjCProperty, 2423218893Sdim PropertyLoc, Base)); 2424207619Srdivacky } 2425207619Srdivacky 2426207619Srdivacky /// \brief Build a new Objective-C "isa" expression. 2427207619Srdivacky /// 2428207619Srdivacky /// By default, performs semantic analysis to build the new expression. 2429207619Srdivacky /// Subclasses may override this routine to provide different behavior. 2430212904Sdim ExprResult RebuildObjCIsaExpr(Expr *BaseArg, SourceLocation IsaLoc, 2431249423Sdim SourceLocation OpLoc, 2432207619Srdivacky bool IsArrow) { 2433207619Srdivacky CXXScopeSpec SS; 2434221345Sdim ExprResult Base = getSema().Owned(BaseArg); 2435207619Srdivacky LookupResult R(getSema(), &getSema().Context.Idents.get("isa"), IsaLoc, 2436207619Srdivacky Sema::LookupMemberName); 2437212904Sdim ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, 2438249423Sdim OpLoc, 2439212904Sdim SS, 0, false); 2440221345Sdim if (Result.isInvalid() || Base.isInvalid()) 2441212904Sdim return ExprError(); 2442239462Sdim 2443207619Srdivacky if (Result.get()) 2444243830Sdim return Result; 2445239462Sdim 2446221345Sdim return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), 2447249423Sdim OpLoc, IsArrow, 2448234353Sdim SS, SourceLocation(), 2449207619Srdivacky /*FirstQualifierInScope=*/0, 2450239462Sdim R, 2451207619Srdivacky /*TemplateArgs=*/0); 2452207619Srdivacky } 2453239462Sdim 2454198092Srdivacky /// \brief Build a new shuffle vector expression. 2455198092Srdivacky /// 2456198092Srdivacky /// By default, performs semantic analysis to build the new expression. 2457198092Srdivacky /// Subclasses may override this routine to provide different behavior. 2458212904Sdim ExprResult RebuildShuffleVectorExpr(SourceLocation BuiltinLoc, 2459218893Sdim MultiExprArg SubExprs, 2460218893Sdim SourceLocation RParenLoc) { 2461198092Srdivacky // Find the declaration for __builtin_shufflevector 2462198092Srdivacky const IdentifierInfo &Name 2463198092Srdivacky = SemaRef.Context.Idents.get("__builtin_shufflevector"); 2464198092Srdivacky TranslationUnitDecl *TUDecl = SemaRef.Context.getTranslationUnitDecl(); 2465198092Srdivacky DeclContext::lookup_result Lookup = TUDecl->lookup(DeclarationName(&Name)); 2466249423Sdim assert(!Lookup.empty() && "No __builtin_shufflevector?"); 2467198092Srdivacky 2468198092Srdivacky // Build a reference to the __builtin_shufflevector builtin 2469249423Sdim FunctionDecl *Builtin = cast<FunctionDecl>(Lookup.front()); 2470243830Sdim Expr *Callee = new (SemaRef.Context) DeclRefExpr(Builtin, false, 2471243830Sdim SemaRef.Context.BuiltinFnTy, 2472243830Sdim VK_RValue, BuiltinLoc); 2473243830Sdim QualType CalleePtrTy = SemaRef.Context.getPointerType(Builtin->getType()); 2474243830Sdim Callee = SemaRef.ImpCastExprToType(Callee, CalleePtrTy, 2475243830Sdim CK_BuiltinFnToFnPtr).take(); 2476198092Srdivacky 2477198092Srdivacky // Build the CallExpr 2478221345Sdim ExprResult TheCall = SemaRef.Owned( 2479243830Sdim new (SemaRef.Context) CallExpr(SemaRef.Context, Callee, SubExprs, 2480243830Sdim Builtin->getCallResultType(), 2481218893Sdim Expr::getValueKindForType(Builtin->getResultType()), 2482221345Sdim RParenLoc)); 2483198092Srdivacky 2484198092Srdivacky // Type-check the __builtin_shufflevector expression. 2485221345Sdim return SemaRef.SemaBuiltinShuffleVector(cast<CallExpr>(TheCall.take())); 2486198092Srdivacky } 2487218893Sdim 2488218893Sdim /// \brief Build a new template argument pack expansion. 2489218893Sdim /// 2490218893Sdim /// By default, performs semantic analysis to build a new pack expansion 2491239462Sdim /// for a template argument. Subclasses may override this routine to provide 2492218893Sdim /// different behavior. 2493218893Sdim TemplateArgumentLoc RebuildPackExpansion(TemplateArgumentLoc Pattern, 2494218893Sdim SourceLocation EllipsisLoc, 2495249423Sdim Optional<unsigned> NumExpansions) { 2496218893Sdim switch (Pattern.getArgument().getKind()) { 2497218893Sdim case TemplateArgument::Expression: { 2498218893Sdim ExprResult Result 2499218893Sdim = getSema().CheckPackExpansion(Pattern.getSourceExpression(), 2500218893Sdim EllipsisLoc, NumExpansions); 2501218893Sdim if (Result.isInvalid()) 2502218893Sdim return TemplateArgumentLoc(); 2503239462Sdim 2504218893Sdim return TemplateArgumentLoc(Result.get(), Result.get()); 2505218893Sdim } 2506239462Sdim 2507218893Sdim case TemplateArgument::Template: 2508218893Sdim return TemplateArgumentLoc(TemplateArgument( 2509218893Sdim Pattern.getArgument().getAsTemplate(), 2510218893Sdim NumExpansions), 2511221345Sdim Pattern.getTemplateQualifierLoc(), 2512218893Sdim Pattern.getTemplateNameLoc(), 2513218893Sdim EllipsisLoc); 2514239462Sdim 2515218893Sdim case TemplateArgument::Null: 2516218893Sdim case TemplateArgument::Integral: 2517218893Sdim case TemplateArgument::Declaration: 2518218893Sdim case TemplateArgument::Pack: 2519218893Sdim case TemplateArgument::TemplateExpansion: 2520243830Sdim case TemplateArgument::NullPtr: 2521218893Sdim llvm_unreachable("Pack expansion pattern has no parameter packs"); 2522239462Sdim 2523218893Sdim case TemplateArgument::Type: 2524239462Sdim if (TypeSourceInfo *Expansion 2525218893Sdim = getSema().CheckPackExpansion(Pattern.getTypeSourceInfo(), 2526218893Sdim EllipsisLoc, 2527218893Sdim NumExpansions)) 2528218893Sdim return TemplateArgumentLoc(TemplateArgument(Expansion->getType()), 2529218893Sdim Expansion); 2530218893Sdim break; 2531218893Sdim } 2532239462Sdim 2533218893Sdim return TemplateArgumentLoc(); 2534218893Sdim } 2535239462Sdim 2536218893Sdim /// \brief Build a new expression pack expansion. 2537218893Sdim /// 2538218893Sdim /// By default, performs semantic analysis to build a new pack expansion 2539239462Sdim /// for an expression. Subclasses may override this routine to provide 2540218893Sdim /// different behavior. 2541218893Sdim ExprResult RebuildPackExpansion(Expr *Pattern, SourceLocation EllipsisLoc, 2542249423Sdim Optional<unsigned> NumExpansions) { 2543218893Sdim return getSema().CheckPackExpansion(Pattern, EllipsisLoc, NumExpansions); 2544218893Sdim } 2545226633Sdim 2546226633Sdim /// \brief Build a new atomic operation expression. 2547226633Sdim /// 2548226633Sdim /// By default, performs semantic analysis to build the new expression. 2549226633Sdim /// Subclasses may override this routine to provide different behavior. 2550226633Sdim ExprResult RebuildAtomicExpr(SourceLocation BuiltinLoc, 2551226633Sdim MultiExprArg SubExprs, 2552226633Sdim QualType RetTy, 2553226633Sdim AtomicExpr::AtomicOp Op, 2554226633Sdim SourceLocation RParenLoc) { 2555226633Sdim // Just create the expression; there is not any interesting semantic 2556226633Sdim // analysis here because we can't actually build an AtomicExpr until 2557226633Sdim // we are sure it is semantically sound. 2558243830Sdim return new (SemaRef.Context) AtomicExpr(BuiltinLoc, SubExprs, RetTy, Op, 2559226633Sdim RParenLoc); 2560226633Sdim } 2561226633Sdim 2562218893Sdimprivate: 2563219077Sdim TypeLoc TransformTypeInObjectScope(TypeLoc TL, 2564219077Sdim QualType ObjectType, 2565219077Sdim NamedDecl *FirstQualifierInScope, 2566219077Sdim CXXScopeSpec &SS); 2567221345Sdim 2568221345Sdim TypeSourceInfo *TransformTypeInObjectScope(TypeSourceInfo *TSInfo, 2569221345Sdim QualType ObjectType, 2570221345Sdim NamedDecl *FirstQualifierInScope, 2571221345Sdim CXXScopeSpec &SS); 2572198092Srdivacky}; 2573198092Srdivacky 2574198092Srdivackytemplate<typename Derived> 2575212904SdimStmtResult TreeTransform<Derived>::TransformStmt(Stmt *S) { 2576198092Srdivacky if (!S) 2577198092Srdivacky return SemaRef.Owned(S); 2578198092Srdivacky 2579198092Srdivacky switch (S->getStmtClass()) { 2580198092Srdivacky case Stmt::NoStmtClass: break; 2581198092Srdivacky 2582198092Srdivacky // Transform individual statement nodes 2583198092Srdivacky#define STMT(Node, Parent) \ 2584198092Srdivacky case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S)); 2585218893Sdim#define ABSTRACT_STMT(Node) 2586198092Srdivacky#define EXPR(Node, Parent) 2587208600Srdivacky#include "clang/AST/StmtNodes.inc" 2588198092Srdivacky 2589198092Srdivacky // Transform expressions by calling TransformExpr. 2590198092Srdivacky#define STMT(Node, Parent) 2591208600Srdivacky#define ABSTRACT_STMT(Stmt) 2592198092Srdivacky#define EXPR(Node, Parent) case Stmt::Node##Class: 2593208600Srdivacky#include "clang/AST/StmtNodes.inc" 2594198092Srdivacky { 2595212904Sdim ExprResult E = getDerived().TransformExpr(cast<Expr>(S)); 2596198092Srdivacky if (E.isInvalid()) 2597212904Sdim return StmtError(); 2598198092Srdivacky 2599249423Sdim return getSema().ActOnExprStmt(E); 2600198092Srdivacky } 2601198092Srdivacky } 2602198092Srdivacky 2603218893Sdim return SemaRef.Owned(S); 2604198092Srdivacky} 2605198092Srdivacky 2606198092Srdivacky 2607198092Srdivackytemplate<typename Derived> 2608212904SdimExprResult TreeTransform<Derived>::TransformExpr(Expr *E) { 2609198092Srdivacky if (!E) 2610198092Srdivacky return SemaRef.Owned(E); 2611198092Srdivacky 2612198092Srdivacky switch (E->getStmtClass()) { 2613198092Srdivacky case Stmt::NoStmtClass: break; 2614198092Srdivacky#define STMT(Node, Parent) case Stmt::Node##Class: break; 2615208600Srdivacky#define ABSTRACT_STMT(Stmt) 2616198092Srdivacky#define EXPR(Node, Parent) \ 2617200583Srdivacky case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E)); 2618208600Srdivacky#include "clang/AST/StmtNodes.inc" 2619198092Srdivacky } 2620198092Srdivacky 2621218893Sdim return SemaRef.Owned(E); 2622198092Srdivacky} 2623198092Srdivacky 2624198092Srdivackytemplate<typename Derived> 2625249423SdimExprResult TreeTransform<Derived>::TransformInitializer(Expr *Init, 2626249423Sdim bool CXXDirectInit) { 2627249423Sdim // Initializers are instantiated like expressions, except that various outer 2628249423Sdim // layers are stripped. 2629249423Sdim if (!Init) 2630249423Sdim return SemaRef.Owned(Init); 2631249423Sdim 2632249423Sdim if (ExprWithCleanups *ExprTemp = dyn_cast<ExprWithCleanups>(Init)) 2633249423Sdim Init = ExprTemp->getSubExpr(); 2634249423Sdim 2635249423Sdim while (CXXBindTemporaryExpr *Binder = dyn_cast<CXXBindTemporaryExpr>(Init)) 2636249423Sdim Init = Binder->getSubExpr(); 2637249423Sdim 2638249423Sdim if (ImplicitCastExpr *ICE = dyn_cast<ImplicitCastExpr>(Init)) 2639249423Sdim Init = ICE->getSubExprAsWritten(); 2640249423Sdim 2641249423Sdim // If this is not a direct-initializer, we only need to reconstruct 2642249423Sdim // InitListExprs. Other forms of copy-initialization will be a no-op if 2643249423Sdim // the initializer is already the right type. 2644249423Sdim CXXConstructExpr *Construct = dyn_cast<CXXConstructExpr>(Init); 2645249423Sdim if (!CXXDirectInit && !(Construct && Construct->isListInitialization())) 2646249423Sdim return getDerived().TransformExpr(Init); 2647249423Sdim 2648249423Sdim // Revert value-initialization back to empty parens. 2649249423Sdim if (CXXScalarValueInitExpr *VIE = dyn_cast<CXXScalarValueInitExpr>(Init)) { 2650249423Sdim SourceRange Parens = VIE->getSourceRange(); 2651251662Sdim return getDerived().RebuildParenListExpr(Parens.getBegin(), None, 2652249423Sdim Parens.getEnd()); 2653249423Sdim } 2654249423Sdim 2655249423Sdim // FIXME: We shouldn't build ImplicitValueInitExprs for direct-initialization. 2656249423Sdim if (isa<ImplicitValueInitExpr>(Init)) 2657251662Sdim return getDerived().RebuildParenListExpr(SourceLocation(), None, 2658249423Sdim SourceLocation()); 2659249423Sdim 2660249423Sdim // Revert initialization by constructor back to a parenthesized or braced list 2661249423Sdim // of expressions. Any other form of initializer can just be reused directly. 2662249423Sdim if (!Construct || isa<CXXTemporaryObjectExpr>(Construct)) 2663249423Sdim return getDerived().TransformExpr(Init); 2664249423Sdim 2665249423Sdim SmallVector<Expr*, 8> NewArgs; 2666249423Sdim bool ArgChanged = false; 2667249423Sdim if (getDerived().TransformExprs(Construct->getArgs(), Construct->getNumArgs(), 2668249423Sdim /*IsCall*/true, NewArgs, &ArgChanged)) 2669249423Sdim return ExprError(); 2670249423Sdim 2671249423Sdim // If this was list initialization, revert to list form. 2672249423Sdim if (Construct->isListInitialization()) 2673249423Sdim return getDerived().RebuildInitList(Construct->getLocStart(), NewArgs, 2674249423Sdim Construct->getLocEnd(), 2675249423Sdim Construct->getType()); 2676249423Sdim 2677249423Sdim // Build a ParenListExpr to represent anything else. 2678249423Sdim SourceRange Parens = Construct->getParenRange(); 2679249423Sdim return getDerived().RebuildParenListExpr(Parens.getBegin(), NewArgs, 2680249423Sdim Parens.getEnd()); 2681249423Sdim} 2682249423Sdim 2683249423Sdimtemplate<typename Derived> 2684239462Sdimbool TreeTransform<Derived>::TransformExprs(Expr **Inputs, 2685239462Sdim unsigned NumInputs, 2686218893Sdim bool IsCall, 2687226633Sdim SmallVectorImpl<Expr *> &Outputs, 2688218893Sdim bool *ArgChanged) { 2689218893Sdim for (unsigned I = 0; I != NumInputs; ++I) { 2690218893Sdim // If requested, drop call arguments that need to be dropped. 2691218893Sdim if (IsCall && getDerived().DropCallArgument(Inputs[I])) { 2692218893Sdim if (ArgChanged) 2693218893Sdim *ArgChanged = true; 2694239462Sdim 2695218893Sdim break; 2696218893Sdim } 2697239462Sdim 2698218893Sdim if (PackExpansionExpr *Expansion = dyn_cast<PackExpansionExpr>(Inputs[I])) { 2699218893Sdim Expr *Pattern = Expansion->getPattern(); 2700239462Sdim 2701226633Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 2702218893Sdim getSema().collectUnexpandedParameterPacks(Pattern, Unexpanded); 2703218893Sdim assert(!Unexpanded.empty() && "Pack expansion without parameter packs?"); 2704239462Sdim 2705218893Sdim // Determine whether the set of unexpanded parameter packs can and should 2706218893Sdim // be expanded. 2707218893Sdim bool Expand = true; 2708218893Sdim bool RetainExpansion = false; 2709249423Sdim Optional<unsigned> OrigNumExpansions = Expansion->getNumExpansions(); 2710249423Sdim Optional<unsigned> NumExpansions = OrigNumExpansions; 2711218893Sdim if (getDerived().TryExpandParameterPacks(Expansion->getEllipsisLoc(), 2712218893Sdim Pattern->getSourceRange(), 2713226633Sdim Unexpanded, 2714218893Sdim Expand, RetainExpansion, 2715218893Sdim NumExpansions)) 2716218893Sdim return true; 2717239462Sdim 2718218893Sdim if (!Expand) { 2719218893Sdim // The transform has determined that we should perform a simple 2720239462Sdim // transformation on the pack expansion, producing another pack 2721218893Sdim // expansion. 2722218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 2723218893Sdim ExprResult OutPattern = getDerived().TransformExpr(Pattern); 2724218893Sdim if (OutPattern.isInvalid()) 2725218893Sdim return true; 2726239462Sdim 2727239462Sdim ExprResult Out = getDerived().RebuildPackExpansion(OutPattern.get(), 2728218893Sdim Expansion->getEllipsisLoc(), 2729218893Sdim NumExpansions); 2730218893Sdim if (Out.isInvalid()) 2731218893Sdim return true; 2732239462Sdim 2733218893Sdim if (ArgChanged) 2734218893Sdim *ArgChanged = true; 2735218893Sdim Outputs.push_back(Out.get()); 2736218893Sdim continue; 2737218893Sdim } 2738224145Sdim 2739224145Sdim // Record right away that the argument was changed. This needs 2740224145Sdim // to happen even if the array expands to nothing. 2741224145Sdim if (ArgChanged) *ArgChanged = true; 2742239462Sdim 2743218893Sdim // The transform has determined that we should perform an elementwise 2744218893Sdim // expansion of the pattern. Do so. 2745218893Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 2746218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 2747218893Sdim ExprResult Out = getDerived().TransformExpr(Pattern); 2748218893Sdim if (Out.isInvalid()) 2749218893Sdim return true; 2750218893Sdim 2751218893Sdim if (Out.get()->containsUnexpandedParameterPack()) { 2752218893Sdim Out = RebuildPackExpansion(Out.get(), Expansion->getEllipsisLoc(), 2753218893Sdim OrigNumExpansions); 2754218893Sdim if (Out.isInvalid()) 2755218893Sdim return true; 2756218893Sdim } 2757239462Sdim 2758218893Sdim Outputs.push_back(Out.get()); 2759218893Sdim } 2760239462Sdim 2761218893Sdim continue; 2762218893Sdim } 2763239462Sdim 2764249423Sdim ExprResult Result = 2765249423Sdim IsCall ? getDerived().TransformInitializer(Inputs[I], /*DirectInit*/false) 2766249423Sdim : getDerived().TransformExpr(Inputs[I]); 2767218893Sdim if (Result.isInvalid()) 2768218893Sdim return true; 2769239462Sdim 2770218893Sdim if (Result.get() != Inputs[I] && ArgChanged) 2771218893Sdim *ArgChanged = true; 2772239462Sdim 2773239462Sdim Outputs.push_back(Result.get()); 2774218893Sdim } 2775239462Sdim 2776218893Sdim return false; 2777218893Sdim} 2778218893Sdim 2779218893Sdimtemplate<typename Derived> 2780219077SdimNestedNameSpecifierLoc 2781219077SdimTreeTransform<Derived>::TransformNestedNameSpecifierLoc( 2782219077Sdim NestedNameSpecifierLoc NNS, 2783219077Sdim QualType ObjectType, 2784219077Sdim NamedDecl *FirstQualifierInScope) { 2785226633Sdim SmallVector<NestedNameSpecifierLoc, 4> Qualifiers; 2786239462Sdim for (NestedNameSpecifierLoc Qualifier = NNS; Qualifier; 2787219077Sdim Qualifier = Qualifier.getPrefix()) 2788219077Sdim Qualifiers.push_back(Qualifier); 2789219077Sdim 2790219077Sdim CXXScopeSpec SS; 2791219077Sdim while (!Qualifiers.empty()) { 2792219077Sdim NestedNameSpecifierLoc Q = Qualifiers.pop_back_val(); 2793219077Sdim NestedNameSpecifier *QNNS = Q.getNestedNameSpecifier(); 2794239462Sdim 2795219077Sdim switch (QNNS->getKind()) { 2796219077Sdim case NestedNameSpecifier::Identifier: 2797239462Sdim if (SemaRef.BuildCXXNestedNameSpecifier(/*Scope=*/0, 2798219077Sdim *QNNS->getAsIdentifier(), 2799239462Sdim Q.getLocalBeginLoc(), 2800219077Sdim Q.getLocalEndLoc(), 2801239462Sdim ObjectType, false, SS, 2802219077Sdim FirstQualifierInScope, false)) 2803219077Sdim return NestedNameSpecifierLoc(); 2804239462Sdim 2805219077Sdim break; 2806239462Sdim 2807219077Sdim case NestedNameSpecifier::Namespace: { 2808219077Sdim NamespaceDecl *NS 2809219077Sdim = cast_or_null<NamespaceDecl>( 2810219077Sdim getDerived().TransformDecl( 2811219077Sdim Q.getLocalBeginLoc(), 2812219077Sdim QNNS->getAsNamespace())); 2813219077Sdim SS.Extend(SemaRef.Context, NS, Q.getLocalBeginLoc(), Q.getLocalEndLoc()); 2814219077Sdim break; 2815219077Sdim } 2816239462Sdim 2817219077Sdim case NestedNameSpecifier::NamespaceAlias: { 2818219077Sdim NamespaceAliasDecl *Alias 2819219077Sdim = cast_or_null<NamespaceAliasDecl>( 2820219077Sdim getDerived().TransformDecl(Q.getLocalBeginLoc(), 2821219077Sdim QNNS->getAsNamespaceAlias())); 2822239462Sdim SS.Extend(SemaRef.Context, Alias, Q.getLocalBeginLoc(), 2823219077Sdim Q.getLocalEndLoc()); 2824219077Sdim break; 2825219077Sdim } 2826239462Sdim 2827219077Sdim case NestedNameSpecifier::Global: 2828219077Sdim // There is no meaningful transformation that one could perform on the 2829219077Sdim // global scope. 2830219077Sdim SS.MakeGlobal(SemaRef.Context, Q.getBeginLoc()); 2831219077Sdim break; 2832239462Sdim 2833219077Sdim case NestedNameSpecifier::TypeSpecWithTemplate: 2834219077Sdim case NestedNameSpecifier::TypeSpec: { 2835219077Sdim TypeLoc TL = TransformTypeInObjectScope(Q.getTypeLoc(), ObjectType, 2836219077Sdim FirstQualifierInScope, SS); 2837239462Sdim 2838219077Sdim if (!TL) 2839219077Sdim return NestedNameSpecifierLoc(); 2840239462Sdim 2841219077Sdim if (TL.getType()->isDependentType() || TL.getType()->isRecordType() || 2842249423Sdim (SemaRef.getLangOpts().CPlusPlus11 && 2843219077Sdim TL.getType()->isEnumeralType())) { 2844239462Sdim assert(!TL.getType().hasLocalQualifiers() && 2845219077Sdim "Can't get cv-qualifiers here"); 2846234353Sdim if (TL.getType()->isEnumeralType()) 2847234353Sdim SemaRef.Diag(TL.getBeginLoc(), 2848234353Sdim diag::warn_cxx98_compat_enum_nested_name_spec); 2849219077Sdim SS.Extend(SemaRef.Context, /*FIXME:*/SourceLocation(), TL, 2850219077Sdim Q.getLocalEndLoc()); 2851219077Sdim break; 2852219077Sdim } 2853223017Sdim // If the nested-name-specifier is an invalid type def, don't emit an 2854223017Sdim // error because a previous error should have already been emitted. 2855249423Sdim TypedefTypeLoc TTL = TL.getAs<TypedefTypeLoc>(); 2856249423Sdim if (!TTL || !TTL.getTypedefNameDecl()->isInvalidDecl()) { 2857239462Sdim SemaRef.Diag(TL.getBeginLoc(), diag::err_nested_name_spec_non_tag) 2858223017Sdim << TL.getType() << SS.getRange(); 2859223017Sdim } 2860219077Sdim return NestedNameSpecifierLoc(); 2861219077Sdim } 2862221345Sdim } 2863239462Sdim 2864221345Sdim // The qualifier-in-scope and object type only apply to the leftmost entity. 2865219077Sdim FirstQualifierInScope = 0; 2866221345Sdim ObjectType = QualType(); 2867219077Sdim } 2868239462Sdim 2869219077Sdim // Don't rebuild the nested-name-specifier if we don't have to. 2870239462Sdim if (SS.getScopeRep() == NNS.getNestedNameSpecifier() && 2871219077Sdim !getDerived().AlwaysRebuild()) 2872219077Sdim return NNS; 2873239462Sdim 2874239462Sdim // If we can re-use the source-location data from the original 2875219077Sdim // nested-name-specifier, do so. 2876219077Sdim if (SS.location_size() == NNS.getDataLength() && 2877219077Sdim memcmp(SS.location_data(), NNS.getOpaqueData(), SS.location_size()) == 0) 2878219077Sdim return NestedNameSpecifierLoc(SS.getScopeRep(), NNS.getOpaqueData()); 2879219077Sdim 2880219077Sdim // Allocate new nested-name-specifier location information. 2881219077Sdim return SS.getWithLocInContext(SemaRef.Context); 2882219077Sdim} 2883219077Sdim 2884219077Sdimtemplate<typename Derived> 2885212904SdimDeclarationNameInfo 2886212904SdimTreeTransform<Derived> 2887218893Sdim::TransformDeclarationNameInfo(const DeclarationNameInfo &NameInfo) { 2888212904Sdim DeclarationName Name = NameInfo.getName(); 2889198092Srdivacky if (!Name) 2890212904Sdim return DeclarationNameInfo(); 2891198092Srdivacky 2892198092Srdivacky switch (Name.getNameKind()) { 2893198092Srdivacky case DeclarationName::Identifier: 2894198092Srdivacky case DeclarationName::ObjCZeroArgSelector: 2895198092Srdivacky case DeclarationName::ObjCOneArgSelector: 2896198092Srdivacky case DeclarationName::ObjCMultiArgSelector: 2897198092Srdivacky case DeclarationName::CXXOperatorName: 2898199990Srdivacky case DeclarationName::CXXLiteralOperatorName: 2899198092Srdivacky case DeclarationName::CXXUsingDirective: 2900212904Sdim return NameInfo; 2901198092Srdivacky 2902198092Srdivacky case DeclarationName::CXXConstructorName: 2903198092Srdivacky case DeclarationName::CXXDestructorName: 2904198092Srdivacky case DeclarationName::CXXConversionFunctionName: { 2905212904Sdim TypeSourceInfo *NewTInfo; 2906212904Sdim CanQualType NewCanTy; 2907212904Sdim if (TypeSourceInfo *OldTInfo = NameInfo.getNamedTypeInfo()) { 2908218893Sdim NewTInfo = getDerived().TransformType(OldTInfo); 2909218893Sdim if (!NewTInfo) 2910218893Sdim return DeclarationNameInfo(); 2911218893Sdim NewCanTy = SemaRef.Context.getCanonicalType(NewTInfo->getType()); 2912212904Sdim } 2913212904Sdim else { 2914212904Sdim NewTInfo = 0; 2915212904Sdim TemporaryBase Rebase(*this, NameInfo.getLoc(), Name); 2916218893Sdim QualType NewT = getDerived().TransformType(Name.getCXXNameType()); 2917212904Sdim if (NewT.isNull()) 2918212904Sdim return DeclarationNameInfo(); 2919212904Sdim NewCanTy = SemaRef.Context.getCanonicalType(NewT); 2920212904Sdim } 2921198092Srdivacky 2922212904Sdim DeclarationName NewName 2923212904Sdim = SemaRef.Context.DeclarationNames.getCXXSpecialName(Name.getNameKind(), 2924212904Sdim NewCanTy); 2925212904Sdim DeclarationNameInfo NewNameInfo(NameInfo); 2926212904Sdim NewNameInfo.setName(NewName); 2927212904Sdim NewNameInfo.setNamedTypeInfo(NewTInfo); 2928212904Sdim return NewNameInfo; 2929198092Srdivacky } 2930198092Srdivacky } 2931198092Srdivacky 2932226633Sdim llvm_unreachable("Unknown name kind."); 2933198092Srdivacky} 2934198092Srdivacky 2935198092Srdivackytemplate<typename Derived> 2936198092SrdivackyTemplateName 2937221345SdimTreeTransform<Derived>::TransformTemplateName(CXXScopeSpec &SS, 2938221345Sdim TemplateName Name, 2939221345Sdim SourceLocation NameLoc, 2940218893Sdim QualType ObjectType, 2941218893Sdim NamedDecl *FirstQualifierInScope) { 2942198092Srdivacky if (QualifiedTemplateName *QTN = Name.getAsQualifiedTemplateName()) { 2943221345Sdim TemplateDecl *Template = QTN->getTemplateDecl(); 2944221345Sdim assert(Template && "qualified template name must refer to a template"); 2945239462Sdim 2946221345Sdim TemplateDecl *TransTemplate 2947239462Sdim = cast_or_null<TemplateDecl>(getDerived().TransformDecl(NameLoc, 2948221345Sdim Template)); 2949221345Sdim if (!TransTemplate) 2950198092Srdivacky return TemplateName(); 2951239462Sdim 2952221345Sdim if (!getDerived().AlwaysRebuild() && 2953221345Sdim SS.getScopeRep() == QTN->getQualifier() && 2954221345Sdim TransTemplate == Template) 2955221345Sdim return Name; 2956239462Sdim 2957221345Sdim return getDerived().RebuildTemplateName(SS, QTN->hasTemplateKeyword(), 2958221345Sdim TransTemplate); 2959198092Srdivacky } 2960239462Sdim 2961198092Srdivacky if (DependentTemplateName *DTN = Name.getAsDependentTemplateName()) { 2962221345Sdim if (SS.getScopeRep()) { 2963218893Sdim // These apply to the scope specifier, not the template. 2964218893Sdim ObjectType = QualType(); 2965218893Sdim FirstQualifierInScope = 0; 2966239462Sdim } 2967239462Sdim 2968198092Srdivacky if (!getDerived().AlwaysRebuild() && 2969221345Sdim SS.getScopeRep() == DTN->getQualifier() && 2970198398Srdivacky ObjectType.isNull()) 2971198092Srdivacky return Name; 2972239462Sdim 2973218893Sdim if (DTN->isIdentifier()) { 2974221345Sdim return getDerived().RebuildTemplateName(SS, 2975239462Sdim *DTN->getIdentifier(), 2976221345Sdim NameLoc, 2977218893Sdim ObjectType, 2978218893Sdim FirstQualifierInScope); 2979218893Sdim } 2980239462Sdim 2981221345Sdim return getDerived().RebuildTemplateName(SS, DTN->getOperator(), NameLoc, 2982198893Srdivacky ObjectType); 2983198092Srdivacky } 2984239462Sdim 2985198092Srdivacky if (TemplateDecl *Template = Name.getAsTemplateDecl()) { 2986198092Srdivacky TemplateDecl *TransTemplate 2987239462Sdim = cast_or_null<TemplateDecl>(getDerived().TransformDecl(NameLoc, 2988221345Sdim Template)); 2989198092Srdivacky if (!TransTemplate) 2990198092Srdivacky return TemplateName(); 2991239462Sdim 2992198092Srdivacky if (!getDerived().AlwaysRebuild() && 2993198092Srdivacky TransTemplate == Template) 2994198092Srdivacky return Name; 2995239462Sdim 2996198092Srdivacky return TemplateName(TransTemplate); 2997198092Srdivacky } 2998239462Sdim 2999218893Sdim if (SubstTemplateTemplateParmPackStorage *SubstPack 3000221345Sdim = Name.getAsSubstTemplateTemplateParmPack()) { 3001218893Sdim TemplateTemplateParmDecl *TransParam 3002221345Sdim = cast_or_null<TemplateTemplateParmDecl>( 3003221345Sdim getDerived().TransformDecl(NameLoc, SubstPack->getParameterPack())); 3004218893Sdim if (!TransParam) 3005218893Sdim return TemplateName(); 3006239462Sdim 3007218893Sdim if (!getDerived().AlwaysRebuild() && 3008218893Sdim TransParam == SubstPack->getParameterPack()) 3009218893Sdim return Name; 3010239462Sdim 3011239462Sdim return getDerived().RebuildTemplateName(TransParam, 3012218893Sdim SubstPack->getArgumentPack()); 3013218893Sdim } 3014239462Sdim 3015199990Srdivacky // These should be getting filtered out before they reach the AST. 3016218893Sdim llvm_unreachable("overloaded function decl survived to here"); 3017198092Srdivacky} 3018198092Srdivacky 3019198092Srdivackytemplate<typename Derived> 3020198893Srdivackyvoid TreeTransform<Derived>::InventTemplateArgumentLoc( 3021198893Srdivacky const TemplateArgument &Arg, 3022198893Srdivacky TemplateArgumentLoc &Output) { 3023198893Srdivacky SourceLocation Loc = getDerived().getBaseLocation(); 3024198092Srdivacky switch (Arg.getKind()) { 3025198092Srdivacky case TemplateArgument::Null: 3026200583Srdivacky llvm_unreachable("null template argument in TreeTransform"); 3027198893Srdivacky break; 3028198893Srdivacky 3029198893Srdivacky case TemplateArgument::Type: 3030198893Srdivacky Output = TemplateArgumentLoc(Arg, 3031200583Srdivacky SemaRef.Context.getTrivialTypeSourceInfo(Arg.getAsType(), Loc)); 3032239462Sdim 3033198893Srdivacky break; 3034198893Srdivacky 3035199482Srdivacky case TemplateArgument::Template: 3036221345Sdim case TemplateArgument::TemplateExpansion: { 3037221345Sdim NestedNameSpecifierLocBuilder Builder; 3038221345Sdim TemplateName Template = Arg.getAsTemplate(); 3039221345Sdim if (DependentTemplateName *DTN = Template.getAsDependentTemplateName()) 3040221345Sdim Builder.MakeTrivial(SemaRef.Context, DTN->getQualifier(), Loc); 3041221345Sdim else if (QualifiedTemplateName *QTN = Template.getAsQualifiedTemplateName()) 3042221345Sdim Builder.MakeTrivial(SemaRef.Context, QTN->getQualifier(), Loc); 3043239462Sdim 3044221345Sdim if (Arg.getKind() == TemplateArgument::Template) 3045239462Sdim Output = TemplateArgumentLoc(Arg, 3046221345Sdim Builder.getWithLocInContext(SemaRef.Context), 3047221345Sdim Loc); 3048221345Sdim else 3049239462Sdim Output = TemplateArgumentLoc(Arg, 3050221345Sdim Builder.getWithLocInContext(SemaRef.Context), 3051221345Sdim Loc, Loc); 3052239462Sdim 3053199482Srdivacky break; 3054221345Sdim } 3055218893Sdim 3056198893Srdivacky case TemplateArgument::Expression: 3057198893Srdivacky Output = TemplateArgumentLoc(Arg, Arg.getAsExpr()); 3058198893Srdivacky break; 3059198893Srdivacky 3060198893Srdivacky case TemplateArgument::Declaration: 3061198092Srdivacky case TemplateArgument::Integral: 3062198893Srdivacky case TemplateArgument::Pack: 3063243830Sdim case TemplateArgument::NullPtr: 3064198893Srdivacky Output = TemplateArgumentLoc(Arg, TemplateArgumentLocInfo()); 3065198893Srdivacky break; 3066198893Srdivacky } 3067198893Srdivacky} 3068198092Srdivacky 3069198893Srdivackytemplate<typename Derived> 3070198893Srdivackybool TreeTransform<Derived>::TransformTemplateArgument( 3071198893Srdivacky const TemplateArgumentLoc &Input, 3072198893Srdivacky TemplateArgumentLoc &Output) { 3073198893Srdivacky const TemplateArgument &Arg = Input.getArgument(); 3074198893Srdivacky switch (Arg.getKind()) { 3075198893Srdivacky case TemplateArgument::Null: 3076198893Srdivacky case TemplateArgument::Integral: 3077243830Sdim case TemplateArgument::Pack: 3078243830Sdim case TemplateArgument::Declaration: 3079243830Sdim case TemplateArgument::NullPtr: 3080243830Sdim llvm_unreachable("Unexpected TemplateArgument"); 3081198893Srdivacky 3082198092Srdivacky case TemplateArgument::Type: { 3083200583Srdivacky TypeSourceInfo *DI = Input.getTypeSourceInfo(); 3084198893Srdivacky if (DI == NULL) 3085200583Srdivacky DI = InventTypeSourceInfo(Input.getArgument().getAsType()); 3086198893Srdivacky 3087198893Srdivacky DI = getDerived().TransformType(DI); 3088198893Srdivacky if (!DI) return true; 3089198893Srdivacky 3090198893Srdivacky Output = TemplateArgumentLoc(TemplateArgument(DI->getType()), DI); 3091198893Srdivacky return false; 3092198092Srdivacky } 3093198092Srdivacky 3094199482Srdivacky case TemplateArgument::Template: { 3095221345Sdim NestedNameSpecifierLoc QualifierLoc = Input.getTemplateQualifierLoc(); 3096221345Sdim if (QualifierLoc) { 3097221345Sdim QualifierLoc = getDerived().TransformNestedNameSpecifierLoc(QualifierLoc); 3098221345Sdim if (!QualifierLoc) 3099221345Sdim return true; 3100221345Sdim } 3101239462Sdim 3102221345Sdim CXXScopeSpec SS; 3103221345Sdim SS.Adopt(QualifierLoc); 3104199482Srdivacky TemplateName Template 3105221345Sdim = getDerived().TransformTemplateName(SS, Arg.getAsTemplate(), 3106221345Sdim Input.getTemplateNameLoc()); 3107199482Srdivacky if (Template.isNull()) 3108199482Srdivacky return true; 3109239462Sdim 3110221345Sdim Output = TemplateArgumentLoc(TemplateArgument(Template), QualifierLoc, 3111199482Srdivacky Input.getTemplateNameLoc()); 3112199482Srdivacky return false; 3113199482Srdivacky } 3114218893Sdim 3115218893Sdim case TemplateArgument::TemplateExpansion: 3116218893Sdim llvm_unreachable("Caller should expand pack expansions"); 3117218893Sdim 3118198092Srdivacky case TemplateArgument::Expression: { 3119234353Sdim // Template argument expressions are constant expressions. 3120198092Srdivacky EnterExpressionEvaluationContext Unevaluated(getSema(), 3121234353Sdim Sema::ConstantEvaluated); 3122198092Srdivacky 3123198893Srdivacky Expr *InputExpr = Input.getSourceExpression(); 3124198893Srdivacky if (!InputExpr) InputExpr = Input.getArgument().getAsExpr(); 3125198893Srdivacky 3126221345Sdim ExprResult E = getDerived().TransformExpr(InputExpr); 3127234353Sdim E = SemaRef.ActOnConstantExpression(E); 3128198893Srdivacky if (E.isInvalid()) return true; 3129212904Sdim Output = TemplateArgumentLoc(TemplateArgument(E.take()), E.take()); 3130198893Srdivacky return false; 3131198092Srdivacky } 3132198092Srdivacky } 3133198092Srdivacky 3134198092Srdivacky // Work around bogus GCC warning 3135198893Srdivacky return true; 3136198092Srdivacky} 3137198092Srdivacky 3138218893Sdim/// \brief Iterator adaptor that invents template argument location information 3139218893Sdim/// for each of the template arguments in its underlying iterator. 3140218893Sdimtemplate<typename Derived, typename InputIterator> 3141218893Sdimclass TemplateArgumentLocInventIterator { 3142218893Sdim TreeTransform<Derived> &Self; 3143218893Sdim InputIterator Iter; 3144239462Sdim 3145218893Sdimpublic: 3146218893Sdim typedef TemplateArgumentLoc value_type; 3147218893Sdim typedef TemplateArgumentLoc reference; 3148218893Sdim typedef typename std::iterator_traits<InputIterator>::difference_type 3149218893Sdim difference_type; 3150218893Sdim typedef std::input_iterator_tag iterator_category; 3151239462Sdim 3152218893Sdim class pointer { 3153218893Sdim TemplateArgumentLoc Arg; 3154239462Sdim 3155218893Sdim public: 3156218893Sdim explicit pointer(TemplateArgumentLoc Arg) : Arg(Arg) { } 3157239462Sdim 3158218893Sdim const TemplateArgumentLoc *operator->() const { return &Arg; } 3159218893Sdim }; 3160239462Sdim 3161218893Sdim TemplateArgumentLocInventIterator() { } 3162239462Sdim 3163218893Sdim explicit TemplateArgumentLocInventIterator(TreeTransform<Derived> &Self, 3164218893Sdim InputIterator Iter) 3165218893Sdim : Self(Self), Iter(Iter) { } 3166239462Sdim 3167218893Sdim TemplateArgumentLocInventIterator &operator++() { 3168218893Sdim ++Iter; 3169218893Sdim return *this; 3170218893Sdim } 3171239462Sdim 3172218893Sdim TemplateArgumentLocInventIterator operator++(int) { 3173218893Sdim TemplateArgumentLocInventIterator Old(*this); 3174218893Sdim ++(*this); 3175218893Sdim return Old; 3176218893Sdim } 3177239462Sdim 3178218893Sdim reference operator*() const { 3179218893Sdim TemplateArgumentLoc Result; 3180218893Sdim Self.InventTemplateArgumentLoc(*Iter, Result); 3181218893Sdim return Result; 3182218893Sdim } 3183239462Sdim 3184218893Sdim pointer operator->() const { return pointer(**this); } 3185239462Sdim 3186218893Sdim friend bool operator==(const TemplateArgumentLocInventIterator &X, 3187218893Sdim const TemplateArgumentLocInventIterator &Y) { 3188218893Sdim return X.Iter == Y.Iter; 3189218893Sdim } 3190218893Sdim 3191218893Sdim friend bool operator!=(const TemplateArgumentLocInventIterator &X, 3192218893Sdim const TemplateArgumentLocInventIterator &Y) { 3193218893Sdim return X.Iter != Y.Iter; 3194218893Sdim } 3195218893Sdim}; 3196239462Sdim 3197218893Sdimtemplate<typename Derived> 3198218893Sdimtemplate<typename InputIterator> 3199218893Sdimbool TreeTransform<Derived>::TransformTemplateArguments(InputIterator First, 3200218893Sdim InputIterator Last, 3201218893Sdim TemplateArgumentListInfo &Outputs) { 3202218893Sdim for (; First != Last; ++First) { 3203218893Sdim TemplateArgumentLoc Out; 3204218893Sdim TemplateArgumentLoc In = *First; 3205239462Sdim 3206218893Sdim if (In.getArgument().getKind() == TemplateArgument::Pack) { 3207218893Sdim // Unpack argument packs, which we translate them into separate 3208218893Sdim // arguments. 3209218893Sdim // FIXME: We could do much better if we could guarantee that the 3210218893Sdim // TemplateArgumentLocInfo for the pack expansion would be usable for 3211218893Sdim // all of the template arguments in the argument pack. 3212239462Sdim typedef TemplateArgumentLocInventIterator<Derived, 3213218893Sdim TemplateArgument::pack_iterator> 3214218893Sdim PackLocIterator; 3215239462Sdim if (TransformTemplateArguments(PackLocIterator(*this, 3216218893Sdim In.getArgument().pack_begin()), 3217218893Sdim PackLocIterator(*this, 3218218893Sdim In.getArgument().pack_end()), 3219218893Sdim Outputs)) 3220218893Sdim return true; 3221239462Sdim 3222218893Sdim continue; 3223218893Sdim } 3224239462Sdim 3225218893Sdim if (In.getArgument().isPackExpansion()) { 3226218893Sdim // We have a pack expansion, for which we will be substituting into 3227218893Sdim // the pattern. 3228218893Sdim SourceLocation Ellipsis; 3229249423Sdim Optional<unsigned> OrigNumExpansions; 3230218893Sdim TemplateArgumentLoc Pattern 3231239462Sdim = In.getPackExpansionPattern(Ellipsis, OrigNumExpansions, 3232218893Sdim getSema().Context); 3233239462Sdim 3234226633Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 3235218893Sdim getSema().collectUnexpandedParameterPacks(Pattern, Unexpanded); 3236218893Sdim assert(!Unexpanded.empty() && "Pack expansion without parameter packs?"); 3237239462Sdim 3238218893Sdim // Determine whether the set of unexpanded parameter packs can and should 3239218893Sdim // be expanded. 3240218893Sdim bool Expand = true; 3241218893Sdim bool RetainExpansion = false; 3242249423Sdim Optional<unsigned> NumExpansions = OrigNumExpansions; 3243218893Sdim if (getDerived().TryExpandParameterPacks(Ellipsis, 3244218893Sdim Pattern.getSourceRange(), 3245226633Sdim Unexpanded, 3246239462Sdim Expand, 3247218893Sdim RetainExpansion, 3248218893Sdim NumExpansions)) 3249218893Sdim return true; 3250239462Sdim 3251218893Sdim if (!Expand) { 3252218893Sdim // The transform has determined that we should perform a simple 3253239462Sdim // transformation on the pack expansion, producing another pack 3254218893Sdim // expansion. 3255218893Sdim TemplateArgumentLoc OutPattern; 3256218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 3257218893Sdim if (getDerived().TransformTemplateArgument(Pattern, OutPattern)) 3258218893Sdim return true; 3259239462Sdim 3260218893Sdim Out = getDerived().RebuildPackExpansion(OutPattern, Ellipsis, 3261218893Sdim NumExpansions); 3262218893Sdim if (Out.getArgument().isNull()) 3263218893Sdim return true; 3264239462Sdim 3265218893Sdim Outputs.addArgument(Out); 3266218893Sdim continue; 3267218893Sdim } 3268239462Sdim 3269218893Sdim // The transform has determined that we should perform an elementwise 3270218893Sdim // expansion of the pattern. Do so. 3271218893Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 3272218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 3273218893Sdim 3274218893Sdim if (getDerived().TransformTemplateArgument(Pattern, Out)) 3275218893Sdim return true; 3276239462Sdim 3277218893Sdim if (Out.getArgument().containsUnexpandedParameterPack()) { 3278218893Sdim Out = getDerived().RebuildPackExpansion(Out, Ellipsis, 3279218893Sdim OrigNumExpansions); 3280218893Sdim if (Out.getArgument().isNull()) 3281218893Sdim return true; 3282218893Sdim } 3283239462Sdim 3284218893Sdim Outputs.addArgument(Out); 3285218893Sdim } 3286239462Sdim 3287218893Sdim // If we're supposed to retain a pack expansion, do so by temporarily 3288218893Sdim // forgetting the partially-substituted parameter pack. 3289218893Sdim if (RetainExpansion) { 3290218893Sdim ForgetPartiallySubstitutedPackRAII Forget(getDerived()); 3291239462Sdim 3292218893Sdim if (getDerived().TransformTemplateArgument(Pattern, Out)) 3293218893Sdim return true; 3294239462Sdim 3295218893Sdim Out = getDerived().RebuildPackExpansion(Out, Ellipsis, 3296218893Sdim OrigNumExpansions); 3297218893Sdim if (Out.getArgument().isNull()) 3298218893Sdim return true; 3299239462Sdim 3300218893Sdim Outputs.addArgument(Out); 3301218893Sdim } 3302239462Sdim 3303218893Sdim continue; 3304218893Sdim } 3305239462Sdim 3306239462Sdim // The simple case: 3307218893Sdim if (getDerived().TransformTemplateArgument(In, Out)) 3308218893Sdim return true; 3309239462Sdim 3310218893Sdim Outputs.addArgument(Out); 3311218893Sdim } 3312239462Sdim 3313218893Sdim return false; 3314218893Sdim 3315218893Sdim} 3316218893Sdim 3317198092Srdivacky//===----------------------------------------------------------------------===// 3318198092Srdivacky// Type transformation 3319198092Srdivacky//===----------------------------------------------------------------------===// 3320198092Srdivacky 3321198092Srdivackytemplate<typename Derived> 3322218893SdimQualType TreeTransform<Derived>::TransformType(QualType T) { 3323198092Srdivacky if (getDerived().AlreadyTransformed(T)) 3324198092Srdivacky return T; 3325198092Srdivacky 3326198398Srdivacky // Temporary workaround. All of these transformations should 3327198398Srdivacky // eventually turn into transformations on TypeLocs. 3328218893Sdim TypeSourceInfo *DI = getSema().Context.getTrivialTypeSourceInfo(T, 3329218893Sdim getDerived().getBaseLocation()); 3330239462Sdim 3331218893Sdim TypeSourceInfo *NewDI = getDerived().TransformType(DI); 3332198092Srdivacky 3333198398Srdivacky if (!NewDI) 3334198398Srdivacky return QualType(); 3335198092Srdivacky 3336198398Srdivacky return NewDI->getType(); 3337198092Srdivacky} 3338198092Srdivacky 3339198092Srdivackytemplate<typename Derived> 3340218893SdimTypeSourceInfo *TreeTransform<Derived>::TransformType(TypeSourceInfo *DI) { 3341234353Sdim // Refine the base location to the type's location. 3342234353Sdim TemporaryBase Rebase(*this, DI->getTypeLoc().getBeginLoc(), 3343234353Sdim getDerived().getBaseEntity()); 3344198398Srdivacky if (getDerived().AlreadyTransformed(DI->getType())) 3345198398Srdivacky return DI; 3346198092Srdivacky 3347198398Srdivacky TypeLocBuilder TLB; 3348198398Srdivacky 3349198398Srdivacky TypeLoc TL = DI->getTypeLoc(); 3350198398Srdivacky TLB.reserve(TL.getFullDataSize()); 3351198398Srdivacky 3352218893Sdim QualType Result = getDerived().TransformType(TLB, TL); 3353198398Srdivacky if (Result.isNull()) 3354198398Srdivacky return 0; 3355198398Srdivacky 3356200583Srdivacky return TLB.getTypeSourceInfo(SemaRef.Context, Result); 3357198092Srdivacky} 3358198092Srdivacky 3359198092Srdivackytemplate<typename Derived> 3360198398SrdivackyQualType 3361218893SdimTreeTransform<Derived>::TransformType(TypeLocBuilder &TLB, TypeLoc T) { 3362198398Srdivacky switch (T.getTypeLocClass()) { 3363198398Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 3364249423Sdim#define TYPELOC(CLASS, PARENT) \ 3365249423Sdim case TypeLoc::CLASS: \ 3366249423Sdim return getDerived().Transform##CLASS##Type(TLB, \ 3367249423Sdim T.castAs<CLASS##TypeLoc>()); 3368198398Srdivacky#include "clang/AST/TypeLocNodes.def" 3369198398Srdivacky } 3370198092Srdivacky 3371200583Srdivacky llvm_unreachable("unhandled type loc!"); 3372198092Srdivacky} 3373198092Srdivacky 3374198398Srdivacky/// FIXME: By default, this routine adds type qualifiers only to types 3375198398Srdivacky/// that can have qualifiers, and silently suppresses those qualifiers 3376198398Srdivacky/// that are not permitted (e.g., qualifiers on reference or function 3377198398Srdivacky/// types). This is the right thing for template instantiation, but 3378198398Srdivacky/// probably not for other clients. 3379198092Srdivackytemplate<typename Derived> 3380198398SrdivackyQualType 3381198398SrdivackyTreeTransform<Derived>::TransformQualifiedType(TypeLocBuilder &TLB, 3382218893Sdim QualifiedTypeLoc T) { 3383199482Srdivacky Qualifiers Quals = T.getType().getLocalQualifiers(); 3384198092Srdivacky 3385218893Sdim QualType Result = getDerived().TransformType(TLB, T.getUnqualifiedLoc()); 3386198398Srdivacky if (Result.isNull()) 3387198092Srdivacky return QualType(); 3388198092Srdivacky 3389198398Srdivacky // Silently suppress qualifiers if the result type can't be qualified. 3390198398Srdivacky // FIXME: this is the right thing for template instantiation, but 3391198398Srdivacky // probably not for other clients. 3392198398Srdivacky if (Result->isFunctionType() || Result->isReferenceType()) 3393198398Srdivacky return Result; 3394198092Srdivacky 3395224145Sdim // Suppress Objective-C lifetime qualifiers if they don't make sense for the 3396224145Sdim // resulting type. 3397224145Sdim if (Quals.hasObjCLifetime()) { 3398224145Sdim if (!Result->isObjCLifetimeType() && !Result->isDependentType()) 3399224145Sdim Quals.removeObjCLifetime(); 3400224145Sdim else if (Result.getObjCLifetime()) { 3401239462Sdim // Objective-C ARC: 3402224145Sdim // A lifetime qualifier applied to a substituted template parameter 3403224145Sdim // overrides the lifetime qualifier from the template argument. 3404249423Sdim const AutoType *AutoTy; 3405239462Sdim if (const SubstTemplateTypeParmType *SubstTypeParam 3406224145Sdim = dyn_cast<SubstTemplateTypeParmType>(Result)) { 3407224145Sdim QualType Replacement = SubstTypeParam->getReplacementType(); 3408224145Sdim Qualifiers Qs = Replacement.getQualifiers(); 3409224145Sdim Qs.removeObjCLifetime(); 3410239462Sdim Replacement 3411224145Sdim = SemaRef.Context.getQualifiedType(Replacement.getUnqualifiedType(), 3412224145Sdim Qs); 3413224145Sdim Result = SemaRef.Context.getSubstTemplateTypeParmType( 3414239462Sdim SubstTypeParam->getReplacedParameter(), 3415224145Sdim Replacement); 3416224145Sdim TLB.TypeWasModifiedSafely(Result); 3417249423Sdim } else if ((AutoTy = dyn_cast<AutoType>(Result)) && AutoTy->isDeduced()) { 3418249423Sdim // 'auto' types behave the same way as template parameters. 3419249423Sdim QualType Deduced = AutoTy->getDeducedType(); 3420249423Sdim Qualifiers Qs = Deduced.getQualifiers(); 3421249423Sdim Qs.removeObjCLifetime(); 3422249423Sdim Deduced = SemaRef.Context.getQualifiedType(Deduced.getUnqualifiedType(), 3423249423Sdim Qs); 3424251662Sdim Result = SemaRef.Context.getAutoType(Deduced, AutoTy->isDecltypeAuto()); 3425249423Sdim TLB.TypeWasModifiedSafely(Result); 3426224145Sdim } else { 3427224145Sdim // Otherwise, complain about the addition of a qualifier to an 3428224145Sdim // already-qualified type. 3429224145Sdim SourceRange R = TLB.getTemporaryTypeLoc(Result).getSourceRange(); 3430224145Sdim SemaRef.Diag(R.getBegin(), diag::err_attr_objc_ownership_redundant) 3431224145Sdim << Result << R; 3432239462Sdim 3433224145Sdim Quals.removeObjCLifetime(); 3434224145Sdim } 3435224145Sdim } 3436224145Sdim } 3437210299Sed if (!Quals.empty()) { 3438210299Sed Result = SemaRef.BuildQualifiedType(Result, T.getBeginLoc(), Quals); 3439249423Sdim // BuildQualifiedType might not add qualifiers if they are invalid. 3440249423Sdim if (Result.hasLocalQualifiers()) 3441249423Sdim TLB.push<QualifiedTypeLoc>(Result); 3442210299Sed // No location information to preserve. 3443210299Sed } 3444198398Srdivacky 3445198398Srdivacky return Result; 3446198092Srdivacky} 3447198092Srdivacky 3448218893Sdimtemplate<typename Derived> 3449221345SdimTypeLoc 3450221345SdimTreeTransform<Derived>::TransformTypeInObjectScope(TypeLoc TL, 3451218893Sdim QualType ObjectType, 3452218893Sdim NamedDecl *UnqualLookup, 3453221345Sdim CXXScopeSpec &SS) { 3454221345Sdim QualType T = TL.getType(); 3455218893Sdim if (getDerived().AlreadyTransformed(T)) 3456221345Sdim return TL; 3457239462Sdim 3458218893Sdim TypeLocBuilder TLB; 3459218893Sdim QualType Result; 3460239462Sdim 3461218893Sdim if (isa<TemplateSpecializationType>(T)) { 3462249423Sdim TemplateSpecializationTypeLoc SpecTL = 3463249423Sdim TL.castAs<TemplateSpecializationTypeLoc>(); 3464239462Sdim 3465218893Sdim TemplateName Template = 3466221345Sdim getDerived().TransformTemplateName(SS, 3467221345Sdim SpecTL.getTypePtr()->getTemplateName(), 3468221345Sdim SpecTL.getTemplateNameLoc(), 3469218893Sdim ObjectType, UnqualLookup); 3470239462Sdim if (Template.isNull()) 3471221345Sdim return TypeLoc(); 3472239462Sdim 3473239462Sdim Result = getDerived().TransformTemplateSpecializationType(TLB, SpecTL, 3474221345Sdim Template); 3475218893Sdim } else if (isa<DependentTemplateSpecializationType>(T)) { 3476249423Sdim DependentTemplateSpecializationTypeLoc SpecTL = 3477249423Sdim TL.castAs<DependentTemplateSpecializationTypeLoc>(); 3478239462Sdim 3479221345Sdim TemplateName Template 3480239462Sdim = getDerived().RebuildTemplateName(SS, 3481239462Sdim *SpecTL.getTypePtr()->getIdentifier(), 3482234353Sdim SpecTL.getTemplateNameLoc(), 3483221345Sdim ObjectType, UnqualLookup); 3484221345Sdim if (Template.isNull()) 3485221345Sdim return TypeLoc(); 3486239462Sdim 3487239462Sdim Result = getDerived().TransformDependentTemplateSpecializationType(TLB, 3488221345Sdim SpecTL, 3489221345Sdim Template, 3490221345Sdim SS); 3491218893Sdim } else { 3492218893Sdim // Nothing special needs to be done for these. 3493221345Sdim Result = getDerived().TransformType(TLB, TL); 3494218893Sdim } 3495239462Sdim 3496239462Sdim if (Result.isNull()) 3497221345Sdim return TypeLoc(); 3498239462Sdim 3499221345Sdim return TLB.getTypeSourceInfo(SemaRef.Context, Result)->getTypeLoc(); 3500218893Sdim} 3501218893Sdim 3502219077Sdimtemplate<typename Derived> 3503221345SdimTypeSourceInfo * 3504221345SdimTreeTransform<Derived>::TransformTypeInObjectScope(TypeSourceInfo *TSInfo, 3505219077Sdim QualType ObjectType, 3506219077Sdim NamedDecl *UnqualLookup, 3507219077Sdim CXXScopeSpec &SS) { 3508219077Sdim // FIXME: Painfully copy-paste from the above! 3509239462Sdim 3510221345Sdim QualType T = TSInfo->getType(); 3511219077Sdim if (getDerived().AlreadyTransformed(T)) 3512221345Sdim return TSInfo; 3513239462Sdim 3514219077Sdim TypeLocBuilder TLB; 3515219077Sdim QualType Result; 3516239462Sdim 3517221345Sdim TypeLoc TL = TSInfo->getTypeLoc(); 3518219077Sdim if (isa<TemplateSpecializationType>(T)) { 3519249423Sdim TemplateSpecializationTypeLoc SpecTL = 3520249423Sdim TL.castAs<TemplateSpecializationTypeLoc>(); 3521239462Sdim 3522221345Sdim TemplateName Template 3523221345Sdim = getDerived().TransformTemplateName(SS, 3524221345Sdim SpecTL.getTypePtr()->getTemplateName(), 3525221345Sdim SpecTL.getTemplateNameLoc(), 3526219077Sdim ObjectType, UnqualLookup); 3527239462Sdim if (Template.isNull()) 3528221345Sdim return 0; 3529239462Sdim 3530239462Sdim Result = getDerived().TransformTemplateSpecializationType(TLB, SpecTL, 3531219077Sdim Template); 3532219077Sdim } else if (isa<DependentTemplateSpecializationType>(T)) { 3533249423Sdim DependentTemplateSpecializationTypeLoc SpecTL = 3534249423Sdim TL.castAs<DependentTemplateSpecializationTypeLoc>(); 3535239462Sdim 3536221345Sdim TemplateName Template 3537239462Sdim = getDerived().RebuildTemplateName(SS, 3538239462Sdim *SpecTL.getTypePtr()->getIdentifier(), 3539234353Sdim SpecTL.getTemplateNameLoc(), 3540221345Sdim ObjectType, UnqualLookup); 3541221345Sdim if (Template.isNull()) 3542221345Sdim return 0; 3543239462Sdim 3544239462Sdim Result = getDerived().TransformDependentTemplateSpecializationType(TLB, 3545221345Sdim SpecTL, 3546221345Sdim Template, 3547221345Sdim SS); 3548219077Sdim } else { 3549219077Sdim // Nothing special needs to be done for these. 3550219077Sdim Result = getDerived().TransformType(TLB, TL); 3551219077Sdim } 3552239462Sdim 3553239462Sdim if (Result.isNull()) 3554221345Sdim return 0; 3555239462Sdim 3556221345Sdim return TLB.getTypeSourceInfo(SemaRef.Context, Result); 3557219077Sdim} 3558219077Sdim 3559198398Srdivackytemplate <class TyLoc> static inline 3560198398SrdivackyQualType TransformTypeSpecType(TypeLocBuilder &TLB, TyLoc T) { 3561198398Srdivacky TyLoc NewT = TLB.push<TyLoc>(T.getType()); 3562198398Srdivacky NewT.setNameLoc(T.getNameLoc()); 3563198398Srdivacky return T.getType(); 3564198398Srdivacky} 3565198092Srdivacky 3566198398Srdivackytemplate<typename Derived> 3567198398SrdivackyQualType TreeTransform<Derived>::TransformBuiltinType(TypeLocBuilder &TLB, 3568218893Sdim BuiltinTypeLoc T) { 3569202879Srdivacky BuiltinTypeLoc NewT = TLB.push<BuiltinTypeLoc>(T.getType()); 3570202879Srdivacky NewT.setBuiltinLoc(T.getBuiltinLoc()); 3571202879Srdivacky if (T.needsExtraLocalData()) 3572202879Srdivacky NewT.getWrittenBuiltinSpecs() = T.getWrittenBuiltinSpecs(); 3573202879Srdivacky return T.getType(); 3574198092Srdivacky} 3575198092Srdivacky 3576198092Srdivackytemplate<typename Derived> 3577198398SrdivackyQualType TreeTransform<Derived>::TransformComplexType(TypeLocBuilder &TLB, 3578218893Sdim ComplexTypeLoc T) { 3579198398Srdivacky // FIXME: recurse? 3580198398Srdivacky return TransformTypeSpecType(TLB, T); 3581198398Srdivacky} 3582198092Srdivacky 3583198398Srdivackytemplate<typename Derived> 3584198398SrdivackyQualType TreeTransform<Derived>::TransformPointerType(TypeLocBuilder &TLB, 3585218893Sdim PointerTypeLoc TL) { 3586239462Sdim QualType PointeeType 3587239462Sdim = getDerived().TransformType(TLB, TL.getPointeeLoc()); 3588207619Srdivacky if (PointeeType.isNull()) 3589207619Srdivacky return QualType(); 3590207619Srdivacky 3591207619Srdivacky QualType Result = TL.getType(); 3592208600Srdivacky if (PointeeType->getAs<ObjCObjectType>()) { 3593207619Srdivacky // A dependent pointer type 'T *' has is being transformed such 3594207619Srdivacky // that an Objective-C class type is being replaced for 'T'. The 3595207619Srdivacky // resulting pointer type is an ObjCObjectPointerType, not a 3596207619Srdivacky // PointerType. 3597208600Srdivacky Result = SemaRef.Context.getObjCObjectPointerType(PointeeType); 3598239462Sdim 3599208600Srdivacky ObjCObjectPointerTypeLoc NewT = TLB.push<ObjCObjectPointerTypeLoc>(Result); 3600208600Srdivacky NewT.setStarLoc(TL.getStarLoc()); 3601207619Srdivacky return Result; 3602207619Srdivacky } 3603218893Sdim 3604207619Srdivacky if (getDerived().AlwaysRebuild() || 3605207619Srdivacky PointeeType != TL.getPointeeLoc().getType()) { 3606207619Srdivacky Result = getDerived().RebuildPointerType(PointeeType, TL.getSigilLoc()); 3607207619Srdivacky if (Result.isNull()) 3608207619Srdivacky return QualType(); 3609207619Srdivacky } 3610239462Sdim 3611224145Sdim // Objective-C ARC can add lifetime qualifiers to the type that we're 3612224145Sdim // pointing to. 3613224145Sdim TLB.TypeWasModifiedSafely(Result->getPointeeType()); 3614239462Sdim 3615207619Srdivacky PointerTypeLoc NewT = TLB.push<PointerTypeLoc>(Result); 3616207619Srdivacky NewT.setSigilLoc(TL.getSigilLoc()); 3617239462Sdim return Result; 3618198092Srdivacky} 3619198092Srdivacky 3620198092Srdivackytemplate<typename Derived> 3621198092SrdivackyQualType 3622198398SrdivackyTreeTransform<Derived>::TransformBlockPointerType(TypeLocBuilder &TLB, 3623218893Sdim BlockPointerTypeLoc TL) { 3624207619Srdivacky QualType PointeeType 3625239462Sdim = getDerived().TransformType(TLB, TL.getPointeeLoc()); 3626239462Sdim if (PointeeType.isNull()) 3627239462Sdim return QualType(); 3628239462Sdim 3629239462Sdim QualType Result = TL.getType(); 3630239462Sdim if (getDerived().AlwaysRebuild() || 3631239462Sdim PointeeType != TL.getPointeeLoc().getType()) { 3632239462Sdim Result = getDerived().RebuildBlockPointerType(PointeeType, 3633207619Srdivacky TL.getSigilLoc()); 3634207619Srdivacky if (Result.isNull()) 3635207619Srdivacky return QualType(); 3636207619Srdivacky } 3637207619Srdivacky 3638207619Srdivacky BlockPointerTypeLoc NewT = TLB.push<BlockPointerTypeLoc>(Result); 3639207619Srdivacky NewT.setSigilLoc(TL.getSigilLoc()); 3640207619Srdivacky return Result; 3641198092Srdivacky} 3642198092Srdivacky 3643198893Srdivacky/// Transforms a reference type. Note that somewhat paradoxically we 3644198893Srdivacky/// don't care whether the type itself is an l-value type or an r-value 3645198893Srdivacky/// type; we only care if the type was *written* as an l-value type 3646198893Srdivacky/// or an r-value type. 3647198092Srdivackytemplate<typename Derived> 3648198092SrdivackyQualType 3649198893SrdivackyTreeTransform<Derived>::TransformReferenceType(TypeLocBuilder &TLB, 3650218893Sdim ReferenceTypeLoc TL) { 3651198893Srdivacky const ReferenceType *T = TL.getTypePtr(); 3652198893Srdivacky 3653198893Srdivacky // Note that this works with the pointee-as-written. 3654198893Srdivacky QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc()); 3655198893Srdivacky if (PointeeType.isNull()) 3656198893Srdivacky return QualType(); 3657198893Srdivacky 3658198893Srdivacky QualType Result = TL.getType(); 3659198893Srdivacky if (getDerived().AlwaysRebuild() || 3660198893Srdivacky PointeeType != T->getPointeeTypeAsWritten()) { 3661198893Srdivacky Result = getDerived().RebuildReferenceType(PointeeType, 3662198893Srdivacky T->isSpelledAsLValue(), 3663198893Srdivacky TL.getSigilLoc()); 3664198893Srdivacky if (Result.isNull()) 3665198893Srdivacky return QualType(); 3666198893Srdivacky } 3667198893Srdivacky 3668224145Sdim // Objective-C ARC can add lifetime qualifiers to the type that we're 3669224145Sdim // referring to. 3670224145Sdim TLB.TypeWasModifiedSafely( 3671224145Sdim Result->getAs<ReferenceType>()->getPointeeTypeAsWritten()); 3672224145Sdim 3673198893Srdivacky // r-value references can be rebuilt as l-value references. 3674198893Srdivacky ReferenceTypeLoc NewTL; 3675198893Srdivacky if (isa<LValueReferenceType>(Result)) 3676198893Srdivacky NewTL = TLB.push<LValueReferenceTypeLoc>(Result); 3677198893Srdivacky else 3678198893Srdivacky NewTL = TLB.push<RValueReferenceTypeLoc>(Result); 3679198893Srdivacky NewTL.setSigilLoc(TL.getSigilLoc()); 3680198893Srdivacky 3681198893Srdivacky return Result; 3682198893Srdivacky} 3683198893Srdivacky 3684198893Srdivackytemplate<typename Derived> 3685198893SrdivackyQualType 3686198398SrdivackyTreeTransform<Derived>::TransformLValueReferenceType(TypeLocBuilder &TLB, 3687218893Sdim LValueReferenceTypeLoc TL) { 3688218893Sdim return TransformReferenceType(TLB, TL); 3689198092Srdivacky} 3690198092Srdivacky 3691198092Srdivackytemplate<typename Derived> 3692198092SrdivackyQualType 3693198398SrdivackyTreeTransform<Derived>::TransformRValueReferenceType(TypeLocBuilder &TLB, 3694218893Sdim RValueReferenceTypeLoc TL) { 3695218893Sdim return TransformReferenceType(TLB, TL); 3696198092Srdivacky} 3697198092Srdivacky 3698198092Srdivackytemplate<typename Derived> 3699198092SrdivackyQualType 3700198398SrdivackyTreeTransform<Derived>::TransformMemberPointerType(TypeLocBuilder &TLB, 3701218893Sdim MemberPointerTypeLoc TL) { 3702198398Srdivacky QualType PointeeType = getDerived().TransformType(TLB, TL.getPointeeLoc()); 3703198398Srdivacky if (PointeeType.isNull()) 3704198092Srdivacky return QualType(); 3705198092Srdivacky 3706221345Sdim TypeSourceInfo* OldClsTInfo = TL.getClassTInfo(); 3707221345Sdim TypeSourceInfo* NewClsTInfo = 0; 3708221345Sdim if (OldClsTInfo) { 3709221345Sdim NewClsTInfo = getDerived().TransformType(OldClsTInfo); 3710221345Sdim if (!NewClsTInfo) 3711221345Sdim return QualType(); 3712221345Sdim } 3713198092Srdivacky 3714221345Sdim const MemberPointerType *T = TL.getTypePtr(); 3715221345Sdim QualType OldClsType = QualType(T->getClass(), 0); 3716221345Sdim QualType NewClsType; 3717221345Sdim if (NewClsTInfo) 3718221345Sdim NewClsType = NewClsTInfo->getType(); 3719221345Sdim else { 3720221345Sdim NewClsType = getDerived().TransformType(OldClsType); 3721221345Sdim if (NewClsType.isNull()) 3722221345Sdim return QualType(); 3723221345Sdim } 3724221345Sdim 3725198398Srdivacky QualType Result = TL.getType(); 3726198398Srdivacky if (getDerived().AlwaysRebuild() || 3727198398Srdivacky PointeeType != T->getPointeeType() || 3728221345Sdim NewClsType != OldClsType) { 3729221345Sdim Result = getDerived().RebuildMemberPointerType(PointeeType, NewClsType, 3730198893Srdivacky TL.getStarLoc()); 3731198398Srdivacky if (Result.isNull()) 3732198398Srdivacky return QualType(); 3733198398Srdivacky } 3734198092Srdivacky 3735198398Srdivacky MemberPointerTypeLoc NewTL = TLB.push<MemberPointerTypeLoc>(Result); 3736198398Srdivacky NewTL.setSigilLoc(TL.getSigilLoc()); 3737221345Sdim NewTL.setClassTInfo(NewClsTInfo); 3738198398Srdivacky 3739198398Srdivacky return Result; 3740198092Srdivacky} 3741198092Srdivacky 3742198092Srdivackytemplate<typename Derived> 3743198092SrdivackyQualType 3744198398SrdivackyTreeTransform<Derived>::TransformConstantArrayType(TypeLocBuilder &TLB, 3745218893Sdim ConstantArrayTypeLoc TL) { 3746218893Sdim const ConstantArrayType *T = TL.getTypePtr(); 3747198398Srdivacky QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 3748198092Srdivacky if (ElementType.isNull()) 3749198092Srdivacky return QualType(); 3750198092Srdivacky 3751198398Srdivacky QualType Result = TL.getType(); 3752198398Srdivacky if (getDerived().AlwaysRebuild() || 3753198398Srdivacky ElementType != T->getElementType()) { 3754198398Srdivacky Result = getDerived().RebuildConstantArrayType(ElementType, 3755198398Srdivacky T->getSizeModifier(), 3756198398Srdivacky T->getSize(), 3757198893Srdivacky T->getIndexTypeCVRQualifiers(), 3758198893Srdivacky TL.getBracketsRange()); 3759198398Srdivacky if (Result.isNull()) 3760198398Srdivacky return QualType(); 3761198398Srdivacky } 3762234353Sdim 3763234353Sdim // We might have either a ConstantArrayType or a VariableArrayType now: 3764234353Sdim // a ConstantArrayType is allowed to have an element type which is a 3765234353Sdim // VariableArrayType if the type is dependent. Fortunately, all array 3766234353Sdim // types have the same location layout. 3767234353Sdim ArrayTypeLoc NewTL = TLB.push<ArrayTypeLoc>(Result); 3768198398Srdivacky NewTL.setLBracketLoc(TL.getLBracketLoc()); 3769198398Srdivacky NewTL.setRBracketLoc(TL.getRBracketLoc()); 3770198092Srdivacky 3771198398Srdivacky Expr *Size = TL.getSizeExpr(); 3772198398Srdivacky if (Size) { 3773234353Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, 3774234353Sdim Sema::ConstantEvaluated); 3775198398Srdivacky Size = getDerived().TransformExpr(Size).template takeAs<Expr>(); 3776234353Sdim Size = SemaRef.ActOnConstantExpression(Size).take(); 3777198398Srdivacky } 3778198398Srdivacky NewTL.setSizeExpr(Size); 3779198398Srdivacky 3780198398Srdivacky return Result; 3781198092Srdivacky} 3782198092Srdivacky 3783198092Srdivackytemplate<typename Derived> 3784198092SrdivackyQualType TreeTransform<Derived>::TransformIncompleteArrayType( 3785198398Srdivacky TypeLocBuilder &TLB, 3786218893Sdim IncompleteArrayTypeLoc TL) { 3787218893Sdim const IncompleteArrayType *T = TL.getTypePtr(); 3788198398Srdivacky QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 3789198092Srdivacky if (ElementType.isNull()) 3790198092Srdivacky return QualType(); 3791198092Srdivacky 3792198398Srdivacky QualType Result = TL.getType(); 3793198398Srdivacky if (getDerived().AlwaysRebuild() || 3794198398Srdivacky ElementType != T->getElementType()) { 3795198398Srdivacky Result = getDerived().RebuildIncompleteArrayType(ElementType, 3796198398Srdivacky T->getSizeModifier(), 3797198893Srdivacky T->getIndexTypeCVRQualifiers(), 3798198893Srdivacky TL.getBracketsRange()); 3799198398Srdivacky if (Result.isNull()) 3800198398Srdivacky return QualType(); 3801198398Srdivacky } 3802239462Sdim 3803198398Srdivacky IncompleteArrayTypeLoc NewTL = TLB.push<IncompleteArrayTypeLoc>(Result); 3804198398Srdivacky NewTL.setLBracketLoc(TL.getLBracketLoc()); 3805198398Srdivacky NewTL.setRBracketLoc(TL.getRBracketLoc()); 3806198398Srdivacky NewTL.setSizeExpr(0); 3807198092Srdivacky 3808198398Srdivacky return Result; 3809198092Srdivacky} 3810198092Srdivacky 3811198092Srdivackytemplate<typename Derived> 3812198398SrdivackyQualType 3813198398SrdivackyTreeTransform<Derived>::TransformVariableArrayType(TypeLocBuilder &TLB, 3814218893Sdim VariableArrayTypeLoc TL) { 3815218893Sdim const VariableArrayType *T = TL.getTypePtr(); 3816198398Srdivacky QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 3817198092Srdivacky if (ElementType.isNull()) 3818198092Srdivacky return QualType(); 3819198092Srdivacky 3820212904Sdim ExprResult SizeResult 3821198398Srdivacky = getDerived().TransformExpr(T->getSizeExpr()); 3822198398Srdivacky if (SizeResult.isInvalid()) 3823198092Srdivacky return QualType(); 3824198092Srdivacky 3825212904Sdim Expr *Size = SizeResult.take(); 3826198398Srdivacky 3827198398Srdivacky QualType Result = TL.getType(); 3828198398Srdivacky if (getDerived().AlwaysRebuild() || 3829198398Srdivacky ElementType != T->getElementType() || 3830198398Srdivacky Size != T->getSizeExpr()) { 3831198398Srdivacky Result = getDerived().RebuildVariableArrayType(ElementType, 3832198398Srdivacky T->getSizeModifier(), 3833212904Sdim Size, 3834198398Srdivacky T->getIndexTypeCVRQualifiers(), 3835198893Srdivacky TL.getBracketsRange()); 3836198398Srdivacky if (Result.isNull()) 3837198398Srdivacky return QualType(); 3838198092Srdivacky } 3839239462Sdim 3840198398Srdivacky VariableArrayTypeLoc NewTL = TLB.push<VariableArrayTypeLoc>(Result); 3841198398Srdivacky NewTL.setLBracketLoc(TL.getLBracketLoc()); 3842198398Srdivacky NewTL.setRBracketLoc(TL.getRBracketLoc()); 3843198398Srdivacky NewTL.setSizeExpr(Size); 3844198092Srdivacky 3845198398Srdivacky return Result; 3846198092Srdivacky} 3847198092Srdivacky 3848198092Srdivackytemplate<typename Derived> 3849198398SrdivackyQualType 3850198398SrdivackyTreeTransform<Derived>::TransformDependentSizedArrayType(TypeLocBuilder &TLB, 3851218893Sdim DependentSizedArrayTypeLoc TL) { 3852218893Sdim const DependentSizedArrayType *T = TL.getTypePtr(); 3853198398Srdivacky QualType ElementType = getDerived().TransformType(TLB, TL.getElementLoc()); 3854198092Srdivacky if (ElementType.isNull()) 3855198092Srdivacky return QualType(); 3856198092Srdivacky 3857234353Sdim // Array bounds are constant expressions. 3858234353Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, 3859234353Sdim Sema::ConstantEvaluated); 3860198092Srdivacky 3861218893Sdim // Prefer the expression from the TypeLoc; the other may have been uniqued. 3862218893Sdim Expr *origSize = TL.getSizeExpr(); 3863218893Sdim if (!origSize) origSize = T->getSizeExpr(); 3864218893Sdim 3865218893Sdim ExprResult sizeResult 3866218893Sdim = getDerived().TransformExpr(origSize); 3867234353Sdim sizeResult = SemaRef.ActOnConstantExpression(sizeResult); 3868218893Sdim if (sizeResult.isInvalid()) 3869198092Srdivacky return QualType(); 3870198092Srdivacky 3871218893Sdim Expr *size = sizeResult.get(); 3872198398Srdivacky 3873198398Srdivacky QualType Result = TL.getType(); 3874198398Srdivacky if (getDerived().AlwaysRebuild() || 3875198398Srdivacky ElementType != T->getElementType() || 3876218893Sdim size != origSize) { 3877198398Srdivacky Result = getDerived().RebuildDependentSizedArrayType(ElementType, 3878198398Srdivacky T->getSizeModifier(), 3879218893Sdim size, 3880198398Srdivacky T->getIndexTypeCVRQualifiers(), 3881198893Srdivacky TL.getBracketsRange()); 3882198398Srdivacky if (Result.isNull()) 3883198398Srdivacky return QualType(); 3884198092Srdivacky } 3885198092Srdivacky 3886198398Srdivacky // We might have any sort of array type now, but fortunately they 3887198398Srdivacky // all have the same location layout. 3888198398Srdivacky ArrayTypeLoc NewTL = TLB.push<ArrayTypeLoc>(Result); 3889198398Srdivacky NewTL.setLBracketLoc(TL.getLBracketLoc()); 3890198398Srdivacky NewTL.setRBracketLoc(TL.getRBracketLoc()); 3891218893Sdim NewTL.setSizeExpr(size); 3892198398Srdivacky 3893198398Srdivacky return Result; 3894198092Srdivacky} 3895198092Srdivacky 3896198092Srdivackytemplate<typename Derived> 3897198092SrdivackyQualType TreeTransform<Derived>::TransformDependentSizedExtVectorType( 3898198398Srdivacky TypeLocBuilder &TLB, 3899218893Sdim DependentSizedExtVectorTypeLoc TL) { 3900218893Sdim const DependentSizedExtVectorType *T = TL.getTypePtr(); 3901198398Srdivacky 3902198398Srdivacky // FIXME: ext vector locs should be nested 3903198092Srdivacky QualType ElementType = getDerived().TransformType(T->getElementType()); 3904198092Srdivacky if (ElementType.isNull()) 3905198092Srdivacky return QualType(); 3906198092Srdivacky 3907234353Sdim // Vector sizes are constant expressions. 3908234353Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, 3909234353Sdim Sema::ConstantEvaluated); 3910198092Srdivacky 3911212904Sdim ExprResult Size = getDerived().TransformExpr(T->getSizeExpr()); 3912234353Sdim Size = SemaRef.ActOnConstantExpression(Size); 3913198092Srdivacky if (Size.isInvalid()) 3914198092Srdivacky return QualType(); 3915198092Srdivacky 3916198398Srdivacky QualType Result = TL.getType(); 3917198398Srdivacky if (getDerived().AlwaysRebuild() || 3918198893Srdivacky ElementType != T->getElementType() || 3919198893Srdivacky Size.get() != T->getSizeExpr()) { 3920198398Srdivacky Result = getDerived().RebuildDependentSizedExtVectorType(ElementType, 3921212904Sdim Size.take(), 3922198398Srdivacky T->getAttributeLoc()); 3923198398Srdivacky if (Result.isNull()) 3924198398Srdivacky return QualType(); 3925198092Srdivacky } 3926198092Srdivacky 3927198398Srdivacky // Result might be dependent or not. 3928198398Srdivacky if (isa<DependentSizedExtVectorType>(Result)) { 3929198398Srdivacky DependentSizedExtVectorTypeLoc NewTL 3930198398Srdivacky = TLB.push<DependentSizedExtVectorTypeLoc>(Result); 3931198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 3932198398Srdivacky } else { 3933198398Srdivacky ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result); 3934198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 3935198398Srdivacky } 3936198398Srdivacky 3937198398Srdivacky return Result; 3938198092Srdivacky} 3939198092Srdivacky 3940198092Srdivackytemplate<typename Derived> 3941198398SrdivackyQualType TreeTransform<Derived>::TransformVectorType(TypeLocBuilder &TLB, 3942218893Sdim VectorTypeLoc TL) { 3943218893Sdim const VectorType *T = TL.getTypePtr(); 3944198092Srdivacky QualType ElementType = getDerived().TransformType(T->getElementType()); 3945198092Srdivacky if (ElementType.isNull()) 3946198092Srdivacky return QualType(); 3947198092Srdivacky 3948198398Srdivacky QualType Result = TL.getType(); 3949198398Srdivacky if (getDerived().AlwaysRebuild() || 3950198398Srdivacky ElementType != T->getElementType()) { 3951203955Srdivacky Result = getDerived().RebuildVectorType(ElementType, T->getNumElements(), 3952218893Sdim T->getVectorKind()); 3953198398Srdivacky if (Result.isNull()) 3954198398Srdivacky return QualType(); 3955198398Srdivacky } 3956239462Sdim 3957198398Srdivacky VectorTypeLoc NewTL = TLB.push<VectorTypeLoc>(Result); 3958198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 3959198092Srdivacky 3960198398Srdivacky return Result; 3961198092Srdivacky} 3962198092Srdivacky 3963198092Srdivackytemplate<typename Derived> 3964198398SrdivackyQualType TreeTransform<Derived>::TransformExtVectorType(TypeLocBuilder &TLB, 3965218893Sdim ExtVectorTypeLoc TL) { 3966218893Sdim const VectorType *T = TL.getTypePtr(); 3967198092Srdivacky QualType ElementType = getDerived().TransformType(T->getElementType()); 3968198092Srdivacky if (ElementType.isNull()) 3969198092Srdivacky return QualType(); 3970198092Srdivacky 3971198398Srdivacky QualType Result = TL.getType(); 3972198398Srdivacky if (getDerived().AlwaysRebuild() || 3973198398Srdivacky ElementType != T->getElementType()) { 3974198398Srdivacky Result = getDerived().RebuildExtVectorType(ElementType, 3975198398Srdivacky T->getNumElements(), 3976198398Srdivacky /*FIXME*/ SourceLocation()); 3977198398Srdivacky if (Result.isNull()) 3978198398Srdivacky return QualType(); 3979198398Srdivacky } 3980239462Sdim 3981198398Srdivacky ExtVectorTypeLoc NewTL = TLB.push<ExtVectorTypeLoc>(Result); 3982198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 3983198092Srdivacky 3984198398Srdivacky return Result; 3985198092Srdivacky} 3986198092Srdivacky 3987249423Sdimtemplate <typename Derived> 3988249423SdimParmVarDecl *TreeTransform<Derived>::TransformFunctionTypeParam( 3989249423Sdim ParmVarDecl *OldParm, int indexAdjustment, Optional<unsigned> NumExpansions, 3990249423Sdim bool ExpectParameterPack) { 3991205219Srdivacky TypeSourceInfo *OldDI = OldParm->getTypeSourceInfo(); 3992218893Sdim TypeSourceInfo *NewDI = 0; 3993239462Sdim 3994218893Sdim if (NumExpansions && isa<PackExpansionType>(OldDI->getType())) { 3995239462Sdim // If we're substituting into a pack expansion type and we know the 3996234353Sdim // length we want to expand to, just substitute for the pattern. 3997218893Sdim TypeLoc OldTL = OldDI->getTypeLoc(); 3998249423Sdim PackExpansionTypeLoc OldExpansionTL = OldTL.castAs<PackExpansionTypeLoc>(); 3999239462Sdim 4000218893Sdim TypeLocBuilder TLB; 4001218893Sdim TypeLoc NewTL = OldDI->getTypeLoc(); 4002218893Sdim TLB.reserve(NewTL.getFullDataSize()); 4003239462Sdim 4004239462Sdim QualType Result = getDerived().TransformType(TLB, 4005218893Sdim OldExpansionTL.getPatternLoc()); 4006218893Sdim if (Result.isNull()) 4007218893Sdim return 0; 4008239462Sdim 4009239462Sdim Result = RebuildPackExpansionType(Result, 4010239462Sdim OldExpansionTL.getPatternLoc().getSourceRange(), 4011218893Sdim OldExpansionTL.getEllipsisLoc(), 4012218893Sdim NumExpansions); 4013218893Sdim if (Result.isNull()) 4014218893Sdim return 0; 4015239462Sdim 4016218893Sdim PackExpansionTypeLoc NewExpansionTL 4017218893Sdim = TLB.push<PackExpansionTypeLoc>(Result); 4018218893Sdim NewExpansionTL.setEllipsisLoc(OldExpansionTL.getEllipsisLoc()); 4019218893Sdim NewDI = TLB.getTypeSourceInfo(SemaRef.Context, Result); 4020218893Sdim } else 4021218893Sdim NewDI = getDerived().TransformType(OldDI); 4022205219Srdivacky if (!NewDI) 4023205219Srdivacky return 0; 4024205219Srdivacky 4025221345Sdim if (NewDI == OldDI && indexAdjustment == 0) 4026205219Srdivacky return OldParm; 4027221345Sdim 4028221345Sdim ParmVarDecl *newParm = ParmVarDecl::Create(SemaRef.Context, 4029221345Sdim OldParm->getDeclContext(), 4030221345Sdim OldParm->getInnerLocStart(), 4031221345Sdim OldParm->getLocation(), 4032221345Sdim OldParm->getIdentifier(), 4033221345Sdim NewDI->getType(), 4034221345Sdim NewDI, 4035221345Sdim OldParm->getStorageClass(), 4036221345Sdim /* DefArg */ NULL); 4037221345Sdim newParm->setScopeInfo(OldParm->getFunctionScopeDepth(), 4038221345Sdim OldParm->getFunctionScopeIndex() + indexAdjustment); 4039221345Sdim return newParm; 4040205219Srdivacky} 4041205219Srdivacky 4042205219Srdivackytemplate<typename Derived> 4043205219Srdivackybool TreeTransform<Derived>:: 4044218893Sdim TransformFunctionTypeParams(SourceLocation Loc, 4045218893Sdim ParmVarDecl **Params, unsigned NumParams, 4046218893Sdim const QualType *ParamTypes, 4047226633Sdim SmallVectorImpl<QualType> &OutParamTypes, 4048226633Sdim SmallVectorImpl<ParmVarDecl*> *PVars) { 4049221345Sdim int indexAdjustment = 0; 4050221345Sdim 4051218893Sdim for (unsigned i = 0; i != NumParams; ++i) { 4052218893Sdim if (ParmVarDecl *OldParm = Params[i]) { 4053221345Sdim assert(OldParm->getFunctionScopeIndex() == i); 4054221345Sdim 4055249423Sdim Optional<unsigned> NumExpansions; 4056221345Sdim ParmVarDecl *NewParm = 0; 4057218893Sdim if (OldParm->isParameterPack()) { 4058218893Sdim // We have a function parameter pack that may need to be expanded. 4059226633Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 4060198092Srdivacky 4061218893Sdim // Find the parameter packs that could be expanded. 4062218893Sdim TypeLoc TL = OldParm->getTypeSourceInfo()->getTypeLoc(); 4063249423Sdim PackExpansionTypeLoc ExpansionTL = TL.castAs<PackExpansionTypeLoc>(); 4064218893Sdim TypeLoc Pattern = ExpansionTL.getPatternLoc(); 4065218893Sdim SemaRef.collectUnexpandedParameterPacks(Pattern, Unexpanded); 4066221345Sdim assert(Unexpanded.size() > 0 && "Could not find parameter packs!"); 4067221345Sdim 4068218893Sdim // Determine whether we should expand the parameter packs. 4069218893Sdim bool ShouldExpand = false; 4070218893Sdim bool RetainExpansion = false; 4071249423Sdim Optional<unsigned> OrigNumExpansions = 4072249423Sdim ExpansionTL.getTypePtr()->getNumExpansions(); 4073218893Sdim NumExpansions = OrigNumExpansions; 4074218893Sdim if (getDerived().TryExpandParameterPacks(ExpansionTL.getEllipsisLoc(), 4075218893Sdim Pattern.getSourceRange(), 4076239462Sdim Unexpanded, 4077239462Sdim ShouldExpand, 4078218893Sdim RetainExpansion, 4079218893Sdim NumExpansions)) { 4080218893Sdim return true; 4081218893Sdim } 4082239462Sdim 4083218893Sdim if (ShouldExpand) { 4084218893Sdim // Expand the function parameter pack into multiple, separate 4085218893Sdim // parameters. 4086218893Sdim getDerived().ExpandingFunctionParameterPack(OldParm); 4087218893Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 4088218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 4089239462Sdim ParmVarDecl *NewParm 4090218893Sdim = getDerived().TransformFunctionTypeParam(OldParm, 4091221345Sdim indexAdjustment++, 4092234353Sdim OrigNumExpansions, 4093234353Sdim /*ExpectParameterPack=*/false); 4094218893Sdim if (!NewParm) 4095218893Sdim return true; 4096239462Sdim 4097218893Sdim OutParamTypes.push_back(NewParm->getType()); 4098218893Sdim if (PVars) 4099218893Sdim PVars->push_back(NewParm); 4100218893Sdim } 4101198092Srdivacky 4102218893Sdim // If we're supposed to retain a pack expansion, do so by temporarily 4103218893Sdim // forgetting the partially-substituted parameter pack. 4104218893Sdim if (RetainExpansion) { 4105218893Sdim ForgetPartiallySubstitutedPackRAII Forget(getDerived()); 4106239462Sdim ParmVarDecl *NewParm 4107218893Sdim = getDerived().TransformFunctionTypeParam(OldParm, 4108221345Sdim indexAdjustment++, 4109234353Sdim OrigNumExpansions, 4110234353Sdim /*ExpectParameterPack=*/false); 4111218893Sdim if (!NewParm) 4112218893Sdim return true; 4113239462Sdim 4114218893Sdim OutParamTypes.push_back(NewParm->getType()); 4115218893Sdim if (PVars) 4116218893Sdim PVars->push_back(NewParm); 4117218893Sdim } 4118198398Srdivacky 4119221345Sdim // The next parameter should have the same adjustment as the 4120221345Sdim // last thing we pushed, but we post-incremented indexAdjustment 4121221345Sdim // on every push. Also, if we push nothing, the adjustment should 4122221345Sdim // go down by one. 4123221345Sdim indexAdjustment--; 4124221345Sdim 4125218893Sdim // We're done with the pack expansion. 4126218893Sdim continue; 4127218893Sdim } 4128239462Sdim 4129239462Sdim // We'll substitute the parameter now without expanding the pack 4130218893Sdim // expansion. 4131221345Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 4132221345Sdim NewParm = getDerived().TransformFunctionTypeParam(OldParm, 4133221345Sdim indexAdjustment, 4134234353Sdim NumExpansions, 4135234353Sdim /*ExpectParameterPack=*/true); 4136221345Sdim } else { 4137249423Sdim NewParm = getDerived().TransformFunctionTypeParam( 4138249423Sdim OldParm, indexAdjustment, None, /*ExpectParameterPack=*/ false); 4139218893Sdim } 4140221345Sdim 4141205219Srdivacky if (!NewParm) 4142205219Srdivacky return true; 4143239462Sdim 4144218893Sdim OutParamTypes.push_back(NewParm->getType()); 4145218893Sdim if (PVars) 4146218893Sdim PVars->push_back(NewParm); 4147218893Sdim continue; 4148218893Sdim } 4149198398Srdivacky 4150198398Srdivacky // Deal with the possibility that we don't have a parameter 4151198398Srdivacky // declaration for this parameter. 4152218893Sdim QualType OldType = ParamTypes[i]; 4153218893Sdim bool IsPackExpansion = false; 4154249423Sdim Optional<unsigned> NumExpansions; 4155221345Sdim QualType NewType; 4156239462Sdim if (const PackExpansionType *Expansion 4157218893Sdim = dyn_cast<PackExpansionType>(OldType)) { 4158218893Sdim // We have a function parameter pack that may need to be expanded. 4159218893Sdim QualType Pattern = Expansion->getPattern(); 4160226633Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 4161218893Sdim getSema().collectUnexpandedParameterPacks(Pattern, Unexpanded); 4162239462Sdim 4163218893Sdim // Determine whether we should expand the parameter packs. 4164218893Sdim bool ShouldExpand = false; 4165218893Sdim bool RetainExpansion = false; 4166218893Sdim if (getDerived().TryExpandParameterPacks(Loc, SourceRange(), 4167239462Sdim Unexpanded, 4168239462Sdim ShouldExpand, 4169218893Sdim RetainExpansion, 4170218893Sdim NumExpansions)) { 4171218893Sdim return true; 4172218893Sdim } 4173239462Sdim 4174218893Sdim if (ShouldExpand) { 4175239462Sdim // Expand the function parameter pack into multiple, separate 4176218893Sdim // parameters. 4177218893Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 4178218893Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 4179218893Sdim QualType NewType = getDerived().TransformType(Pattern); 4180218893Sdim if (NewType.isNull()) 4181218893Sdim return true; 4182198398Srdivacky 4183218893Sdim OutParamTypes.push_back(NewType); 4184218893Sdim if (PVars) 4185218893Sdim PVars->push_back(0); 4186218893Sdim } 4187239462Sdim 4188218893Sdim // We're done with the pack expansion. 4189218893Sdim continue; 4190218893Sdim } 4191239462Sdim 4192218893Sdim // If we're supposed to retain a pack expansion, do so by temporarily 4193218893Sdim // forgetting the partially-substituted parameter pack. 4194218893Sdim if (RetainExpansion) { 4195218893Sdim ForgetPartiallySubstitutedPackRAII Forget(getDerived()); 4196218893Sdim QualType NewType = getDerived().TransformType(Pattern); 4197218893Sdim if (NewType.isNull()) 4198218893Sdim return true; 4199239462Sdim 4200218893Sdim OutParamTypes.push_back(NewType); 4201218893Sdim if (PVars) 4202218893Sdim PVars->push_back(0); 4203218893Sdim } 4204218893Sdim 4205239462Sdim // We'll substitute the parameter now without expanding the pack 4206218893Sdim // expansion. 4207218893Sdim OldType = Expansion->getPattern(); 4208218893Sdim IsPackExpansion = true; 4209221345Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 4210221345Sdim NewType = getDerived().TransformType(OldType); 4211221345Sdim } else { 4212221345Sdim NewType = getDerived().TransformType(OldType); 4213198398Srdivacky } 4214239462Sdim 4215218893Sdim if (NewType.isNull()) 4216218893Sdim return true; 4217198398Srdivacky 4218218893Sdim if (IsPackExpansion) 4219218893Sdim NewType = getSema().Context.getPackExpansionType(NewType, 4220218893Sdim NumExpansions); 4221239462Sdim 4222218893Sdim OutParamTypes.push_back(NewType); 4223218893Sdim if (PVars) 4224218893Sdim PVars->push_back(0); 4225198092Srdivacky } 4226198092Srdivacky 4227221345Sdim#ifndef NDEBUG 4228221345Sdim if (PVars) { 4229221345Sdim for (unsigned i = 0, e = PVars->size(); i != e; ++i) 4230221345Sdim if (ParmVarDecl *parm = (*PVars)[i]) 4231221345Sdim assert(parm->getFunctionScopeIndex() == i); 4232218893Sdim } 4233221345Sdim#endif 4234205219Srdivacky 4235221345Sdim return false; 4236221345Sdim} 4237221345Sdim 4238205219Srdivackytemplate<typename Derived> 4239205219SrdivackyQualType 4240205219SrdivackyTreeTransform<Derived>::TransformFunctionProtoType(TypeLocBuilder &TLB, 4241218893Sdim FunctionProtoTypeLoc TL) { 4242234982Sdim return getDerived().TransformFunctionProtoType(TLB, TL, 0, 0); 4243234982Sdim} 4244234982Sdim 4245234982Sdimtemplate<typename Derived> 4246234982SdimQualType 4247234982SdimTreeTransform<Derived>::TransformFunctionProtoType(TypeLocBuilder &TLB, 4248234982Sdim FunctionProtoTypeLoc TL, 4249234982Sdim CXXRecordDecl *ThisContext, 4250234982Sdim unsigned ThisTypeQuals) { 4251212904Sdim // Transform the parameters and return type. 4252212904Sdim // 4253234982Sdim // We are required to instantiate the params and return type in source order. 4254218893Sdim // When the function has a trailing return type, we instantiate the 4255218893Sdim // parameters before the return type, since the return type can then refer 4256218893Sdim // to the parameters themselves (via decltype, sizeof, etc.). 4257218893Sdim // 4258226633Sdim SmallVector<QualType, 4> ParamTypes; 4259226633Sdim SmallVector<ParmVarDecl*, 4> ParamDecls; 4260218893Sdim const FunctionProtoType *T = TL.getTypePtr(); 4261212904Sdim 4262218893Sdim QualType ResultType; 4263218893Sdim 4264239462Sdim if (T->hasTrailingReturn()) { 4265239462Sdim if (getDerived().TransformFunctionTypeParams(TL.getBeginLoc(), 4266218893Sdim TL.getParmArray(), 4267218893Sdim TL.getNumArgs(), 4268239462Sdim TL.getTypePtr()->arg_type_begin(), 4269218893Sdim ParamTypes, &ParamDecls)) 4270218893Sdim return QualType(); 4271218893Sdim 4272234982Sdim { 4273234982Sdim // C++11 [expr.prim.general]p3: 4274239462Sdim // If a declaration declares a member function or member function 4275239462Sdim // template of a class X, the expression this is a prvalue of type 4276234982Sdim // "pointer to cv-qualifier-seq X" between the optional cv-qualifer-seq 4277239462Sdim // and the end of the function-definition, member-declarator, or 4278234982Sdim // declarator. 4279234982Sdim Sema::CXXThisScopeRAII ThisScope(SemaRef, ThisContext, ThisTypeQuals); 4280239462Sdim 4281234982Sdim ResultType = getDerived().TransformType(TLB, TL.getResultLoc()); 4282234982Sdim if (ResultType.isNull()) 4283234982Sdim return QualType(); 4284234982Sdim } 4285218893Sdim } 4286218893Sdim else { 4287218893Sdim ResultType = getDerived().TransformType(TLB, TL.getResultLoc()); 4288218893Sdim if (ResultType.isNull()) 4289218893Sdim return QualType(); 4290218893Sdim 4291239462Sdim if (getDerived().TransformFunctionTypeParams(TL.getBeginLoc(), 4292218893Sdim TL.getParmArray(), 4293218893Sdim TL.getNumArgs(), 4294239462Sdim TL.getTypePtr()->arg_type_begin(), 4295218893Sdim ParamTypes, &ParamDecls)) 4296218893Sdim return QualType(); 4297218893Sdim } 4298218893Sdim 4299234982Sdim // FIXME: Need to transform the exception-specification too. 4300234982Sdim 4301198398Srdivacky QualType Result = TL.getType(); 4302198398Srdivacky if (getDerived().AlwaysRebuild() || 4303198398Srdivacky ResultType != T->getResultType() || 4304218893Sdim T->getNumArgs() != ParamTypes.size() || 4305198398Srdivacky !std::equal(T->arg_type_begin(), T->arg_type_end(), ParamTypes.begin())) { 4306249423Sdim Result = getDerived().RebuildFunctionProtoType(ResultType, ParamTypes, 4307249423Sdim T->getExtProtoInfo()); 4308198398Srdivacky if (Result.isNull()) 4309198398Srdivacky return QualType(); 4310198398Srdivacky } 4311198092Srdivacky 4312198398Srdivacky FunctionProtoTypeLoc NewTL = TLB.push<FunctionProtoTypeLoc>(Result); 4313221345Sdim NewTL.setLocalRangeBegin(TL.getLocalRangeBegin()); 4314243830Sdim NewTL.setLParenLoc(TL.getLParenLoc()); 4315243830Sdim NewTL.setRParenLoc(TL.getRParenLoc()); 4316221345Sdim NewTL.setLocalRangeEnd(TL.getLocalRangeEnd()); 4317198398Srdivacky for (unsigned i = 0, e = NewTL.getNumArgs(); i != e; ++i) 4318198398Srdivacky NewTL.setArg(i, ParamDecls[i]); 4319198398Srdivacky 4320198398Srdivacky return Result; 4321198092Srdivacky} 4322198092Srdivacky 4323198092Srdivackytemplate<typename Derived> 4324198092SrdivackyQualType TreeTransform<Derived>::TransformFunctionNoProtoType( 4325198398Srdivacky TypeLocBuilder &TLB, 4326218893Sdim FunctionNoProtoTypeLoc TL) { 4327218893Sdim const FunctionNoProtoType *T = TL.getTypePtr(); 4328198398Srdivacky QualType ResultType = getDerived().TransformType(TLB, TL.getResultLoc()); 4329198398Srdivacky if (ResultType.isNull()) 4330198398Srdivacky return QualType(); 4331198398Srdivacky 4332198398Srdivacky QualType Result = TL.getType(); 4333198398Srdivacky if (getDerived().AlwaysRebuild() || 4334198398Srdivacky ResultType != T->getResultType()) 4335198398Srdivacky Result = getDerived().RebuildFunctionNoProtoType(ResultType); 4336198398Srdivacky 4337198398Srdivacky FunctionNoProtoTypeLoc NewTL = TLB.push<FunctionNoProtoTypeLoc>(Result); 4338221345Sdim NewTL.setLocalRangeBegin(TL.getLocalRangeBegin()); 4339243830Sdim NewTL.setLParenLoc(TL.getLParenLoc()); 4340243830Sdim NewTL.setRParenLoc(TL.getRParenLoc()); 4341221345Sdim NewTL.setLocalRangeEnd(TL.getLocalRangeEnd()); 4342198398Srdivacky 4343198398Srdivacky return Result; 4344198092Srdivacky} 4345198092Srdivacky 4346200583Srdivackytemplate<typename Derived> QualType 4347200583SrdivackyTreeTransform<Derived>::TransformUnresolvedUsingType(TypeLocBuilder &TLB, 4348218893Sdim UnresolvedUsingTypeLoc TL) { 4349218893Sdim const UnresolvedUsingType *T = TL.getTypePtr(); 4350204643Srdivacky Decl *D = getDerived().TransformDecl(TL.getNameLoc(), T->getDecl()); 4351200583Srdivacky if (!D) 4352200583Srdivacky return QualType(); 4353200583Srdivacky 4354200583Srdivacky QualType Result = TL.getType(); 4355200583Srdivacky if (getDerived().AlwaysRebuild() || D != T->getDecl()) { 4356200583Srdivacky Result = getDerived().RebuildUnresolvedUsingType(D); 4357200583Srdivacky if (Result.isNull()) 4358200583Srdivacky return QualType(); 4359200583Srdivacky } 4360200583Srdivacky 4361200583Srdivacky // We might get an arbitrary type spec type back. We should at 4362200583Srdivacky // least always get a type spec type, though. 4363200583Srdivacky TypeSpecTypeLoc NewTL = TLB.pushTypeSpec(Result); 4364200583Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4365200583Srdivacky 4366200583Srdivacky return Result; 4367200583Srdivacky} 4368200583Srdivacky 4369198092Srdivackytemplate<typename Derived> 4370198398SrdivackyQualType TreeTransform<Derived>::TransformTypedefType(TypeLocBuilder &TLB, 4371218893Sdim TypedefTypeLoc TL) { 4372218893Sdim const TypedefType *T = TL.getTypePtr(); 4373221345Sdim TypedefNameDecl *Typedef 4374221345Sdim = cast_or_null<TypedefNameDecl>(getDerived().TransformDecl(TL.getNameLoc(), 4375221345Sdim T->getDecl())); 4376198092Srdivacky if (!Typedef) 4377198092Srdivacky return QualType(); 4378198092Srdivacky 4379198398Srdivacky QualType Result = TL.getType(); 4380198398Srdivacky if (getDerived().AlwaysRebuild() || 4381198398Srdivacky Typedef != T->getDecl()) { 4382198398Srdivacky Result = getDerived().RebuildTypedefType(Typedef); 4383198398Srdivacky if (Result.isNull()) 4384198398Srdivacky return QualType(); 4385198398Srdivacky } 4386198092Srdivacky 4387198398Srdivacky TypedefTypeLoc NewTL = TLB.push<TypedefTypeLoc>(Result); 4388198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4389198398Srdivacky 4390198398Srdivacky return Result; 4391198092Srdivacky} 4392198092Srdivacky 4393198092Srdivackytemplate<typename Derived> 4394198398SrdivackyQualType TreeTransform<Derived>::TransformTypeOfExprType(TypeLocBuilder &TLB, 4395218893Sdim TypeOfExprTypeLoc TL) { 4396198092Srdivacky // typeof expressions are not potentially evaluated contexts 4397243830Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated, 4398243830Sdim Sema::ReuseLambdaContextDecl); 4399198092Srdivacky 4400212904Sdim ExprResult E = getDerived().TransformExpr(TL.getUnderlyingExpr()); 4401198092Srdivacky if (E.isInvalid()) 4402198092Srdivacky return QualType(); 4403198092Srdivacky 4404234353Sdim E = SemaRef.HandleExprEvaluationContextForTypeof(E.get()); 4405234353Sdim if (E.isInvalid()) 4406234353Sdim return QualType(); 4407234353Sdim 4408198398Srdivacky QualType Result = TL.getType(); 4409198398Srdivacky if (getDerived().AlwaysRebuild() || 4410202379Srdivacky E.get() != TL.getUnderlyingExpr()) { 4411218893Sdim Result = getDerived().RebuildTypeOfExprType(E.get(), TL.getTypeofLoc()); 4412198398Srdivacky if (Result.isNull()) 4413198398Srdivacky return QualType(); 4414198092Srdivacky } 4415198398Srdivacky else E.take(); 4416198092Srdivacky 4417198398Srdivacky TypeOfExprTypeLoc NewTL = TLB.push<TypeOfExprTypeLoc>(Result); 4418202379Srdivacky NewTL.setTypeofLoc(TL.getTypeofLoc()); 4419202379Srdivacky NewTL.setLParenLoc(TL.getLParenLoc()); 4420202379Srdivacky NewTL.setRParenLoc(TL.getRParenLoc()); 4421198398Srdivacky 4422198398Srdivacky return Result; 4423198092Srdivacky} 4424198092Srdivacky 4425198092Srdivackytemplate<typename Derived> 4426198398SrdivackyQualType TreeTransform<Derived>::TransformTypeOfType(TypeLocBuilder &TLB, 4427218893Sdim TypeOfTypeLoc TL) { 4428202379Srdivacky TypeSourceInfo* Old_Under_TI = TL.getUnderlyingTInfo(); 4429202379Srdivacky TypeSourceInfo* New_Under_TI = getDerived().TransformType(Old_Under_TI); 4430202379Srdivacky if (!New_Under_TI) 4431198092Srdivacky return QualType(); 4432198092Srdivacky 4433198398Srdivacky QualType Result = TL.getType(); 4434202379Srdivacky if (getDerived().AlwaysRebuild() || New_Under_TI != Old_Under_TI) { 4435202379Srdivacky Result = getDerived().RebuildTypeOfType(New_Under_TI->getType()); 4436198398Srdivacky if (Result.isNull()) 4437198398Srdivacky return QualType(); 4438198398Srdivacky } 4439198092Srdivacky 4440198398Srdivacky TypeOfTypeLoc NewTL = TLB.push<TypeOfTypeLoc>(Result); 4441202379Srdivacky NewTL.setTypeofLoc(TL.getTypeofLoc()); 4442202379Srdivacky NewTL.setLParenLoc(TL.getLParenLoc()); 4443202379Srdivacky NewTL.setRParenLoc(TL.getRParenLoc()); 4444202379Srdivacky NewTL.setUnderlyingTInfo(New_Under_TI); 4445198398Srdivacky 4446198398Srdivacky return Result; 4447198092Srdivacky} 4448198092Srdivacky 4449198092Srdivackytemplate<typename Derived> 4450198398SrdivackyQualType TreeTransform<Derived>::TransformDecltypeType(TypeLocBuilder &TLB, 4451218893Sdim DecltypeTypeLoc TL) { 4452218893Sdim const DecltypeType *T = TL.getTypePtr(); 4453198398Srdivacky 4454198092Srdivacky // decltype expressions are not potentially evaluated contexts 4455234353Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated, 0, 4456234353Sdim /*IsDecltype=*/ true); 4457198092Srdivacky 4458212904Sdim ExprResult E = getDerived().TransformExpr(T->getUnderlyingExpr()); 4459198092Srdivacky if (E.isInvalid()) 4460198092Srdivacky return QualType(); 4461198092Srdivacky 4462234353Sdim E = getSema().ActOnDecltypeExpression(E.take()); 4463234353Sdim if (E.isInvalid()) 4464234353Sdim return QualType(); 4465234353Sdim 4466198398Srdivacky QualType Result = TL.getType(); 4467198398Srdivacky if (getDerived().AlwaysRebuild() || 4468198398Srdivacky E.get() != T->getUnderlyingExpr()) { 4469218893Sdim Result = getDerived().RebuildDecltypeType(E.get(), TL.getNameLoc()); 4470198398Srdivacky if (Result.isNull()) 4471198398Srdivacky return QualType(); 4472198092Srdivacky } 4473198398Srdivacky else E.take(); 4474198092Srdivacky 4475198398Srdivacky DecltypeTypeLoc NewTL = TLB.push<DecltypeTypeLoc>(Result); 4476198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4477198398Srdivacky 4478198398Srdivacky return Result; 4479198092Srdivacky} 4480198092Srdivacky 4481198092Srdivackytemplate<typename Derived> 4482223017SdimQualType TreeTransform<Derived>::TransformUnaryTransformType( 4483223017Sdim TypeLocBuilder &TLB, 4484223017Sdim UnaryTransformTypeLoc TL) { 4485223017Sdim QualType Result = TL.getType(); 4486223017Sdim if (Result->isDependentType()) { 4487223017Sdim const UnaryTransformType *T = TL.getTypePtr(); 4488223017Sdim QualType NewBase = 4489223017Sdim getDerived().TransformType(TL.getUnderlyingTInfo())->getType(); 4490223017Sdim Result = getDerived().RebuildUnaryTransformType(NewBase, 4491223017Sdim T->getUTTKind(), 4492223017Sdim TL.getKWLoc()); 4493223017Sdim if (Result.isNull()) 4494223017Sdim return QualType(); 4495223017Sdim } 4496223017Sdim 4497223017Sdim UnaryTransformTypeLoc NewTL = TLB.push<UnaryTransformTypeLoc>(Result); 4498223017Sdim NewTL.setKWLoc(TL.getKWLoc()); 4499223017Sdim NewTL.setParensRange(TL.getParensRange()); 4500223017Sdim NewTL.setUnderlyingTInfo(TL.getUnderlyingTInfo()); 4501223017Sdim return Result; 4502223017Sdim} 4503223017Sdim 4504223017Sdimtemplate<typename Derived> 4505218893SdimQualType TreeTransform<Derived>::TransformAutoType(TypeLocBuilder &TLB, 4506218893Sdim AutoTypeLoc TL) { 4507218893Sdim const AutoType *T = TL.getTypePtr(); 4508218893Sdim QualType OldDeduced = T->getDeducedType(); 4509218893Sdim QualType NewDeduced; 4510218893Sdim if (!OldDeduced.isNull()) { 4511218893Sdim NewDeduced = getDerived().TransformType(OldDeduced); 4512218893Sdim if (NewDeduced.isNull()) 4513218893Sdim return QualType(); 4514218893Sdim } 4515218893Sdim 4516218893Sdim QualType Result = TL.getType(); 4517251662Sdim if (getDerived().AlwaysRebuild() || NewDeduced != OldDeduced || 4518251662Sdim T->isDependentType()) { 4519251662Sdim Result = getDerived().RebuildAutoType(NewDeduced, T->isDecltypeAuto()); 4520218893Sdim if (Result.isNull()) 4521218893Sdim return QualType(); 4522218893Sdim } 4523218893Sdim 4524218893Sdim AutoTypeLoc NewTL = TLB.push<AutoTypeLoc>(Result); 4525218893Sdim NewTL.setNameLoc(TL.getNameLoc()); 4526218893Sdim 4527218893Sdim return Result; 4528218893Sdim} 4529218893Sdim 4530218893Sdimtemplate<typename Derived> 4531198398SrdivackyQualType TreeTransform<Derived>::TransformRecordType(TypeLocBuilder &TLB, 4532218893Sdim RecordTypeLoc TL) { 4533218893Sdim const RecordType *T = TL.getTypePtr(); 4534198092Srdivacky RecordDecl *Record 4535204643Srdivacky = cast_or_null<RecordDecl>(getDerived().TransformDecl(TL.getNameLoc(), 4536204643Srdivacky T->getDecl())); 4537198092Srdivacky if (!Record) 4538198092Srdivacky return QualType(); 4539198092Srdivacky 4540198398Srdivacky QualType Result = TL.getType(); 4541198398Srdivacky if (getDerived().AlwaysRebuild() || 4542198398Srdivacky Record != T->getDecl()) { 4543198398Srdivacky Result = getDerived().RebuildRecordType(Record); 4544198398Srdivacky if (Result.isNull()) 4545198398Srdivacky return QualType(); 4546198398Srdivacky } 4547198092Srdivacky 4548198398Srdivacky RecordTypeLoc NewTL = TLB.push<RecordTypeLoc>(Result); 4549198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4550198398Srdivacky 4551198398Srdivacky return Result; 4552198092Srdivacky} 4553198092Srdivacky 4554198092Srdivackytemplate<typename Derived> 4555198398SrdivackyQualType TreeTransform<Derived>::TransformEnumType(TypeLocBuilder &TLB, 4556218893Sdim EnumTypeLoc TL) { 4557218893Sdim const EnumType *T = TL.getTypePtr(); 4558198092Srdivacky EnumDecl *Enum 4559204643Srdivacky = cast_or_null<EnumDecl>(getDerived().TransformDecl(TL.getNameLoc(), 4560204643Srdivacky T->getDecl())); 4561198092Srdivacky if (!Enum) 4562198092Srdivacky return QualType(); 4563198092Srdivacky 4564198398Srdivacky QualType Result = TL.getType(); 4565198398Srdivacky if (getDerived().AlwaysRebuild() || 4566198398Srdivacky Enum != T->getDecl()) { 4567198398Srdivacky Result = getDerived().RebuildEnumType(Enum); 4568198398Srdivacky if (Result.isNull()) 4569198398Srdivacky return QualType(); 4570198398Srdivacky } 4571198092Srdivacky 4572198398Srdivacky EnumTypeLoc NewTL = TLB.push<EnumTypeLoc>(Result); 4573198398Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4574198398Srdivacky 4575198398Srdivacky return Result; 4576198092Srdivacky} 4577198092Srdivacky 4578204962Srdivackytemplate<typename Derived> 4579204962SrdivackyQualType TreeTransform<Derived>::TransformInjectedClassNameType( 4580204962Srdivacky TypeLocBuilder &TLB, 4581218893Sdim InjectedClassNameTypeLoc TL) { 4582204962Srdivacky Decl *D = getDerived().TransformDecl(TL.getNameLoc(), 4583204962Srdivacky TL.getTypePtr()->getDecl()); 4584204962Srdivacky if (!D) return QualType(); 4585198092Srdivacky 4586204962Srdivacky QualType T = SemaRef.Context.getTypeDeclType(cast<TypeDecl>(D)); 4587204962Srdivacky TLB.pushTypeSpec(T).setNameLoc(TL.getNameLoc()); 4588204962Srdivacky return T; 4589204962Srdivacky} 4590204962Srdivacky 4591198092Srdivackytemplate<typename Derived> 4592198092SrdivackyQualType TreeTransform<Derived>::TransformTemplateTypeParmType( 4593198398Srdivacky TypeLocBuilder &TLB, 4594218893Sdim TemplateTypeParmTypeLoc TL) { 4595198398Srdivacky return TransformTypeSpecType(TLB, TL); 4596198092Srdivacky} 4597198092Srdivacky 4598198092Srdivackytemplate<typename Derived> 4599198398SrdivackyQualType TreeTransform<Derived>::TransformSubstTemplateTypeParmType( 4600198398Srdivacky TypeLocBuilder &TLB, 4601218893Sdim SubstTemplateTypeParmTypeLoc TL) { 4602221345Sdim const SubstTemplateTypeParmType *T = TL.getTypePtr(); 4603239462Sdim 4604221345Sdim // Substitute into the replacement type, which itself might involve something 4605221345Sdim // that needs to be transformed. This only tends to occur with default 4606221345Sdim // template arguments of template template parameters. 4607221345Sdim TemporaryBase Rebase(*this, TL.getNameLoc(), DeclarationName()); 4608221345Sdim QualType Replacement = getDerived().TransformType(T->getReplacementType()); 4609221345Sdim if (Replacement.isNull()) 4610221345Sdim return QualType(); 4611239462Sdim 4612221345Sdim // Always canonicalize the replacement type. 4613221345Sdim Replacement = SemaRef.Context.getCanonicalType(Replacement); 4614221345Sdim QualType Result 4615239462Sdim = SemaRef.Context.getSubstTemplateTypeParmType(T->getReplacedParameter(), 4616221345Sdim Replacement); 4617239462Sdim 4618221345Sdim // Propagate type-source information. 4619221345Sdim SubstTemplateTypeParmTypeLoc NewTL 4620221345Sdim = TLB.push<SubstTemplateTypeParmTypeLoc>(Result); 4621221345Sdim NewTL.setNameLoc(TL.getNameLoc()); 4622221345Sdim return Result; 4623221345Sdim 4624198398Srdivacky} 4625198398Srdivacky 4626198398Srdivackytemplate<typename Derived> 4627218893SdimQualType TreeTransform<Derived>::TransformSubstTemplateTypeParmPackType( 4628218893Sdim TypeLocBuilder &TLB, 4629218893Sdim SubstTemplateTypeParmPackTypeLoc TL) { 4630218893Sdim return TransformTypeSpecType(TLB, TL); 4631218893Sdim} 4632198398Srdivacky 4633198398Srdivackytemplate<typename Derived> 4634198092SrdivackyQualType TreeTransform<Derived>::TransformTemplateSpecializationType( 4635198893Srdivacky TypeLocBuilder &TLB, 4636218893Sdim TemplateSpecializationTypeLoc TL) { 4637198893Srdivacky const TemplateSpecializationType *T = TL.getTypePtr(); 4638198893Srdivacky 4639221345Sdim // The nested-name-specifier never matters in a TemplateSpecializationType, 4640221345Sdim // because we can't have a dependent nested-name-specifier anyway. 4641221345Sdim CXXScopeSpec SS; 4642198092Srdivacky TemplateName Template 4643221345Sdim = getDerived().TransformTemplateName(SS, T->getTemplateName(), 4644221345Sdim TL.getTemplateNameLoc()); 4645198092Srdivacky if (Template.isNull()) 4646198092Srdivacky return QualType(); 4647198092Srdivacky 4648218893Sdim return getDerived().TransformTemplateSpecializationType(TLB, TL, Template); 4649218893Sdim} 4650218893Sdim 4651226633Sdimtemplate<typename Derived> 4652226633SdimQualType TreeTransform<Derived>::TransformAtomicType(TypeLocBuilder &TLB, 4653226633Sdim AtomicTypeLoc TL) { 4654226633Sdim QualType ValueType = getDerived().TransformType(TLB, TL.getValueLoc()); 4655226633Sdim if (ValueType.isNull()) 4656226633Sdim return QualType(); 4657226633Sdim 4658226633Sdim QualType Result = TL.getType(); 4659226633Sdim if (getDerived().AlwaysRebuild() || 4660226633Sdim ValueType != TL.getValueLoc().getType()) { 4661226633Sdim Result = getDerived().RebuildAtomicType(ValueType, TL.getKWLoc()); 4662226633Sdim if (Result.isNull()) 4663226633Sdim return QualType(); 4664226633Sdim } 4665226633Sdim 4666226633Sdim AtomicTypeLoc NewTL = TLB.push<AtomicTypeLoc>(Result); 4667226633Sdim NewTL.setKWLoc(TL.getKWLoc()); 4668226633Sdim NewTL.setLParenLoc(TL.getLParenLoc()); 4669226633Sdim NewTL.setRParenLoc(TL.getRParenLoc()); 4670226633Sdim 4671226633Sdim return Result; 4672226633Sdim} 4673226633Sdim 4674239462Sdim /// \brief Simple iterator that traverses the template arguments in a 4675218893Sdim /// container that provides a \c getArgLoc() member function. 4676218893Sdim /// 4677218893Sdim /// This iterator is intended to be used with the iterator form of 4678218893Sdim /// \c TreeTransform<Derived>::TransformTemplateArguments(). 4679218893Sdim template<typename ArgLocContainer> 4680218893Sdim class TemplateArgumentLocContainerIterator { 4681218893Sdim ArgLocContainer *Container; 4682218893Sdim unsigned Index; 4683239462Sdim 4684218893Sdim public: 4685218893Sdim typedef TemplateArgumentLoc value_type; 4686218893Sdim typedef TemplateArgumentLoc reference; 4687218893Sdim typedef int difference_type; 4688218893Sdim typedef std::input_iterator_tag iterator_category; 4689239462Sdim 4690218893Sdim class pointer { 4691218893Sdim TemplateArgumentLoc Arg; 4692239462Sdim 4693218893Sdim public: 4694218893Sdim explicit pointer(TemplateArgumentLoc Arg) : Arg(Arg) { } 4695239462Sdim 4696218893Sdim const TemplateArgumentLoc *operator->() const { 4697218893Sdim return &Arg; 4698218893Sdim } 4699218893Sdim }; 4700239462Sdim 4701239462Sdim 4702218893Sdim TemplateArgumentLocContainerIterator() {} 4703239462Sdim 4704218893Sdim TemplateArgumentLocContainerIterator(ArgLocContainer &Container, 4705218893Sdim unsigned Index) 4706218893Sdim : Container(&Container), Index(Index) { } 4707239462Sdim 4708218893Sdim TemplateArgumentLocContainerIterator &operator++() { 4709218893Sdim ++Index; 4710218893Sdim return *this; 4711218893Sdim } 4712239462Sdim 4713218893Sdim TemplateArgumentLocContainerIterator operator++(int) { 4714218893Sdim TemplateArgumentLocContainerIterator Old(*this); 4715218893Sdim ++(*this); 4716218893Sdim return Old; 4717218893Sdim } 4718239462Sdim 4719218893Sdim TemplateArgumentLoc operator*() const { 4720218893Sdim return Container->getArgLoc(Index); 4721218893Sdim } 4722239462Sdim 4723218893Sdim pointer operator->() const { 4724218893Sdim return pointer(Container->getArgLoc(Index)); 4725218893Sdim } 4726239462Sdim 4727218893Sdim friend bool operator==(const TemplateArgumentLocContainerIterator &X, 4728218893Sdim const TemplateArgumentLocContainerIterator &Y) { 4729218893Sdim return X.Container == Y.Container && X.Index == Y.Index; 4730218893Sdim } 4731239462Sdim 4732218893Sdim friend bool operator!=(const TemplateArgumentLocContainerIterator &X, 4733218893Sdim const TemplateArgumentLocContainerIterator &Y) { 4734218893Sdim return !(X == Y); 4735218893Sdim } 4736218893Sdim }; 4737239462Sdim 4738239462Sdim 4739218893Sdimtemplate <typename Derived> 4740218893SdimQualType TreeTransform<Derived>::TransformTemplateSpecializationType( 4741218893Sdim TypeLocBuilder &TLB, 4742218893Sdim TemplateSpecializationTypeLoc TL, 4743218893Sdim TemplateName Template) { 4744199990Srdivacky TemplateArgumentListInfo NewTemplateArgs; 4745199990Srdivacky NewTemplateArgs.setLAngleLoc(TL.getLAngleLoc()); 4746199990Srdivacky NewTemplateArgs.setRAngleLoc(TL.getRAngleLoc()); 4747218893Sdim typedef TemplateArgumentLocContainerIterator<TemplateSpecializationTypeLoc> 4748218893Sdim ArgIterator; 4749239462Sdim if (getDerived().TransformTemplateArguments(ArgIterator(TL, 0), 4750218893Sdim ArgIterator(TL, TL.getNumArgs()), 4751218893Sdim NewTemplateArgs)) 4752218893Sdim return QualType(); 4753199990Srdivacky 4754198893Srdivacky // FIXME: maybe don't rebuild if all the template arguments are the same. 4755198893Srdivacky 4756198893Srdivacky QualType Result = 4757198893Srdivacky getDerived().RebuildTemplateSpecializationType(Template, 4758198893Srdivacky TL.getTemplateNameLoc(), 4759199990Srdivacky NewTemplateArgs); 4760198893Srdivacky 4761198893Srdivacky if (!Result.isNull()) { 4762223017Sdim // Specializations of template template parameters are represented as 4763223017Sdim // TemplateSpecializationTypes, and substitution of type alias templates 4764223017Sdim // within a dependent context can transform them into 4765223017Sdim // DependentTemplateSpecializationTypes. 4766223017Sdim if (isa<DependentTemplateSpecializationType>(Result)) { 4767223017Sdim DependentTemplateSpecializationTypeLoc NewTL 4768223017Sdim = TLB.push<DependentTemplateSpecializationTypeLoc>(Result); 4769234353Sdim NewTL.setElaboratedKeywordLoc(SourceLocation()); 4770223017Sdim NewTL.setQualifierLoc(NestedNameSpecifierLoc()); 4771234353Sdim NewTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 4772234353Sdim NewTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 4773223017Sdim NewTL.setLAngleLoc(TL.getLAngleLoc()); 4774223017Sdim NewTL.setRAngleLoc(TL.getRAngleLoc()); 4775223017Sdim for (unsigned i = 0, e = NewTemplateArgs.size(); i != e; ++i) 4776223017Sdim NewTL.setArgLocInfo(i, NewTemplateArgs[i].getLocInfo()); 4777223017Sdim return Result; 4778223017Sdim } 4779223017Sdim 4780198893Srdivacky TemplateSpecializationTypeLoc NewTL 4781198893Srdivacky = TLB.push<TemplateSpecializationTypeLoc>(Result); 4782234353Sdim NewTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 4783198893Srdivacky NewTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 4784198893Srdivacky NewTL.setLAngleLoc(TL.getLAngleLoc()); 4785198893Srdivacky NewTL.setRAngleLoc(TL.getRAngleLoc()); 4786198893Srdivacky for (unsigned i = 0, e = NewTemplateArgs.size(); i != e; ++i) 4787198893Srdivacky NewTL.setArgLocInfo(i, NewTemplateArgs[i].getLocInfo()); 4788198092Srdivacky } 4789198092Srdivacky 4790198893Srdivacky return Result; 4791198092Srdivacky} 4792198092Srdivacky 4793221345Sdimtemplate <typename Derived> 4794221345SdimQualType TreeTransform<Derived>::TransformDependentTemplateSpecializationType( 4795221345Sdim TypeLocBuilder &TLB, 4796221345Sdim DependentTemplateSpecializationTypeLoc TL, 4797221345Sdim TemplateName Template, 4798221345Sdim CXXScopeSpec &SS) { 4799221345Sdim TemplateArgumentListInfo NewTemplateArgs; 4800221345Sdim NewTemplateArgs.setLAngleLoc(TL.getLAngleLoc()); 4801221345Sdim NewTemplateArgs.setRAngleLoc(TL.getRAngleLoc()); 4802221345Sdim typedef TemplateArgumentLocContainerIterator< 4803221345Sdim DependentTemplateSpecializationTypeLoc> ArgIterator; 4804239462Sdim if (getDerived().TransformTemplateArguments(ArgIterator(TL, 0), 4805221345Sdim ArgIterator(TL, TL.getNumArgs()), 4806221345Sdim NewTemplateArgs)) 4807221345Sdim return QualType(); 4808239462Sdim 4809221345Sdim // FIXME: maybe don't rebuild if all the template arguments are the same. 4810239462Sdim 4811221345Sdim if (DependentTemplateName *DTN = Template.getAsDependentTemplateName()) { 4812221345Sdim QualType Result 4813221345Sdim = getSema().Context.getDependentTemplateSpecializationType( 4814221345Sdim TL.getTypePtr()->getKeyword(), 4815221345Sdim DTN->getQualifier(), 4816221345Sdim DTN->getIdentifier(), 4817221345Sdim NewTemplateArgs); 4818239462Sdim 4819221345Sdim DependentTemplateSpecializationTypeLoc NewTL 4820221345Sdim = TLB.push<DependentTemplateSpecializationTypeLoc>(Result); 4821234353Sdim NewTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 4822221345Sdim NewTL.setQualifierLoc(SS.getWithLocInContext(SemaRef.Context)); 4823234353Sdim NewTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 4824234353Sdim NewTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 4825221345Sdim NewTL.setLAngleLoc(TL.getLAngleLoc()); 4826221345Sdim NewTL.setRAngleLoc(TL.getRAngleLoc()); 4827221345Sdim for (unsigned i = 0, e = NewTemplateArgs.size(); i != e; ++i) 4828221345Sdim NewTL.setArgLocInfo(i, NewTemplateArgs[i].getLocInfo()); 4829221345Sdim return Result; 4830221345Sdim } 4831239462Sdim 4832239462Sdim QualType Result 4833221345Sdim = getDerived().RebuildTemplateSpecializationType(Template, 4834234353Sdim TL.getTemplateNameLoc(), 4835221345Sdim NewTemplateArgs); 4836239462Sdim 4837221345Sdim if (!Result.isNull()) { 4838221345Sdim /// FIXME: Wrap this in an elaborated-type-specifier? 4839221345Sdim TemplateSpecializationTypeLoc NewTL 4840221345Sdim = TLB.push<TemplateSpecializationTypeLoc>(Result); 4841234353Sdim NewTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 4842234353Sdim NewTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 4843221345Sdim NewTL.setLAngleLoc(TL.getLAngleLoc()); 4844221345Sdim NewTL.setRAngleLoc(TL.getRAngleLoc()); 4845221345Sdim for (unsigned i = 0, e = NewTemplateArgs.size(); i != e; ++i) 4846221345Sdim NewTL.setArgLocInfo(i, NewTemplateArgs[i].getLocInfo()); 4847221345Sdim } 4848239462Sdim 4849221345Sdim return Result; 4850221345Sdim} 4851221345Sdim 4852198092Srdivackytemplate<typename Derived> 4853198398SrdivackyQualType 4854208600SrdivackyTreeTransform<Derived>::TransformElaboratedType(TypeLocBuilder &TLB, 4855218893Sdim ElaboratedTypeLoc TL) { 4856218893Sdim const ElaboratedType *T = TL.getTypePtr(); 4857198092Srdivacky 4858221345Sdim NestedNameSpecifierLoc QualifierLoc; 4859208600Srdivacky // NOTE: the qualifier in an ElaboratedType is optional. 4860221345Sdim if (TL.getQualifierLoc()) { 4861239462Sdim QualifierLoc 4862221345Sdim = getDerived().TransformNestedNameSpecifierLoc(TL.getQualifierLoc()); 4863221345Sdim if (!QualifierLoc) 4864208600Srdivacky return QualType(); 4865208600Srdivacky } 4866198092Srdivacky 4867218893Sdim QualType NamedT = getDerived().TransformType(TLB, TL.getNamedTypeLoc()); 4868218893Sdim if (NamedT.isNull()) 4869218893Sdim return QualType(); 4870208600Srdivacky 4871223017Sdim // C++0x [dcl.type.elab]p2: 4872223017Sdim // If the identifier resolves to a typedef-name or the simple-template-id 4873223017Sdim // resolves to an alias template specialization, the 4874223017Sdim // elaborated-type-specifier is ill-formed. 4875223017Sdim if (T->getKeyword() != ETK_None && T->getKeyword() != ETK_Typename) { 4876223017Sdim if (const TemplateSpecializationType *TST = 4877223017Sdim NamedT->getAs<TemplateSpecializationType>()) { 4878223017Sdim TemplateName Template = TST->getTemplateName(); 4879223017Sdim if (TypeAliasTemplateDecl *TAT = 4880223017Sdim dyn_cast_or_null<TypeAliasTemplateDecl>(Template.getAsTemplateDecl())) { 4881223017Sdim SemaRef.Diag(TL.getNamedTypeLoc().getBeginLoc(), 4882223017Sdim diag::err_tag_reference_non_tag) << 4; 4883223017Sdim SemaRef.Diag(TAT->getLocation(), diag::note_declared_at); 4884223017Sdim } 4885223017Sdim } 4886223017Sdim } 4887223017Sdim 4888198398Srdivacky QualType Result = TL.getType(); 4889198398Srdivacky if (getDerived().AlwaysRebuild() || 4890221345Sdim QualifierLoc != TL.getQualifierLoc() || 4891208600Srdivacky NamedT != T->getNamedType()) { 4892234353Sdim Result = getDerived().RebuildElaboratedType(TL.getElaboratedKeywordLoc(), 4893239462Sdim T->getKeyword(), 4894221345Sdim QualifierLoc, NamedT); 4895198398Srdivacky if (Result.isNull()) 4896198398Srdivacky return QualType(); 4897198398Srdivacky } 4898198092Srdivacky 4899208600Srdivacky ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result); 4900234353Sdim NewTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 4901221345Sdim NewTL.setQualifierLoc(QualifierLoc); 4902198398Srdivacky return Result; 4903198092Srdivacky} 4904198092Srdivacky 4905198092Srdivackytemplate<typename Derived> 4906218893SdimQualType TreeTransform<Derived>::TransformAttributedType( 4907218893Sdim TypeLocBuilder &TLB, 4908218893Sdim AttributedTypeLoc TL) { 4909218893Sdim const AttributedType *oldType = TL.getTypePtr(); 4910218893Sdim QualType modifiedType = getDerived().TransformType(TLB, TL.getModifiedLoc()); 4911218893Sdim if (modifiedType.isNull()) 4912218893Sdim return QualType(); 4913218893Sdim 4914218893Sdim QualType result = TL.getType(); 4915218893Sdim 4916218893Sdim // FIXME: dependent operand expressions? 4917218893Sdim if (getDerived().AlwaysRebuild() || 4918218893Sdim modifiedType != oldType->getModifiedType()) { 4919218893Sdim // TODO: this is really lame; we should really be rebuilding the 4920218893Sdim // equivalent type from first principles. 4921218893Sdim QualType equivalentType 4922218893Sdim = getDerived().TransformType(oldType->getEquivalentType()); 4923218893Sdim if (equivalentType.isNull()) 4924218893Sdim return QualType(); 4925218893Sdim result = SemaRef.Context.getAttributedType(oldType->getAttrKind(), 4926218893Sdim modifiedType, 4927218893Sdim equivalentType); 4928218893Sdim } 4929218893Sdim 4930218893Sdim AttributedTypeLoc newTL = TLB.push<AttributedTypeLoc>(result); 4931218893Sdim newTL.setAttrNameLoc(TL.getAttrNameLoc()); 4932218893Sdim if (TL.hasAttrOperand()) 4933218893Sdim newTL.setAttrOperandParensRange(TL.getAttrOperandParensRange()); 4934218893Sdim if (TL.hasAttrExprOperand()) 4935218893Sdim newTL.setAttrExprOperand(TL.getAttrExprOperand()); 4936218893Sdim else if (TL.hasAttrEnumOperand()) 4937218893Sdim newTL.setAttrEnumOperandLoc(TL.getAttrEnumOperandLoc()); 4938218893Sdim 4939218893Sdim return result; 4940218893Sdim} 4941218893Sdim 4942218893Sdimtemplate<typename Derived> 4943218893SdimQualType 4944218893SdimTreeTransform<Derived>::TransformParenType(TypeLocBuilder &TLB, 4945218893Sdim ParenTypeLoc TL) { 4946218893Sdim QualType Inner = getDerived().TransformType(TLB, TL.getInnerLoc()); 4947218893Sdim if (Inner.isNull()) 4948218893Sdim return QualType(); 4949218893Sdim 4950218893Sdim QualType Result = TL.getType(); 4951218893Sdim if (getDerived().AlwaysRebuild() || 4952218893Sdim Inner != TL.getInnerLoc().getType()) { 4953218893Sdim Result = getDerived().RebuildParenType(Inner); 4954218893Sdim if (Result.isNull()) 4955218893Sdim return QualType(); 4956218893Sdim } 4957218893Sdim 4958218893Sdim ParenTypeLoc NewTL = TLB.push<ParenTypeLoc>(Result); 4959218893Sdim NewTL.setLParenLoc(TL.getLParenLoc()); 4960218893Sdim NewTL.setRParenLoc(TL.getRParenLoc()); 4961218893Sdim return Result; 4962218893Sdim} 4963218893Sdim 4964218893Sdimtemplate<typename Derived> 4965206084SrdivackyQualType TreeTransform<Derived>::TransformDependentNameType(TypeLocBuilder &TLB, 4966218893Sdim DependentNameTypeLoc TL) { 4967218893Sdim const DependentNameType *T = TL.getTypePtr(); 4968198893Srdivacky 4969221345Sdim NestedNameSpecifierLoc QualifierLoc 4970221345Sdim = getDerived().TransformNestedNameSpecifierLoc(TL.getQualifierLoc()); 4971221345Sdim if (!QualifierLoc) 4972198092Srdivacky return QualType(); 4973198092Srdivacky 4974210299Sed QualType Result 4975221345Sdim = getDerived().RebuildDependentNameType(T->getKeyword(), 4976234353Sdim TL.getElaboratedKeywordLoc(), 4977221345Sdim QualifierLoc, 4978210299Sed T->getIdentifier(), 4979210299Sed TL.getNameLoc()); 4980198398Srdivacky if (Result.isNull()) 4981198398Srdivacky return QualType(); 4982198092Srdivacky 4983208600Srdivacky if (const ElaboratedType* ElabT = Result->getAs<ElaboratedType>()) { 4984208600Srdivacky QualType NamedT = ElabT->getNamedType(); 4985210299Sed TLB.pushTypeSpec(NamedT).setNameLoc(TL.getNameLoc()); 4986210299Sed 4987208600Srdivacky ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result); 4988234353Sdim NewTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 4989221345Sdim NewTL.setQualifierLoc(QualifierLoc); 4990210299Sed } else { 4991208600Srdivacky DependentNameTypeLoc NewTL = TLB.push<DependentNameTypeLoc>(Result); 4992234353Sdim NewTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 4993221345Sdim NewTL.setQualifierLoc(QualifierLoc); 4994208600Srdivacky NewTL.setNameLoc(TL.getNameLoc()); 4995208600Srdivacky } 4996198398Srdivacky return Result; 4997198092Srdivacky} 4998198092Srdivacky 4999198092Srdivackytemplate<typename Derived> 5000210299SedQualType TreeTransform<Derived>:: 5001210299Sed TransformDependentTemplateSpecializationType(TypeLocBuilder &TLB, 5002218893Sdim DependentTemplateSpecializationTypeLoc TL) { 5003221345Sdim NestedNameSpecifierLoc QualifierLoc; 5004221345Sdim if (TL.getQualifierLoc()) { 5005221345Sdim QualifierLoc 5006221345Sdim = getDerived().TransformNestedNameSpecifierLoc(TL.getQualifierLoc()); 5007221345Sdim if (!QualifierLoc) 5008221345Sdim return QualType(); 5009221345Sdim } 5010239462Sdim 5011218893Sdim return getDerived() 5012221345Sdim .TransformDependentTemplateSpecializationType(TLB, TL, QualifierLoc); 5013218893Sdim} 5014218893Sdim 5015218893Sdimtemplate<typename Derived> 5016218893SdimQualType TreeTransform<Derived>:: 5017221345SdimTransformDependentTemplateSpecializationType(TypeLocBuilder &TLB, 5018221345Sdim DependentTemplateSpecializationTypeLoc TL, 5019221345Sdim NestedNameSpecifierLoc QualifierLoc) { 5020218893Sdim const DependentTemplateSpecializationType *T = TL.getTypePtr(); 5021239462Sdim 5022210299Sed TemplateArgumentListInfo NewTemplateArgs; 5023210299Sed NewTemplateArgs.setLAngleLoc(TL.getLAngleLoc()); 5024210299Sed NewTemplateArgs.setRAngleLoc(TL.getRAngleLoc()); 5025239462Sdim 5026218893Sdim typedef TemplateArgumentLocContainerIterator< 5027221345Sdim DependentTemplateSpecializationTypeLoc> ArgIterator; 5028218893Sdim if (getDerived().TransformTemplateArguments(ArgIterator(TL, 0), 5029218893Sdim ArgIterator(TL, TL.getNumArgs()), 5030218893Sdim NewTemplateArgs)) 5031218893Sdim return QualType(); 5032239462Sdim 5033218893Sdim QualType Result 5034218893Sdim = getDerived().RebuildDependentTemplateSpecializationType(T->getKeyword(), 5035221345Sdim QualifierLoc, 5036218893Sdim T->getIdentifier(), 5037234353Sdim TL.getTemplateNameLoc(), 5038221345Sdim NewTemplateArgs); 5039210299Sed if (Result.isNull()) 5040210299Sed return QualType(); 5041239462Sdim 5042210299Sed if (const ElaboratedType *ElabT = dyn_cast<ElaboratedType>(Result)) { 5043210299Sed QualType NamedT = ElabT->getNamedType(); 5044239462Sdim 5045210299Sed // Copy information relevant to the template specialization. 5046210299Sed TemplateSpecializationTypeLoc NamedTL 5047210299Sed = TLB.push<TemplateSpecializationTypeLoc>(NamedT); 5048234353Sdim NamedTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 5049234353Sdim NamedTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 5050210299Sed NamedTL.setLAngleLoc(TL.getLAngleLoc()); 5051210299Sed NamedTL.setRAngleLoc(TL.getRAngleLoc()); 5052221345Sdim for (unsigned I = 0, E = NewTemplateArgs.size(); I != E; ++I) 5053221345Sdim NamedTL.setArgLocInfo(I, NewTemplateArgs[I].getLocInfo()); 5054239462Sdim 5055210299Sed // Copy information relevant to the elaborated type. 5056210299Sed ElaboratedTypeLoc NewTL = TLB.push<ElaboratedTypeLoc>(Result); 5057234353Sdim NewTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 5058221345Sdim NewTL.setQualifierLoc(QualifierLoc); 5059221345Sdim } else if (isa<DependentTemplateSpecializationType>(Result)) { 5060221345Sdim DependentTemplateSpecializationTypeLoc SpecTL 5061221345Sdim = TLB.push<DependentTemplateSpecializationTypeLoc>(Result); 5062234353Sdim SpecTL.setElaboratedKeywordLoc(TL.getElaboratedKeywordLoc()); 5063221345Sdim SpecTL.setQualifierLoc(QualifierLoc); 5064234353Sdim SpecTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 5065234353Sdim SpecTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 5066221345Sdim SpecTL.setLAngleLoc(TL.getLAngleLoc()); 5067221345Sdim SpecTL.setRAngleLoc(TL.getRAngleLoc()); 5068221345Sdim for (unsigned I = 0, E = NewTemplateArgs.size(); I != E; ++I) 5069221345Sdim SpecTL.setArgLocInfo(I, NewTemplateArgs[I].getLocInfo()); 5070210299Sed } else { 5071221345Sdim TemplateSpecializationTypeLoc SpecTL 5072221345Sdim = TLB.push<TemplateSpecializationTypeLoc>(Result); 5073234353Sdim SpecTL.setTemplateKeywordLoc(TL.getTemplateKeywordLoc()); 5074234353Sdim SpecTL.setTemplateNameLoc(TL.getTemplateNameLoc()); 5075221345Sdim SpecTL.setLAngleLoc(TL.getLAngleLoc()); 5076221345Sdim SpecTL.setRAngleLoc(TL.getRAngleLoc()); 5077221345Sdim for (unsigned I = 0, E = NewTemplateArgs.size(); I != E; ++I) 5078221345Sdim SpecTL.setArgLocInfo(I, NewTemplateArgs[I].getLocInfo()); 5079210299Sed } 5080210299Sed return Result; 5081210299Sed} 5082210299Sed 5083210299Sedtemplate<typename Derived> 5084218893SdimQualType TreeTransform<Derived>::TransformPackExpansionType(TypeLocBuilder &TLB, 5085218893Sdim PackExpansionTypeLoc TL) { 5086239462Sdim QualType Pattern 5087239462Sdim = getDerived().TransformType(TLB, TL.getPatternLoc()); 5088218893Sdim if (Pattern.isNull()) 5089218893Sdim return QualType(); 5090239462Sdim 5091239462Sdim QualType Result = TL.getType(); 5092218893Sdim if (getDerived().AlwaysRebuild() || 5093218893Sdim Pattern != TL.getPatternLoc().getType()) { 5094239462Sdim Result = getDerived().RebuildPackExpansionType(Pattern, 5095218893Sdim TL.getPatternLoc().getSourceRange(), 5096218893Sdim TL.getEllipsisLoc(), 5097218893Sdim TL.getTypePtr()->getNumExpansions()); 5098218893Sdim if (Result.isNull()) 5099218893Sdim return QualType(); 5100218893Sdim } 5101239462Sdim 5102218893Sdim PackExpansionTypeLoc NewT = TLB.push<PackExpansionTypeLoc>(Result); 5103218893Sdim NewT.setEllipsisLoc(TL.getEllipsisLoc()); 5104218893Sdim return Result; 5105218893Sdim} 5106218893Sdim 5107218893Sdimtemplate<typename Derived> 5108198398SrdivackyQualType 5109198398SrdivackyTreeTransform<Derived>::TransformObjCInterfaceType(TypeLocBuilder &TLB, 5110218893Sdim ObjCInterfaceTypeLoc TL) { 5111207619Srdivacky // ObjCInterfaceType is never dependent. 5112208600Srdivacky TLB.pushFullCopy(TL); 5113207619Srdivacky return TL.getType(); 5114198092Srdivacky} 5115198092Srdivacky 5116198092Srdivackytemplate<typename Derived> 5117198398SrdivackyQualType 5118208600SrdivackyTreeTransform<Derived>::TransformObjCObjectType(TypeLocBuilder &TLB, 5119218893Sdim ObjCObjectTypeLoc TL) { 5120208600Srdivacky // ObjCObjectType is never dependent. 5121208600Srdivacky TLB.pushFullCopy(TL); 5122208600Srdivacky return TL.getType(); 5123208600Srdivacky} 5124208600Srdivacky 5125208600Srdivackytemplate<typename Derived> 5126208600SrdivackyQualType 5127198398SrdivackyTreeTransform<Derived>::TransformObjCObjectPointerType(TypeLocBuilder &TLB, 5128218893Sdim ObjCObjectPointerTypeLoc TL) { 5129207619Srdivacky // ObjCObjectPointerType is never dependent. 5130208600Srdivacky TLB.pushFullCopy(TL); 5131207619Srdivacky return TL.getType(); 5132198092Srdivacky} 5133198092Srdivacky 5134198092Srdivacky//===----------------------------------------------------------------------===// 5135198092Srdivacky// Statement transformation 5136198092Srdivacky//===----------------------------------------------------------------------===// 5137198092Srdivackytemplate<typename Derived> 5138212904SdimStmtResult 5139198092SrdivackyTreeTransform<Derived>::TransformNullStmt(NullStmt *S) { 5140218893Sdim return SemaRef.Owned(S); 5141198092Srdivacky} 5142198092Srdivacky 5143198092Srdivackytemplate<typename Derived> 5144212904SdimStmtResult 5145198092SrdivackyTreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S) { 5146198092Srdivacky return getDerived().TransformCompoundStmt(S, false); 5147198092Srdivacky} 5148198092Srdivacky 5149198092Srdivackytemplate<typename Derived> 5150212904SdimStmtResult 5151198092SrdivackyTreeTransform<Derived>::TransformCompoundStmt(CompoundStmt *S, 5152198092Srdivacky bool IsStmtExpr) { 5153234353Sdim Sema::CompoundScopeRAII CompoundScope(getSema()); 5154234353Sdim 5155212904Sdim bool SubStmtInvalid = false; 5156198092Srdivacky bool SubStmtChanged = false; 5157243830Sdim SmallVector<Stmt*, 8> Statements; 5158198092Srdivacky for (CompoundStmt::body_iterator B = S->body_begin(), BEnd = S->body_end(); 5159198092Srdivacky B != BEnd; ++B) { 5160212904Sdim StmtResult Result = getDerived().TransformStmt(*B); 5161212904Sdim if (Result.isInvalid()) { 5162212904Sdim // Immediately fail if this was a DeclStmt, since it's very 5163212904Sdim // likely that this will cause problems for future statements. 5164212904Sdim if (isa<DeclStmt>(*B)) 5165212904Sdim return StmtError(); 5166198092Srdivacky 5167212904Sdim // Otherwise, just keep processing substatements and fail later. 5168212904Sdim SubStmtInvalid = true; 5169212904Sdim continue; 5170212904Sdim } 5171212904Sdim 5172198092Srdivacky SubStmtChanged = SubStmtChanged || Result.get() != *B; 5173198092Srdivacky Statements.push_back(Result.takeAs<Stmt>()); 5174198092Srdivacky } 5175198092Srdivacky 5176212904Sdim if (SubStmtInvalid) 5177212904Sdim return StmtError(); 5178212904Sdim 5179198092Srdivacky if (!getDerived().AlwaysRebuild() && 5180198092Srdivacky !SubStmtChanged) 5181218893Sdim return SemaRef.Owned(S); 5182198092Srdivacky 5183198092Srdivacky return getDerived().RebuildCompoundStmt(S->getLBracLoc(), 5184243830Sdim Statements, 5185198092Srdivacky S->getRBracLoc(), 5186198092Srdivacky IsStmtExpr); 5187198092Srdivacky} 5188198092Srdivacky 5189198092Srdivackytemplate<typename Derived> 5190212904SdimStmtResult 5191198092SrdivackyTreeTransform<Derived>::TransformCaseStmt(CaseStmt *S) { 5192212904Sdim ExprResult LHS, RHS; 5193199512Srdivacky { 5194234353Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, 5195234353Sdim Sema::ConstantEvaluated); 5196198092Srdivacky 5197199512Srdivacky // Transform the left-hand case value. 5198199512Srdivacky LHS = getDerived().TransformExpr(S->getLHS()); 5199234353Sdim LHS = SemaRef.ActOnConstantExpression(LHS); 5200199512Srdivacky if (LHS.isInvalid()) 5201212904Sdim return StmtError(); 5202198092Srdivacky 5203199512Srdivacky // Transform the right-hand case value (for the GNU case-range extension). 5204199512Srdivacky RHS = getDerived().TransformExpr(S->getRHS()); 5205234353Sdim RHS = SemaRef.ActOnConstantExpression(RHS); 5206199512Srdivacky if (RHS.isInvalid()) 5207212904Sdim return StmtError(); 5208199512Srdivacky } 5209198092Srdivacky 5210198092Srdivacky // Build the case statement. 5211198092Srdivacky // Case statements are always rebuilt so that they will attached to their 5212198092Srdivacky // transformed switch statement. 5213212904Sdim StmtResult Case = getDerived().RebuildCaseStmt(S->getCaseLoc(), 5214212904Sdim LHS.get(), 5215198092Srdivacky S->getEllipsisLoc(), 5216212904Sdim RHS.get(), 5217198092Srdivacky S->getColonLoc()); 5218198092Srdivacky if (Case.isInvalid()) 5219212904Sdim return StmtError(); 5220198092Srdivacky 5221198092Srdivacky // Transform the statement following the case 5222212904Sdim StmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 5223198092Srdivacky if (SubStmt.isInvalid()) 5224212904Sdim return StmtError(); 5225198092Srdivacky 5226198092Srdivacky // Attach the body to the case statement 5227212904Sdim return getDerived().RebuildCaseStmtBody(Case.get(), SubStmt.get()); 5228198092Srdivacky} 5229198092Srdivacky 5230198092Srdivackytemplate<typename Derived> 5231212904SdimStmtResult 5232198092SrdivackyTreeTransform<Derived>::TransformDefaultStmt(DefaultStmt *S) { 5233198092Srdivacky // Transform the statement following the default case 5234212904Sdim StmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 5235198092Srdivacky if (SubStmt.isInvalid()) 5236212904Sdim return StmtError(); 5237198092Srdivacky 5238198092Srdivacky // Default statements are always rebuilt 5239198092Srdivacky return getDerived().RebuildDefaultStmt(S->getDefaultLoc(), S->getColonLoc(), 5240212904Sdim SubStmt.get()); 5241198092Srdivacky} 5242198092Srdivacky 5243198092Srdivackytemplate<typename Derived> 5244212904SdimStmtResult 5245198092SrdivackyTreeTransform<Derived>::TransformLabelStmt(LabelStmt *S) { 5246212904Sdim StmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 5247198092Srdivacky if (SubStmt.isInvalid()) 5248212904Sdim return StmtError(); 5249198092Srdivacky 5250218893Sdim Decl *LD = getDerived().TransformDecl(S->getDecl()->getLocation(), 5251218893Sdim S->getDecl()); 5252218893Sdim if (!LD) 5253218893Sdim return StmtError(); 5254234982Sdim 5255234982Sdim 5256198092Srdivacky // FIXME: Pass the real colon location in. 5257218893Sdim return getDerived().RebuildLabelStmt(S->getIdentLoc(), 5258218893Sdim cast<LabelDecl>(LD), SourceLocation(), 5259212904Sdim SubStmt.get()); 5260198092Srdivacky} 5261198092Srdivacky 5262198092Srdivackytemplate<typename Derived> 5263212904SdimStmtResult 5264234982SdimTreeTransform<Derived>::TransformAttributedStmt(AttributedStmt *S) { 5265234982Sdim StmtResult SubStmt = getDerived().TransformStmt(S->getSubStmt()); 5266234982Sdim if (SubStmt.isInvalid()) 5267234982Sdim return StmtError(); 5268234982Sdim 5269234982Sdim // TODO: transform attributes 5270234982Sdim if (SubStmt.get() == S->getSubStmt() /* && attrs are the same */) 5271234982Sdim return S; 5272234982Sdim 5273234982Sdim return getDerived().RebuildAttributedStmt(S->getAttrLoc(), 5274234982Sdim S->getAttrs(), 5275234982Sdim SubStmt.get()); 5276234982Sdim} 5277234982Sdim 5278234982Sdimtemplate<typename Derived> 5279234982SdimStmtResult 5280198092SrdivackyTreeTransform<Derived>::TransformIfStmt(IfStmt *S) { 5281198092Srdivacky // Transform the condition 5282212904Sdim ExprResult Cond; 5283199990Srdivacky VarDecl *ConditionVar = 0; 5284199990Srdivacky if (S->getConditionVariable()) { 5285239462Sdim ConditionVar 5286199990Srdivacky = cast_or_null<VarDecl>( 5287204643Srdivacky getDerived().TransformDefinition( 5288204643Srdivacky S->getConditionVariable()->getLocation(), 5289204643Srdivacky S->getConditionVariable())); 5290199990Srdivacky if (!ConditionVar) 5291212904Sdim return StmtError(); 5292199990Srdivacky } else { 5293199990Srdivacky Cond = getDerived().TransformExpr(S->getCond()); 5294239462Sdim 5295199990Srdivacky if (Cond.isInvalid()) 5296212904Sdim return StmtError(); 5297239462Sdim 5298208600Srdivacky // Convert the condition to a boolean value. 5299208600Srdivacky if (S->getCond()) { 5300239462Sdim ExprResult CondE = getSema().ActOnBooleanCondition(0, S->getIfLoc(), 5301218893Sdim Cond.get()); 5302208600Srdivacky if (CondE.isInvalid()) 5303212904Sdim return StmtError(); 5304239462Sdim 5305212904Sdim Cond = CondE.get(); 5306208600Srdivacky } 5307199990Srdivacky } 5308239462Sdim 5309212904Sdim Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond.take())); 5310212904Sdim if (!S->getConditionVariable() && S->getCond() && !FullCond.get()) 5311212904Sdim return StmtError(); 5312239462Sdim 5313198092Srdivacky // Transform the "then" branch. 5314212904Sdim StmtResult Then = getDerived().TransformStmt(S->getThen()); 5315198092Srdivacky if (Then.isInvalid()) 5316212904Sdim return StmtError(); 5317198092Srdivacky 5318198092Srdivacky // Transform the "else" branch. 5319212904Sdim StmtResult Else = getDerived().TransformStmt(S->getElse()); 5320198092Srdivacky if (Else.isInvalid()) 5321212904Sdim return StmtError(); 5322198092Srdivacky 5323198092Srdivacky if (!getDerived().AlwaysRebuild() && 5324212904Sdim FullCond.get() == S->getCond() && 5325199990Srdivacky ConditionVar == S->getConditionVariable() && 5326198092Srdivacky Then.get() == S->getThen() && 5327198092Srdivacky Else.get() == S->getElse()) 5328218893Sdim return SemaRef.Owned(S); 5329198092Srdivacky 5330199990Srdivacky return getDerived().RebuildIfStmt(S->getIfLoc(), FullCond, ConditionVar, 5331212904Sdim Then.get(), 5332212904Sdim S->getElseLoc(), Else.get()); 5333198092Srdivacky} 5334198092Srdivacky 5335198092Srdivackytemplate<typename Derived> 5336212904SdimStmtResult 5337198092SrdivackyTreeTransform<Derived>::TransformSwitchStmt(SwitchStmt *S) { 5338198092Srdivacky // Transform the condition. 5339212904Sdim ExprResult Cond; 5340199990Srdivacky VarDecl *ConditionVar = 0; 5341199990Srdivacky if (S->getConditionVariable()) { 5342239462Sdim ConditionVar 5343199990Srdivacky = cast_or_null<VarDecl>( 5344204643Srdivacky getDerived().TransformDefinition( 5345204643Srdivacky S->getConditionVariable()->getLocation(), 5346204643Srdivacky S->getConditionVariable())); 5347199990Srdivacky if (!ConditionVar) 5348212904Sdim return StmtError(); 5349199990Srdivacky } else { 5350199990Srdivacky Cond = getDerived().TransformExpr(S->getCond()); 5351239462Sdim 5352199990Srdivacky if (Cond.isInvalid()) 5353212904Sdim return StmtError(); 5354199990Srdivacky } 5355198092Srdivacky 5356198092Srdivacky // Rebuild the switch statement. 5357212904Sdim StmtResult Switch 5358212904Sdim = getDerived().RebuildSwitchStmtStart(S->getSwitchLoc(), Cond.get(), 5359208600Srdivacky ConditionVar); 5360198092Srdivacky if (Switch.isInvalid()) 5361212904Sdim return StmtError(); 5362198092Srdivacky 5363198092Srdivacky // Transform the body of the switch statement. 5364212904Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5365198092Srdivacky if (Body.isInvalid()) 5366212904Sdim return StmtError(); 5367198092Srdivacky 5368198092Srdivacky // Complete the switch statement. 5369212904Sdim return getDerived().RebuildSwitchStmtBody(S->getSwitchLoc(), Switch.get(), 5370212904Sdim Body.get()); 5371198092Srdivacky} 5372198092Srdivacky 5373198092Srdivackytemplate<typename Derived> 5374212904SdimStmtResult 5375198092SrdivackyTreeTransform<Derived>::TransformWhileStmt(WhileStmt *S) { 5376198092Srdivacky // Transform the condition 5377212904Sdim ExprResult Cond; 5378199990Srdivacky VarDecl *ConditionVar = 0; 5379199990Srdivacky if (S->getConditionVariable()) { 5380239462Sdim ConditionVar 5381199990Srdivacky = cast_or_null<VarDecl>( 5382204643Srdivacky getDerived().TransformDefinition( 5383204643Srdivacky S->getConditionVariable()->getLocation(), 5384204643Srdivacky S->getConditionVariable())); 5385199990Srdivacky if (!ConditionVar) 5386212904Sdim return StmtError(); 5387199990Srdivacky } else { 5388199990Srdivacky Cond = getDerived().TransformExpr(S->getCond()); 5389239462Sdim 5390199990Srdivacky if (Cond.isInvalid()) 5391212904Sdim return StmtError(); 5392208600Srdivacky 5393208600Srdivacky if (S->getCond()) { 5394208600Srdivacky // Convert the condition to a boolean value. 5395239462Sdim ExprResult CondE = getSema().ActOnBooleanCondition(0, S->getWhileLoc(), 5396218893Sdim Cond.get()); 5397208600Srdivacky if (CondE.isInvalid()) 5398212904Sdim return StmtError(); 5399212904Sdim Cond = CondE; 5400208600Srdivacky } 5401199990Srdivacky } 5402198092Srdivacky 5403212904Sdim Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond.take())); 5404212904Sdim if (!S->getConditionVariable() && S->getCond() && !FullCond.get()) 5405212904Sdim return StmtError(); 5406198092Srdivacky 5407198092Srdivacky // Transform the body 5408212904Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5409198092Srdivacky if (Body.isInvalid()) 5410212904Sdim return StmtError(); 5411198092Srdivacky 5412198092Srdivacky if (!getDerived().AlwaysRebuild() && 5413212904Sdim FullCond.get() == S->getCond() && 5414199990Srdivacky ConditionVar == S->getConditionVariable() && 5415198092Srdivacky Body.get() == S->getBody()) 5416212904Sdim return Owned(S); 5417198092Srdivacky 5418208600Srdivacky return getDerived().RebuildWhileStmt(S->getWhileLoc(), FullCond, 5419212904Sdim ConditionVar, Body.get()); 5420198092Srdivacky} 5421198092Srdivacky 5422198092Srdivackytemplate<typename Derived> 5423212904SdimStmtResult 5424198092SrdivackyTreeTransform<Derived>::TransformDoStmt(DoStmt *S) { 5425198092Srdivacky // Transform the body 5426212904Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5427198092Srdivacky if (Body.isInvalid()) 5428212904Sdim return StmtError(); 5429198092Srdivacky 5430208600Srdivacky // Transform the condition 5431212904Sdim ExprResult Cond = getDerived().TransformExpr(S->getCond()); 5432208600Srdivacky if (Cond.isInvalid()) 5433212904Sdim return StmtError(); 5434239462Sdim 5435198092Srdivacky if (!getDerived().AlwaysRebuild() && 5436198092Srdivacky Cond.get() == S->getCond() && 5437198092Srdivacky Body.get() == S->getBody()) 5438218893Sdim return SemaRef.Owned(S); 5439198092Srdivacky 5440212904Sdim return getDerived().RebuildDoStmt(S->getDoLoc(), Body.get(), S->getWhileLoc(), 5441212904Sdim /*FIXME:*/S->getWhileLoc(), Cond.get(), 5442198092Srdivacky S->getRParenLoc()); 5443198092Srdivacky} 5444198092Srdivacky 5445198092Srdivackytemplate<typename Derived> 5446212904SdimStmtResult 5447198092SrdivackyTreeTransform<Derived>::TransformForStmt(ForStmt *S) { 5448198092Srdivacky // Transform the initialization statement 5449212904Sdim StmtResult Init = getDerived().TransformStmt(S->getInit()); 5450198092Srdivacky if (Init.isInvalid()) 5451212904Sdim return StmtError(); 5452198092Srdivacky 5453198092Srdivacky // Transform the condition 5454212904Sdim ExprResult Cond; 5455199990Srdivacky VarDecl *ConditionVar = 0; 5456199990Srdivacky if (S->getConditionVariable()) { 5457239462Sdim ConditionVar 5458199990Srdivacky = cast_or_null<VarDecl>( 5459204643Srdivacky getDerived().TransformDefinition( 5460204643Srdivacky S->getConditionVariable()->getLocation(), 5461204643Srdivacky S->getConditionVariable())); 5462199990Srdivacky if (!ConditionVar) 5463212904Sdim return StmtError(); 5464199990Srdivacky } else { 5465199990Srdivacky Cond = getDerived().TransformExpr(S->getCond()); 5466239462Sdim 5467199990Srdivacky if (Cond.isInvalid()) 5468212904Sdim return StmtError(); 5469208600Srdivacky 5470208600Srdivacky if (S->getCond()) { 5471208600Srdivacky // Convert the condition to a boolean value. 5472239462Sdim ExprResult CondE = getSema().ActOnBooleanCondition(0, S->getForLoc(), 5473218893Sdim Cond.get()); 5474208600Srdivacky if (CondE.isInvalid()) 5475212904Sdim return StmtError(); 5476208600Srdivacky 5477212904Sdim Cond = CondE.get(); 5478208600Srdivacky } 5479199990Srdivacky } 5480198092Srdivacky 5481239462Sdim Sema::FullExprArg FullCond(getSema().MakeFullExpr(Cond.take())); 5482212904Sdim if (!S->getConditionVariable() && S->getCond() && !FullCond.get()) 5483212904Sdim return StmtError(); 5484208600Srdivacky 5485198092Srdivacky // Transform the increment 5486212904Sdim ExprResult Inc = getDerived().TransformExpr(S->getInc()); 5487198092Srdivacky if (Inc.isInvalid()) 5488212904Sdim return StmtError(); 5489198092Srdivacky 5490249423Sdim Sema::FullExprArg FullInc(getSema().MakeFullDiscardedValueExpr(Inc.get())); 5491212904Sdim if (S->getInc() && !FullInc.get()) 5492212904Sdim return StmtError(); 5493208600Srdivacky 5494198092Srdivacky // Transform the body 5495212904Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5496198092Srdivacky if (Body.isInvalid()) 5497212904Sdim return StmtError(); 5498198092Srdivacky 5499198092Srdivacky if (!getDerived().AlwaysRebuild() && 5500198092Srdivacky Init.get() == S->getInit() && 5501212904Sdim FullCond.get() == S->getCond() && 5502198092Srdivacky Inc.get() == S->getInc() && 5503198092Srdivacky Body.get() == S->getBody()) 5504218893Sdim return SemaRef.Owned(S); 5505198092Srdivacky 5506198092Srdivacky return getDerived().RebuildForStmt(S->getForLoc(), S->getLParenLoc(), 5507212904Sdim Init.get(), FullCond, ConditionVar, 5508212904Sdim FullInc, S->getRParenLoc(), Body.get()); 5509198092Srdivacky} 5510198092Srdivacky 5511198092Srdivackytemplate<typename Derived> 5512212904SdimStmtResult 5513198092SrdivackyTreeTransform<Derived>::TransformGotoStmt(GotoStmt *S) { 5514218893Sdim Decl *LD = getDerived().TransformDecl(S->getLabel()->getLocation(), 5515218893Sdim S->getLabel()); 5516218893Sdim if (!LD) 5517218893Sdim return StmtError(); 5518239462Sdim 5519198092Srdivacky // Goto statements must always be rebuilt, to resolve the label. 5520198092Srdivacky return getDerived().RebuildGotoStmt(S->getGotoLoc(), S->getLabelLoc(), 5521218893Sdim cast<LabelDecl>(LD)); 5522198092Srdivacky} 5523198092Srdivacky 5524198092Srdivackytemplate<typename Derived> 5525212904SdimStmtResult 5526198092SrdivackyTreeTransform<Derived>::TransformIndirectGotoStmt(IndirectGotoStmt *S) { 5527212904Sdim ExprResult Target = getDerived().TransformExpr(S->getTarget()); 5528198092Srdivacky if (Target.isInvalid()) 5529212904Sdim return StmtError(); 5530234353Sdim Target = SemaRef.MaybeCreateExprWithCleanups(Target.take()); 5531198092Srdivacky 5532198092Srdivacky if (!getDerived().AlwaysRebuild() && 5533198092Srdivacky Target.get() == S->getTarget()) 5534218893Sdim return SemaRef.Owned(S); 5535198092Srdivacky 5536198092Srdivacky return getDerived().RebuildIndirectGotoStmt(S->getGotoLoc(), S->getStarLoc(), 5537212904Sdim Target.get()); 5538198092Srdivacky} 5539198092Srdivacky 5540198092Srdivackytemplate<typename Derived> 5541212904SdimStmtResult 5542198092SrdivackyTreeTransform<Derived>::TransformContinueStmt(ContinueStmt *S) { 5543218893Sdim return SemaRef.Owned(S); 5544198092Srdivacky} 5545198092Srdivacky 5546198092Srdivackytemplate<typename Derived> 5547212904SdimStmtResult 5548198092SrdivackyTreeTransform<Derived>::TransformBreakStmt(BreakStmt *S) { 5549218893Sdim return SemaRef.Owned(S); 5550198092Srdivacky} 5551198092Srdivacky 5552198092Srdivackytemplate<typename Derived> 5553212904SdimStmtResult 5554198092SrdivackyTreeTransform<Derived>::TransformReturnStmt(ReturnStmt *S) { 5555212904Sdim ExprResult Result = getDerived().TransformExpr(S->getRetValue()); 5556198092Srdivacky if (Result.isInvalid()) 5557212904Sdim return StmtError(); 5558198092Srdivacky 5559198092Srdivacky // FIXME: We always rebuild the return statement because there is no way 5560198092Srdivacky // to tell whether the return type of the function has changed. 5561212904Sdim return getDerived().RebuildReturnStmt(S->getReturnLoc(), Result.get()); 5562198092Srdivacky} 5563198092Srdivacky 5564198092Srdivackytemplate<typename Derived> 5565212904SdimStmtResult 5566198092SrdivackyTreeTransform<Derived>::TransformDeclStmt(DeclStmt *S) { 5567198092Srdivacky bool DeclChanged = false; 5568226633Sdim SmallVector<Decl *, 4> Decls; 5569198092Srdivacky for (DeclStmt::decl_iterator D = S->decl_begin(), DEnd = S->decl_end(); 5570198092Srdivacky D != DEnd; ++D) { 5571204643Srdivacky Decl *Transformed = getDerived().TransformDefinition((*D)->getLocation(), 5572204643Srdivacky *D); 5573198092Srdivacky if (!Transformed) 5574212904Sdim return StmtError(); 5575198092Srdivacky 5576198092Srdivacky if (Transformed != *D) 5577198092Srdivacky DeclChanged = true; 5578198092Srdivacky 5579198092Srdivacky Decls.push_back(Transformed); 5580198092Srdivacky } 5581198092Srdivacky 5582198092Srdivacky if (!getDerived().AlwaysRebuild() && !DeclChanged) 5583218893Sdim return SemaRef.Owned(S); 5584198092Srdivacky 5585198092Srdivacky return getDerived().RebuildDeclStmt(Decls.data(), Decls.size(), 5586198092Srdivacky S->getStartLoc(), S->getEndLoc()); 5587198092Srdivacky} 5588198092Srdivacky 5589198092Srdivackytemplate<typename Derived> 5590212904SdimStmtResult 5591243830SdimTreeTransform<Derived>::TransformGCCAsmStmt(GCCAsmStmt *S) { 5592239462Sdim 5593243830Sdim SmallVector<Expr*, 8> Constraints; 5594243830Sdim SmallVector<Expr*, 8> Exprs; 5595226633Sdim SmallVector<IdentifierInfo *, 4> Names; 5596203955Srdivacky 5597212904Sdim ExprResult AsmString; 5598243830Sdim SmallVector<Expr*, 8> Clobbers; 5599203955Srdivacky 5600203955Srdivacky bool ExprsChanged = false; 5601239462Sdim 5602203955Srdivacky // Go through the outputs. 5603203955Srdivacky for (unsigned I = 0, E = S->getNumOutputs(); I != E; ++I) { 5604203955Srdivacky Names.push_back(S->getOutputIdentifier(I)); 5605239462Sdim 5606203955Srdivacky // No need to transform the constraint literal. 5607218893Sdim Constraints.push_back(S->getOutputConstraintLiteral(I)); 5608239462Sdim 5609203955Srdivacky // Transform the output expr. 5610203955Srdivacky Expr *OutputExpr = S->getOutputExpr(I); 5611212904Sdim ExprResult Result = getDerived().TransformExpr(OutputExpr); 5612203955Srdivacky if (Result.isInvalid()) 5613212904Sdim return StmtError(); 5614239462Sdim 5615203955Srdivacky ExprsChanged |= Result.get() != OutputExpr; 5616239462Sdim 5617212904Sdim Exprs.push_back(Result.get()); 5618203955Srdivacky } 5619239462Sdim 5620203955Srdivacky // Go through the inputs. 5621203955Srdivacky for (unsigned I = 0, E = S->getNumInputs(); I != E; ++I) { 5622203955Srdivacky Names.push_back(S->getInputIdentifier(I)); 5623239462Sdim 5624203955Srdivacky // No need to transform the constraint literal. 5625218893Sdim Constraints.push_back(S->getInputConstraintLiteral(I)); 5626239462Sdim 5627203955Srdivacky // Transform the input expr. 5628203955Srdivacky Expr *InputExpr = S->getInputExpr(I); 5629212904Sdim ExprResult Result = getDerived().TransformExpr(InputExpr); 5630203955Srdivacky if (Result.isInvalid()) 5631212904Sdim return StmtError(); 5632239462Sdim 5633203955Srdivacky ExprsChanged |= Result.get() != InputExpr; 5634239462Sdim 5635212904Sdim Exprs.push_back(Result.get()); 5636203955Srdivacky } 5637239462Sdim 5638203955Srdivacky if (!getDerived().AlwaysRebuild() && !ExprsChanged) 5639218893Sdim return SemaRef.Owned(S); 5640203955Srdivacky 5641203955Srdivacky // Go through the clobbers. 5642203955Srdivacky for (unsigned I = 0, E = S->getNumClobbers(); I != E; ++I) 5643243830Sdim Clobbers.push_back(S->getClobberStringLiteral(I)); 5644203955Srdivacky 5645203955Srdivacky // No need to transform the asm string literal. 5646203955Srdivacky AsmString = SemaRef.Owned(S->getAsmString()); 5647243830Sdim return getDerived().RebuildGCCAsmStmt(S->getAsmLoc(), S->isSimple(), 5648243830Sdim S->isVolatile(), S->getNumOutputs(), 5649243830Sdim S->getNumInputs(), Names.data(), 5650243830Sdim Constraints, Exprs, AsmString.get(), 5651243830Sdim Clobbers, S->getRParenLoc()); 5652198092Srdivacky} 5653198092Srdivacky 5654239462Sdimtemplate<typename Derived> 5655239462SdimStmtResult 5656239462SdimTreeTransform<Derived>::TransformMSAsmStmt(MSAsmStmt *S) { 5657239462Sdim ArrayRef<Token> AsmToks = 5658239462Sdim llvm::makeArrayRef(S->getAsmToks(), S->getNumAsmToks()); 5659198092Srdivacky 5660251662Sdim bool HadError = false, HadChange = false; 5661251662Sdim 5662251662Sdim ArrayRef<Expr*> SrcExprs = S->getAllExprs(); 5663251662Sdim SmallVector<Expr*, 8> TransformedExprs; 5664251662Sdim TransformedExprs.reserve(SrcExprs.size()); 5665251662Sdim for (unsigned i = 0, e = SrcExprs.size(); i != e; ++i) { 5666251662Sdim ExprResult Result = getDerived().TransformExpr(SrcExprs[i]); 5667251662Sdim if (!Result.isUsable()) { 5668251662Sdim HadError = true; 5669251662Sdim } else { 5670251662Sdim HadChange |= (Result.get() != SrcExprs[i]); 5671251662Sdim TransformedExprs.push_back(Result.take()); 5672251662Sdim } 5673251662Sdim } 5674251662Sdim 5675251662Sdim if (HadError) return StmtError(); 5676251662Sdim if (!HadChange && !getDerived().AlwaysRebuild()) 5677251662Sdim return Owned(S); 5678251662Sdim 5679239462Sdim return getDerived().RebuildMSAsmStmt(S->getAsmLoc(), S->getLBraceLoc(), 5680251662Sdim AsmToks, S->getAsmString(), 5681251662Sdim S->getNumOutputs(), S->getNumInputs(), 5682251662Sdim S->getAllConstraints(), S->getClobbers(), 5683251662Sdim TransformedExprs, S->getEndLoc()); 5684239462Sdim} 5685239462Sdim 5686198092Srdivackytemplate<typename Derived> 5687212904SdimStmtResult 5688198092SrdivackyTreeTransform<Derived>::TransformObjCAtTryStmt(ObjCAtTryStmt *S) { 5689207619Srdivacky // Transform the body of the @try. 5690212904Sdim StmtResult TryBody = getDerived().TransformStmt(S->getTryBody()); 5691207619Srdivacky if (TryBody.isInvalid()) 5692212904Sdim return StmtError(); 5693239462Sdim 5694207619Srdivacky // Transform the @catch statements (if present). 5695207619Srdivacky bool AnyCatchChanged = false; 5696243830Sdim SmallVector<Stmt*, 8> CatchStmts; 5697207619Srdivacky for (unsigned I = 0, N = S->getNumCatchStmts(); I != N; ++I) { 5698212904Sdim StmtResult Catch = getDerived().TransformStmt(S->getCatchStmt(I)); 5699207619Srdivacky if (Catch.isInvalid()) 5700212904Sdim return StmtError(); 5701207619Srdivacky if (Catch.get() != S->getCatchStmt(I)) 5702207619Srdivacky AnyCatchChanged = true; 5703207619Srdivacky CatchStmts.push_back(Catch.release()); 5704207619Srdivacky } 5705239462Sdim 5706207619Srdivacky // Transform the @finally statement (if present). 5707212904Sdim StmtResult Finally; 5708207619Srdivacky if (S->getFinallyStmt()) { 5709207619Srdivacky Finally = getDerived().TransformStmt(S->getFinallyStmt()); 5710207619Srdivacky if (Finally.isInvalid()) 5711212904Sdim return StmtError(); 5712207619Srdivacky } 5713207619Srdivacky 5714207619Srdivacky // If nothing changed, just retain this statement. 5715207619Srdivacky if (!getDerived().AlwaysRebuild() && 5716207619Srdivacky TryBody.get() == S->getTryBody() && 5717207619Srdivacky !AnyCatchChanged && 5718207619Srdivacky Finally.get() == S->getFinallyStmt()) 5719218893Sdim return SemaRef.Owned(S); 5720239462Sdim 5721207619Srdivacky // Build a new statement. 5722212904Sdim return getDerived().RebuildObjCAtTryStmt(S->getAtTryLoc(), TryBody.get(), 5723243830Sdim CatchStmts, Finally.get()); 5724198092Srdivacky} 5725198092Srdivacky 5726198092Srdivackytemplate<typename Derived> 5727212904SdimStmtResult 5728198092SrdivackyTreeTransform<Derived>::TransformObjCAtCatchStmt(ObjCAtCatchStmt *S) { 5729207619Srdivacky // Transform the @catch parameter, if there is one. 5730207619Srdivacky VarDecl *Var = 0; 5731207619Srdivacky if (VarDecl *FromVar = S->getCatchParamDecl()) { 5732207619Srdivacky TypeSourceInfo *TSInfo = 0; 5733207619Srdivacky if (FromVar->getTypeSourceInfo()) { 5734207619Srdivacky TSInfo = getDerived().TransformType(FromVar->getTypeSourceInfo()); 5735207619Srdivacky if (!TSInfo) 5736212904Sdim return StmtError(); 5737207619Srdivacky } 5738239462Sdim 5739207619Srdivacky QualType T; 5740207619Srdivacky if (TSInfo) 5741207619Srdivacky T = TSInfo->getType(); 5742207619Srdivacky else { 5743207619Srdivacky T = getDerived().TransformType(FromVar->getType()); 5744207619Srdivacky if (T.isNull()) 5745239462Sdim return StmtError(); 5746207619Srdivacky } 5747239462Sdim 5748207619Srdivacky Var = getDerived().RebuildObjCExceptionDecl(FromVar, TSInfo, T); 5749207619Srdivacky if (!Var) 5750212904Sdim return StmtError(); 5751207619Srdivacky } 5752239462Sdim 5753212904Sdim StmtResult Body = getDerived().TransformStmt(S->getCatchBody()); 5754207619Srdivacky if (Body.isInvalid()) 5755212904Sdim return StmtError(); 5756239462Sdim 5757239462Sdim return getDerived().RebuildObjCAtCatchStmt(S->getAtCatchLoc(), 5758207619Srdivacky S->getRParenLoc(), 5759212904Sdim Var, Body.get()); 5760198092Srdivacky} 5761198092Srdivacky 5762198092Srdivackytemplate<typename Derived> 5763212904SdimStmtResult 5764198092SrdivackyTreeTransform<Derived>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt *S) { 5765207619Srdivacky // Transform the body. 5766212904Sdim StmtResult Body = getDerived().TransformStmt(S->getFinallyBody()); 5767207619Srdivacky if (Body.isInvalid()) 5768212904Sdim return StmtError(); 5769239462Sdim 5770207619Srdivacky // If nothing changed, just retain this statement. 5771207619Srdivacky if (!getDerived().AlwaysRebuild() && 5772207619Srdivacky Body.get() == S->getFinallyBody()) 5773218893Sdim return SemaRef.Owned(S); 5774207619Srdivacky 5775207619Srdivacky // Build a new statement. 5776207619Srdivacky return getDerived().RebuildObjCAtFinallyStmt(S->getAtFinallyLoc(), 5777212904Sdim Body.get()); 5778198092Srdivacky} 5779198092Srdivacky 5780198092Srdivackytemplate<typename Derived> 5781212904SdimStmtResult 5782198092SrdivackyTreeTransform<Derived>::TransformObjCAtThrowStmt(ObjCAtThrowStmt *S) { 5783212904Sdim ExprResult Operand; 5784207619Srdivacky if (S->getThrowExpr()) { 5785207619Srdivacky Operand = getDerived().TransformExpr(S->getThrowExpr()); 5786207619Srdivacky if (Operand.isInvalid()) 5787212904Sdim return StmtError(); 5788207619Srdivacky } 5789239462Sdim 5790207619Srdivacky if (!getDerived().AlwaysRebuild() && 5791207619Srdivacky Operand.get() == S->getThrowExpr()) 5792218893Sdim return getSema().Owned(S); 5793239462Sdim 5794212904Sdim return getDerived().RebuildObjCAtThrowStmt(S->getThrowLoc(), Operand.get()); 5795198092Srdivacky} 5796198092Srdivacky 5797198092Srdivackytemplate<typename Derived> 5798212904SdimStmtResult 5799198092SrdivackyTreeTransform<Derived>::TransformObjCAtSynchronizedStmt( 5800198092Srdivacky ObjCAtSynchronizedStmt *S) { 5801207619Srdivacky // Transform the object we are locking. 5802212904Sdim ExprResult Object = getDerived().TransformExpr(S->getSynchExpr()); 5803207619Srdivacky if (Object.isInvalid()) 5804212904Sdim return StmtError(); 5805226633Sdim Object = 5806226633Sdim getDerived().RebuildObjCAtSynchronizedOperand(S->getAtSynchronizedLoc(), 5807226633Sdim Object.get()); 5808226633Sdim if (Object.isInvalid()) 5809226633Sdim return StmtError(); 5810239462Sdim 5811207619Srdivacky // Transform the body. 5812212904Sdim StmtResult Body = getDerived().TransformStmt(S->getSynchBody()); 5813207619Srdivacky if (Body.isInvalid()) 5814212904Sdim return StmtError(); 5815239462Sdim 5816207619Srdivacky // If nothing change, just retain the current statement. 5817207619Srdivacky if (!getDerived().AlwaysRebuild() && 5818207619Srdivacky Object.get() == S->getSynchExpr() && 5819207619Srdivacky Body.get() == S->getSynchBody()) 5820218893Sdim return SemaRef.Owned(S); 5821207619Srdivacky 5822207619Srdivacky // Build a new statement. 5823207619Srdivacky return getDerived().RebuildObjCAtSynchronizedStmt(S->getAtSynchronizedLoc(), 5824212904Sdim Object.get(), Body.get()); 5825198092Srdivacky} 5826198092Srdivacky 5827198092Srdivackytemplate<typename Derived> 5828212904SdimStmtResult 5829224145SdimTreeTransform<Derived>::TransformObjCAutoreleasePoolStmt( 5830224145Sdim ObjCAutoreleasePoolStmt *S) { 5831224145Sdim // Transform the body. 5832224145Sdim StmtResult Body = getDerived().TransformStmt(S->getSubStmt()); 5833224145Sdim if (Body.isInvalid()) 5834224145Sdim return StmtError(); 5835239462Sdim 5836224145Sdim // If nothing changed, just retain this statement. 5837224145Sdim if (!getDerived().AlwaysRebuild() && 5838224145Sdim Body.get() == S->getSubStmt()) 5839224145Sdim return SemaRef.Owned(S); 5840224145Sdim 5841224145Sdim // Build a new statement. 5842224145Sdim return getDerived().RebuildObjCAutoreleasePoolStmt( 5843224145Sdim S->getAtLoc(), Body.get()); 5844224145Sdim} 5845224145Sdim 5846224145Sdimtemplate<typename Derived> 5847224145SdimStmtResult 5848198092SrdivackyTreeTransform<Derived>::TransformObjCForCollectionStmt( 5849198092Srdivacky ObjCForCollectionStmt *S) { 5850207619Srdivacky // Transform the element statement. 5851212904Sdim StmtResult Element = getDerived().TransformStmt(S->getElement()); 5852207619Srdivacky if (Element.isInvalid()) 5853212904Sdim return StmtError(); 5854239462Sdim 5855207619Srdivacky // Transform the collection expression. 5856212904Sdim ExprResult Collection = getDerived().TransformExpr(S->getCollection()); 5857207619Srdivacky if (Collection.isInvalid()) 5858212904Sdim return StmtError(); 5859239462Sdim 5860207619Srdivacky // Transform the body. 5861212904Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5862207619Srdivacky if (Body.isInvalid()) 5863212904Sdim return StmtError(); 5864239462Sdim 5865207619Srdivacky // If nothing changed, just retain this statement. 5866207619Srdivacky if (!getDerived().AlwaysRebuild() && 5867207619Srdivacky Element.get() == S->getElement() && 5868207619Srdivacky Collection.get() == S->getCollection() && 5869207619Srdivacky Body.get() == S->getBody()) 5870218893Sdim return SemaRef.Owned(S); 5871239462Sdim 5872207619Srdivacky // Build a new statement. 5873207619Srdivacky return getDerived().RebuildObjCForCollectionStmt(S->getForLoc(), 5874212904Sdim Element.get(), 5875212904Sdim Collection.get(), 5876207619Srdivacky S->getRParenLoc(), 5877212904Sdim Body.get()); 5878198092Srdivacky} 5879198092Srdivacky 5880198092Srdivacky 5881198092Srdivackytemplate<typename Derived> 5882212904SdimStmtResult 5883198092SrdivackyTreeTransform<Derived>::TransformCXXCatchStmt(CXXCatchStmt *S) { 5884198092Srdivacky // Transform the exception declaration, if any. 5885198092Srdivacky VarDecl *Var = 0; 5886198092Srdivacky if (S->getExceptionDecl()) { 5887198092Srdivacky VarDecl *ExceptionDecl = S->getExceptionDecl(); 5888218893Sdim TypeSourceInfo *T = getDerived().TransformType( 5889218893Sdim ExceptionDecl->getTypeSourceInfo()); 5890218893Sdim if (!T) 5891212904Sdim return StmtError(); 5892198092Srdivacky 5893218893Sdim Var = getDerived().RebuildExceptionDecl(ExceptionDecl, T, 5894221345Sdim ExceptionDecl->getInnerLocStart(), 5895221345Sdim ExceptionDecl->getLocation(), 5896221345Sdim ExceptionDecl->getIdentifier()); 5897212904Sdim if (!Var || Var->isInvalidDecl()) 5898212904Sdim return StmtError(); 5899198092Srdivacky } 5900198092Srdivacky 5901198092Srdivacky // Transform the actual exception handler. 5902212904Sdim StmtResult Handler = getDerived().TransformStmt(S->getHandlerBlock()); 5903212904Sdim if (Handler.isInvalid()) 5904212904Sdim return StmtError(); 5905198092Srdivacky 5906198092Srdivacky if (!getDerived().AlwaysRebuild() && 5907198092Srdivacky !Var && 5908198092Srdivacky Handler.get() == S->getHandlerBlock()) 5909218893Sdim return SemaRef.Owned(S); 5910198092Srdivacky 5911198092Srdivacky return getDerived().RebuildCXXCatchStmt(S->getCatchLoc(), 5912198092Srdivacky Var, 5913212904Sdim Handler.get()); 5914198092Srdivacky} 5915198092Srdivacky 5916198092Srdivackytemplate<typename Derived> 5917212904SdimStmtResult 5918198092SrdivackyTreeTransform<Derived>::TransformCXXTryStmt(CXXTryStmt *S) { 5919198092Srdivacky // Transform the try block itself. 5920212904Sdim StmtResult TryBlock 5921198092Srdivacky = getDerived().TransformCompoundStmt(S->getTryBlock()); 5922198092Srdivacky if (TryBlock.isInvalid()) 5923212904Sdim return StmtError(); 5924198092Srdivacky 5925198092Srdivacky // Transform the handlers. 5926198092Srdivacky bool HandlerChanged = false; 5927243830Sdim SmallVector<Stmt*, 8> Handlers; 5928198092Srdivacky for (unsigned I = 0, N = S->getNumHandlers(); I != N; ++I) { 5929212904Sdim StmtResult Handler 5930198092Srdivacky = getDerived().TransformCXXCatchStmt(S->getHandler(I)); 5931198092Srdivacky if (Handler.isInvalid()) 5932212904Sdim return StmtError(); 5933198092Srdivacky 5934198092Srdivacky HandlerChanged = HandlerChanged || Handler.get() != S->getHandler(I); 5935198092Srdivacky Handlers.push_back(Handler.takeAs<Stmt>()); 5936198092Srdivacky } 5937198092Srdivacky 5938198092Srdivacky if (!getDerived().AlwaysRebuild() && 5939198092Srdivacky TryBlock.get() == S->getTryBlock() && 5940198092Srdivacky !HandlerChanged) 5941218893Sdim return SemaRef.Owned(S); 5942198092Srdivacky 5943212904Sdim return getDerived().RebuildCXXTryStmt(S->getTryLoc(), TryBlock.get(), 5944243830Sdim Handlers); 5945198092Srdivacky} 5946198092Srdivacky 5947221345Sdimtemplate<typename Derived> 5948221345SdimStmtResult 5949221345SdimTreeTransform<Derived>::TransformCXXForRangeStmt(CXXForRangeStmt *S) { 5950221345Sdim StmtResult Range = getDerived().TransformStmt(S->getRangeStmt()); 5951221345Sdim if (Range.isInvalid()) 5952221345Sdim return StmtError(); 5953221345Sdim 5954221345Sdim StmtResult BeginEnd = getDerived().TransformStmt(S->getBeginEndStmt()); 5955221345Sdim if (BeginEnd.isInvalid()) 5956221345Sdim return StmtError(); 5957221345Sdim 5958221345Sdim ExprResult Cond = getDerived().TransformExpr(S->getCond()); 5959221345Sdim if (Cond.isInvalid()) 5960221345Sdim return StmtError(); 5961234353Sdim if (Cond.get()) 5962234353Sdim Cond = SemaRef.CheckBooleanCondition(Cond.take(), S->getColonLoc()); 5963234353Sdim if (Cond.isInvalid()) 5964234353Sdim return StmtError(); 5965234353Sdim if (Cond.get()) 5966234353Sdim Cond = SemaRef.MaybeCreateExprWithCleanups(Cond.take()); 5967221345Sdim 5968221345Sdim ExprResult Inc = getDerived().TransformExpr(S->getInc()); 5969221345Sdim if (Inc.isInvalid()) 5970221345Sdim return StmtError(); 5971234353Sdim if (Inc.get()) 5972234353Sdim Inc = SemaRef.MaybeCreateExprWithCleanups(Inc.take()); 5973221345Sdim 5974221345Sdim StmtResult LoopVar = getDerived().TransformStmt(S->getLoopVarStmt()); 5975221345Sdim if (LoopVar.isInvalid()) 5976221345Sdim return StmtError(); 5977221345Sdim 5978221345Sdim StmtResult NewStmt = S; 5979221345Sdim if (getDerived().AlwaysRebuild() || 5980221345Sdim Range.get() != S->getRangeStmt() || 5981221345Sdim BeginEnd.get() != S->getBeginEndStmt() || 5982221345Sdim Cond.get() != S->getCond() || 5983221345Sdim Inc.get() != S->getInc() || 5984251662Sdim LoopVar.get() != S->getLoopVarStmt()) { 5985221345Sdim NewStmt = getDerived().RebuildCXXForRangeStmt(S->getForLoc(), 5986221345Sdim S->getColonLoc(), Range.get(), 5987221345Sdim BeginEnd.get(), Cond.get(), 5988221345Sdim Inc.get(), LoopVar.get(), 5989221345Sdim S->getRParenLoc()); 5990251662Sdim if (NewStmt.isInvalid()) 5991251662Sdim return StmtError(); 5992251662Sdim } 5993221345Sdim 5994221345Sdim StmtResult Body = getDerived().TransformStmt(S->getBody()); 5995221345Sdim if (Body.isInvalid()) 5996221345Sdim return StmtError(); 5997221345Sdim 5998221345Sdim // Body has changed but we didn't rebuild the for-range statement. Rebuild 5999221345Sdim // it now so we have a new statement to attach the body to. 6000251662Sdim if (Body.get() != S->getBody() && NewStmt.get() == S) { 6001221345Sdim NewStmt = getDerived().RebuildCXXForRangeStmt(S->getForLoc(), 6002221345Sdim S->getColonLoc(), Range.get(), 6003221345Sdim BeginEnd.get(), Cond.get(), 6004221345Sdim Inc.get(), LoopVar.get(), 6005221345Sdim S->getRParenLoc()); 6006251662Sdim if (NewStmt.isInvalid()) 6007251662Sdim return StmtError(); 6008251662Sdim } 6009221345Sdim 6010221345Sdim if (NewStmt.get() == S) 6011221345Sdim return SemaRef.Owned(S); 6012221345Sdim 6013221345Sdim return FinishCXXForRangeStmt(NewStmt.get(), Body.get()); 6014221345Sdim} 6015221345Sdim 6016221345Sdimtemplate<typename Derived> 6017221345SdimStmtResult 6018234353SdimTreeTransform<Derived>::TransformMSDependentExistsStmt( 6019234353Sdim MSDependentExistsStmt *S) { 6020234353Sdim // Transform the nested-name-specifier, if any. 6021234353Sdim NestedNameSpecifierLoc QualifierLoc; 6022234353Sdim if (S->getQualifierLoc()) { 6023239462Sdim QualifierLoc 6024234353Sdim = getDerived().TransformNestedNameSpecifierLoc(S->getQualifierLoc()); 6025234353Sdim if (!QualifierLoc) 6026234353Sdim return StmtError(); 6027234353Sdim } 6028234353Sdim 6029234353Sdim // Transform the declaration name. 6030234353Sdim DeclarationNameInfo NameInfo = S->getNameInfo(); 6031234353Sdim if (NameInfo.getName()) { 6032234353Sdim NameInfo = getDerived().TransformDeclarationNameInfo(NameInfo); 6033234353Sdim if (!NameInfo.getName()) 6034234353Sdim return StmtError(); 6035234353Sdim } 6036234353Sdim 6037234353Sdim // Check whether anything changed. 6038234353Sdim if (!getDerived().AlwaysRebuild() && 6039234353Sdim QualifierLoc == S->getQualifierLoc() && 6040234353Sdim NameInfo.getName() == S->getNameInfo().getName()) 6041234353Sdim return S; 6042239462Sdim 6043234353Sdim // Determine whether this name exists, if we can. 6044234353Sdim CXXScopeSpec SS; 6045234353Sdim SS.Adopt(QualifierLoc); 6046234353Sdim bool Dependent = false; 6047234353Sdim switch (getSema().CheckMicrosoftIfExistsSymbol(/*S=*/0, SS, NameInfo)) { 6048234353Sdim case Sema::IER_Exists: 6049234353Sdim if (S->isIfExists()) 6050234353Sdim break; 6051239462Sdim 6052234353Sdim return new (getSema().Context) NullStmt(S->getKeywordLoc()); 6053234353Sdim 6054234353Sdim case Sema::IER_DoesNotExist: 6055234353Sdim if (S->isIfNotExists()) 6056234353Sdim break; 6057239462Sdim 6058234353Sdim return new (getSema().Context) NullStmt(S->getKeywordLoc()); 6059239462Sdim 6060234353Sdim case Sema::IER_Dependent: 6061234353Sdim Dependent = true; 6062234353Sdim break; 6063239462Sdim 6064234353Sdim case Sema::IER_Error: 6065234353Sdim return StmtError(); 6066234353Sdim } 6067239462Sdim 6068234353Sdim // We need to continue with the instantiation, so do so now. 6069234353Sdim StmtResult SubStmt = getDerived().TransformCompoundStmt(S->getSubStmt()); 6070234353Sdim if (SubStmt.isInvalid()) 6071234353Sdim return StmtError(); 6072239462Sdim 6073234353Sdim // If we have resolved the name, just transform to the substatement. 6074234353Sdim if (!Dependent) 6075234353Sdim return SubStmt; 6076239462Sdim 6077234353Sdim // The name is still dependent, so build a dependent expression again. 6078234353Sdim return getDerived().RebuildMSDependentExistsStmt(S->getKeywordLoc(), 6079234353Sdim S->isIfExists(), 6080234353Sdim QualifierLoc, 6081234353Sdim NameInfo, 6082234353Sdim SubStmt.get()); 6083234353Sdim} 6084234353Sdim 6085234353Sdimtemplate<typename Derived> 6086251662SdimExprResult 6087251662SdimTreeTransform<Derived>::TransformMSPropertyRefExpr(MSPropertyRefExpr *E) { 6088251662Sdim NestedNameSpecifierLoc QualifierLoc; 6089251662Sdim if (E->getQualifierLoc()) { 6090251662Sdim QualifierLoc 6091251662Sdim = getDerived().TransformNestedNameSpecifierLoc(E->getQualifierLoc()); 6092251662Sdim if (!QualifierLoc) 6093251662Sdim return ExprError(); 6094251662Sdim } 6095251662Sdim 6096251662Sdim MSPropertyDecl *PD = cast_or_null<MSPropertyDecl>( 6097251662Sdim getDerived().TransformDecl(E->getMemberLoc(), E->getPropertyDecl())); 6098251662Sdim if (!PD) 6099251662Sdim return ExprError(); 6100251662Sdim 6101251662Sdim ExprResult Base = getDerived().TransformExpr(E->getBaseExpr()); 6102251662Sdim if (Base.isInvalid()) 6103251662Sdim return ExprError(); 6104251662Sdim 6105251662Sdim return new (SemaRef.getASTContext()) 6106251662Sdim MSPropertyRefExpr(Base.get(), PD, E->isArrow(), 6107251662Sdim SemaRef.getASTContext().PseudoObjectTy, VK_LValue, 6108251662Sdim QualifierLoc, E->getMemberLoc()); 6109251662Sdim} 6110251662Sdim 6111251662Sdimtemplate<typename Derived> 6112234353SdimStmtResult 6113221345SdimTreeTransform<Derived>::TransformSEHTryStmt(SEHTryStmt *S) { 6114221345Sdim StmtResult TryBlock; // = getDerived().TransformCompoundStmt(S->getTryBlock()); 6115221345Sdim if(TryBlock.isInvalid()) return StmtError(); 6116221345Sdim 6117221345Sdim StmtResult Handler = getDerived().TransformSEHHandler(S->getHandler()); 6118221345Sdim if(!getDerived().AlwaysRebuild() && 6119221345Sdim TryBlock.get() == S->getTryBlock() && 6120221345Sdim Handler.get() == S->getHandler()) 6121221345Sdim return SemaRef.Owned(S); 6122221345Sdim 6123221345Sdim return getDerived().RebuildSEHTryStmt(S->getIsCXXTry(), 6124221345Sdim S->getTryLoc(), 6125221345Sdim TryBlock.take(), 6126221345Sdim Handler.take()); 6127221345Sdim} 6128221345Sdim 6129221345Sdimtemplate<typename Derived> 6130221345SdimStmtResult 6131221345SdimTreeTransform<Derived>::TransformSEHFinallyStmt(SEHFinallyStmt *S) { 6132221345Sdim StmtResult Block; // = getDerived().TransformCompoundStatement(S->getBlock()); 6133221345Sdim if(Block.isInvalid()) return StmtError(); 6134221345Sdim 6135221345Sdim return getDerived().RebuildSEHFinallyStmt(S->getFinallyLoc(), 6136221345Sdim Block.take()); 6137221345Sdim} 6138221345Sdim 6139221345Sdimtemplate<typename Derived> 6140221345SdimStmtResult 6141221345SdimTreeTransform<Derived>::TransformSEHExceptStmt(SEHExceptStmt *S) { 6142221345Sdim ExprResult FilterExpr = getDerived().TransformExpr(S->getFilterExpr()); 6143221345Sdim if(FilterExpr.isInvalid()) return StmtError(); 6144221345Sdim 6145221345Sdim StmtResult Block; // = getDerived().TransformCompoundStatement(S->getBlock()); 6146221345Sdim if(Block.isInvalid()) return StmtError(); 6147221345Sdim 6148221345Sdim return getDerived().RebuildSEHExceptStmt(S->getExceptLoc(), 6149221345Sdim FilterExpr.take(), 6150221345Sdim Block.take()); 6151221345Sdim} 6152221345Sdim 6153221345Sdimtemplate<typename Derived> 6154221345SdimStmtResult 6155221345SdimTreeTransform<Derived>::TransformSEHHandler(Stmt *Handler) { 6156221345Sdim if(isa<SEHFinallyStmt>(Handler)) 6157221345Sdim return getDerived().TransformSEHFinallyStmt(cast<SEHFinallyStmt>(Handler)); 6158221345Sdim else 6159221345Sdim return getDerived().TransformSEHExceptStmt(cast<SEHExceptStmt>(Handler)); 6160221345Sdim} 6161221345Sdim 6162198092Srdivacky//===----------------------------------------------------------------------===// 6163198092Srdivacky// Expression transformation 6164198092Srdivacky//===----------------------------------------------------------------------===// 6165198092Srdivackytemplate<typename Derived> 6166212904SdimExprResult 6167200583SrdivackyTreeTransform<Derived>::TransformPredefinedExpr(PredefinedExpr *E) { 6168218893Sdim return SemaRef.Owned(E); 6169198092Srdivacky} 6170198092Srdivacky 6171198092Srdivackytemplate<typename Derived> 6172212904SdimExprResult 6173200583SrdivackyTreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) { 6174221345Sdim NestedNameSpecifierLoc QualifierLoc; 6175221345Sdim if (E->getQualifierLoc()) { 6176221345Sdim QualifierLoc 6177221345Sdim = getDerived().TransformNestedNameSpecifierLoc(E->getQualifierLoc()); 6178221345Sdim if (!QualifierLoc) 6179212904Sdim return ExprError(); 6180198893Srdivacky } 6181200583Srdivacky 6182200583Srdivacky ValueDecl *ND 6183204643Srdivacky = cast_or_null<ValueDecl>(getDerived().TransformDecl(E->getLocation(), 6184204643Srdivacky E->getDecl())); 6185198092Srdivacky if (!ND) 6186212904Sdim return ExprError(); 6187198092Srdivacky 6188212904Sdim DeclarationNameInfo NameInfo = E->getNameInfo(); 6189212904Sdim if (NameInfo.getName()) { 6190212904Sdim NameInfo = getDerived().TransformDeclarationNameInfo(NameInfo); 6191212904Sdim if (!NameInfo.getName()) 6192212904Sdim return ExprError(); 6193212904Sdim } 6194212904Sdim 6195212904Sdim if (!getDerived().AlwaysRebuild() && 6196221345Sdim QualifierLoc == E->getQualifierLoc() && 6197198893Srdivacky ND == E->getDecl() && 6198212904Sdim NameInfo.getName() == E->getDecl()->getDeclName() && 6199212904Sdim !E->hasExplicitTemplateArgs()) { 6200200583Srdivacky 6201200583Srdivacky // Mark it referenced in the new context regardless. 6202200583Srdivacky // FIXME: this is a bit instantiation-specific. 6203234353Sdim SemaRef.MarkDeclRefReferenced(E); 6204200583Srdivacky 6205218893Sdim return SemaRef.Owned(E); 6206200583Srdivacky } 6207198092Srdivacky 6208200583Srdivacky TemplateArgumentListInfo TransArgs, *TemplateArgs = 0; 6209212904Sdim if (E->hasExplicitTemplateArgs()) { 6210200583Srdivacky TemplateArgs = &TransArgs; 6211200583Srdivacky TransArgs.setLAngleLoc(E->getLAngleLoc()); 6212200583Srdivacky TransArgs.setRAngleLoc(E->getRAngleLoc()); 6213218893Sdim if (getDerived().TransformTemplateArguments(E->getTemplateArgs(), 6214218893Sdim E->getNumTemplateArgs(), 6215218893Sdim TransArgs)) 6216218893Sdim return ExprError(); 6217200583Srdivacky } 6218198893Srdivacky 6219239462Sdim return getDerived().RebuildDeclRefExpr(QualifierLoc, ND, NameInfo, 6220221345Sdim TemplateArgs); 6221198092Srdivacky} 6222198092Srdivacky 6223198092Srdivackytemplate<typename Derived> 6224212904SdimExprResult 6225200583SrdivackyTreeTransform<Derived>::TransformIntegerLiteral(IntegerLiteral *E) { 6226218893Sdim return SemaRef.Owned(E); 6227198092Srdivacky} 6228198092Srdivacky 6229198092Srdivackytemplate<typename Derived> 6230212904SdimExprResult 6231200583SrdivackyTreeTransform<Derived>::TransformFloatingLiteral(FloatingLiteral *E) { 6232218893Sdim return SemaRef.Owned(E); 6233198092Srdivacky} 6234198092Srdivacky 6235198092Srdivackytemplate<typename Derived> 6236212904SdimExprResult 6237200583SrdivackyTreeTransform<Derived>::TransformImaginaryLiteral(ImaginaryLiteral *E) { 6238218893Sdim return SemaRef.Owned(E); 6239198092Srdivacky} 6240198092Srdivacky 6241198092Srdivackytemplate<typename Derived> 6242212904SdimExprResult 6243200583SrdivackyTreeTransform<Derived>::TransformStringLiteral(StringLiteral *E) { 6244218893Sdim return SemaRef.Owned(E); 6245198092Srdivacky} 6246198092Srdivacky 6247198092Srdivackytemplate<typename Derived> 6248212904SdimExprResult 6249200583SrdivackyTreeTransform<Derived>::TransformCharacterLiteral(CharacterLiteral *E) { 6250218893Sdim return SemaRef.Owned(E); 6251198092Srdivacky} 6252198092Srdivacky 6253198092Srdivackytemplate<typename Derived> 6254212904SdimExprResult 6255234353SdimTreeTransform<Derived>::TransformUserDefinedLiteral(UserDefinedLiteral *E) { 6256251662Sdim if (FunctionDecl *FD = E->getDirectCallee()) 6257251662Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), FD); 6258234353Sdim return SemaRef.MaybeBindToTemporary(E); 6259234353Sdim} 6260234353Sdim 6261234353Sdimtemplate<typename Derived> 6262234353SdimExprResult 6263221345SdimTreeTransform<Derived>::TransformGenericSelectionExpr(GenericSelectionExpr *E) { 6264221345Sdim ExprResult ControllingExpr = 6265221345Sdim getDerived().TransformExpr(E->getControllingExpr()); 6266221345Sdim if (ControllingExpr.isInvalid()) 6267221345Sdim return ExprError(); 6268221345Sdim 6269226633Sdim SmallVector<Expr *, 4> AssocExprs; 6270226633Sdim SmallVector<TypeSourceInfo *, 4> AssocTypes; 6271221345Sdim for (unsigned i = 0; i != E->getNumAssocs(); ++i) { 6272221345Sdim TypeSourceInfo *TS = E->getAssocTypeSourceInfo(i); 6273221345Sdim if (TS) { 6274221345Sdim TypeSourceInfo *AssocType = getDerived().TransformType(TS); 6275221345Sdim if (!AssocType) 6276221345Sdim return ExprError(); 6277221345Sdim AssocTypes.push_back(AssocType); 6278221345Sdim } else { 6279221345Sdim AssocTypes.push_back(0); 6280221345Sdim } 6281221345Sdim 6282221345Sdim ExprResult AssocExpr = getDerived().TransformExpr(E->getAssocExpr(i)); 6283221345Sdim if (AssocExpr.isInvalid()) 6284221345Sdim return ExprError(); 6285221345Sdim AssocExprs.push_back(AssocExpr.release()); 6286221345Sdim } 6287221345Sdim 6288221345Sdim return getDerived().RebuildGenericSelectionExpr(E->getGenericLoc(), 6289221345Sdim E->getDefaultLoc(), 6290221345Sdim E->getRParenLoc(), 6291221345Sdim ControllingExpr.release(), 6292221345Sdim AssocTypes.data(), 6293221345Sdim AssocExprs.data(), 6294221345Sdim E->getNumAssocs()); 6295221345Sdim} 6296221345Sdim 6297221345Sdimtemplate<typename Derived> 6298221345SdimExprResult 6299200583SrdivackyTreeTransform<Derived>::TransformParenExpr(ParenExpr *E) { 6300212904Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 6301198092Srdivacky if (SubExpr.isInvalid()) 6302212904Sdim return ExprError(); 6303198092Srdivacky 6304198092Srdivacky if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr()) 6305218893Sdim return SemaRef.Owned(E); 6306198092Srdivacky 6307212904Sdim return getDerived().RebuildParenExpr(SubExpr.get(), E->getLParen(), 6308198092Srdivacky E->getRParen()); 6309198092Srdivacky} 6310198092Srdivacky 6311243830Sdim/// \brief The operand of a unary address-of operator has special rules: it's 6312243830Sdim/// allowed to refer to a non-static member of a class even if there's no 'this' 6313243830Sdim/// object available. 6314198092Srdivackytemplate<typename Derived> 6315212904SdimExprResult 6316243830SdimTreeTransform<Derived>::TransformAddressOfOperand(Expr *E) { 6317243830Sdim if (DependentScopeDeclRefExpr *DRE = dyn_cast<DependentScopeDeclRefExpr>(E)) 6318243830Sdim return getDerived().TransformDependentScopeDeclRefExpr(DRE, true); 6319243830Sdim else 6320243830Sdim return getDerived().TransformExpr(E); 6321243830Sdim} 6322243830Sdim 6323243830Sdimtemplate<typename Derived> 6324243830SdimExprResult 6325200583SrdivackyTreeTransform<Derived>::TransformUnaryOperator(UnaryOperator *E) { 6326243830Sdim ExprResult SubExpr = TransformAddressOfOperand(E->getSubExpr()); 6327198092Srdivacky if (SubExpr.isInvalid()) 6328212904Sdim return ExprError(); 6329198092Srdivacky 6330198092Srdivacky if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getSubExpr()) 6331218893Sdim return SemaRef.Owned(E); 6332198092Srdivacky 6333198092Srdivacky return getDerived().RebuildUnaryOperator(E->getOperatorLoc(), 6334198092Srdivacky E->getOpcode(), 6335212904Sdim SubExpr.get()); 6336198092Srdivacky} 6337198092Srdivacky 6338198092Srdivackytemplate<typename Derived> 6339212904SdimExprResult 6340207619SrdivackyTreeTransform<Derived>::TransformOffsetOfExpr(OffsetOfExpr *E) { 6341207619Srdivacky // Transform the type. 6342207619Srdivacky TypeSourceInfo *Type = getDerived().TransformType(E->getTypeSourceInfo()); 6343207619Srdivacky if (!Type) 6344212904Sdim return ExprError(); 6345239462Sdim 6346207619Srdivacky // Transform all of the components into components similar to what the 6347207619Srdivacky // parser uses. 6348239462Sdim // FIXME: It would be slightly more efficient in the non-dependent case to 6349239462Sdim // just map FieldDecls, rather than requiring the rebuilder to look for 6350239462Sdim // the fields again. However, __builtin_offsetof is rare enough in 6351207619Srdivacky // template code that we don't care. 6352207619Srdivacky bool ExprChanged = false; 6353212904Sdim typedef Sema::OffsetOfComponent Component; 6354207619Srdivacky typedef OffsetOfExpr::OffsetOfNode Node; 6355226633Sdim SmallVector<Component, 4> Components; 6356207619Srdivacky for (unsigned I = 0, N = E->getNumComponents(); I != N; ++I) { 6357207619Srdivacky const Node &ON = E->getComponent(I); 6358207619Srdivacky Component Comp; 6359207619Srdivacky Comp.isBrackets = true; 6360221345Sdim Comp.LocStart = ON.getSourceRange().getBegin(); 6361221345Sdim Comp.LocEnd = ON.getSourceRange().getEnd(); 6362207619Srdivacky switch (ON.getKind()) { 6363207619Srdivacky case Node::Array: { 6364207619Srdivacky Expr *FromIndex = E->getIndexExpr(ON.getArrayExprIndex()); 6365212904Sdim ExprResult Index = getDerived().TransformExpr(FromIndex); 6366207619Srdivacky if (Index.isInvalid()) 6367212904Sdim return ExprError(); 6368239462Sdim 6369207619Srdivacky ExprChanged = ExprChanged || Index.get() != FromIndex; 6370207619Srdivacky Comp.isBrackets = true; 6371212904Sdim Comp.U.E = Index.get(); 6372207619Srdivacky break; 6373207619Srdivacky } 6374239462Sdim 6375207619Srdivacky case Node::Field: 6376207619Srdivacky case Node::Identifier: 6377207619Srdivacky Comp.isBrackets = false; 6378207619Srdivacky Comp.U.IdentInfo = ON.getFieldName(); 6379207619Srdivacky if (!Comp.U.IdentInfo) 6380207619Srdivacky continue; 6381239462Sdim 6382207619Srdivacky break; 6383239462Sdim 6384207619Srdivacky case Node::Base: 6385207619Srdivacky // Will be recomputed during the rebuild. 6386207619Srdivacky continue; 6387207619Srdivacky } 6388239462Sdim 6389207619Srdivacky Components.push_back(Comp); 6390207619Srdivacky } 6391239462Sdim 6392207619Srdivacky // If nothing changed, retain the existing expression. 6393207619Srdivacky if (!getDerived().AlwaysRebuild() && 6394207619Srdivacky Type == E->getTypeSourceInfo() && 6395207619Srdivacky !ExprChanged) 6396218893Sdim return SemaRef.Owned(E); 6397239462Sdim 6398207619Srdivacky // Build a new offsetof expression. 6399207619Srdivacky return getDerived().RebuildOffsetOfExpr(E->getOperatorLoc(), Type, 6400207619Srdivacky Components.data(), Components.size(), 6401207619Srdivacky E->getRParenLoc()); 6402207619Srdivacky} 6403207619Srdivacky 6404207619Srdivackytemplate<typename Derived> 6405212904SdimExprResult 6406218893SdimTreeTransform<Derived>::TransformOpaqueValueExpr(OpaqueValueExpr *E) { 6407218893Sdim assert(getDerived().AlreadyTransformed(E->getType()) && 6408218893Sdim "opaque value expression requires transformation"); 6409218893Sdim return SemaRef.Owned(E); 6410218893Sdim} 6411218893Sdim 6412218893Sdimtemplate<typename Derived> 6413218893SdimExprResult 6414234353SdimTreeTransform<Derived>::TransformPseudoObjectExpr(PseudoObjectExpr *E) { 6415234353Sdim // Rebuild the syntactic form. The original syntactic form has 6416234353Sdim // opaque-value expressions in it, so strip those away and rebuild 6417234353Sdim // the result. This is a really awful way of doing this, but the 6418234353Sdim // better solution (rebuilding the semantic expressions and 6419234353Sdim // rebinding OVEs as necessary) doesn't work; we'd need 6420234353Sdim // TreeTransform to not strip away implicit conversions. 6421234353Sdim Expr *newSyntacticForm = SemaRef.recreateSyntacticForm(E); 6422234353Sdim ExprResult result = getDerived().TransformExpr(newSyntacticForm); 6423234353Sdim if (result.isInvalid()) return ExprError(); 6424234353Sdim 6425234353Sdim // If that gives us a pseudo-object result back, the pseudo-object 6426234353Sdim // expression must have been an lvalue-to-rvalue conversion which we 6427234353Sdim // should reapply. 6428234353Sdim if (result.get()->hasPlaceholderType(BuiltinType::PseudoObject)) 6429234353Sdim result = SemaRef.checkPseudoObjectRValue(result.take()); 6430234353Sdim 6431234353Sdim return result; 6432234353Sdim} 6433234353Sdim 6434234353Sdimtemplate<typename Derived> 6435234353SdimExprResult 6436221345SdimTreeTransform<Derived>::TransformUnaryExprOrTypeTraitExpr( 6437221345Sdim UnaryExprOrTypeTraitExpr *E) { 6438198092Srdivacky if (E->isArgumentType()) { 6439200583Srdivacky TypeSourceInfo *OldT = E->getArgumentTypeInfo(); 6440198893Srdivacky 6441200583Srdivacky TypeSourceInfo *NewT = getDerived().TransformType(OldT); 6442198893Srdivacky if (!NewT) 6443212904Sdim return ExprError(); 6444198092Srdivacky 6445198893Srdivacky if (!getDerived().AlwaysRebuild() && OldT == NewT) 6446218893Sdim return SemaRef.Owned(E); 6447198092Srdivacky 6448221345Sdim return getDerived().RebuildUnaryExprOrTypeTrait(NewT, E->getOperatorLoc(), 6449221345Sdim E->getKind(), 6450221345Sdim E->getSourceRange()); 6451198092Srdivacky } 6452198092Srdivacky 6453234353Sdim // C++0x [expr.sizeof]p1: 6454234353Sdim // The operand is either an expression, which is an unevaluated operand 6455234353Sdim // [...] 6456243830Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated, 6457243830Sdim Sema::ReuseLambdaContextDecl); 6458198092Srdivacky 6459234353Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getArgumentExpr()); 6460234353Sdim if (SubExpr.isInvalid()) 6461234353Sdim return ExprError(); 6462198092Srdivacky 6463234353Sdim if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr()) 6464234353Sdim return SemaRef.Owned(E); 6465198092Srdivacky 6466221345Sdim return getDerived().RebuildUnaryExprOrTypeTrait(SubExpr.get(), 6467221345Sdim E->getOperatorLoc(), 6468221345Sdim E->getKind(), 6469221345Sdim E->getSourceRange()); 6470198092Srdivacky} 6471198092Srdivacky 6472198092Srdivackytemplate<typename Derived> 6473212904SdimExprResult 6474200583SrdivackyTreeTransform<Derived>::TransformArraySubscriptExpr(ArraySubscriptExpr *E) { 6475212904Sdim ExprResult LHS = getDerived().TransformExpr(E->getLHS()); 6476198092Srdivacky if (LHS.isInvalid()) 6477212904Sdim return ExprError(); 6478198092Srdivacky 6479212904Sdim ExprResult RHS = getDerived().TransformExpr(E->getRHS()); 6480198092Srdivacky if (RHS.isInvalid()) 6481212904Sdim return ExprError(); 6482198092Srdivacky 6483198092Srdivacky 6484198092Srdivacky if (!getDerived().AlwaysRebuild() && 6485198092Srdivacky LHS.get() == E->getLHS() && 6486198092Srdivacky RHS.get() == E->getRHS()) 6487218893Sdim return SemaRef.Owned(E); 6488198092Srdivacky 6489212904Sdim return getDerived().RebuildArraySubscriptExpr(LHS.get(), 6490198092Srdivacky /*FIXME:*/E->getLHS()->getLocStart(), 6491212904Sdim RHS.get(), 6492198092Srdivacky E->getRBracketLoc()); 6493198092Srdivacky} 6494198092Srdivacky 6495198092Srdivackytemplate<typename Derived> 6496212904SdimExprResult 6497200583SrdivackyTreeTransform<Derived>::TransformCallExpr(CallExpr *E) { 6498198092Srdivacky // Transform the callee. 6499212904Sdim ExprResult Callee = getDerived().TransformExpr(E->getCallee()); 6500198092Srdivacky if (Callee.isInvalid()) 6501212904Sdim return ExprError(); 6502198092Srdivacky 6503198092Srdivacky // Transform arguments. 6504198092Srdivacky bool ArgChanged = false; 6505243830Sdim SmallVector<Expr*, 8> Args; 6506239462Sdim if (getDerived().TransformExprs(E->getArgs(), E->getNumArgs(), true, Args, 6507218893Sdim &ArgChanged)) 6508218893Sdim return ExprError(); 6509239462Sdim 6510198092Srdivacky if (!getDerived().AlwaysRebuild() && 6511198092Srdivacky Callee.get() == E->getCallee() && 6512198092Srdivacky !ArgChanged) 6513243830Sdim return SemaRef.MaybeBindToTemporary(E); 6514198092Srdivacky 6515198092Srdivacky // FIXME: Wrong source location information for the '('. 6516198092Srdivacky SourceLocation FakeLParenLoc 6517198092Srdivacky = ((Expr *)Callee.get())->getSourceRange().getBegin(); 6518212904Sdim return getDerived().RebuildCallExpr(Callee.get(), FakeLParenLoc, 6519243830Sdim Args, 6520198092Srdivacky E->getRParenLoc()); 6521198092Srdivacky} 6522198092Srdivacky 6523198092Srdivackytemplate<typename Derived> 6524212904SdimExprResult 6525200583SrdivackyTreeTransform<Derived>::TransformMemberExpr(MemberExpr *E) { 6526212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 6527198092Srdivacky if (Base.isInvalid()) 6528212904Sdim return ExprError(); 6529198092Srdivacky 6530221345Sdim NestedNameSpecifierLoc QualifierLoc; 6531198092Srdivacky if (E->hasQualifier()) { 6532221345Sdim QualifierLoc 6533221345Sdim = getDerived().TransformNestedNameSpecifierLoc(E->getQualifierLoc()); 6534239462Sdim 6535221345Sdim if (!QualifierLoc) 6536212904Sdim return ExprError(); 6537198092Srdivacky } 6538234353Sdim SourceLocation TemplateKWLoc = E->getTemplateKeywordLoc(); 6539198092Srdivacky 6540200583Srdivacky ValueDecl *Member 6541204643Srdivacky = cast_or_null<ValueDecl>(getDerived().TransformDecl(E->getMemberLoc(), 6542204643Srdivacky E->getMemberDecl())); 6543198092Srdivacky if (!Member) 6544212904Sdim return ExprError(); 6545198092Srdivacky 6546206084Srdivacky NamedDecl *FoundDecl = E->getFoundDecl(); 6547206084Srdivacky if (FoundDecl == E->getMemberDecl()) { 6548206084Srdivacky FoundDecl = Member; 6549206084Srdivacky } else { 6550206084Srdivacky FoundDecl = cast_or_null<NamedDecl>( 6551206084Srdivacky getDerived().TransformDecl(E->getMemberLoc(), FoundDecl)); 6552206084Srdivacky if (!FoundDecl) 6553212904Sdim return ExprError(); 6554206084Srdivacky } 6555206084Srdivacky 6556198092Srdivacky if (!getDerived().AlwaysRebuild() && 6557198092Srdivacky Base.get() == E->getBase() && 6558221345Sdim QualifierLoc == E->getQualifierLoc() && 6559198954Srdivacky Member == E->getMemberDecl() && 6560206084Srdivacky FoundDecl == E->getFoundDecl() && 6561212904Sdim !E->hasExplicitTemplateArgs()) { 6562239462Sdim 6563201361Srdivacky // Mark it referenced in the new context regardless. 6564201361Srdivacky // FIXME: this is a bit instantiation-specific. 6565234353Sdim SemaRef.MarkMemberReferenced(E); 6566234353Sdim 6567218893Sdim return SemaRef.Owned(E); 6568201361Srdivacky } 6569198092Srdivacky 6570199990Srdivacky TemplateArgumentListInfo TransArgs; 6571212904Sdim if (E->hasExplicitTemplateArgs()) { 6572199990Srdivacky TransArgs.setLAngleLoc(E->getLAngleLoc()); 6573199990Srdivacky TransArgs.setRAngleLoc(E->getRAngleLoc()); 6574218893Sdim if (getDerived().TransformTemplateArguments(E->getTemplateArgs(), 6575218893Sdim E->getNumTemplateArgs(), 6576218893Sdim TransArgs)) 6577218893Sdim return ExprError(); 6578198954Srdivacky } 6579239462Sdim 6580198092Srdivacky // FIXME: Bogus source location for the operator 6581198092Srdivacky SourceLocation FakeOperatorLoc 6582198092Srdivacky = SemaRef.PP.getLocForEndOfToken(E->getBase()->getSourceRange().getEnd()); 6583198092Srdivacky 6584202379Srdivacky // FIXME: to do this check properly, we will need to preserve the 6585202379Srdivacky // first-qualifier-in-scope here, just in case we had a dependent 6586202379Srdivacky // base (and therefore couldn't do the check) and a 6587202379Srdivacky // nested-name-qualifier (and therefore could do the lookup). 6588202379Srdivacky NamedDecl *FirstQualifierInScope = 0; 6589202379Srdivacky 6590212904Sdim return getDerived().RebuildMemberExpr(Base.get(), FakeOperatorLoc, 6591198092Srdivacky E->isArrow(), 6592221345Sdim QualifierLoc, 6593234353Sdim TemplateKWLoc, 6594212904Sdim E->getMemberNameInfo(), 6595198954Srdivacky Member, 6596206084Srdivacky FoundDecl, 6597212904Sdim (E->hasExplicitTemplateArgs() 6598199990Srdivacky ? &TransArgs : 0), 6599202379Srdivacky FirstQualifierInScope); 6600198092Srdivacky} 6601198092Srdivacky 6602198092Srdivackytemplate<typename Derived> 6603212904SdimExprResult 6604200583SrdivackyTreeTransform<Derived>::TransformBinaryOperator(BinaryOperator *E) { 6605212904Sdim ExprResult LHS = getDerived().TransformExpr(E->getLHS()); 6606198092Srdivacky if (LHS.isInvalid()) 6607212904Sdim return ExprError(); 6608198092Srdivacky 6609212904Sdim ExprResult RHS = getDerived().TransformExpr(E->getRHS()); 6610198092Srdivacky if (RHS.isInvalid()) 6611212904Sdim return ExprError(); 6612198092Srdivacky 6613198092Srdivacky if (!getDerived().AlwaysRebuild() && 6614198092Srdivacky LHS.get() == E->getLHS() && 6615198092Srdivacky RHS.get() == E->getRHS()) 6616218893Sdim return SemaRef.Owned(E); 6617198092Srdivacky 6618243830Sdim Sema::FPContractStateRAII FPContractState(getSema()); 6619243830Sdim getSema().FPFeatures.fp_contract = E->isFPContractable(); 6620243830Sdim 6621198092Srdivacky return getDerived().RebuildBinaryOperator(E->getOperatorLoc(), E->getOpcode(), 6622212904Sdim LHS.get(), RHS.get()); 6623198092Srdivacky} 6624198092Srdivacky 6625198092Srdivackytemplate<typename Derived> 6626212904SdimExprResult 6627198092SrdivackyTreeTransform<Derived>::TransformCompoundAssignOperator( 6628200583Srdivacky CompoundAssignOperator *E) { 6629200583Srdivacky return getDerived().TransformBinaryOperator(E); 6630198092Srdivacky} 6631198092Srdivacky 6632198092Srdivackytemplate<typename Derived> 6633218893SdimExprResult TreeTransform<Derived>:: 6634218893SdimTransformBinaryConditionalOperator(BinaryConditionalOperator *e) { 6635218893Sdim // Just rebuild the common and RHS expressions and see whether we 6636218893Sdim // get any changes. 6637218893Sdim 6638218893Sdim ExprResult commonExpr = getDerived().TransformExpr(e->getCommon()); 6639218893Sdim if (commonExpr.isInvalid()) 6640218893Sdim return ExprError(); 6641218893Sdim 6642218893Sdim ExprResult rhs = getDerived().TransformExpr(e->getFalseExpr()); 6643218893Sdim if (rhs.isInvalid()) 6644218893Sdim return ExprError(); 6645218893Sdim 6646218893Sdim if (!getDerived().AlwaysRebuild() && 6647218893Sdim commonExpr.get() == e->getCommon() && 6648218893Sdim rhs.get() == e->getFalseExpr()) 6649218893Sdim return SemaRef.Owned(e); 6650218893Sdim 6651218893Sdim return getDerived().RebuildConditionalOperator(commonExpr.take(), 6652218893Sdim e->getQuestionLoc(), 6653218893Sdim 0, 6654218893Sdim e->getColonLoc(), 6655218893Sdim rhs.get()); 6656218893Sdim} 6657218893Sdim 6658218893Sdimtemplate<typename Derived> 6659212904SdimExprResult 6660200583SrdivackyTreeTransform<Derived>::TransformConditionalOperator(ConditionalOperator *E) { 6661212904Sdim ExprResult Cond = getDerived().TransformExpr(E->getCond()); 6662198092Srdivacky if (Cond.isInvalid()) 6663212904Sdim return ExprError(); 6664198092Srdivacky 6665212904Sdim ExprResult LHS = getDerived().TransformExpr(E->getLHS()); 6666198092Srdivacky if (LHS.isInvalid()) 6667212904Sdim return ExprError(); 6668198092Srdivacky 6669212904Sdim ExprResult RHS = getDerived().TransformExpr(E->getRHS()); 6670198092Srdivacky if (RHS.isInvalid()) 6671212904Sdim return ExprError(); 6672198092Srdivacky 6673198092Srdivacky if (!getDerived().AlwaysRebuild() && 6674198092Srdivacky Cond.get() == E->getCond() && 6675198092Srdivacky LHS.get() == E->getLHS() && 6676198092Srdivacky RHS.get() == E->getRHS()) 6677218893Sdim return SemaRef.Owned(E); 6678198092Srdivacky 6679212904Sdim return getDerived().RebuildConditionalOperator(Cond.get(), 6680198092Srdivacky E->getQuestionLoc(), 6681212904Sdim LHS.get(), 6682198092Srdivacky E->getColonLoc(), 6683212904Sdim RHS.get()); 6684198092Srdivacky} 6685198092Srdivacky 6686198092Srdivackytemplate<typename Derived> 6687212904SdimExprResult 6688200583SrdivackyTreeTransform<Derived>::TransformImplicitCastExpr(ImplicitCastExpr *E) { 6689200583Srdivacky // Implicit casts are eliminated during transformation, since they 6690200583Srdivacky // will be recomputed by semantic analysis after transformation. 6691200583Srdivacky return getDerived().TransformExpr(E->getSubExprAsWritten()); 6692198092Srdivacky} 6693198092Srdivacky 6694198092Srdivackytemplate<typename Derived> 6695212904SdimExprResult 6696200583SrdivackyTreeTransform<Derived>::TransformCStyleCastExpr(CStyleCastExpr *E) { 6697218893Sdim TypeSourceInfo *Type = getDerived().TransformType(E->getTypeInfoAsWritten()); 6698218893Sdim if (!Type) 6699218893Sdim return ExprError(); 6700239462Sdim 6701212904Sdim ExprResult SubExpr 6702200583Srdivacky = getDerived().TransformExpr(E->getSubExprAsWritten()); 6703198092Srdivacky if (SubExpr.isInvalid()) 6704212904Sdim return ExprError(); 6705198092Srdivacky 6706198092Srdivacky if (!getDerived().AlwaysRebuild() && 6707218893Sdim Type == E->getTypeInfoAsWritten() && 6708198092Srdivacky SubExpr.get() == E->getSubExpr()) 6709218893Sdim return SemaRef.Owned(E); 6710198092Srdivacky 6711202879Srdivacky return getDerived().RebuildCStyleCastExpr(E->getLParenLoc(), 6712218893Sdim Type, 6713198092Srdivacky E->getRParenLoc(), 6714212904Sdim SubExpr.get()); 6715198092Srdivacky} 6716198092Srdivacky 6717198092Srdivackytemplate<typename Derived> 6718212904SdimExprResult 6719200583SrdivackyTreeTransform<Derived>::TransformCompoundLiteralExpr(CompoundLiteralExpr *E) { 6720202879Srdivacky TypeSourceInfo *OldT = E->getTypeSourceInfo(); 6721202879Srdivacky TypeSourceInfo *NewT = getDerived().TransformType(OldT); 6722202879Srdivacky if (!NewT) 6723212904Sdim return ExprError(); 6724198092Srdivacky 6725212904Sdim ExprResult Init = getDerived().TransformExpr(E->getInitializer()); 6726198092Srdivacky if (Init.isInvalid()) 6727212904Sdim return ExprError(); 6728198092Srdivacky 6729198092Srdivacky if (!getDerived().AlwaysRebuild() && 6730202879Srdivacky OldT == NewT && 6731198092Srdivacky Init.get() == E->getInitializer()) 6732234353Sdim return SemaRef.MaybeBindToTemporary(E); 6733198092Srdivacky 6734202879Srdivacky // Note: the expression type doesn't necessarily match the 6735202879Srdivacky // type-as-written, but that's okay, because it should always be 6736202879Srdivacky // derivable from the initializer. 6737202879Srdivacky 6738202879Srdivacky return getDerived().RebuildCompoundLiteralExpr(E->getLParenLoc(), NewT, 6739198092Srdivacky /*FIXME:*/E->getInitializer()->getLocEnd(), 6740212904Sdim Init.get()); 6741198092Srdivacky} 6742198092Srdivacky 6743198092Srdivackytemplate<typename Derived> 6744212904SdimExprResult 6745200583SrdivackyTreeTransform<Derived>::TransformExtVectorElementExpr(ExtVectorElementExpr *E) { 6746212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 6747198092Srdivacky if (Base.isInvalid()) 6748212904Sdim return ExprError(); 6749198092Srdivacky 6750198092Srdivacky if (!getDerived().AlwaysRebuild() && 6751198092Srdivacky Base.get() == E->getBase()) 6752218893Sdim return SemaRef.Owned(E); 6753198092Srdivacky 6754198092Srdivacky // FIXME: Bad source location 6755198092Srdivacky SourceLocation FakeOperatorLoc 6756198092Srdivacky = SemaRef.PP.getLocForEndOfToken(E->getBase()->getLocEnd()); 6757212904Sdim return getDerived().RebuildExtVectorElementExpr(Base.get(), FakeOperatorLoc, 6758198092Srdivacky E->getAccessorLoc(), 6759198092Srdivacky E->getAccessor()); 6760198092Srdivacky} 6761198092Srdivacky 6762198092Srdivackytemplate<typename Derived> 6763212904SdimExprResult 6764200583SrdivackyTreeTransform<Derived>::TransformInitListExpr(InitListExpr *E) { 6765198092Srdivacky bool InitChanged = false; 6766198092Srdivacky 6767243830Sdim SmallVector<Expr*, 4> Inits; 6768239462Sdim if (getDerived().TransformExprs(E->getInits(), E->getNumInits(), false, 6769218893Sdim Inits, &InitChanged)) 6770218893Sdim return ExprError(); 6771239462Sdim 6772198092Srdivacky if (!getDerived().AlwaysRebuild() && !InitChanged) 6773218893Sdim return SemaRef.Owned(E); 6774198092Srdivacky 6775243830Sdim return getDerived().RebuildInitList(E->getLBraceLoc(), Inits, 6776199482Srdivacky E->getRBraceLoc(), E->getType()); 6777198092Srdivacky} 6778198092Srdivacky 6779198092Srdivackytemplate<typename Derived> 6780212904SdimExprResult 6781200583SrdivackyTreeTransform<Derived>::TransformDesignatedInitExpr(DesignatedInitExpr *E) { 6782198092Srdivacky Designation Desig; 6783198092Srdivacky 6784198092Srdivacky // transform the initializer value 6785212904Sdim ExprResult Init = getDerived().TransformExpr(E->getInit()); 6786198092Srdivacky if (Init.isInvalid()) 6787212904Sdim return ExprError(); 6788198092Srdivacky 6789198092Srdivacky // transform the designators. 6790243830Sdim SmallVector<Expr*, 4> ArrayExprs; 6791198092Srdivacky bool ExprChanged = false; 6792198092Srdivacky for (DesignatedInitExpr::designators_iterator D = E->designators_begin(), 6793198092Srdivacky DEnd = E->designators_end(); 6794198092Srdivacky D != DEnd; ++D) { 6795198092Srdivacky if (D->isFieldDesignator()) { 6796198092Srdivacky Desig.AddDesignator(Designator::getField(D->getFieldName(), 6797198092Srdivacky D->getDotLoc(), 6798198092Srdivacky D->getFieldLoc())); 6799198092Srdivacky continue; 6800198092Srdivacky } 6801198092Srdivacky 6802198092Srdivacky if (D->isArrayDesignator()) { 6803212904Sdim ExprResult Index = getDerived().TransformExpr(E->getArrayIndex(*D)); 6804198092Srdivacky if (Index.isInvalid()) 6805212904Sdim return ExprError(); 6806198092Srdivacky 6807198092Srdivacky Desig.AddDesignator(Designator::getArray(Index.get(), 6808198092Srdivacky D->getLBracketLoc())); 6809198092Srdivacky 6810198092Srdivacky ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(*D); 6811198092Srdivacky ArrayExprs.push_back(Index.release()); 6812198092Srdivacky continue; 6813198092Srdivacky } 6814198092Srdivacky 6815198092Srdivacky assert(D->isArrayRangeDesignator() && "New kind of designator?"); 6816212904Sdim ExprResult Start 6817198092Srdivacky = getDerived().TransformExpr(E->getArrayRangeStart(*D)); 6818198092Srdivacky if (Start.isInvalid()) 6819212904Sdim return ExprError(); 6820198092Srdivacky 6821212904Sdim ExprResult End = getDerived().TransformExpr(E->getArrayRangeEnd(*D)); 6822198092Srdivacky if (End.isInvalid()) 6823212904Sdim return ExprError(); 6824198092Srdivacky 6825198092Srdivacky Desig.AddDesignator(Designator::getArrayRange(Start.get(), 6826198092Srdivacky End.get(), 6827198092Srdivacky D->getLBracketLoc(), 6828198092Srdivacky D->getEllipsisLoc())); 6829198092Srdivacky 6830198092Srdivacky ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(*D) || 6831198092Srdivacky End.get() != E->getArrayRangeEnd(*D); 6832198092Srdivacky 6833198092Srdivacky ArrayExprs.push_back(Start.release()); 6834198092Srdivacky ArrayExprs.push_back(End.release()); 6835198092Srdivacky } 6836198092Srdivacky 6837198092Srdivacky if (!getDerived().AlwaysRebuild() && 6838198092Srdivacky Init.get() == E->getInit() && 6839198092Srdivacky !ExprChanged) 6840218893Sdim return SemaRef.Owned(E); 6841198092Srdivacky 6842243830Sdim return getDerived().RebuildDesignatedInitExpr(Desig, ArrayExprs, 6843198092Srdivacky E->getEqualOrColonLoc(), 6844212904Sdim E->usesGNUSyntax(), Init.get()); 6845198092Srdivacky} 6846198092Srdivacky 6847198092Srdivackytemplate<typename Derived> 6848212904SdimExprResult 6849198092SrdivackyTreeTransform<Derived>::TransformImplicitValueInitExpr( 6850200583Srdivacky ImplicitValueInitExpr *E) { 6851198893Srdivacky TemporaryBase Rebase(*this, E->getLocStart(), DeclarationName()); 6852239462Sdim 6853198893Srdivacky // FIXME: Will we ever have proper type location here? Will we actually 6854198893Srdivacky // need to transform the type? 6855198092Srdivacky QualType T = getDerived().TransformType(E->getType()); 6856198092Srdivacky if (T.isNull()) 6857212904Sdim return ExprError(); 6858198092Srdivacky 6859198092Srdivacky if (!getDerived().AlwaysRebuild() && 6860198092Srdivacky T == E->getType()) 6861218893Sdim return SemaRef.Owned(E); 6862198092Srdivacky 6863198092Srdivacky return getDerived().RebuildImplicitValueInitExpr(T); 6864198092Srdivacky} 6865198092Srdivacky 6866198092Srdivackytemplate<typename Derived> 6867212904SdimExprResult 6868200583SrdivackyTreeTransform<Derived>::TransformVAArgExpr(VAArgExpr *E) { 6869212904Sdim TypeSourceInfo *TInfo = getDerived().TransformType(E->getWrittenTypeInfo()); 6870212904Sdim if (!TInfo) 6871212904Sdim return ExprError(); 6872198092Srdivacky 6873212904Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 6874198092Srdivacky if (SubExpr.isInvalid()) 6875212904Sdim return ExprError(); 6876198092Srdivacky 6877198092Srdivacky if (!getDerived().AlwaysRebuild() && 6878212904Sdim TInfo == E->getWrittenTypeInfo() && 6879198092Srdivacky SubExpr.get() == E->getSubExpr()) 6880218893Sdim return SemaRef.Owned(E); 6881198092Srdivacky 6882212904Sdim return getDerived().RebuildVAArgExpr(E->getBuiltinLoc(), SubExpr.get(), 6883212904Sdim TInfo, E->getRParenLoc()); 6884198092Srdivacky} 6885198092Srdivacky 6886198092Srdivackytemplate<typename Derived> 6887212904SdimExprResult 6888200583SrdivackyTreeTransform<Derived>::TransformParenListExpr(ParenListExpr *E) { 6889198092Srdivacky bool ArgumentChanged = false; 6890243830Sdim SmallVector<Expr*, 4> Inits; 6891218893Sdim if (TransformExprs(E->getExprs(), E->getNumExprs(), true, Inits, 6892218893Sdim &ArgumentChanged)) 6893218893Sdim return ExprError(); 6894239462Sdim 6895198092Srdivacky return getDerived().RebuildParenListExpr(E->getLParenLoc(), 6896243830Sdim Inits, 6897198092Srdivacky E->getRParenLoc()); 6898198092Srdivacky} 6899198092Srdivacky 6900198092Srdivacky/// \brief Transform an address-of-label expression. 6901198092Srdivacky/// 6902198092Srdivacky/// By default, the transformation of an address-of-label expression always 6903198092Srdivacky/// rebuilds the expression, so that the label identifier can be resolved to 6904198092Srdivacky/// the corresponding label statement by semantic analysis. 6905198092Srdivackytemplate<typename Derived> 6906212904SdimExprResult 6907200583SrdivackyTreeTransform<Derived>::TransformAddrLabelExpr(AddrLabelExpr *E) { 6908218893Sdim Decl *LD = getDerived().TransformDecl(E->getLabel()->getLocation(), 6909218893Sdim E->getLabel()); 6910218893Sdim if (!LD) 6911218893Sdim return ExprError(); 6912239462Sdim 6913198092Srdivacky return getDerived().RebuildAddrLabelExpr(E->getAmpAmpLoc(), E->getLabelLoc(), 6914218893Sdim cast<LabelDecl>(LD)); 6915198092Srdivacky} 6916198092Srdivacky 6917198092Srdivackytemplate<typename Derived> 6918239462SdimExprResult 6919200583SrdivackyTreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) { 6920234353Sdim SemaRef.ActOnStartStmtExpr(); 6921212904Sdim StmtResult SubStmt 6922198092Srdivacky = getDerived().TransformCompoundStmt(E->getSubStmt(), true); 6923234353Sdim if (SubStmt.isInvalid()) { 6924234353Sdim SemaRef.ActOnStmtExprError(); 6925212904Sdim return ExprError(); 6926234353Sdim } 6927198092Srdivacky 6928198092Srdivacky if (!getDerived().AlwaysRebuild() && 6929234353Sdim SubStmt.get() == E->getSubStmt()) { 6930234353Sdim // Calling this an 'error' is unintuitive, but it does the right thing. 6931234353Sdim SemaRef.ActOnStmtExprError(); 6932234353Sdim return SemaRef.MaybeBindToTemporary(E); 6933234353Sdim } 6934198092Srdivacky 6935198092Srdivacky return getDerived().RebuildStmtExpr(E->getLParenLoc(), 6936212904Sdim SubStmt.get(), 6937198092Srdivacky E->getRParenLoc()); 6938198092Srdivacky} 6939198092Srdivacky 6940198092Srdivackytemplate<typename Derived> 6941212904SdimExprResult 6942200583SrdivackyTreeTransform<Derived>::TransformChooseExpr(ChooseExpr *E) { 6943212904Sdim ExprResult Cond = getDerived().TransformExpr(E->getCond()); 6944198092Srdivacky if (Cond.isInvalid()) 6945212904Sdim return ExprError(); 6946198092Srdivacky 6947212904Sdim ExprResult LHS = getDerived().TransformExpr(E->getLHS()); 6948198092Srdivacky if (LHS.isInvalid()) 6949212904Sdim return ExprError(); 6950198092Srdivacky 6951212904Sdim ExprResult RHS = getDerived().TransformExpr(E->getRHS()); 6952198092Srdivacky if (RHS.isInvalid()) 6953212904Sdim return ExprError(); 6954198092Srdivacky 6955198092Srdivacky if (!getDerived().AlwaysRebuild() && 6956198092Srdivacky Cond.get() == E->getCond() && 6957198092Srdivacky LHS.get() == E->getLHS() && 6958198092Srdivacky RHS.get() == E->getRHS()) 6959218893Sdim return SemaRef.Owned(E); 6960198092Srdivacky 6961198092Srdivacky return getDerived().RebuildChooseExpr(E->getBuiltinLoc(), 6962212904Sdim Cond.get(), LHS.get(), RHS.get(), 6963198092Srdivacky E->getRParenLoc()); 6964198092Srdivacky} 6965198092Srdivacky 6966198092Srdivackytemplate<typename Derived> 6967212904SdimExprResult 6968200583SrdivackyTreeTransform<Derived>::TransformGNUNullExpr(GNUNullExpr *E) { 6969218893Sdim return SemaRef.Owned(E); 6970198092Srdivacky} 6971198092Srdivacky 6972198092Srdivackytemplate<typename Derived> 6973212904SdimExprResult 6974200583SrdivackyTreeTransform<Derived>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr *E) { 6975200583Srdivacky switch (E->getOperator()) { 6976200583Srdivacky case OO_New: 6977200583Srdivacky case OO_Delete: 6978200583Srdivacky case OO_Array_New: 6979200583Srdivacky case OO_Array_Delete: 6980200583Srdivacky llvm_unreachable("new and delete operators cannot use CXXOperatorCallExpr"); 6981239462Sdim 6982200583Srdivacky case OO_Call: { 6983200583Srdivacky // This is a call to an object's operator(). 6984200583Srdivacky assert(E->getNumArgs() >= 1 && "Object call is missing arguments"); 6985200583Srdivacky 6986200583Srdivacky // Transform the object itself. 6987212904Sdim ExprResult Object = getDerived().TransformExpr(E->getArg(0)); 6988200583Srdivacky if (Object.isInvalid()) 6989212904Sdim return ExprError(); 6990200583Srdivacky 6991200583Srdivacky // FIXME: Poor location information 6992200583Srdivacky SourceLocation FakeLParenLoc 6993200583Srdivacky = SemaRef.PP.getLocForEndOfToken( 6994200583Srdivacky static_cast<Expr *>(Object.get())->getLocEnd()); 6995200583Srdivacky 6996200583Srdivacky // Transform the call arguments. 6997243830Sdim SmallVector<Expr*, 8> Args; 6998239462Sdim if (getDerived().TransformExprs(E->getArgs() + 1, E->getNumArgs() - 1, true, 6999218893Sdim Args)) 7000218893Sdim return ExprError(); 7001200583Srdivacky 7002212904Sdim return getDerived().RebuildCallExpr(Object.get(), FakeLParenLoc, 7003243830Sdim Args, 7004200583Srdivacky E->getLocEnd()); 7005200583Srdivacky } 7006200583Srdivacky 7007200583Srdivacky#define OVERLOADED_OPERATOR(Name,Spelling,Token,Unary,Binary,MemberOnly) \ 7008200583Srdivacky case OO_##Name: 7009200583Srdivacky#define OVERLOADED_OPERATOR_MULTI(Name,Spelling,Unary,Binary,MemberOnly) 7010200583Srdivacky#include "clang/Basic/OperatorKinds.def" 7011200583Srdivacky case OO_Subscript: 7012200583Srdivacky // Handled below. 7013200583Srdivacky break; 7014200583Srdivacky 7015200583Srdivacky case OO_Conditional: 7016200583Srdivacky llvm_unreachable("conditional operator is not actually overloadable"); 7017200583Srdivacky 7018200583Srdivacky case OO_None: 7019200583Srdivacky case NUM_OVERLOADED_OPERATORS: 7020200583Srdivacky llvm_unreachable("not an overloaded operator?"); 7021200583Srdivacky } 7022200583Srdivacky 7023212904Sdim ExprResult Callee = getDerived().TransformExpr(E->getCallee()); 7024198092Srdivacky if (Callee.isInvalid()) 7025212904Sdim return ExprError(); 7026198092Srdivacky 7027243830Sdim ExprResult First; 7028243830Sdim if (E->getOperator() == OO_Amp) 7029243830Sdim First = getDerived().TransformAddressOfOperand(E->getArg(0)); 7030243830Sdim else 7031243830Sdim First = getDerived().TransformExpr(E->getArg(0)); 7032198092Srdivacky if (First.isInvalid()) 7033212904Sdim return ExprError(); 7034198092Srdivacky 7035212904Sdim ExprResult Second; 7036198092Srdivacky if (E->getNumArgs() == 2) { 7037198092Srdivacky Second = getDerived().TransformExpr(E->getArg(1)); 7038198092Srdivacky if (Second.isInvalid()) 7039212904Sdim return ExprError(); 7040198092Srdivacky } 7041198092Srdivacky 7042198092Srdivacky if (!getDerived().AlwaysRebuild() && 7043198092Srdivacky Callee.get() == E->getCallee() && 7044198092Srdivacky First.get() == E->getArg(0) && 7045198092Srdivacky (E->getNumArgs() != 2 || Second.get() == E->getArg(1))) 7046234353Sdim return SemaRef.MaybeBindToTemporary(E); 7047198092Srdivacky 7048243830Sdim Sema::FPContractStateRAII FPContractState(getSema()); 7049243830Sdim getSema().FPFeatures.fp_contract = E->isFPContractable(); 7050243830Sdim 7051198092Srdivacky return getDerived().RebuildCXXOperatorCallExpr(E->getOperator(), 7052198092Srdivacky E->getOperatorLoc(), 7053212904Sdim Callee.get(), 7054212904Sdim First.get(), 7055212904Sdim Second.get()); 7056198092Srdivacky} 7057198092Srdivacky 7058198092Srdivackytemplate<typename Derived> 7059212904SdimExprResult 7060200583SrdivackyTreeTransform<Derived>::TransformCXXMemberCallExpr(CXXMemberCallExpr *E) { 7061200583Srdivacky return getDerived().TransformCallExpr(E); 7062198092Srdivacky} 7063198092Srdivacky 7064198092Srdivackytemplate<typename Derived> 7065212904SdimExprResult 7066218893SdimTreeTransform<Derived>::TransformCUDAKernelCallExpr(CUDAKernelCallExpr *E) { 7067218893Sdim // Transform the callee. 7068218893Sdim ExprResult Callee = getDerived().TransformExpr(E->getCallee()); 7069218893Sdim if (Callee.isInvalid()) 7070218893Sdim return ExprError(); 7071198092Srdivacky 7072218893Sdim // Transform exec config. 7073218893Sdim ExprResult EC = getDerived().TransformCallExpr(E->getConfig()); 7074218893Sdim if (EC.isInvalid()) 7075218893Sdim return ExprError(); 7076198092Srdivacky 7077218893Sdim // Transform arguments. 7078218893Sdim bool ArgChanged = false; 7079243830Sdim SmallVector<Expr*, 8> Args; 7080239462Sdim if (getDerived().TransformExprs(E->getArgs(), E->getNumArgs(), true, Args, 7081218893Sdim &ArgChanged)) 7082218893Sdim return ExprError(); 7083218893Sdim 7084218893Sdim if (!getDerived().AlwaysRebuild() && 7085218893Sdim Callee.get() == E->getCallee() && 7086218893Sdim !ArgChanged) 7087234353Sdim return SemaRef.MaybeBindToTemporary(E); 7088218893Sdim 7089218893Sdim // FIXME: Wrong source location information for the '('. 7090218893Sdim SourceLocation FakeLParenLoc 7091218893Sdim = ((Expr *)Callee.get())->getSourceRange().getBegin(); 7092218893Sdim return getDerived().RebuildCallExpr(Callee.get(), FakeLParenLoc, 7093243830Sdim Args, 7094218893Sdim E->getRParenLoc(), EC.get()); 7095218893Sdim} 7096218893Sdim 7097218893Sdimtemplate<typename Derived> 7098218893SdimExprResult 7099218893SdimTreeTransform<Derived>::TransformCXXNamedCastExpr(CXXNamedCastExpr *E) { 7100218893Sdim TypeSourceInfo *Type = getDerived().TransformType(E->getTypeInfoAsWritten()); 7101218893Sdim if (!Type) 7102218893Sdim return ExprError(); 7103239462Sdim 7104212904Sdim ExprResult SubExpr 7105200583Srdivacky = getDerived().TransformExpr(E->getSubExprAsWritten()); 7106198092Srdivacky if (SubExpr.isInvalid()) 7107212904Sdim return ExprError(); 7108198092Srdivacky 7109198092Srdivacky if (!getDerived().AlwaysRebuild() && 7110218893Sdim Type == E->getTypeInfoAsWritten() && 7111198092Srdivacky SubExpr.get() == E->getSubExpr()) 7112218893Sdim return SemaRef.Owned(E); 7113198092Srdivacky return getDerived().RebuildCXXNamedCastExpr(E->getOperatorLoc(), 7114198092Srdivacky E->getStmtClass(), 7115249423Sdim E->getAngleBrackets().getBegin(), 7116218893Sdim Type, 7117249423Sdim E->getAngleBrackets().getEnd(), 7118249423Sdim // FIXME. this should be '(' location 7119249423Sdim E->getAngleBrackets().getEnd(), 7120212904Sdim SubExpr.get(), 7121243830Sdim E->getRParenLoc()); 7122198092Srdivacky} 7123198092Srdivacky 7124198092Srdivackytemplate<typename Derived> 7125212904SdimExprResult 7126200583SrdivackyTreeTransform<Derived>::TransformCXXStaticCastExpr(CXXStaticCastExpr *E) { 7127200583Srdivacky return getDerived().TransformCXXNamedCastExpr(E); 7128198092Srdivacky} 7129198092Srdivacky 7130198092Srdivackytemplate<typename Derived> 7131212904SdimExprResult 7132200583SrdivackyTreeTransform<Derived>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr *E) { 7133200583Srdivacky return getDerived().TransformCXXNamedCastExpr(E); 7134198092Srdivacky} 7135198092Srdivacky 7136198092Srdivackytemplate<typename Derived> 7137212904SdimExprResult 7138198092SrdivackyTreeTransform<Derived>::TransformCXXReinterpretCastExpr( 7139200583Srdivacky CXXReinterpretCastExpr *E) { 7140200583Srdivacky return getDerived().TransformCXXNamedCastExpr(E); 7141198092Srdivacky} 7142198092Srdivacky 7143198092Srdivackytemplate<typename Derived> 7144212904SdimExprResult 7145200583SrdivackyTreeTransform<Derived>::TransformCXXConstCastExpr(CXXConstCastExpr *E) { 7146200583Srdivacky return getDerived().TransformCXXNamedCastExpr(E); 7147198092Srdivacky} 7148198092Srdivacky 7149198092Srdivackytemplate<typename Derived> 7150212904SdimExprResult 7151198092SrdivackyTreeTransform<Derived>::TransformCXXFunctionalCastExpr( 7152200583Srdivacky CXXFunctionalCastExpr *E) { 7153218893Sdim TypeSourceInfo *Type = getDerived().TransformType(E->getTypeInfoAsWritten()); 7154218893Sdim if (!Type) 7155218893Sdim return ExprError(); 7156198092Srdivacky 7157212904Sdim ExprResult SubExpr 7158200583Srdivacky = getDerived().TransformExpr(E->getSubExprAsWritten()); 7159198092Srdivacky if (SubExpr.isInvalid()) 7160212904Sdim return ExprError(); 7161198092Srdivacky 7162198092Srdivacky if (!getDerived().AlwaysRebuild() && 7163218893Sdim Type == E->getTypeInfoAsWritten() && 7164198092Srdivacky SubExpr.get() == E->getSubExpr()) 7165218893Sdim return SemaRef.Owned(E); 7166198092Srdivacky 7167218893Sdim return getDerived().RebuildCXXFunctionalCastExpr(Type, 7168198092Srdivacky /*FIXME:*/E->getSubExpr()->getLocStart(), 7169212904Sdim SubExpr.get(), 7170198092Srdivacky E->getRParenLoc()); 7171198092Srdivacky} 7172198092Srdivacky 7173198092Srdivackytemplate<typename Derived> 7174212904SdimExprResult 7175200583SrdivackyTreeTransform<Derived>::TransformCXXTypeidExpr(CXXTypeidExpr *E) { 7176198092Srdivacky if (E->isTypeOperand()) { 7177207619Srdivacky TypeSourceInfo *TInfo 7178207619Srdivacky = getDerived().TransformType(E->getTypeOperandSourceInfo()); 7179207619Srdivacky if (!TInfo) 7180212904Sdim return ExprError(); 7181198092Srdivacky 7182198092Srdivacky if (!getDerived().AlwaysRebuild() && 7183207619Srdivacky TInfo == E->getTypeOperandSourceInfo()) 7184218893Sdim return SemaRef.Owned(E); 7185198092Srdivacky 7186207619Srdivacky return getDerived().RebuildCXXTypeidExpr(E->getType(), 7187207619Srdivacky E->getLocStart(), 7188207619Srdivacky TInfo, 7189198092Srdivacky E->getLocEnd()); 7190198092Srdivacky } 7191198092Srdivacky 7192234353Sdim // We don't know whether the subexpression is potentially evaluated until 7193234353Sdim // after we perform semantic analysis. We speculatively assume it is 7194234353Sdim // unevaluated; it will get fixed later if the subexpression is in fact 7195198092Srdivacky // potentially evaluated. 7196243830Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated, 7197243830Sdim Sema::ReuseLambdaContextDecl); 7198198092Srdivacky 7199212904Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand()); 7200198092Srdivacky if (SubExpr.isInvalid()) 7201212904Sdim return ExprError(); 7202198092Srdivacky 7203198092Srdivacky if (!getDerived().AlwaysRebuild() && 7204198092Srdivacky SubExpr.get() == E->getExprOperand()) 7205218893Sdim return SemaRef.Owned(E); 7206198092Srdivacky 7207207619Srdivacky return getDerived().RebuildCXXTypeidExpr(E->getType(), 7208207619Srdivacky E->getLocStart(), 7209212904Sdim SubExpr.get(), 7210198092Srdivacky E->getLocEnd()); 7211198092Srdivacky} 7212198092Srdivacky 7213198092Srdivackytemplate<typename Derived> 7214212904SdimExprResult 7215218893SdimTreeTransform<Derived>::TransformCXXUuidofExpr(CXXUuidofExpr *E) { 7216218893Sdim if (E->isTypeOperand()) { 7217218893Sdim TypeSourceInfo *TInfo 7218218893Sdim = getDerived().TransformType(E->getTypeOperandSourceInfo()); 7219218893Sdim if (!TInfo) 7220218893Sdim return ExprError(); 7221218893Sdim 7222218893Sdim if (!getDerived().AlwaysRebuild() && 7223218893Sdim TInfo == E->getTypeOperandSourceInfo()) 7224218893Sdim return SemaRef.Owned(E); 7225218893Sdim 7226221345Sdim return getDerived().RebuildCXXUuidofExpr(E->getType(), 7227218893Sdim E->getLocStart(), 7228218893Sdim TInfo, 7229218893Sdim E->getLocEnd()); 7230218893Sdim } 7231218893Sdim 7232218893Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); 7233218893Sdim 7234218893Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getExprOperand()); 7235218893Sdim if (SubExpr.isInvalid()) 7236218893Sdim return ExprError(); 7237218893Sdim 7238218893Sdim if (!getDerived().AlwaysRebuild() && 7239218893Sdim SubExpr.get() == E->getExprOperand()) 7240218893Sdim return SemaRef.Owned(E); 7241218893Sdim 7242218893Sdim return getDerived().RebuildCXXUuidofExpr(E->getType(), 7243218893Sdim E->getLocStart(), 7244218893Sdim SubExpr.get(), 7245218893Sdim E->getLocEnd()); 7246218893Sdim} 7247218893Sdim 7248218893Sdimtemplate<typename Derived> 7249218893SdimExprResult 7250200583SrdivackyTreeTransform<Derived>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr *E) { 7251218893Sdim return SemaRef.Owned(E); 7252198092Srdivacky} 7253198092Srdivacky 7254198092Srdivackytemplate<typename Derived> 7255212904SdimExprResult 7256198092SrdivackyTreeTransform<Derived>::TransformCXXNullPtrLiteralExpr( 7257200583Srdivacky CXXNullPtrLiteralExpr *E) { 7258218893Sdim return SemaRef.Owned(E); 7259198092Srdivacky} 7260198092Srdivacky 7261198092Srdivackytemplate<typename Derived> 7262212904SdimExprResult 7263200583SrdivackyTreeTransform<Derived>::TransformCXXThisExpr(CXXThisExpr *E) { 7264218893Sdim DeclContext *DC = getSema().getFunctionLevelDeclContext(); 7265223017Sdim QualType T; 7266223017Sdim if (CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(DC)) 7267223017Sdim T = MD->getThisType(getSema().Context); 7268249423Sdim else if (CXXRecordDecl *Record = dyn_cast<CXXRecordDecl>(DC)) { 7269223017Sdim T = getSema().Context.getPointerType( 7270249423Sdim getSema().Context.getRecordType(Record)); 7271249423Sdim } else { 7272249423Sdim assert(SemaRef.Context.getDiagnostics().hasErrorOccurred() && 7273249423Sdim "this in the wrong scope?"); 7274249423Sdim return ExprError(); 7275249423Sdim } 7276198092Srdivacky 7277234353Sdim if (!getDerived().AlwaysRebuild() && T == E->getType()) { 7278234353Sdim // Make sure that we capture 'this'. 7279234353Sdim getSema().CheckCXXThisCapture(E->getLocStart()); 7280218893Sdim return SemaRef.Owned(E); 7281234353Sdim } 7282239462Sdim 7283202379Srdivacky return getDerived().RebuildCXXThisExpr(E->getLocStart(), T, E->isImplicit()); 7284198092Srdivacky} 7285198092Srdivacky 7286198092Srdivackytemplate<typename Derived> 7287212904SdimExprResult 7288200583SrdivackyTreeTransform<Derived>::TransformCXXThrowExpr(CXXThrowExpr *E) { 7289212904Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 7290198092Srdivacky if (SubExpr.isInvalid()) 7291212904Sdim return ExprError(); 7292198092Srdivacky 7293198092Srdivacky if (!getDerived().AlwaysRebuild() && 7294198092Srdivacky SubExpr.get() == E->getSubExpr()) 7295218893Sdim return SemaRef.Owned(E); 7296198092Srdivacky 7297224145Sdim return getDerived().RebuildCXXThrowExpr(E->getThrowLoc(), SubExpr.get(), 7298224145Sdim E->isThrownVariableInScope()); 7299198092Srdivacky} 7300198092Srdivacky 7301198092Srdivackytemplate<typename Derived> 7302212904SdimExprResult 7303200583SrdivackyTreeTransform<Derived>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E) { 7304198092Srdivacky ParmVarDecl *Param 7305204643Srdivacky = cast_or_null<ParmVarDecl>(getDerived().TransformDecl(E->getLocStart(), 7306204643Srdivacky E->getParam())); 7307198092Srdivacky if (!Param) 7308212904Sdim return ExprError(); 7309198092Srdivacky 7310203955Srdivacky if (!getDerived().AlwaysRebuild() && 7311198092Srdivacky Param == E->getParam()) 7312218893Sdim return SemaRef.Owned(E); 7313198092Srdivacky 7314201361Srdivacky return getDerived().RebuildCXXDefaultArgExpr(E->getUsedLocation(), Param); 7315198092Srdivacky} 7316198092Srdivacky 7317198092Srdivackytemplate<typename Derived> 7318212904SdimExprResult 7319251662SdimTreeTransform<Derived>::TransformCXXDefaultInitExpr(CXXDefaultInitExpr *E) { 7320251662Sdim FieldDecl *Field 7321251662Sdim = cast_or_null<FieldDecl>(getDerived().TransformDecl(E->getLocStart(), 7322251662Sdim E->getField())); 7323251662Sdim if (!Field) 7324251662Sdim return ExprError(); 7325251662Sdim 7326251662Sdim if (!getDerived().AlwaysRebuild() && Field == E->getField()) 7327251662Sdim return SemaRef.Owned(E); 7328251662Sdim 7329251662Sdim return getDerived().RebuildCXXDefaultInitExpr(E->getExprLoc(), Field); 7330251662Sdim} 7331251662Sdim 7332251662Sdimtemplate<typename Derived> 7333251662SdimExprResult 7334218893SdimTreeTransform<Derived>::TransformCXXScalarValueInitExpr( 7335218893Sdim CXXScalarValueInitExpr *E) { 7336218893Sdim TypeSourceInfo *T = getDerived().TransformType(E->getTypeSourceInfo()); 7337218893Sdim if (!T) 7338212904Sdim return ExprError(); 7339239462Sdim 7340198092Srdivacky if (!getDerived().AlwaysRebuild() && 7341218893Sdim T == E->getTypeSourceInfo()) 7342218893Sdim return SemaRef.Owned(E); 7343198092Srdivacky 7344239462Sdim return getDerived().RebuildCXXScalarValueInitExpr(T, 7345218893Sdim /*FIXME:*/T->getTypeLoc().getEndLoc(), 7346210299Sed E->getRParenLoc()); 7347198092Srdivacky} 7348198092Srdivacky 7349198092Srdivackytemplate<typename Derived> 7350212904SdimExprResult 7351200583SrdivackyTreeTransform<Derived>::TransformCXXNewExpr(CXXNewExpr *E) { 7352198092Srdivacky // Transform the type that we're allocating 7353218893Sdim TypeSourceInfo *AllocTypeInfo 7354218893Sdim = getDerived().TransformType(E->getAllocatedTypeSourceInfo()); 7355218893Sdim if (!AllocTypeInfo) 7356212904Sdim return ExprError(); 7357198092Srdivacky 7358198092Srdivacky // Transform the size of the array we're allocating (if any). 7359212904Sdim ExprResult ArraySize = getDerived().TransformExpr(E->getArraySize()); 7360198092Srdivacky if (ArraySize.isInvalid()) 7361212904Sdim return ExprError(); 7362198092Srdivacky 7363198092Srdivacky // Transform the placement arguments (if any). 7364198092Srdivacky bool ArgumentChanged = false; 7365243830Sdim SmallVector<Expr*, 8> PlacementArgs; 7366239462Sdim if (getDerived().TransformExprs(E->getPlacementArgs(), 7367218893Sdim E->getNumPlacementArgs(), true, 7368218893Sdim PlacementArgs, &ArgumentChanged)) 7369234353Sdim return ExprError(); 7370198092Srdivacky 7371234353Sdim // Transform the initializer (if any). 7372234353Sdim Expr *OldInit = E->getInitializer(); 7373234353Sdim ExprResult NewInit; 7374234353Sdim if (OldInit) 7375234353Sdim NewInit = getDerived().TransformExpr(OldInit); 7376234353Sdim if (NewInit.isInvalid()) 7377234353Sdim return ExprError(); 7378198092Srdivacky 7379234353Sdim // Transform new operator and delete operator. 7380204643Srdivacky FunctionDecl *OperatorNew = 0; 7381204643Srdivacky if (E->getOperatorNew()) { 7382204643Srdivacky OperatorNew = cast_or_null<FunctionDecl>( 7383204643Srdivacky getDerived().TransformDecl(E->getLocStart(), 7384204643Srdivacky E->getOperatorNew())); 7385204643Srdivacky if (!OperatorNew) 7386212904Sdim return ExprError(); 7387204643Srdivacky } 7388204643Srdivacky 7389204643Srdivacky FunctionDecl *OperatorDelete = 0; 7390204643Srdivacky if (E->getOperatorDelete()) { 7391204643Srdivacky OperatorDelete = cast_or_null<FunctionDecl>( 7392204643Srdivacky getDerived().TransformDecl(E->getLocStart(), 7393204643Srdivacky E->getOperatorDelete())); 7394204643Srdivacky if (!OperatorDelete) 7395212904Sdim return ExprError(); 7396204643Srdivacky } 7397239462Sdim 7398198092Srdivacky if (!getDerived().AlwaysRebuild() && 7399218893Sdim AllocTypeInfo == E->getAllocatedTypeSourceInfo() && 7400198092Srdivacky ArraySize.get() == E->getArraySize() && 7401234353Sdim NewInit.get() == OldInit && 7402204643Srdivacky OperatorNew == E->getOperatorNew() && 7403204643Srdivacky OperatorDelete == E->getOperatorDelete() && 7404204643Srdivacky !ArgumentChanged) { 7405204643Srdivacky // Mark any declarations we need as referenced. 7406204643Srdivacky // FIXME: instantiation-specific. 7407204643Srdivacky if (OperatorNew) 7408234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), OperatorNew); 7409204643Srdivacky if (OperatorDelete) 7410234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), OperatorDelete); 7411239462Sdim 7412234353Sdim if (E->isArray() && !E->getAllocatedType()->isDependentType()) { 7413226633Sdim QualType ElementType 7414226633Sdim = SemaRef.Context.getBaseElementType(E->getAllocatedType()); 7415226633Sdim if (const RecordType *RecordT = ElementType->getAs<RecordType>()) { 7416226633Sdim CXXRecordDecl *Record = cast<CXXRecordDecl>(RecordT->getDecl()); 7417226633Sdim if (CXXDestructorDecl *Destructor = SemaRef.LookupDestructor(Record)) { 7418234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), Destructor); 7419226633Sdim } 7420226633Sdim } 7421226633Sdim } 7422234353Sdim 7423218893Sdim return SemaRef.Owned(E); 7424204643Srdivacky } 7425198092Srdivacky 7426218893Sdim QualType AllocType = AllocTypeInfo->getType(); 7427201361Srdivacky if (!ArraySize.get()) { 7428201361Srdivacky // If no array size was specified, but the new expression was 7429201361Srdivacky // instantiated with an array type (e.g., "new T" where T is 7430201361Srdivacky // instantiated with "int[4]"), extract the outer bound from the 7431201361Srdivacky // array type as our array size. We do this with constant and 7432201361Srdivacky // dependently-sized array types. 7433201361Srdivacky const ArrayType *ArrayT = SemaRef.Context.getAsArrayType(AllocType); 7434201361Srdivacky if (!ArrayT) { 7435201361Srdivacky // Do nothing 7436201361Srdivacky } else if (const ConstantArrayType *ConsArrayT 7437201361Srdivacky = dyn_cast<ConstantArrayType>(ArrayT)) { 7438239462Sdim ArraySize 7439212904Sdim = SemaRef.Owned(IntegerLiteral::Create(SemaRef.Context, 7440239462Sdim ConsArrayT->getSize(), 7441212904Sdim SemaRef.Context.getSizeType(), 7442212904Sdim /*FIXME:*/E->getLocStart())); 7443201361Srdivacky AllocType = ConsArrayT->getElementType(); 7444201361Srdivacky } else if (const DependentSizedArrayType *DepArrayT 7445201361Srdivacky = dyn_cast<DependentSizedArrayType>(ArrayT)) { 7446201361Srdivacky if (DepArrayT->getSizeExpr()) { 7447218893Sdim ArraySize = SemaRef.Owned(DepArrayT->getSizeExpr()); 7448201361Srdivacky AllocType = DepArrayT->getElementType(); 7449201361Srdivacky } 7450201361Srdivacky } 7451201361Srdivacky } 7452234353Sdim 7453198092Srdivacky return getDerived().RebuildCXXNewExpr(E->getLocStart(), 7454198092Srdivacky E->isGlobalNew(), 7455198092Srdivacky /*FIXME:*/E->getLocStart(), 7456243830Sdim PlacementArgs, 7457198092Srdivacky /*FIXME:*/E->getLocStart(), 7458210299Sed E->getTypeIdParens(), 7459198092Srdivacky AllocType, 7460218893Sdim AllocTypeInfo, 7461212904Sdim ArraySize.get(), 7462234353Sdim E->getDirectInitRange(), 7463234353Sdim NewInit.take()); 7464198092Srdivacky} 7465198092Srdivacky 7466198092Srdivackytemplate<typename Derived> 7467212904SdimExprResult 7468200583SrdivackyTreeTransform<Derived>::TransformCXXDeleteExpr(CXXDeleteExpr *E) { 7469212904Sdim ExprResult Operand = getDerived().TransformExpr(E->getArgument()); 7470198092Srdivacky if (Operand.isInvalid()) 7471212904Sdim return ExprError(); 7472198092Srdivacky 7473204643Srdivacky // Transform the delete operator, if known. 7474204643Srdivacky FunctionDecl *OperatorDelete = 0; 7475204643Srdivacky if (E->getOperatorDelete()) { 7476204643Srdivacky OperatorDelete = cast_or_null<FunctionDecl>( 7477204643Srdivacky getDerived().TransformDecl(E->getLocStart(), 7478204643Srdivacky E->getOperatorDelete())); 7479204643Srdivacky if (!OperatorDelete) 7480212904Sdim return ExprError(); 7481204643Srdivacky } 7482239462Sdim 7483198092Srdivacky if (!getDerived().AlwaysRebuild() && 7484204643Srdivacky Operand.get() == E->getArgument() && 7485204643Srdivacky OperatorDelete == E->getOperatorDelete()) { 7486204643Srdivacky // Mark any declarations we need as referenced. 7487204643Srdivacky // FIXME: instantiation-specific. 7488204643Srdivacky if (OperatorDelete) 7489234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), OperatorDelete); 7490239462Sdim 7491218893Sdim if (!E->getArgument()->isTypeDependent()) { 7492218893Sdim QualType Destroyed = SemaRef.Context.getBaseElementType( 7493218893Sdim E->getDestroyedType()); 7494218893Sdim if (const RecordType *DestroyedRec = Destroyed->getAs<RecordType>()) { 7495218893Sdim CXXRecordDecl *Record = cast<CXXRecordDecl>(DestroyedRec->getDecl()); 7496239462Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), 7497234353Sdim SemaRef.LookupDestructor(Record)); 7498218893Sdim } 7499218893Sdim } 7500239462Sdim 7501218893Sdim return SemaRef.Owned(E); 7502204643Srdivacky } 7503198092Srdivacky 7504198092Srdivacky return getDerived().RebuildCXXDeleteExpr(E->getLocStart(), 7505198092Srdivacky E->isGlobalDelete(), 7506198092Srdivacky E->isArrayForm(), 7507212904Sdim Operand.get()); 7508198092Srdivacky} 7509198092Srdivacky 7510198092Srdivackytemplate<typename Derived> 7511212904SdimExprResult 7512198092SrdivackyTreeTransform<Derived>::TransformCXXPseudoDestructorExpr( 7513200583Srdivacky CXXPseudoDestructorExpr *E) { 7514212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 7515198092Srdivacky if (Base.isInvalid()) 7516212904Sdim return ExprError(); 7517198092Srdivacky 7518212904Sdim ParsedType ObjectTypePtr; 7519204643Srdivacky bool MayBePseudoDestructor = false; 7520239462Sdim Base = SemaRef.ActOnStartCXXMemberReference(0, Base.get(), 7521204643Srdivacky E->getOperatorLoc(), 7522204643Srdivacky E->isArrow()? tok::arrow : tok::period, 7523204643Srdivacky ObjectTypePtr, 7524204643Srdivacky MayBePseudoDestructor); 7525204643Srdivacky if (Base.isInvalid()) 7526212904Sdim return ExprError(); 7527239462Sdim 7528212904Sdim QualType ObjectType = ObjectTypePtr.get(); 7529219077Sdim NestedNameSpecifierLoc QualifierLoc = E->getQualifierLoc(); 7530219077Sdim if (QualifierLoc) { 7531219077Sdim QualifierLoc 7532219077Sdim = getDerived().TransformNestedNameSpecifierLoc(QualifierLoc, ObjectType); 7533219077Sdim if (!QualifierLoc) 7534218893Sdim return ExprError(); 7535218893Sdim } 7536219077Sdim CXXScopeSpec SS; 7537219077Sdim SS.Adopt(QualifierLoc); 7538198092Srdivacky 7539204643Srdivacky PseudoDestructorTypeStorage Destroyed; 7540204643Srdivacky if (E->getDestroyedTypeInfo()) { 7541204643Srdivacky TypeSourceInfo *DestroyedTypeInfo 7542218893Sdim = getDerived().TransformTypeInObjectScope(E->getDestroyedTypeInfo(), 7543221345Sdim ObjectType, 0, SS); 7544204643Srdivacky if (!DestroyedTypeInfo) 7545212904Sdim return ExprError(); 7546204643Srdivacky Destroyed = DestroyedTypeInfo; 7547234353Sdim } else if (!ObjectType.isNull() && ObjectType->isDependentType()) { 7548204643Srdivacky // We aren't likely to be able to resolve the identifier down to a type 7549204643Srdivacky // now anyway, so just retain the identifier. 7550204643Srdivacky Destroyed = PseudoDestructorTypeStorage(E->getDestroyedTypeIdentifier(), 7551204643Srdivacky E->getDestroyedTypeLoc()); 7552204643Srdivacky } else { 7553204643Srdivacky // Look for a destructor known with the given name. 7554212904Sdim ParsedType T = SemaRef.getDestructorName(E->getTildeLoc(), 7555204643Srdivacky *E->getDestroyedTypeIdentifier(), 7556204643Srdivacky E->getDestroyedTypeLoc(), 7557204643Srdivacky /*Scope=*/0, 7558204643Srdivacky SS, ObjectTypePtr, 7559204643Srdivacky false); 7560204643Srdivacky if (!T) 7561212904Sdim return ExprError(); 7562239462Sdim 7563204643Srdivacky Destroyed 7564204643Srdivacky = SemaRef.Context.getTrivialTypeSourceInfo(SemaRef.GetTypeFromParser(T), 7565204643Srdivacky E->getDestroyedTypeLoc()); 7566198092Srdivacky } 7567198092Srdivacky 7568204643Srdivacky TypeSourceInfo *ScopeTypeInfo = 0; 7569204643Srdivacky if (E->getScopeTypeInfo()) { 7570249423Sdim CXXScopeSpec EmptySS; 7571249423Sdim ScopeTypeInfo = getDerived().TransformTypeInObjectScope( 7572249423Sdim E->getScopeTypeInfo(), ObjectType, 0, EmptySS); 7573204643Srdivacky if (!ScopeTypeInfo) 7574212904Sdim return ExprError(); 7575204643Srdivacky } 7576239462Sdim 7577212904Sdim return getDerived().RebuildCXXPseudoDestructorExpr(Base.get(), 7578198092Srdivacky E->getOperatorLoc(), 7579198092Srdivacky E->isArrow(), 7580219077Sdim SS, 7581204643Srdivacky ScopeTypeInfo, 7582204643Srdivacky E->getColonColonLoc(), 7583204643Srdivacky E->getTildeLoc(), 7584204643Srdivacky Destroyed); 7585198092Srdivacky} 7586198092Srdivacky 7587198092Srdivackytemplate<typename Derived> 7588212904SdimExprResult 7589199990SrdivackyTreeTransform<Derived>::TransformUnresolvedLookupExpr( 7590200583Srdivacky UnresolvedLookupExpr *Old) { 7591199990Srdivacky LookupResult R(SemaRef, Old->getName(), Old->getNameLoc(), 7592199990Srdivacky Sema::LookupOrdinaryName); 7593199990Srdivacky 7594199990Srdivacky // Transform all the decls. 7595199990Srdivacky for (UnresolvedLookupExpr::decls_iterator I = Old->decls_begin(), 7596199990Srdivacky E = Old->decls_end(); I != E; ++I) { 7597204643Srdivacky NamedDecl *InstD = static_cast<NamedDecl*>( 7598204643Srdivacky getDerived().TransformDecl(Old->getNameLoc(), 7599204643Srdivacky *I)); 7600200583Srdivacky if (!InstD) { 7601200583Srdivacky // Silently ignore these if a UsingShadowDecl instantiated to nothing. 7602200583Srdivacky // This can happen because of dependent hiding. 7603200583Srdivacky if (isa<UsingShadowDecl>(*I)) 7604200583Srdivacky continue; 7605200583Srdivacky else 7606212904Sdim return ExprError(); 7607200583Srdivacky } 7608199990Srdivacky 7609199990Srdivacky // Expand using declarations. 7610199990Srdivacky if (isa<UsingDecl>(InstD)) { 7611199990Srdivacky UsingDecl *UD = cast<UsingDecl>(InstD); 7612199990Srdivacky for (UsingDecl::shadow_iterator I = UD->shadow_begin(), 7613199990Srdivacky E = UD->shadow_end(); I != E; ++I) 7614199990Srdivacky R.addDecl(*I); 7615199990Srdivacky continue; 7616199990Srdivacky } 7617199990Srdivacky 7618199990Srdivacky R.addDecl(InstD); 7619199990Srdivacky } 7620199990Srdivacky 7621199990Srdivacky // Resolve a kind, but don't do any further analysis. If it's 7622199990Srdivacky // ambiguous, the callee needs to deal with it. 7623199990Srdivacky R.resolveKind(); 7624199990Srdivacky 7625199990Srdivacky // Rebuild the nested-name qualifier, if present. 7626199990Srdivacky CXXScopeSpec SS; 7627221345Sdim if (Old->getQualifierLoc()) { 7628221345Sdim NestedNameSpecifierLoc QualifierLoc 7629221345Sdim = getDerived().TransformNestedNameSpecifierLoc(Old->getQualifierLoc()); 7630221345Sdim if (!QualifierLoc) 7631212904Sdim return ExprError(); 7632239462Sdim 7633221345Sdim SS.Adopt(QualifierLoc); 7634239462Sdim } 7635239462Sdim 7636207619Srdivacky if (Old->getNamingClass()) { 7637207619Srdivacky CXXRecordDecl *NamingClass 7638207619Srdivacky = cast_or_null<CXXRecordDecl>(getDerived().TransformDecl( 7639207619Srdivacky Old->getNameLoc(), 7640207619Srdivacky Old->getNamingClass())); 7641207619Srdivacky if (!NamingClass) 7642212904Sdim return ExprError(); 7643239462Sdim 7644207619Srdivacky R.setNamingClass(NamingClass); 7645199990Srdivacky } 7646199990Srdivacky 7647234353Sdim SourceLocation TemplateKWLoc = Old->getTemplateKeywordLoc(); 7648234353Sdim 7649234353Sdim // If we have neither explicit template arguments, nor the template keyword, 7650234353Sdim // it's a normal declaration name. 7651234353Sdim if (!Old->hasExplicitTemplateArgs() && !TemplateKWLoc.isValid()) 7652199990Srdivacky return getDerived().RebuildDeclarationNameExpr(SS, R, Old->requiresADL()); 7653199990Srdivacky 7654199990Srdivacky // If we have template arguments, rebuild them, then rebuild the 7655199990Srdivacky // templateid expression. 7656199990Srdivacky TemplateArgumentListInfo TransArgs(Old->getLAngleLoc(), Old->getRAngleLoc()); 7657243830Sdim if (Old->hasExplicitTemplateArgs() && 7658243830Sdim getDerived().TransformTemplateArguments(Old->getTemplateArgs(), 7659218893Sdim Old->getNumTemplateArgs(), 7660218893Sdim TransArgs)) 7661218893Sdim return ExprError(); 7662199990Srdivacky 7663234353Sdim return getDerived().RebuildTemplateIdExpr(SS, TemplateKWLoc, R, 7664234353Sdim Old->requiresADL(), &TransArgs); 7665198092Srdivacky} 7666198092Srdivacky 7667198092Srdivackytemplate<typename Derived> 7668212904SdimExprResult 7669200583SrdivackyTreeTransform<Derived>::TransformUnaryTypeTraitExpr(UnaryTypeTraitExpr *E) { 7670218893Sdim TypeSourceInfo *T = getDerived().TransformType(E->getQueriedTypeSourceInfo()); 7671218893Sdim if (!T) 7672212904Sdim return ExprError(); 7673198092Srdivacky 7674198092Srdivacky if (!getDerived().AlwaysRebuild() && 7675218893Sdim T == E->getQueriedTypeSourceInfo()) 7676218893Sdim return SemaRef.Owned(E); 7677198092Srdivacky 7678198092Srdivacky return getDerived().RebuildUnaryTypeTrait(E->getTrait(), 7679198092Srdivacky E->getLocStart(), 7680198092Srdivacky T, 7681198092Srdivacky E->getLocEnd()); 7682198092Srdivacky} 7683198092Srdivacky 7684198092Srdivackytemplate<typename Derived> 7685212904SdimExprResult 7686218893SdimTreeTransform<Derived>::TransformBinaryTypeTraitExpr(BinaryTypeTraitExpr *E) { 7687218893Sdim TypeSourceInfo *LhsT = getDerived().TransformType(E->getLhsTypeSourceInfo()); 7688218893Sdim if (!LhsT) 7689218893Sdim return ExprError(); 7690218893Sdim 7691218893Sdim TypeSourceInfo *RhsT = getDerived().TransformType(E->getRhsTypeSourceInfo()); 7692218893Sdim if (!RhsT) 7693218893Sdim return ExprError(); 7694218893Sdim 7695218893Sdim if (!getDerived().AlwaysRebuild() && 7696218893Sdim LhsT == E->getLhsTypeSourceInfo() && RhsT == E->getRhsTypeSourceInfo()) 7697218893Sdim return SemaRef.Owned(E); 7698218893Sdim 7699218893Sdim return getDerived().RebuildBinaryTypeTrait(E->getTrait(), 7700218893Sdim E->getLocStart(), 7701218893Sdim LhsT, RhsT, 7702218893Sdim E->getLocEnd()); 7703218893Sdim} 7704218893Sdim 7705218893Sdimtemplate<typename Derived> 7706218893SdimExprResult 7707234353SdimTreeTransform<Derived>::TransformTypeTraitExpr(TypeTraitExpr *E) { 7708234353Sdim bool ArgChanged = false; 7709249423Sdim SmallVector<TypeSourceInfo *, 4> Args; 7710234353Sdim for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I) { 7711234353Sdim TypeSourceInfo *From = E->getArg(I); 7712234353Sdim TypeLoc FromTL = From->getTypeLoc(); 7713249423Sdim if (!FromTL.getAs<PackExpansionTypeLoc>()) { 7714234353Sdim TypeLocBuilder TLB; 7715234353Sdim TLB.reserve(FromTL.getFullDataSize()); 7716234353Sdim QualType To = getDerived().TransformType(TLB, FromTL); 7717234353Sdim if (To.isNull()) 7718234353Sdim return ExprError(); 7719239462Sdim 7720234353Sdim if (To == From->getType()) 7721234353Sdim Args.push_back(From); 7722234353Sdim else { 7723234353Sdim Args.push_back(TLB.getTypeSourceInfo(SemaRef.Context, To)); 7724234353Sdim ArgChanged = true; 7725234353Sdim } 7726234353Sdim continue; 7727234353Sdim } 7728239462Sdim 7729234353Sdim ArgChanged = true; 7730239462Sdim 7731234353Sdim // We have a pack expansion. Instantiate it. 7732249423Sdim PackExpansionTypeLoc ExpansionTL = FromTL.castAs<PackExpansionTypeLoc>(); 7733234353Sdim TypeLoc PatternTL = ExpansionTL.getPatternLoc(); 7734234353Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 7735234353Sdim SemaRef.collectUnexpandedParameterPacks(PatternTL, Unexpanded); 7736239462Sdim 7737234353Sdim // Determine whether the set of unexpanded parameter packs can and should 7738234353Sdim // be expanded. 7739234353Sdim bool Expand = true; 7740234353Sdim bool RetainExpansion = false; 7741249423Sdim Optional<unsigned> OrigNumExpansions = 7742249423Sdim ExpansionTL.getTypePtr()->getNumExpansions(); 7743249423Sdim Optional<unsigned> NumExpansions = OrigNumExpansions; 7744234353Sdim if (getDerived().TryExpandParameterPacks(ExpansionTL.getEllipsisLoc(), 7745234353Sdim PatternTL.getSourceRange(), 7746234353Sdim Unexpanded, 7747234353Sdim Expand, RetainExpansion, 7748234353Sdim NumExpansions)) 7749234353Sdim return ExprError(); 7750239462Sdim 7751234353Sdim if (!Expand) { 7752234353Sdim // The transform has determined that we should perform a simple 7753239462Sdim // transformation on the pack expansion, producing another pack 7754234353Sdim // expansion. 7755234353Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 7756239462Sdim 7757234353Sdim TypeLocBuilder TLB; 7758234353Sdim TLB.reserve(From->getTypeLoc().getFullDataSize()); 7759234353Sdim 7760234353Sdim QualType To = getDerived().TransformType(TLB, PatternTL); 7761234353Sdim if (To.isNull()) 7762234353Sdim return ExprError(); 7763234353Sdim 7764239462Sdim To = getDerived().RebuildPackExpansionType(To, 7765234353Sdim PatternTL.getSourceRange(), 7766234353Sdim ExpansionTL.getEllipsisLoc(), 7767234353Sdim NumExpansions); 7768234353Sdim if (To.isNull()) 7769234353Sdim return ExprError(); 7770239462Sdim 7771234353Sdim PackExpansionTypeLoc ToExpansionTL 7772234353Sdim = TLB.push<PackExpansionTypeLoc>(To); 7773234353Sdim ToExpansionTL.setEllipsisLoc(ExpansionTL.getEllipsisLoc()); 7774234353Sdim Args.push_back(TLB.getTypeSourceInfo(SemaRef.Context, To)); 7775234353Sdim continue; 7776234353Sdim } 7777234353Sdim 7778234353Sdim // Expand the pack expansion by substituting for each argument in the 7779234353Sdim // pack(s). 7780234353Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 7781234353Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(SemaRef, I); 7782234353Sdim TypeLocBuilder TLB; 7783234353Sdim TLB.reserve(PatternTL.getFullDataSize()); 7784234353Sdim QualType To = getDerived().TransformType(TLB, PatternTL); 7785234353Sdim if (To.isNull()) 7786234353Sdim return ExprError(); 7787234353Sdim 7788234353Sdim Args.push_back(TLB.getTypeSourceInfo(SemaRef.Context, To)); 7789234353Sdim } 7790239462Sdim 7791234353Sdim if (!RetainExpansion) 7792234353Sdim continue; 7793239462Sdim 7794234353Sdim // If we're supposed to retain a pack expansion, do so by temporarily 7795234353Sdim // forgetting the partially-substituted parameter pack. 7796234353Sdim ForgetPartiallySubstitutedPackRAII Forget(getDerived()); 7797234353Sdim 7798234353Sdim TypeLocBuilder TLB; 7799234353Sdim TLB.reserve(From->getTypeLoc().getFullDataSize()); 7800239462Sdim 7801234353Sdim QualType To = getDerived().TransformType(TLB, PatternTL); 7802234353Sdim if (To.isNull()) 7803234353Sdim return ExprError(); 7804239462Sdim 7805239462Sdim To = getDerived().RebuildPackExpansionType(To, 7806234353Sdim PatternTL.getSourceRange(), 7807234353Sdim ExpansionTL.getEllipsisLoc(), 7808234353Sdim NumExpansions); 7809234353Sdim if (To.isNull()) 7810234353Sdim return ExprError(); 7811239462Sdim 7812234353Sdim PackExpansionTypeLoc ToExpansionTL 7813234353Sdim = TLB.push<PackExpansionTypeLoc>(To); 7814234353Sdim ToExpansionTL.setEllipsisLoc(ExpansionTL.getEllipsisLoc()); 7815234353Sdim Args.push_back(TLB.getTypeSourceInfo(SemaRef.Context, To)); 7816234353Sdim } 7817239462Sdim 7818234353Sdim if (!getDerived().AlwaysRebuild() && !ArgChanged) 7819234353Sdim return SemaRef.Owned(E); 7820234353Sdim 7821234353Sdim return getDerived().RebuildTypeTrait(E->getTrait(), 7822234353Sdim E->getLocStart(), 7823234353Sdim Args, 7824234353Sdim E->getLocEnd()); 7825234353Sdim} 7826234353Sdim 7827234353Sdimtemplate<typename Derived> 7828234353SdimExprResult 7829221345SdimTreeTransform<Derived>::TransformArrayTypeTraitExpr(ArrayTypeTraitExpr *E) { 7830221345Sdim TypeSourceInfo *T = getDerived().TransformType(E->getQueriedTypeSourceInfo()); 7831221345Sdim if (!T) 7832221345Sdim return ExprError(); 7833221345Sdim 7834221345Sdim if (!getDerived().AlwaysRebuild() && 7835221345Sdim T == E->getQueriedTypeSourceInfo()) 7836221345Sdim return SemaRef.Owned(E); 7837221345Sdim 7838221345Sdim ExprResult SubExpr; 7839221345Sdim { 7840221345Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); 7841221345Sdim SubExpr = getDerived().TransformExpr(E->getDimensionExpression()); 7842221345Sdim if (SubExpr.isInvalid()) 7843221345Sdim return ExprError(); 7844221345Sdim 7845221345Sdim if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getDimensionExpression()) 7846221345Sdim return SemaRef.Owned(E); 7847221345Sdim } 7848221345Sdim 7849221345Sdim return getDerived().RebuildArrayTypeTrait(E->getTrait(), 7850221345Sdim E->getLocStart(), 7851221345Sdim T, 7852221345Sdim SubExpr.get(), 7853221345Sdim E->getLocEnd()); 7854221345Sdim} 7855221345Sdim 7856221345Sdimtemplate<typename Derived> 7857221345SdimExprResult 7858221345SdimTreeTransform<Derived>::TransformExpressionTraitExpr(ExpressionTraitExpr *E) { 7859221345Sdim ExprResult SubExpr; 7860221345Sdim { 7861221345Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); 7862221345Sdim SubExpr = getDerived().TransformExpr(E->getQueriedExpression()); 7863221345Sdim if (SubExpr.isInvalid()) 7864221345Sdim return ExprError(); 7865221345Sdim 7866221345Sdim if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getQueriedExpression()) 7867221345Sdim return SemaRef.Owned(E); 7868221345Sdim } 7869221345Sdim 7870221345Sdim return getDerived().RebuildExpressionTrait( 7871221345Sdim E->getTrait(), E->getLocStart(), SubExpr.get(), E->getLocEnd()); 7872221345Sdim} 7873221345Sdim 7874221345Sdimtemplate<typename Derived> 7875221345SdimExprResult 7876199990SrdivackyTreeTransform<Derived>::TransformDependentScopeDeclRefExpr( 7877212904Sdim DependentScopeDeclRefExpr *E) { 7878243830Sdim return TransformDependentScopeDeclRefExpr(E, /*IsAddressOfOperand*/false); 7879243830Sdim} 7880243830Sdim 7881243830Sdimtemplate<typename Derived> 7882243830SdimExprResult 7883243830SdimTreeTransform<Derived>::TransformDependentScopeDeclRefExpr( 7884243830Sdim DependentScopeDeclRefExpr *E, 7885243830Sdim bool IsAddressOfOperand) { 7886219077Sdim NestedNameSpecifierLoc QualifierLoc 7887219077Sdim = getDerived().TransformNestedNameSpecifierLoc(E->getQualifierLoc()); 7888219077Sdim if (!QualifierLoc) 7889212904Sdim return ExprError(); 7890234353Sdim SourceLocation TemplateKWLoc = E->getTemplateKeywordLoc(); 7891198092Srdivacky 7892218893Sdim // TODO: If this is a conversion-function-id, verify that the 7893218893Sdim // destination type name (if present) resolves the same way after 7894218893Sdim // instantiation as it did in the local scope. 7895218893Sdim 7896212904Sdim DeclarationNameInfo NameInfo 7897212904Sdim = getDerived().TransformDeclarationNameInfo(E->getNameInfo()); 7898212904Sdim if (!NameInfo.getName()) 7899212904Sdim return ExprError(); 7900198092Srdivacky 7901199990Srdivacky if (!E->hasExplicitTemplateArgs()) { 7902199990Srdivacky if (!getDerived().AlwaysRebuild() && 7903219077Sdim QualifierLoc == E->getQualifierLoc() && 7904212904Sdim // Note: it is sufficient to compare the Name component of NameInfo: 7905212904Sdim // if name has not changed, DNLoc has not changed either. 7906212904Sdim NameInfo.getName() == E->getDeclName()) 7907218893Sdim return SemaRef.Owned(E); 7908198092Srdivacky 7909219077Sdim return getDerived().RebuildDependentScopeDeclRefExpr(QualifierLoc, 7910234353Sdim TemplateKWLoc, 7911212904Sdim NameInfo, 7912243830Sdim /*TemplateArgs*/ 0, 7913243830Sdim IsAddressOfOperand); 7914199990Srdivacky } 7915198092Srdivacky 7916199990Srdivacky TemplateArgumentListInfo TransArgs(E->getLAngleLoc(), E->getRAngleLoc()); 7917218893Sdim if (getDerived().TransformTemplateArguments(E->getTemplateArgs(), 7918218893Sdim E->getNumTemplateArgs(), 7919218893Sdim TransArgs)) 7920218893Sdim return ExprError(); 7921198092Srdivacky 7922219077Sdim return getDerived().RebuildDependentScopeDeclRefExpr(QualifierLoc, 7923234353Sdim TemplateKWLoc, 7924212904Sdim NameInfo, 7925243830Sdim &TransArgs, 7926243830Sdim IsAddressOfOperand); 7927198092Srdivacky} 7928198092Srdivacky 7929198092Srdivackytemplate<typename Derived> 7930212904SdimExprResult 7931200583SrdivackyTreeTransform<Derived>::TransformCXXConstructExpr(CXXConstructExpr *E) { 7932249423Sdim // CXXConstructExprs other than for list-initialization and 7933249423Sdim // CXXTemporaryObjectExpr are always implicit, so when we have 7934249423Sdim // a 1-argument construction we just transform that argument. 7935249423Sdim if ((E->getNumArgs() == 1 || 7936249423Sdim (E->getNumArgs() > 1 && getDerived().DropCallArgument(E->getArg(1)))) && 7937249423Sdim (!getDerived().DropCallArgument(E->getArg(0))) && 7938249423Sdim !E->isListInitialization()) 7939203955Srdivacky return getDerived().TransformExpr(E->getArg(0)); 7940203955Srdivacky 7941198092Srdivacky TemporaryBase Rebase(*this, /*FIXME*/E->getLocStart(), DeclarationName()); 7942198092Srdivacky 7943198092Srdivacky QualType T = getDerived().TransformType(E->getType()); 7944198092Srdivacky if (T.isNull()) 7945212904Sdim return ExprError(); 7946198092Srdivacky 7947198092Srdivacky CXXConstructorDecl *Constructor 7948198092Srdivacky = cast_or_null<CXXConstructorDecl>( 7949204643Srdivacky getDerived().TransformDecl(E->getLocStart(), 7950204643Srdivacky E->getConstructor())); 7951198092Srdivacky if (!Constructor) 7952212904Sdim return ExprError(); 7953198092Srdivacky 7954198092Srdivacky bool ArgumentChanged = false; 7955243830Sdim SmallVector<Expr*, 8> Args; 7956239462Sdim if (getDerived().TransformExprs(E->getArgs(), E->getNumArgs(), true, Args, 7957218893Sdim &ArgumentChanged)) 7958218893Sdim return ExprError(); 7959239462Sdim 7960198092Srdivacky if (!getDerived().AlwaysRebuild() && 7961198092Srdivacky T == E->getType() && 7962198092Srdivacky Constructor == E->getConstructor() && 7963204643Srdivacky !ArgumentChanged) { 7964204643Srdivacky // Mark the constructor as referenced. 7965204643Srdivacky // FIXME: Instantiation-specific 7966234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), Constructor); 7967218893Sdim return SemaRef.Owned(E); 7968204643Srdivacky } 7969198092Srdivacky 7970200583Srdivacky return getDerived().RebuildCXXConstructExpr(T, /*FIXME:*/E->getLocStart(), 7971200583Srdivacky Constructor, E->isElidable(), 7972243830Sdim Args, 7973226633Sdim E->hadMultipleCandidates(), 7974249423Sdim E->isListInitialization(), 7975212904Sdim E->requiresZeroInitialization(), 7976218893Sdim E->getConstructionKind(), 7977218893Sdim E->getParenRange()); 7978198092Srdivacky} 7979198092Srdivacky 7980198092Srdivacky/// \brief Transform a C++ temporary-binding expression. 7981198092Srdivacky/// 7982201361Srdivacky/// Since CXXBindTemporaryExpr nodes are implicitly generated, we just 7983201361Srdivacky/// transform the subexpression and return that. 7984198092Srdivackytemplate<typename Derived> 7985212904SdimExprResult 7986200583SrdivackyTreeTransform<Derived>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr *E) { 7987201361Srdivacky return getDerived().TransformExpr(E->getSubExpr()); 7988198092Srdivacky} 7989198092Srdivacky 7990218893Sdim/// \brief Transform a C++ expression that contains cleanups that should 7991218893Sdim/// be run after the expression is evaluated. 7992198092Srdivacky/// 7993218893Sdim/// Since ExprWithCleanups nodes are implicitly generated, we 7994201361Srdivacky/// just transform the subexpression and return that. 7995198092Srdivackytemplate<typename Derived> 7996212904SdimExprResult 7997218893SdimTreeTransform<Derived>::TransformExprWithCleanups(ExprWithCleanups *E) { 7998201361Srdivacky return getDerived().TransformExpr(E->getSubExpr()); 7999198092Srdivacky} 8000198092Srdivacky 8001198092Srdivackytemplate<typename Derived> 8002212904SdimExprResult 8003198092SrdivackyTreeTransform<Derived>::TransformCXXTemporaryObjectExpr( 8004218893Sdim CXXTemporaryObjectExpr *E) { 8005218893Sdim TypeSourceInfo *T = getDerived().TransformType(E->getTypeSourceInfo()); 8006218893Sdim if (!T) 8007212904Sdim return ExprError(); 8008198092Srdivacky 8009198092Srdivacky CXXConstructorDecl *Constructor 8010198092Srdivacky = cast_or_null<CXXConstructorDecl>( 8011239462Sdim getDerived().TransformDecl(E->getLocStart(), 8012204643Srdivacky E->getConstructor())); 8013198092Srdivacky if (!Constructor) 8014212904Sdim return ExprError(); 8015198092Srdivacky 8016198092Srdivacky bool ArgumentChanged = false; 8017243830Sdim SmallVector<Expr*, 8> Args; 8018198092Srdivacky Args.reserve(E->getNumArgs()); 8019239462Sdim if (TransformExprs(E->getArgs(), E->getNumArgs(), true, Args, 8020218893Sdim &ArgumentChanged)) 8021218893Sdim return ExprError(); 8022204643Srdivacky 8023198092Srdivacky if (!getDerived().AlwaysRebuild() && 8024218893Sdim T == E->getTypeSourceInfo() && 8025198092Srdivacky Constructor == E->getConstructor() && 8026204643Srdivacky !ArgumentChanged) { 8027204643Srdivacky // FIXME: Instantiation-specific 8028234353Sdim SemaRef.MarkFunctionReferenced(E->getLocStart(), Constructor); 8029218893Sdim return SemaRef.MaybeBindToTemporary(E); 8030204643Srdivacky } 8031239462Sdim 8032249423Sdim // FIXME: Pass in E->isListInitialization(). 8033218893Sdim return getDerived().RebuildCXXTemporaryObjectExpr(T, 8034218893Sdim /*FIXME:*/T->getTypeLoc().getEndLoc(), 8035243830Sdim Args, 8036198092Srdivacky E->getLocEnd()); 8037198092Srdivacky} 8038198092Srdivacky 8039198092Srdivackytemplate<typename Derived> 8040212904SdimExprResult 8041234353SdimTreeTransform<Derived>::TransformLambdaExpr(LambdaExpr *E) { 8042234353Sdim // Transform the type of the lambda parameters and start the definition of 8043234353Sdim // the lambda itself. 8044234353Sdim TypeSourceInfo *MethodTy 8045239462Sdim = TransformType(E->getCallOperator()->getTypeSourceInfo()); 8046234353Sdim if (!MethodTy) 8047234353Sdim return ExprError(); 8048234353Sdim 8049243830Sdim // Create the local class that will describe the lambda. 8050243830Sdim CXXRecordDecl *Class 8051243830Sdim = getSema().createLambdaClosureType(E->getIntroducerRange(), 8052243830Sdim MethodTy, 8053243830Sdim /*KnownDependent=*/false); 8054243830Sdim getDerived().transformedLocalDecl(E->getLambdaClass(), Class); 8055243830Sdim 8056234353Sdim // Transform lambda parameters. 8057249423Sdim SmallVector<QualType, 4> ParamTypes; 8058249423Sdim SmallVector<ParmVarDecl *, 4> Params; 8059234353Sdim if (getDerived().TransformFunctionTypeParams(E->getLocStart(), 8060234353Sdim E->getCallOperator()->param_begin(), 8061234353Sdim E->getCallOperator()->param_size(), 8062234353Sdim 0, ParamTypes, &Params)) 8063239462Sdim return ExprError(); 8064234353Sdim 8065234353Sdim // Build the call operator. 8066234353Sdim CXXMethodDecl *CallOperator 8067234353Sdim = getSema().startLambdaDefinition(Class, E->getIntroducerRange(), 8068239462Sdim MethodTy, 8069234353Sdim E->getCallOperator()->getLocEnd(), 8070239462Sdim Params); 8071234353Sdim getDerived().transformAttrs(E->getCallOperator(), CallOperator); 8072234353Sdim 8073239462Sdim return getDerived().TransformLambdaScope(E, CallOperator); 8074239462Sdim} 8075239462Sdim 8076239462Sdimtemplate<typename Derived> 8077239462SdimExprResult 8078239462SdimTreeTransform<Derived>::TransformLambdaScope(LambdaExpr *E, 8079239462Sdim CXXMethodDecl *CallOperator) { 8080234353Sdim // Introduce the context of the call operator. 8081234353Sdim Sema::ContextRAII SavedContext(getSema(), CallOperator); 8082234353Sdim 8083234353Sdim // Enter the scope of the lambda. 8084234353Sdim sema::LambdaScopeInfo *LSI 8085234353Sdim = getSema().enterLambdaScope(CallOperator, E->getIntroducerRange(), 8086234353Sdim E->getCaptureDefault(), 8087234353Sdim E->hasExplicitParameters(), 8088234353Sdim E->hasExplicitResultType(), 8089234353Sdim E->isMutable()); 8090239462Sdim 8091234353Sdim // Transform captures. 8092239462Sdim bool Invalid = false; 8093234353Sdim bool FinishedExplicitCaptures = false; 8094239462Sdim for (LambdaExpr::capture_iterator C = E->capture_begin(), 8095234353Sdim CEnd = E->capture_end(); 8096234353Sdim C != CEnd; ++C) { 8097234353Sdim // When we hit the first implicit capture, tell Sema that we've finished 8098234353Sdim // the list of explicit captures. 8099234353Sdim if (!FinishedExplicitCaptures && C->isImplicit()) { 8100234353Sdim getSema().finishLambdaExplicitCaptures(LSI); 8101234353Sdim FinishedExplicitCaptures = true; 8102234353Sdim } 8103239462Sdim 8104234353Sdim // Capturing 'this' is trivial. 8105234353Sdim if (C->capturesThis()) { 8106234353Sdim getSema().CheckCXXThisCapture(C->getLocation(), C->isExplicit()); 8107234353Sdim continue; 8108234353Sdim } 8109239462Sdim 8110234353Sdim // Determine the capture kind for Sema. 8111234353Sdim Sema::TryCaptureKind Kind 8112234353Sdim = C->isImplicit()? Sema::TryCapture_Implicit 8113234353Sdim : C->getCaptureKind() == LCK_ByCopy 8114234353Sdim ? Sema::TryCapture_ExplicitByVal 8115234353Sdim : Sema::TryCapture_ExplicitByRef; 8116234353Sdim SourceLocation EllipsisLoc; 8117234353Sdim if (C->isPackExpansion()) { 8118234353Sdim UnexpandedParameterPack Unexpanded(C->getCapturedVar(), C->getLocation()); 8119234353Sdim bool ShouldExpand = false; 8120234353Sdim bool RetainExpansion = false; 8121249423Sdim Optional<unsigned> NumExpansions; 8122239462Sdim if (getDerived().TryExpandParameterPacks(C->getEllipsisLoc(), 8123239462Sdim C->getLocation(), 8124234353Sdim Unexpanded, 8125234353Sdim ShouldExpand, RetainExpansion, 8126234353Sdim NumExpansions)) 8127234353Sdim return ExprError(); 8128239462Sdim 8129234353Sdim if (ShouldExpand) { 8130234353Sdim // The transform has determined that we should perform an expansion; 8131234353Sdim // transform and capture each of the arguments. 8132234353Sdim // expansion of the pattern. Do so. 8133234353Sdim VarDecl *Pack = C->getCapturedVar(); 8134234353Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 8135234353Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 8136234353Sdim VarDecl *CapturedVar 8137239462Sdim = cast_or_null<VarDecl>(getDerived().TransformDecl(C->getLocation(), 8138234353Sdim Pack)); 8139234353Sdim if (!CapturedVar) { 8140234353Sdim Invalid = true; 8141234353Sdim continue; 8142234353Sdim } 8143239462Sdim 8144234353Sdim // Capture the transformed variable. 8145239462Sdim getSema().tryCaptureVariable(CapturedVar, C->getLocation(), Kind); 8146239462Sdim } 8147234353Sdim continue; 8148234353Sdim } 8149239462Sdim 8150234353Sdim EllipsisLoc = C->getEllipsisLoc(); 8151234353Sdim } 8152239462Sdim 8153234353Sdim // Transform the captured variable. 8154234353Sdim VarDecl *CapturedVar 8155239462Sdim = cast_or_null<VarDecl>(getDerived().TransformDecl(C->getLocation(), 8156234353Sdim C->getCapturedVar())); 8157234353Sdim if (!CapturedVar) { 8158234353Sdim Invalid = true; 8159234353Sdim continue; 8160234353Sdim } 8161239462Sdim 8162234353Sdim // Capture the transformed variable. 8163234353Sdim getSema().tryCaptureVariable(CapturedVar, C->getLocation(), Kind); 8164234353Sdim } 8165234353Sdim if (!FinishedExplicitCaptures) 8166234353Sdim getSema().finishLambdaExplicitCaptures(LSI); 8167234353Sdim 8168234353Sdim 8169234353Sdim // Enter a new evaluation context to insulate the lambda from any 8170234353Sdim // cleanups from the enclosing full-expression. 8171239462Sdim getSema().PushExpressionEvaluationContext(Sema::PotentiallyEvaluated); 8172234353Sdim 8173234353Sdim if (Invalid) { 8174239462Sdim getSema().ActOnLambdaError(E->getLocStart(), /*CurScope=*/0, 8175234353Sdim /*IsInstantiation=*/true); 8176234353Sdim return ExprError(); 8177234353Sdim } 8178234353Sdim 8179234353Sdim // Instantiate the body of the lambda expression. 8180234353Sdim StmtResult Body = getDerived().TransformStmt(E->getBody()); 8181234353Sdim if (Body.isInvalid()) { 8182239462Sdim getSema().ActOnLambdaError(E->getLocStart(), /*CurScope=*/0, 8183234353Sdim /*IsInstantiation=*/true); 8184239462Sdim return ExprError(); 8185234353Sdim } 8186234353Sdim 8187239462Sdim return getSema().ActOnLambdaExpr(E->getLocStart(), Body.take(), 8188234353Sdim /*CurScope=*/0, /*IsInstantiation=*/true); 8189234353Sdim} 8190234353Sdim 8191234353Sdimtemplate<typename Derived> 8192234353SdimExprResult 8193198092SrdivackyTreeTransform<Derived>::TransformCXXUnresolvedConstructExpr( 8194200583Srdivacky CXXUnresolvedConstructExpr *E) { 8195218893Sdim TypeSourceInfo *T = getDerived().TransformType(E->getTypeSourceInfo()); 8196218893Sdim if (!T) 8197212904Sdim return ExprError(); 8198198092Srdivacky 8199198092Srdivacky bool ArgumentChanged = false; 8200243830Sdim SmallVector<Expr*, 8> Args; 8201218893Sdim Args.reserve(E->arg_size()); 8202239462Sdim if (getDerived().TransformExprs(E->arg_begin(), E->arg_size(), true, Args, 8203218893Sdim &ArgumentChanged)) 8204218893Sdim return ExprError(); 8205239462Sdim 8206198092Srdivacky if (!getDerived().AlwaysRebuild() && 8207218893Sdim T == E->getTypeSourceInfo() && 8208198092Srdivacky !ArgumentChanged) 8209218893Sdim return SemaRef.Owned(E); 8210198092Srdivacky 8211198092Srdivacky // FIXME: we're faking the locations of the commas 8212218893Sdim return getDerived().RebuildCXXUnresolvedConstructExpr(T, 8213198092Srdivacky E->getLParenLoc(), 8214243830Sdim Args, 8215198092Srdivacky E->getRParenLoc()); 8216198092Srdivacky} 8217198092Srdivacky 8218198092Srdivackytemplate<typename Derived> 8219212904SdimExprResult 8220199990SrdivackyTreeTransform<Derived>::TransformCXXDependentScopeMemberExpr( 8221212904Sdim CXXDependentScopeMemberExpr *E) { 8222198092Srdivacky // Transform the base of the expression. 8223212904Sdim ExprResult Base((Expr*) 0); 8224200583Srdivacky Expr *OldBase; 8225200583Srdivacky QualType BaseType; 8226200583Srdivacky QualType ObjectType; 8227200583Srdivacky if (!E->isImplicitAccess()) { 8228200583Srdivacky OldBase = E->getBase(); 8229200583Srdivacky Base = getDerived().TransformExpr(OldBase); 8230200583Srdivacky if (Base.isInvalid()) 8231212904Sdim return ExprError(); 8232198092Srdivacky 8233200583Srdivacky // Start the member reference and compute the object's type. 8234212904Sdim ParsedType ObjectTy; 8235204643Srdivacky bool MayBePseudoDestructor = false; 8236212904Sdim Base = SemaRef.ActOnStartCXXMemberReference(0, Base.get(), 8237200583Srdivacky E->getOperatorLoc(), 8238198092Srdivacky E->isArrow()? tok::arrow : tok::period, 8239204643Srdivacky ObjectTy, 8240204643Srdivacky MayBePseudoDestructor); 8241200583Srdivacky if (Base.isInvalid()) 8242212904Sdim return ExprError(); 8243198092Srdivacky 8244212904Sdim ObjectType = ObjectTy.get(); 8245200583Srdivacky BaseType = ((Expr*) Base.get())->getType(); 8246200583Srdivacky } else { 8247200583Srdivacky OldBase = 0; 8248200583Srdivacky BaseType = getDerived().TransformType(E->getBaseType()); 8249200583Srdivacky ObjectType = BaseType->getAs<PointerType>()->getPointeeType(); 8250200583Srdivacky } 8251200583Srdivacky 8252198398Srdivacky // Transform the first part of the nested-name-specifier that qualifies 8253198398Srdivacky // the member name. 8254198092Srdivacky NamedDecl *FirstQualifierInScope 8255198398Srdivacky = getDerived().TransformFirstQualifierInScope( 8256221345Sdim E->getFirstQualifierFoundInScope(), 8257221345Sdim E->getQualifierLoc().getBeginLoc()); 8258198092Srdivacky 8259221345Sdim NestedNameSpecifierLoc QualifierLoc; 8260198092Srdivacky if (E->getQualifier()) { 8261221345Sdim QualifierLoc 8262221345Sdim = getDerived().TransformNestedNameSpecifierLoc(E->getQualifierLoc(), 8263221345Sdim ObjectType, 8264221345Sdim FirstQualifierInScope); 8265221345Sdim if (!QualifierLoc) 8266212904Sdim return ExprError(); 8267198092Srdivacky } 8268198092Srdivacky 8269234353Sdim SourceLocation TemplateKWLoc = E->getTemplateKeywordLoc(); 8270234353Sdim 8271218893Sdim // TODO: If this is a conversion-function-id, verify that the 8272218893Sdim // destination type name (if present) resolves the same way after 8273218893Sdim // instantiation as it did in the local scope. 8274218893Sdim 8275212904Sdim DeclarationNameInfo NameInfo 8276218893Sdim = getDerived().TransformDeclarationNameInfo(E->getMemberNameInfo()); 8277212904Sdim if (!NameInfo.getName()) 8278212904Sdim return ExprError(); 8279198092Srdivacky 8280200583Srdivacky if (!E->hasExplicitTemplateArgs()) { 8281198092Srdivacky // This is a reference to a member without an explicitly-specified 8282198092Srdivacky // template argument list. Optimize for this common case. 8283198092Srdivacky if (!getDerived().AlwaysRebuild() && 8284200583Srdivacky Base.get() == OldBase && 8285200583Srdivacky BaseType == E->getBaseType() && 8286221345Sdim QualifierLoc == E->getQualifierLoc() && 8287212904Sdim NameInfo.getName() == E->getMember() && 8288198092Srdivacky FirstQualifierInScope == E->getFirstQualifierFoundInScope()) 8289218893Sdim return SemaRef.Owned(E); 8290198092Srdivacky 8291212904Sdim return getDerived().RebuildCXXDependentScopeMemberExpr(Base.get(), 8292200583Srdivacky BaseType, 8293198092Srdivacky E->isArrow(), 8294198092Srdivacky E->getOperatorLoc(), 8295221345Sdim QualifierLoc, 8296234353Sdim TemplateKWLoc, 8297199990Srdivacky FirstQualifierInScope, 8298212904Sdim NameInfo, 8299199990Srdivacky /*TemplateArgs*/ 0); 8300198092Srdivacky } 8301198092Srdivacky 8302199990Srdivacky TemplateArgumentListInfo TransArgs(E->getLAngleLoc(), E->getRAngleLoc()); 8303218893Sdim if (getDerived().TransformTemplateArguments(E->getTemplateArgs(), 8304218893Sdim E->getNumTemplateArgs(), 8305218893Sdim TransArgs)) 8306218893Sdim return ExprError(); 8307198092Srdivacky 8308212904Sdim return getDerived().RebuildCXXDependentScopeMemberExpr(Base.get(), 8309200583Srdivacky BaseType, 8310198092Srdivacky E->isArrow(), 8311198092Srdivacky E->getOperatorLoc(), 8312221345Sdim QualifierLoc, 8313234353Sdim TemplateKWLoc, 8314199990Srdivacky FirstQualifierInScope, 8315212904Sdim NameInfo, 8316199990Srdivacky &TransArgs); 8317198092Srdivacky} 8318198092Srdivacky 8319198092Srdivackytemplate<typename Derived> 8320212904SdimExprResult 8321200583SrdivackyTreeTransform<Derived>::TransformUnresolvedMemberExpr(UnresolvedMemberExpr *Old) { 8322199990Srdivacky // Transform the base of the expression. 8323212904Sdim ExprResult Base((Expr*) 0); 8324200583Srdivacky QualType BaseType; 8325200583Srdivacky if (!Old->isImplicitAccess()) { 8326200583Srdivacky Base = getDerived().TransformExpr(Old->getBase()); 8327200583Srdivacky if (Base.isInvalid()) 8328212904Sdim return ExprError(); 8329234353Sdim Base = getSema().PerformMemberExprBaseConversion(Base.take(), 8330234353Sdim Old->isArrow()); 8331234353Sdim if (Base.isInvalid()) 8332234353Sdim return ExprError(); 8333234353Sdim BaseType = Base.get()->getType(); 8334200583Srdivacky } else { 8335200583Srdivacky BaseType = getDerived().TransformType(Old->getBaseType()); 8336200583Srdivacky } 8337199990Srdivacky 8338221345Sdim NestedNameSpecifierLoc QualifierLoc; 8339221345Sdim if (Old->getQualifierLoc()) { 8340221345Sdim QualifierLoc 8341221345Sdim = getDerived().TransformNestedNameSpecifierLoc(Old->getQualifierLoc()); 8342221345Sdim if (!QualifierLoc) 8343212904Sdim return ExprError(); 8344199990Srdivacky } 8345199990Srdivacky 8346234353Sdim SourceLocation TemplateKWLoc = Old->getTemplateKeywordLoc(); 8347234353Sdim 8348212904Sdim LookupResult R(SemaRef, Old->getMemberNameInfo(), 8349199990Srdivacky Sema::LookupOrdinaryName); 8350199990Srdivacky 8351199990Srdivacky // Transform all the decls. 8352199990Srdivacky for (UnresolvedMemberExpr::decls_iterator I = Old->decls_begin(), 8353199990Srdivacky E = Old->decls_end(); I != E; ++I) { 8354204643Srdivacky NamedDecl *InstD = static_cast<NamedDecl*>( 8355204643Srdivacky getDerived().TransformDecl(Old->getMemberLoc(), 8356204643Srdivacky *I)); 8357200583Srdivacky if (!InstD) { 8358200583Srdivacky // Silently ignore these if a UsingShadowDecl instantiated to nothing. 8359200583Srdivacky // This can happen because of dependent hiding. 8360200583Srdivacky if (isa<UsingShadowDecl>(*I)) 8361200583Srdivacky continue; 8362221345Sdim else { 8363221345Sdim R.clear(); 8364212904Sdim return ExprError(); 8365221345Sdim } 8366200583Srdivacky } 8367199990Srdivacky 8368199990Srdivacky // Expand using declarations. 8369199990Srdivacky if (isa<UsingDecl>(InstD)) { 8370199990Srdivacky UsingDecl *UD = cast<UsingDecl>(InstD); 8371199990Srdivacky for (UsingDecl::shadow_iterator I = UD->shadow_begin(), 8372199990Srdivacky E = UD->shadow_end(); I != E; ++I) 8373199990Srdivacky R.addDecl(*I); 8374199990Srdivacky continue; 8375199990Srdivacky } 8376199990Srdivacky 8377199990Srdivacky R.addDecl(InstD); 8378199990Srdivacky } 8379199990Srdivacky 8380199990Srdivacky R.resolveKind(); 8381199990Srdivacky 8382207619Srdivacky // Determine the naming class. 8383208600Srdivacky if (Old->getNamingClass()) { 8384239462Sdim CXXRecordDecl *NamingClass 8385207619Srdivacky = cast_or_null<CXXRecordDecl>(getDerived().TransformDecl( 8386207619Srdivacky Old->getMemberLoc(), 8387207619Srdivacky Old->getNamingClass())); 8388207619Srdivacky if (!NamingClass) 8389212904Sdim return ExprError(); 8390239462Sdim 8391207619Srdivacky R.setNamingClass(NamingClass); 8392207619Srdivacky } 8393239462Sdim 8394199990Srdivacky TemplateArgumentListInfo TransArgs; 8395199990Srdivacky if (Old->hasExplicitTemplateArgs()) { 8396199990Srdivacky TransArgs.setLAngleLoc(Old->getLAngleLoc()); 8397199990Srdivacky TransArgs.setRAngleLoc(Old->getRAngleLoc()); 8398218893Sdim if (getDerived().TransformTemplateArguments(Old->getTemplateArgs(), 8399218893Sdim Old->getNumTemplateArgs(), 8400218893Sdim TransArgs)) 8401218893Sdim return ExprError(); 8402199990Srdivacky } 8403202379Srdivacky 8404202379Srdivacky // FIXME: to do this check properly, we will need to preserve the 8405202379Srdivacky // first-qualifier-in-scope here, just in case we had a dependent 8406202379Srdivacky // base (and therefore couldn't do the check) and a 8407202379Srdivacky // nested-name-qualifier (and therefore could do the lookup). 8408202379Srdivacky NamedDecl *FirstQualifierInScope = 0; 8409239462Sdim 8410212904Sdim return getDerived().RebuildUnresolvedMemberExpr(Base.get(), 8411200583Srdivacky BaseType, 8412199990Srdivacky Old->getOperatorLoc(), 8413199990Srdivacky Old->isArrow(), 8414221345Sdim QualifierLoc, 8415234353Sdim TemplateKWLoc, 8416202379Srdivacky FirstQualifierInScope, 8417199990Srdivacky R, 8418199990Srdivacky (Old->hasExplicitTemplateArgs() 8419199990Srdivacky ? &TransArgs : 0)); 8420199990Srdivacky} 8421199990Srdivacky 8422199990Srdivackytemplate<typename Derived> 8423212904SdimExprResult 8424218893SdimTreeTransform<Derived>::TransformCXXNoexceptExpr(CXXNoexceptExpr *E) { 8425223017Sdim EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); 8426218893Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getOperand()); 8427218893Sdim if (SubExpr.isInvalid()) 8428218893Sdim return ExprError(); 8429218893Sdim 8430218893Sdim if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getOperand()) 8431218893Sdim return SemaRef.Owned(E); 8432218893Sdim 8433218893Sdim return getDerived().RebuildCXXNoexceptExpr(E->getSourceRange(),SubExpr.get()); 8434218893Sdim} 8435218893Sdim 8436218893Sdimtemplate<typename Derived> 8437218893SdimExprResult 8438218893SdimTreeTransform<Derived>::TransformPackExpansionExpr(PackExpansionExpr *E) { 8439218893Sdim ExprResult Pattern = getDerived().TransformExpr(E->getPattern()); 8440218893Sdim if (Pattern.isInvalid()) 8441218893Sdim return ExprError(); 8442239462Sdim 8443218893Sdim if (!getDerived().AlwaysRebuild() && Pattern.get() == E->getPattern()) 8444218893Sdim return SemaRef.Owned(E); 8445218893Sdim 8446218893Sdim return getDerived().RebuildPackExpansion(Pattern.get(), E->getEllipsisLoc(), 8447218893Sdim E->getNumExpansions()); 8448218893Sdim} 8449218893Sdim 8450218893Sdimtemplate<typename Derived> 8451218893SdimExprResult 8452218893SdimTreeTransform<Derived>::TransformSizeOfPackExpr(SizeOfPackExpr *E) { 8453218893Sdim // If E is not value-dependent, then nothing will change when we transform it. 8454218893Sdim // Note: This is an instantiation-centric view. 8455218893Sdim if (!E->isValueDependent()) 8456218893Sdim return SemaRef.Owned(E); 8457218893Sdim 8458218893Sdim // Note: None of the implementations of TryExpandParameterPacks can ever 8459218893Sdim // produce a diagnostic when given only a single unexpanded parameter pack, 8460239462Sdim // so 8461218893Sdim UnexpandedParameterPack Unexpanded(E->getPack(), E->getPackLoc()); 8462218893Sdim bool ShouldExpand = false; 8463218893Sdim bool RetainExpansion = false; 8464249423Sdim Optional<unsigned> NumExpansions; 8465239462Sdim if (getDerived().TryExpandParameterPacks(E->getOperatorLoc(), E->getPackLoc(), 8466226633Sdim Unexpanded, 8467218893Sdim ShouldExpand, RetainExpansion, 8468218893Sdim NumExpansions)) 8469218893Sdim return ExprError(); 8470239462Sdim 8471226633Sdim if (RetainExpansion) 8472218893Sdim return SemaRef.Owned(E); 8473239462Sdim 8474226633Sdim NamedDecl *Pack = E->getPack(); 8475226633Sdim if (!ShouldExpand) { 8476239462Sdim Pack = cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getPackLoc(), 8477226633Sdim Pack)); 8478226633Sdim if (!Pack) 8479226633Sdim return ExprError(); 8480226633Sdim } 8481226633Sdim 8482239462Sdim 8483218893Sdim // We now know the length of the parameter pack, so build a new expression 8484218893Sdim // that stores that length. 8485239462Sdim return getDerived().RebuildSizeOfPackExpr(E->getOperatorLoc(), Pack, 8486239462Sdim E->getPackLoc(), E->getRParenLoc(), 8487226633Sdim NumExpansions); 8488218893Sdim} 8489218893Sdim 8490218893Sdimtemplate<typename Derived> 8491218893SdimExprResult 8492218893SdimTreeTransform<Derived>::TransformSubstNonTypeTemplateParmPackExpr( 8493218893Sdim SubstNonTypeTemplateParmPackExpr *E) { 8494218893Sdim // Default behavior is to do nothing with this transformation. 8495218893Sdim return SemaRef.Owned(E); 8496218893Sdim} 8497218893Sdim 8498218893Sdimtemplate<typename Derived> 8499218893SdimExprResult 8500224145SdimTreeTransform<Derived>::TransformSubstNonTypeTemplateParmExpr( 8501224145Sdim SubstNonTypeTemplateParmExpr *E) { 8502224145Sdim // Default behavior is to do nothing with this transformation. 8503224145Sdim return SemaRef.Owned(E); 8504224145Sdim} 8505224145Sdim 8506224145Sdimtemplate<typename Derived> 8507224145SdimExprResult 8508243830SdimTreeTransform<Derived>::TransformFunctionParmPackExpr(FunctionParmPackExpr *E) { 8509243830Sdim // Default behavior is to do nothing with this transformation. 8510243830Sdim return SemaRef.Owned(E); 8511243830Sdim} 8512243830Sdim 8513243830Sdimtemplate<typename Derived> 8514243830SdimExprResult 8515224145SdimTreeTransform<Derived>::TransformMaterializeTemporaryExpr( 8516224145Sdim MaterializeTemporaryExpr *E) { 8517224145Sdim return getDerived().TransformExpr(E->GetTemporaryExpr()); 8518224145Sdim} 8519239462Sdim 8520224145Sdimtemplate<typename Derived> 8521224145SdimExprResult 8522200583SrdivackyTreeTransform<Derived>::TransformObjCStringLiteral(ObjCStringLiteral *E) { 8523234353Sdim return SemaRef.MaybeBindToTemporary(E); 8524234353Sdim} 8525234353Sdim 8526234353Sdimtemplate<typename Derived> 8527234353SdimExprResult 8528234353SdimTreeTransform<Derived>::TransformObjCBoolLiteralExpr(ObjCBoolLiteralExpr *E) { 8529218893Sdim return SemaRef.Owned(E); 8530198092Srdivacky} 8531198092Srdivacky 8532198092Srdivackytemplate<typename Derived> 8533212904SdimExprResult 8534239462SdimTreeTransform<Derived>::TransformObjCBoxedExpr(ObjCBoxedExpr *E) { 8535239462Sdim ExprResult SubExpr = getDerived().TransformExpr(E->getSubExpr()); 8536239462Sdim if (SubExpr.isInvalid()) 8537239462Sdim return ExprError(); 8538239462Sdim 8539239462Sdim if (!getDerived().AlwaysRebuild() && 8540239462Sdim SubExpr.get() == E->getSubExpr()) 8541239462Sdim return SemaRef.Owned(E); 8542239462Sdim 8543239462Sdim return getDerived().RebuildObjCBoxedExpr(E->getSourceRange(), SubExpr.get()); 8544234353Sdim} 8545234353Sdim 8546234353Sdimtemplate<typename Derived> 8547234353SdimExprResult 8548234353SdimTreeTransform<Derived>::TransformObjCArrayLiteral(ObjCArrayLiteral *E) { 8549234353Sdim // Transform each of the elements. 8550249423Sdim SmallVector<Expr *, 8> Elements; 8551234353Sdim bool ArgChanged = false; 8552239462Sdim if (getDerived().TransformExprs(E->getElements(), E->getNumElements(), 8553234353Sdim /*IsCall=*/false, Elements, &ArgChanged)) 8554234353Sdim return ExprError(); 8555239462Sdim 8556234353Sdim if (!getDerived().AlwaysRebuild() && !ArgChanged) 8557234353Sdim return SemaRef.MaybeBindToTemporary(E); 8558239462Sdim 8559234353Sdim return getDerived().RebuildObjCArrayLiteral(E->getSourceRange(), 8560234353Sdim Elements.data(), 8561234353Sdim Elements.size()); 8562234353Sdim} 8563234353Sdim 8564234353Sdimtemplate<typename Derived> 8565234353SdimExprResult 8566234353SdimTreeTransform<Derived>::TransformObjCDictionaryLiteral( 8567239462Sdim ObjCDictionaryLiteral *E) { 8568234353Sdim // Transform each of the elements. 8569249423Sdim SmallVector<ObjCDictionaryElement, 8> Elements; 8570234353Sdim bool ArgChanged = false; 8571234353Sdim for (unsigned I = 0, N = E->getNumElements(); I != N; ++I) { 8572234353Sdim ObjCDictionaryElement OrigElement = E->getKeyValueElement(I); 8573239462Sdim 8574234353Sdim if (OrigElement.isPackExpansion()) { 8575234353Sdim // This key/value element is a pack expansion. 8576234353Sdim SmallVector<UnexpandedParameterPack, 2> Unexpanded; 8577234353Sdim getSema().collectUnexpandedParameterPacks(OrigElement.Key, Unexpanded); 8578234353Sdim getSema().collectUnexpandedParameterPacks(OrigElement.Value, Unexpanded); 8579234353Sdim assert(!Unexpanded.empty() && "Pack expansion without parameter packs?"); 8580234353Sdim 8581234353Sdim // Determine whether the set of unexpanded parameter packs can 8582234353Sdim // and should be expanded. 8583234353Sdim bool Expand = true; 8584234353Sdim bool RetainExpansion = false; 8585249423Sdim Optional<unsigned> OrigNumExpansions = OrigElement.NumExpansions; 8586249423Sdim Optional<unsigned> NumExpansions = OrigNumExpansions; 8587234353Sdim SourceRange PatternRange(OrigElement.Key->getLocStart(), 8588234353Sdim OrigElement.Value->getLocEnd()); 8589234353Sdim if (getDerived().TryExpandParameterPacks(OrigElement.EllipsisLoc, 8590234353Sdim PatternRange, 8591234353Sdim Unexpanded, 8592234353Sdim Expand, RetainExpansion, 8593234353Sdim NumExpansions)) 8594234353Sdim return ExprError(); 8595234353Sdim 8596234353Sdim if (!Expand) { 8597234353Sdim // The transform has determined that we should perform a simple 8598239462Sdim // transformation on the pack expansion, producing another pack 8599234353Sdim // expansion. 8600234353Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), -1); 8601234353Sdim ExprResult Key = getDerived().TransformExpr(OrigElement.Key); 8602234353Sdim if (Key.isInvalid()) 8603234353Sdim return ExprError(); 8604234353Sdim 8605234353Sdim if (Key.get() != OrigElement.Key) 8606234353Sdim ArgChanged = true; 8607234353Sdim 8608234353Sdim ExprResult Value = getDerived().TransformExpr(OrigElement.Value); 8609234353Sdim if (Value.isInvalid()) 8610234353Sdim return ExprError(); 8611239462Sdim 8612234353Sdim if (Value.get() != OrigElement.Value) 8613234353Sdim ArgChanged = true; 8614234353Sdim 8615239462Sdim ObjCDictionaryElement Expansion = { 8616234353Sdim Key.get(), Value.get(), OrigElement.EllipsisLoc, NumExpansions 8617234353Sdim }; 8618234353Sdim Elements.push_back(Expansion); 8619234353Sdim continue; 8620234353Sdim } 8621234353Sdim 8622234353Sdim // Record right away that the argument was changed. This needs 8623234353Sdim // to happen even if the array expands to nothing. 8624234353Sdim ArgChanged = true; 8625239462Sdim 8626234353Sdim // The transform has determined that we should perform an elementwise 8627234353Sdim // expansion of the pattern. Do so. 8628234353Sdim for (unsigned I = 0; I != *NumExpansions; ++I) { 8629234353Sdim Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); 8630234353Sdim ExprResult Key = getDerived().TransformExpr(OrigElement.Key); 8631234353Sdim if (Key.isInvalid()) 8632234353Sdim return ExprError(); 8633234353Sdim 8634234353Sdim ExprResult Value = getDerived().TransformExpr(OrigElement.Value); 8635234353Sdim if (Value.isInvalid()) 8636234353Sdim return ExprError(); 8637234353Sdim 8638239462Sdim ObjCDictionaryElement Element = { 8639234353Sdim Key.get(), Value.get(), SourceLocation(), NumExpansions 8640234353Sdim }; 8641234353Sdim 8642234353Sdim // If any unexpanded parameter packs remain, we still have a 8643234353Sdim // pack expansion. 8644234353Sdim if (Key.get()->containsUnexpandedParameterPack() || 8645234353Sdim Value.get()->containsUnexpandedParameterPack()) 8646234353Sdim Element.EllipsisLoc = OrigElement.EllipsisLoc; 8647239462Sdim 8648234353Sdim Elements.push_back(Element); 8649234353Sdim } 8650234353Sdim 8651234353Sdim // We've finished with this pack expansion. 8652234353Sdim continue; 8653234353Sdim } 8654234353Sdim 8655234353Sdim // Transform and check key. 8656234353Sdim ExprResult Key = getDerived().TransformExpr(OrigElement.Key); 8657234353Sdim if (Key.isInvalid()) 8658234353Sdim return ExprError(); 8659239462Sdim 8660234353Sdim if (Key.get() != OrigElement.Key) 8661234353Sdim ArgChanged = true; 8662239462Sdim 8663234353Sdim // Transform and check value. 8664234353Sdim ExprResult Value 8665234353Sdim = getDerived().TransformExpr(OrigElement.Value); 8666234353Sdim if (Value.isInvalid()) 8667234353Sdim return ExprError(); 8668239462Sdim 8669234353Sdim if (Value.get() != OrigElement.Value) 8670234353Sdim ArgChanged = true; 8671239462Sdim 8672239462Sdim ObjCDictionaryElement Element = { 8673249423Sdim Key.get(), Value.get(), SourceLocation(), None 8674234353Sdim }; 8675234353Sdim Elements.push_back(Element); 8676234353Sdim } 8677239462Sdim 8678234353Sdim if (!getDerived().AlwaysRebuild() && !ArgChanged) 8679234353Sdim return SemaRef.MaybeBindToTemporary(E); 8680234353Sdim 8681234353Sdim return getDerived().RebuildObjCDictionaryLiteral(E->getSourceRange(), 8682234353Sdim Elements.data(), 8683234353Sdim Elements.size()); 8684234353Sdim} 8685234353Sdim 8686234353Sdimtemplate<typename Derived> 8687234353SdimExprResult 8688200583SrdivackyTreeTransform<Derived>::TransformObjCEncodeExpr(ObjCEncodeExpr *E) { 8689207619Srdivacky TypeSourceInfo *EncodedTypeInfo 8690207619Srdivacky = getDerived().TransformType(E->getEncodedTypeSourceInfo()); 8691207619Srdivacky if (!EncodedTypeInfo) 8692212904Sdim return ExprError(); 8693198092Srdivacky 8694198092Srdivacky if (!getDerived().AlwaysRebuild() && 8695207619Srdivacky EncodedTypeInfo == E->getEncodedTypeSourceInfo()) 8696218893Sdim return SemaRef.Owned(E); 8697198092Srdivacky 8698198092Srdivacky return getDerived().RebuildObjCEncodeExpr(E->getAtLoc(), 8699207619Srdivacky EncodedTypeInfo, 8700198092Srdivacky E->getRParenLoc()); 8701198092Srdivacky} 8702198092Srdivacky 8703198092Srdivackytemplate<typename Derived> 8704224145SdimExprResult TreeTransform<Derived>:: 8705224145SdimTransformObjCIndirectCopyRestoreExpr(ObjCIndirectCopyRestoreExpr *E) { 8706251662Sdim // This is a kind of implicit conversion, and it needs to get dropped 8707251662Sdim // and recomputed for the same general reasons that ImplicitCastExprs 8708251662Sdim // do, as well a more specific one: this expression is only valid when 8709251662Sdim // it appears *immediately* as an argument expression. 8710251662Sdim return getDerived().TransformExpr(E->getSubExpr()); 8711224145Sdim} 8712224145Sdim 8713224145Sdimtemplate<typename Derived> 8714224145SdimExprResult TreeTransform<Derived>:: 8715224145SdimTransformObjCBridgedCastExpr(ObjCBridgedCastExpr *E) { 8716239462Sdim TypeSourceInfo *TSInfo 8717224145Sdim = getDerived().TransformType(E->getTypeInfoAsWritten()); 8718224145Sdim if (!TSInfo) 8719224145Sdim return ExprError(); 8720239462Sdim 8721224145Sdim ExprResult Result = getDerived().TransformExpr(E->getSubExpr()); 8722239462Sdim if (Result.isInvalid()) 8723224145Sdim return ExprError(); 8724239462Sdim 8725224145Sdim if (!getDerived().AlwaysRebuild() && 8726224145Sdim TSInfo == E->getTypeInfoAsWritten() && 8727224145Sdim Result.get() == E->getSubExpr()) 8728224145Sdim return SemaRef.Owned(E); 8729239462Sdim 8730224145Sdim return SemaRef.BuildObjCBridgedCast(E->getLParenLoc(), E->getBridgeKind(), 8731239462Sdim E->getBridgeKeywordLoc(), TSInfo, 8732224145Sdim Result.get()); 8733224145Sdim} 8734224145Sdim 8735224145Sdimtemplate<typename Derived> 8736212904SdimExprResult 8737200583SrdivackyTreeTransform<Derived>::TransformObjCMessageExpr(ObjCMessageExpr *E) { 8738207619Srdivacky // Transform arguments. 8739207619Srdivacky bool ArgChanged = false; 8740243830Sdim SmallVector<Expr*, 8> Args; 8741218893Sdim Args.reserve(E->getNumArgs()); 8742239462Sdim if (getDerived().TransformExprs(E->getArgs(), E->getNumArgs(), false, Args, 8743218893Sdim &ArgChanged)) 8744218893Sdim return ExprError(); 8745239462Sdim 8746207619Srdivacky if (E->getReceiverKind() == ObjCMessageExpr::Class) { 8747207619Srdivacky // Class message: transform the receiver type. 8748207619Srdivacky TypeSourceInfo *ReceiverTypeInfo 8749207619Srdivacky = getDerived().TransformType(E->getClassReceiverTypeInfo()); 8750207619Srdivacky if (!ReceiverTypeInfo) 8751212904Sdim return ExprError(); 8752239462Sdim 8753207619Srdivacky // If nothing changed, just retain the existing message send. 8754207619Srdivacky if (!getDerived().AlwaysRebuild() && 8755207619Srdivacky ReceiverTypeInfo == E->getClassReceiverTypeInfo() && !ArgChanged) 8756234353Sdim return SemaRef.MaybeBindToTemporary(E); 8757207619Srdivacky 8758207619Srdivacky // Build a new class message send. 8759226633Sdim SmallVector<SourceLocation, 16> SelLocs; 8760226633Sdim E->getSelectorLocs(SelLocs); 8761207619Srdivacky return getDerived().RebuildObjCMessageExpr(ReceiverTypeInfo, 8762207619Srdivacky E->getSelector(), 8763226633Sdim SelLocs, 8764207619Srdivacky E->getMethodDecl(), 8765207619Srdivacky E->getLeftLoc(), 8766243830Sdim Args, 8767207619Srdivacky E->getRightLoc()); 8768207619Srdivacky } 8769207619Srdivacky 8770207619Srdivacky // Instance message: transform the receiver 8771207619Srdivacky assert(E->getReceiverKind() == ObjCMessageExpr::Instance && 8772207619Srdivacky "Only class and instance messages may be instantiated"); 8773212904Sdim ExprResult Receiver 8774207619Srdivacky = getDerived().TransformExpr(E->getInstanceReceiver()); 8775207619Srdivacky if (Receiver.isInvalid()) 8776212904Sdim return ExprError(); 8777207619Srdivacky 8778207619Srdivacky // If nothing changed, just retain the existing message send. 8779207619Srdivacky if (!getDerived().AlwaysRebuild() && 8780207619Srdivacky Receiver.get() == E->getInstanceReceiver() && !ArgChanged) 8781234353Sdim return SemaRef.MaybeBindToTemporary(E); 8782239462Sdim 8783207619Srdivacky // Build a new instance message send. 8784226633Sdim SmallVector<SourceLocation, 16> SelLocs; 8785226633Sdim E->getSelectorLocs(SelLocs); 8786212904Sdim return getDerived().RebuildObjCMessageExpr(Receiver.get(), 8787207619Srdivacky E->getSelector(), 8788226633Sdim SelLocs, 8789207619Srdivacky E->getMethodDecl(), 8790207619Srdivacky E->getLeftLoc(), 8791243830Sdim Args, 8792207619Srdivacky E->getRightLoc()); 8793198092Srdivacky} 8794198092Srdivacky 8795198092Srdivackytemplate<typename Derived> 8796212904SdimExprResult 8797200583SrdivackyTreeTransform<Derived>::TransformObjCSelectorExpr(ObjCSelectorExpr *E) { 8798218893Sdim return SemaRef.Owned(E); 8799198092Srdivacky} 8800198092Srdivacky 8801198092Srdivackytemplate<typename Derived> 8802212904SdimExprResult 8803200583SrdivackyTreeTransform<Derived>::TransformObjCProtocolExpr(ObjCProtocolExpr *E) { 8804218893Sdim return SemaRef.Owned(E); 8805198092Srdivacky} 8806198092Srdivacky 8807198092Srdivackytemplate<typename Derived> 8808212904SdimExprResult 8809200583SrdivackyTreeTransform<Derived>::TransformObjCIvarRefExpr(ObjCIvarRefExpr *E) { 8810207619Srdivacky // Transform the base expression. 8811212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 8812207619Srdivacky if (Base.isInvalid()) 8813212904Sdim return ExprError(); 8814207619Srdivacky 8815207619Srdivacky // We don't need to transform the ivar; it will never change. 8816239462Sdim 8817207619Srdivacky // If nothing changed, just retain the existing expression. 8818207619Srdivacky if (!getDerived().AlwaysRebuild() && 8819207619Srdivacky Base.get() == E->getBase()) 8820218893Sdim return SemaRef.Owned(E); 8821239462Sdim 8822212904Sdim return getDerived().RebuildObjCIvarRefExpr(Base.get(), E->getDecl(), 8823207619Srdivacky E->getLocation(), 8824207619Srdivacky E->isArrow(), E->isFreeIvar()); 8825198092Srdivacky} 8826198092Srdivacky 8827198092Srdivackytemplate<typename Derived> 8828212904SdimExprResult 8829200583SrdivackyTreeTransform<Derived>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr *E) { 8830218893Sdim // 'super' and types never change. Property never changes. Just 8831218893Sdim // retain the existing expression. 8832218893Sdim if (!E->isObjectReceiver()) 8833218893Sdim return SemaRef.Owned(E); 8834239462Sdim 8835207619Srdivacky // Transform the base expression. 8836212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 8837207619Srdivacky if (Base.isInvalid()) 8838212904Sdim return ExprError(); 8839239462Sdim 8840207619Srdivacky // We don't need to transform the property; it will never change. 8841239462Sdim 8842207619Srdivacky // If nothing changed, just retain the existing expression. 8843207619Srdivacky if (!getDerived().AlwaysRebuild() && 8844207619Srdivacky Base.get() == E->getBase()) 8845218893Sdim return SemaRef.Owned(E); 8846198092Srdivacky 8847218893Sdim if (E->isExplicitProperty()) 8848218893Sdim return getDerived().RebuildObjCPropertyRefExpr(Base.get(), 8849218893Sdim E->getExplicitProperty(), 8850218893Sdim E->getLocation()); 8851198092Srdivacky 8852218893Sdim return getDerived().RebuildObjCPropertyRefExpr(Base.get(), 8853234353Sdim SemaRef.Context.PseudoObjectTy, 8854218893Sdim E->getImplicitPropertyGetter(), 8855218893Sdim E->getImplicitPropertySetter(), 8856218893Sdim E->getLocation()); 8857198092Srdivacky} 8858198092Srdivacky 8859198092Srdivackytemplate<typename Derived> 8860212904SdimExprResult 8861234353SdimTreeTransform<Derived>::TransformObjCSubscriptRefExpr(ObjCSubscriptRefExpr *E) { 8862234353Sdim // Transform the base expression. 8863234353Sdim ExprResult Base = getDerived().TransformExpr(E->getBaseExpr()); 8864234353Sdim if (Base.isInvalid()) 8865234353Sdim return ExprError(); 8866234353Sdim 8867234353Sdim // Transform the key expression. 8868234353Sdim ExprResult Key = getDerived().TransformExpr(E->getKeyExpr()); 8869234353Sdim if (Key.isInvalid()) 8870234353Sdim return ExprError(); 8871234353Sdim 8872234353Sdim // If nothing changed, just retain the existing expression. 8873234353Sdim if (!getDerived().AlwaysRebuild() && 8874234353Sdim Key.get() == E->getKeyExpr() && Base.get() == E->getBaseExpr()) 8875234353Sdim return SemaRef.Owned(E); 8876234353Sdim 8877239462Sdim return getDerived().RebuildObjCSubscriptRefExpr(E->getRBracket(), 8878234353Sdim Base.get(), Key.get(), 8879234353Sdim E->getAtIndexMethodDecl(), 8880234353Sdim E->setAtIndexMethodDecl()); 8881234353Sdim} 8882234353Sdim 8883234353Sdimtemplate<typename Derived> 8884234353SdimExprResult 8885200583SrdivackyTreeTransform<Derived>::TransformObjCIsaExpr(ObjCIsaExpr *E) { 8886207619Srdivacky // Transform the base expression. 8887212904Sdim ExprResult Base = getDerived().TransformExpr(E->getBase()); 8888207619Srdivacky if (Base.isInvalid()) 8889212904Sdim return ExprError(); 8890239462Sdim 8891207619Srdivacky // If nothing changed, just retain the existing expression. 8892207619Srdivacky if (!getDerived().AlwaysRebuild() && 8893207619Srdivacky Base.get() == E->getBase()) 8894218893Sdim return SemaRef.Owned(E); 8895239462Sdim 8896212904Sdim return getDerived().RebuildObjCIsaExpr(Base.get(), E->getIsaMemberLoc(), 8897249423Sdim E->getOpLoc(), 8898207619Srdivacky E->isArrow()); 8899198092Srdivacky} 8900198092Srdivacky 8901198092Srdivackytemplate<typename Derived> 8902212904SdimExprResult 8903200583SrdivackyTreeTransform<Derived>::TransformShuffleVectorExpr(ShuffleVectorExpr *E) { 8904198092Srdivacky bool ArgumentChanged = false; 8905243830Sdim SmallVector<Expr*, 8> SubExprs; 8906218893Sdim SubExprs.reserve(E->getNumSubExprs()); 8907239462Sdim if (getDerived().TransformExprs(E->getSubExprs(), E->getNumSubExprs(), false, 8908218893Sdim SubExprs, &ArgumentChanged)) 8909218893Sdim return ExprError(); 8910198092Srdivacky 8911198092Srdivacky if (!getDerived().AlwaysRebuild() && 8912198092Srdivacky !ArgumentChanged) 8913218893Sdim return SemaRef.Owned(E); 8914198092Srdivacky 8915198092Srdivacky return getDerived().RebuildShuffleVectorExpr(E->getBuiltinLoc(), 8916243830Sdim SubExprs, 8917198092Srdivacky E->getRParenLoc()); 8918198092Srdivacky} 8919198092Srdivacky 8920198092Srdivackytemplate<typename Derived> 8921212904SdimExprResult 8922200583SrdivackyTreeTransform<Derived>::TransformBlockExpr(BlockExpr *E) { 8923218893Sdim BlockDecl *oldBlock = E->getBlockDecl(); 8924239462Sdim 8925218893Sdim SemaRef.ActOnBlockStart(E->getCaretLocation(), /*Scope=*/0); 8926218893Sdim BlockScopeInfo *blockScope = SemaRef.getCurBlock(); 8927218893Sdim 8928218893Sdim blockScope->TheDecl->setIsVariadic(oldBlock->isVariadic()); 8929234353Sdim blockScope->TheDecl->setBlockMissingReturnType( 8930234353Sdim oldBlock->blockMissingReturnType()); 8931239462Sdim 8932226633Sdim SmallVector<ParmVarDecl*, 4> params; 8933226633Sdim SmallVector<QualType, 4> paramTypes; 8934239462Sdim 8935210299Sed // Parameter substitution. 8936218893Sdim if (getDerived().TransformFunctionTypeParams(E->getCaretLocation(), 8937218893Sdim oldBlock->param_begin(), 8938218893Sdim oldBlock->param_size(), 8939234353Sdim 0, paramTypes, ¶ms)) { 8940234353Sdim getSema().ActOnBlockError(E->getCaretLocation(), /*Scope=*/0); 8941234353Sdim return ExprError(); 8942234353Sdim } 8943218893Sdim 8944249423Sdim const FunctionProtoType *exprFunctionType = E->getFunctionType(); 8945234353Sdim QualType exprResultType = 8946234353Sdim getDerived().TransformType(exprFunctionType->getResultType()); 8947218893Sdim 8948218893Sdim // Don't allow returning a objc interface by value. 8949234353Sdim if (exprResultType->isObjCObjectType()) { 8950239462Sdim getSema().Diag(E->getCaretLocation(), 8951239462Sdim diag::err_object_cannot_be_passed_returned_by_value) 8952234353Sdim << 0 << exprResultType; 8953234353Sdim getSema().ActOnBlockError(E->getCaretLocation(), /*Scope=*/0); 8954218893Sdim return ExprError(); 8955210299Sed } 8956218893Sdim 8957249423Sdim QualType functionType = 8958249423Sdim getDerived().RebuildFunctionProtoType(exprResultType, paramTypes, 8959249423Sdim exprFunctionType->getExtProtoInfo()); 8960218893Sdim blockScope->FunctionType = functionType; 8961218893Sdim 8962218893Sdim // Set the parameters on the block decl. 8963218893Sdim if (!params.empty()) 8964226633Sdim blockScope->TheDecl->setParams(params); 8965234353Sdim 8966234353Sdim if (!oldBlock->blockMissingReturnType()) { 8967234353Sdim blockScope->HasImplicitReturnType = false; 8968234353Sdim blockScope->ReturnType = exprResultType; 8969234353Sdim } 8970239462Sdim 8971210299Sed // Transform the body 8972218893Sdim StmtResult body = getDerived().TransformStmt(E->getBody()); 8973234353Sdim if (body.isInvalid()) { 8974234353Sdim getSema().ActOnBlockError(E->getCaretLocation(), /*Scope=*/0); 8975212904Sdim return ExprError(); 8976234353Sdim } 8977218893Sdim 8978218893Sdim#ifndef NDEBUG 8979218893Sdim // In builds with assertions, make sure that we captured everything we 8980218893Sdim // captured before. 8981223017Sdim if (!SemaRef.getDiagnostics().hasErrorOccurred()) { 8982223017Sdim for (BlockDecl::capture_iterator i = oldBlock->capture_begin(), 8983223017Sdim e = oldBlock->capture_end(); i != e; ++i) { 8984223017Sdim VarDecl *oldCapture = i->getVariable(); 8985218893Sdim 8986223017Sdim // Ignore parameter packs. 8987223017Sdim if (isa<ParmVarDecl>(oldCapture) && 8988223017Sdim cast<ParmVarDecl>(oldCapture)->isParameterPack()) 8989223017Sdim continue; 8990218893Sdim 8991223017Sdim VarDecl *newCapture = 8992223017Sdim cast<VarDecl>(getDerived().TransformDecl(E->getCaretLocation(), 8993223017Sdim oldCapture)); 8994223017Sdim assert(blockScope->CaptureMap.count(newCapture)); 8995223017Sdim } 8996234353Sdim assert(oldBlock->capturesCXXThis() == blockScope->isCXXThisCaptured()); 8997218893Sdim } 8998218893Sdim#endif 8999218893Sdim 9000218893Sdim return SemaRef.ActOnBlockStmtExpr(E->getCaretLocation(), body.get(), 9001218893Sdim /*Scope=*/0); 9002198092Srdivacky} 9003198092Srdivacky 9004198092Srdivackytemplate<typename Derived> 9005212904SdimExprResult 9006223017SdimTreeTransform<Derived>::TransformAsTypeExpr(AsTypeExpr *E) { 9007226633Sdim llvm_unreachable("Cannot transform asType expressions yet"); 9008223017Sdim} 9009226633Sdim 9010226633Sdimtemplate<typename Derived> 9011226633SdimExprResult 9012226633SdimTreeTransform<Derived>::TransformAtomicExpr(AtomicExpr *E) { 9013226633Sdim QualType RetTy = getDerived().TransformType(E->getType()); 9014226633Sdim bool ArgumentChanged = false; 9015243830Sdim SmallVector<Expr*, 8> SubExprs; 9016226633Sdim SubExprs.reserve(E->getNumSubExprs()); 9017226633Sdim if (getDerived().TransformExprs(E->getSubExprs(), E->getNumSubExprs(), false, 9018226633Sdim SubExprs, &ArgumentChanged)) 9019226633Sdim return ExprError(); 9020226633Sdim 9021226633Sdim if (!getDerived().AlwaysRebuild() && 9022226633Sdim !ArgumentChanged) 9023226633Sdim return SemaRef.Owned(E); 9024226633Sdim 9025243830Sdim return getDerived().RebuildAtomicExpr(E->getBuiltinLoc(), SubExprs, 9026226633Sdim RetTy, E->getOp(), E->getRParenLoc()); 9027226633Sdim} 9028239462Sdim 9029198092Srdivacky//===----------------------------------------------------------------------===// 9030198092Srdivacky// Type reconstruction 9031198092Srdivacky//===----------------------------------------------------------------------===// 9032198092Srdivacky 9033198092Srdivackytemplate<typename Derived> 9034198893SrdivackyQualType TreeTransform<Derived>::RebuildPointerType(QualType PointeeType, 9035198893Srdivacky SourceLocation Star) { 9036210299Sed return SemaRef.BuildPointerType(PointeeType, Star, 9037198092Srdivacky getDerived().getBaseEntity()); 9038198092Srdivacky} 9039198092Srdivacky 9040198092Srdivackytemplate<typename Derived> 9041198893SrdivackyQualType TreeTransform<Derived>::RebuildBlockPointerType(QualType PointeeType, 9042198893Srdivacky SourceLocation Star) { 9043210299Sed return SemaRef.BuildBlockPointerType(PointeeType, Star, 9044198092Srdivacky getDerived().getBaseEntity()); 9045198092Srdivacky} 9046198092Srdivacky 9047198092Srdivackytemplate<typename Derived> 9048198092SrdivackyQualType 9049198893SrdivackyTreeTransform<Derived>::RebuildReferenceType(QualType ReferentType, 9050198893Srdivacky bool WrittenAsLValue, 9051198893Srdivacky SourceLocation Sigil) { 9052210299Sed return SemaRef.BuildReferenceType(ReferentType, WrittenAsLValue, 9053198893Srdivacky Sigil, getDerived().getBaseEntity()); 9054198092Srdivacky} 9055198092Srdivacky 9056198092Srdivackytemplate<typename Derived> 9057198092SrdivackyQualType 9058198893SrdivackyTreeTransform<Derived>::RebuildMemberPointerType(QualType PointeeType, 9059198893Srdivacky QualType ClassType, 9060198893Srdivacky SourceLocation Sigil) { 9061210299Sed return SemaRef.BuildMemberPointerType(PointeeType, ClassType, 9062198893Srdivacky Sigil, getDerived().getBaseEntity()); 9063198092Srdivacky} 9064198092Srdivacky 9065198092Srdivackytemplate<typename Derived> 9066198092SrdivackyQualType 9067198092SrdivackyTreeTransform<Derived>::RebuildArrayType(QualType ElementType, 9068198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 9069198092Srdivacky const llvm::APInt *Size, 9070198092Srdivacky Expr *SizeExpr, 9071198092Srdivacky unsigned IndexTypeQuals, 9072198092Srdivacky SourceRange BracketsRange) { 9073198092Srdivacky if (SizeExpr || !Size) 9074198092Srdivacky return SemaRef.BuildArrayType(ElementType, SizeMod, SizeExpr, 9075198092Srdivacky IndexTypeQuals, BracketsRange, 9076198092Srdivacky getDerived().getBaseEntity()); 9077198092Srdivacky 9078198092Srdivacky QualType Types[] = { 9079198092Srdivacky SemaRef.Context.UnsignedCharTy, SemaRef.Context.UnsignedShortTy, 9080198092Srdivacky SemaRef.Context.UnsignedIntTy, SemaRef.Context.UnsignedLongTy, 9081198092Srdivacky SemaRef.Context.UnsignedLongLongTy, SemaRef.Context.UnsignedInt128Ty 9082198092Srdivacky }; 9083198092Srdivacky const unsigned NumTypes = sizeof(Types) / sizeof(QualType); 9084198092Srdivacky QualType SizeType; 9085198092Srdivacky for (unsigned I = 0; I != NumTypes; ++I) 9086198092Srdivacky if (Size->getBitWidth() == SemaRef.Context.getIntWidth(Types[I])) { 9087198092Srdivacky SizeType = Types[I]; 9088198092Srdivacky break; 9089198092Srdivacky } 9090198092Srdivacky 9091234353Sdim // Note that we can return a VariableArrayType here in the case where 9092234353Sdim // the element type was a dependent VariableArrayType. 9093234353Sdim IntegerLiteral *ArraySize 9094234353Sdim = IntegerLiteral::Create(SemaRef.Context, *Size, SizeType, 9095234353Sdim /*FIXME*/BracketsRange.getBegin()); 9096234353Sdim return SemaRef.BuildArrayType(ElementType, SizeMod, ArraySize, 9097198092Srdivacky IndexTypeQuals, BracketsRange, 9098198092Srdivacky getDerived().getBaseEntity()); 9099198092Srdivacky} 9100198092Srdivacky 9101198092Srdivackytemplate<typename Derived> 9102198092SrdivackyQualType 9103198092SrdivackyTreeTransform<Derived>::RebuildConstantArrayType(QualType ElementType, 9104198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 9105198092Srdivacky const llvm::APInt &Size, 9106198893Srdivacky unsigned IndexTypeQuals, 9107198893Srdivacky SourceRange BracketsRange) { 9108198092Srdivacky return getDerived().RebuildArrayType(ElementType, SizeMod, &Size, 0, 9109198893Srdivacky IndexTypeQuals, BracketsRange); 9110198092Srdivacky} 9111198092Srdivacky 9112198092Srdivackytemplate<typename Derived> 9113198092SrdivackyQualType 9114198092SrdivackyTreeTransform<Derived>::RebuildIncompleteArrayType(QualType ElementType, 9115198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 9116198893Srdivacky unsigned IndexTypeQuals, 9117198893Srdivacky SourceRange BracketsRange) { 9118198092Srdivacky return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 0, 9119198893Srdivacky IndexTypeQuals, BracketsRange); 9120198092Srdivacky} 9121198092Srdivacky 9122198092Srdivackytemplate<typename Derived> 9123198092SrdivackyQualType 9124198092SrdivackyTreeTransform<Derived>::RebuildVariableArrayType(QualType ElementType, 9125198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 9126212904Sdim Expr *SizeExpr, 9127198092Srdivacky unsigned IndexTypeQuals, 9128198092Srdivacky SourceRange BracketsRange) { 9129198092Srdivacky return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 9130212904Sdim SizeExpr, 9131198092Srdivacky IndexTypeQuals, BracketsRange); 9132198092Srdivacky} 9133198092Srdivacky 9134198092Srdivackytemplate<typename Derived> 9135198092SrdivackyQualType 9136198092SrdivackyTreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType, 9137198092Srdivacky ArrayType::ArraySizeModifier SizeMod, 9138212904Sdim Expr *SizeExpr, 9139198092Srdivacky unsigned IndexTypeQuals, 9140198092Srdivacky SourceRange BracketsRange) { 9141198092Srdivacky return getDerived().RebuildArrayType(ElementType, SizeMod, 0, 9142212904Sdim SizeExpr, 9143198092Srdivacky IndexTypeQuals, BracketsRange); 9144198092Srdivacky} 9145198092Srdivacky 9146198092Srdivackytemplate<typename Derived> 9147198092SrdivackyQualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType, 9148218893Sdim unsigned NumElements, 9149218893Sdim VectorType::VectorKind VecKind) { 9150198092Srdivacky // FIXME: semantic checking! 9151218893Sdim return SemaRef.Context.getVectorType(ElementType, NumElements, VecKind); 9152198092Srdivacky} 9153198092Srdivacky 9154198092Srdivackytemplate<typename Derived> 9155198092SrdivackyQualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType, 9156198092Srdivacky unsigned NumElements, 9157198092Srdivacky SourceLocation AttributeLoc) { 9158198092Srdivacky llvm::APInt numElements(SemaRef.Context.getIntWidth(SemaRef.Context.IntTy), 9159198092Srdivacky NumElements, true); 9160198092Srdivacky IntegerLiteral *VectorSize 9161212904Sdim = IntegerLiteral::Create(SemaRef.Context, numElements, SemaRef.Context.IntTy, 9162212904Sdim AttributeLoc); 9163212904Sdim return SemaRef.BuildExtVectorType(ElementType, VectorSize, AttributeLoc); 9164198092Srdivacky} 9165198092Srdivacky 9166198092Srdivackytemplate<typename Derived> 9167198092SrdivackyQualType 9168198092SrdivackyTreeTransform<Derived>::RebuildDependentSizedExtVectorType(QualType ElementType, 9169212904Sdim Expr *SizeExpr, 9170198092Srdivacky SourceLocation AttributeLoc) { 9171212904Sdim return SemaRef.BuildExtVectorType(ElementType, SizeExpr, AttributeLoc); 9172198092Srdivacky} 9173198092Srdivacky 9174198092Srdivackytemplate<typename Derived> 9175249423SdimQualType TreeTransform<Derived>::RebuildFunctionProtoType( 9176249423Sdim QualType T, 9177249423Sdim llvm::MutableArrayRef<QualType> ParamTypes, 9178249423Sdim const FunctionProtoType::ExtProtoInfo &EPI) { 9179249423Sdim return SemaRef.BuildFunctionType(T, ParamTypes, 9180198092Srdivacky getDerived().getBaseLocation(), 9181212904Sdim getDerived().getBaseEntity(), 9182249423Sdim EPI); 9183198092Srdivacky} 9184198092Srdivacky 9185198092Srdivackytemplate<typename Derived> 9186198398SrdivackyQualType TreeTransform<Derived>::RebuildFunctionNoProtoType(QualType T) { 9187198398Srdivacky return SemaRef.Context.getFunctionNoProtoType(T); 9188198398Srdivacky} 9189198398Srdivacky 9190198398Srdivackytemplate<typename Derived> 9191200583SrdivackyQualType TreeTransform<Derived>::RebuildUnresolvedUsingType(Decl *D) { 9192200583Srdivacky assert(D && "no decl found"); 9193200583Srdivacky if (D->isInvalidDecl()) return QualType(); 9194200583Srdivacky 9195207619Srdivacky // FIXME: Doesn't account for ObjCInterfaceDecl! 9196200583Srdivacky TypeDecl *Ty; 9197200583Srdivacky if (isa<UsingDecl>(D)) { 9198200583Srdivacky UsingDecl *Using = cast<UsingDecl>(D); 9199200583Srdivacky assert(Using->isTypeName() && 9200200583Srdivacky "UnresolvedUsingTypenameDecl transformed to non-typename using"); 9201200583Srdivacky 9202200583Srdivacky // A valid resolved using typename decl points to exactly one type decl. 9203200583Srdivacky assert(++Using->shadow_begin() == Using->shadow_end()); 9204200583Srdivacky Ty = cast<TypeDecl>((*Using->shadow_begin())->getTargetDecl()); 9205239462Sdim 9206200583Srdivacky } else { 9207200583Srdivacky assert(isa<UnresolvedUsingTypenameDecl>(D) && 9208200583Srdivacky "UnresolvedUsingTypenameDecl transformed to non-using decl"); 9209200583Srdivacky Ty = cast<UnresolvedUsingTypenameDecl>(D); 9210200583Srdivacky } 9211200583Srdivacky 9212200583Srdivacky return SemaRef.Context.getTypeDeclType(Ty); 9213200583Srdivacky} 9214200583Srdivacky 9215200583Srdivackytemplate<typename Derived> 9216218893SdimQualType TreeTransform<Derived>::RebuildTypeOfExprType(Expr *E, 9217218893Sdim SourceLocation Loc) { 9218218893Sdim return SemaRef.BuildTypeofExprType(E, Loc); 9219198092Srdivacky} 9220198092Srdivacky 9221198092Srdivackytemplate<typename Derived> 9222198092SrdivackyQualType TreeTransform<Derived>::RebuildTypeOfType(QualType Underlying) { 9223198092Srdivacky return SemaRef.Context.getTypeOfType(Underlying); 9224198092Srdivacky} 9225198092Srdivacky 9226198092Srdivackytemplate<typename Derived> 9227218893SdimQualType TreeTransform<Derived>::RebuildDecltypeType(Expr *E, 9228218893Sdim SourceLocation Loc) { 9229218893Sdim return SemaRef.BuildDecltypeType(E, Loc); 9230198092Srdivacky} 9231198092Srdivacky 9232198092Srdivackytemplate<typename Derived> 9233223017SdimQualType TreeTransform<Derived>::RebuildUnaryTransformType(QualType BaseType, 9234223017Sdim UnaryTransformType::UTTKind UKind, 9235223017Sdim SourceLocation Loc) { 9236223017Sdim return SemaRef.BuildUnaryTransformType(BaseType, UKind, Loc); 9237223017Sdim} 9238223017Sdim 9239223017Sdimtemplate<typename Derived> 9240198092SrdivackyQualType TreeTransform<Derived>::RebuildTemplateSpecializationType( 9241198893Srdivacky TemplateName Template, 9242198893Srdivacky SourceLocation TemplateNameLoc, 9243221345Sdim TemplateArgumentListInfo &TemplateArgs) { 9244199990Srdivacky return SemaRef.CheckTemplateIdType(Template, TemplateNameLoc, TemplateArgs); 9245198092Srdivacky} 9246198092Srdivacky 9247198092Srdivackytemplate<typename Derived> 9248226633SdimQualType TreeTransform<Derived>::RebuildAtomicType(QualType ValueType, 9249226633Sdim SourceLocation KWLoc) { 9250226633Sdim return SemaRef.BuildAtomicType(ValueType, KWLoc); 9251226633Sdim} 9252226633Sdim 9253226633Sdimtemplate<typename Derived> 9254198092SrdivackyTemplateName 9255221345SdimTreeTransform<Derived>::RebuildTemplateName(CXXScopeSpec &SS, 9256198092Srdivacky bool TemplateKW, 9257198092Srdivacky TemplateDecl *Template) { 9258221345Sdim return SemaRef.Context.getQualifiedTemplateName(SS.getScopeRep(), TemplateKW, 9259198092Srdivacky Template); 9260198092Srdivacky} 9261198092Srdivacky 9262198092Srdivackytemplate<typename Derived> 9263198092SrdivackyTemplateName 9264221345SdimTreeTransform<Derived>::RebuildTemplateName(CXXScopeSpec &SS, 9265221345Sdim const IdentifierInfo &Name, 9266221345Sdim SourceLocation NameLoc, 9267218893Sdim QualType ObjectType, 9268218893Sdim NamedDecl *FirstQualifierInScope) { 9269221345Sdim UnqualifiedId TemplateName; 9270221345Sdim TemplateName.setIdentifier(&Name, NameLoc); 9271210299Sed Sema::TemplateTy Template; 9272234353Sdim SourceLocation TemplateKWLoc; // FIXME: retrieve it from caller. 9273210299Sed getSema().ActOnDependentTemplateName(/*Scope=*/0, 9274234353Sdim SS, TemplateKWLoc, TemplateName, 9275212904Sdim ParsedType::make(ObjectType), 9276210299Sed /*EnteringContext=*/false, 9277210299Sed Template); 9278218893Sdim return Template.get(); 9279198092Srdivacky} 9280198092Srdivacky 9281198092Srdivackytemplate<typename Derived> 9282198893SrdivackyTemplateName 9283221345SdimTreeTransform<Derived>::RebuildTemplateName(CXXScopeSpec &SS, 9284198893Srdivacky OverloadedOperatorKind Operator, 9285221345Sdim SourceLocation NameLoc, 9286198893Srdivacky QualType ObjectType) { 9287198893Srdivacky UnqualifiedId Name; 9288221345Sdim // FIXME: Bogus location information. 9289234353Sdim SourceLocation SymbolLocations[3] = { NameLoc, NameLoc, NameLoc }; 9290221345Sdim Name.setOperatorFunctionId(NameLoc, Operator, SymbolLocations); 9291234353Sdim SourceLocation TemplateKWLoc; // FIXME: retrieve it from caller. 9292210299Sed Sema::TemplateTy Template; 9293210299Sed getSema().ActOnDependentTemplateName(/*Scope=*/0, 9294234353Sdim SS, TemplateKWLoc, Name, 9295212904Sdim ParsedType::make(ObjectType), 9296210299Sed /*EnteringContext=*/false, 9297210299Sed Template); 9298210299Sed return Template.template getAsVal<TemplateName>(); 9299198893Srdivacky} 9300239462Sdim 9301198893Srdivackytemplate<typename Derived> 9302212904SdimExprResult 9303198092SrdivackyTreeTransform<Derived>::RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op, 9304198092Srdivacky SourceLocation OpLoc, 9305212904Sdim Expr *OrigCallee, 9306212904Sdim Expr *First, 9307212904Sdim Expr *Second) { 9308212904Sdim Expr *Callee = OrigCallee->IgnoreParenCasts(); 9309212904Sdim bool isPostIncDec = Second && (Op == OO_PlusPlus || Op == OO_MinusMinus); 9310198092Srdivacky 9311198092Srdivacky // Determine whether this should be a builtin operation. 9312198893Srdivacky if (Op == OO_Subscript) { 9313212904Sdim if (!First->getType()->isOverloadableType() && 9314212904Sdim !Second->getType()->isOverloadableType()) 9315212904Sdim return getSema().CreateBuiltinArraySubscriptExpr(First, 9316212904Sdim Callee->getLocStart(), 9317212904Sdim Second, OpLoc); 9318199482Srdivacky } else if (Op == OO_Arrow) { 9319199482Srdivacky // -> is never a builtin operation. 9320212904Sdim return SemaRef.BuildOverloadedArrowExpr(0, First, OpLoc); 9321212904Sdim } else if (Second == 0 || isPostIncDec) { 9322212904Sdim if (!First->getType()->isOverloadableType()) { 9323198092Srdivacky // The argument is not of overloadable type, so try to create a 9324198092Srdivacky // built-in unary operation. 9325212904Sdim UnaryOperatorKind Opc 9326198092Srdivacky = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec); 9327198092Srdivacky 9328212904Sdim return getSema().CreateBuiltinUnaryOp(OpLoc, Opc, First); 9329198092Srdivacky } 9330198092Srdivacky } else { 9331212904Sdim if (!First->getType()->isOverloadableType() && 9332212904Sdim !Second->getType()->isOverloadableType()) { 9333198092Srdivacky // Neither of the arguments is an overloadable type, so try to 9334198092Srdivacky // create a built-in binary operation. 9335212904Sdim BinaryOperatorKind Opc = BinaryOperator::getOverloadedOpcode(Op); 9336212904Sdim ExprResult Result 9337212904Sdim = SemaRef.CreateBuiltinBinOp(OpLoc, Opc, First, Second); 9338198092Srdivacky if (Result.isInvalid()) 9339212904Sdim return ExprError(); 9340198092Srdivacky 9341243830Sdim return Result; 9342198092Srdivacky } 9343198092Srdivacky } 9344198092Srdivacky 9345198092Srdivacky // Compute the transformed set of functions (and function templates) to be 9346198092Srdivacky // used during overload resolution. 9347203955Srdivacky UnresolvedSet<16> Functions; 9348198092Srdivacky 9349212904Sdim if (UnresolvedLookupExpr *ULE = dyn_cast<UnresolvedLookupExpr>(Callee)) { 9350199990Srdivacky assert(ULE->requiresADL()); 9351198092Srdivacky 9352199990Srdivacky // FIXME: Do we have to check 9353199990Srdivacky // IsAcceptableNonMemberOperatorCandidate for each of these? 9354203955Srdivacky Functions.append(ULE->decls_begin(), ULE->decls_end()); 9355199990Srdivacky } else { 9356243830Sdim // If we've resolved this to a particular non-member function, just call 9357243830Sdim // that function. If we resolved it to a member function, 9358243830Sdim // CreateOverloaded* will find that function for us. 9359243830Sdim NamedDecl *ND = cast<DeclRefExpr>(Callee)->getDecl(); 9360243830Sdim if (!isa<CXXMethodDecl>(ND)) 9361243830Sdim Functions.addDecl(ND); 9362199990Srdivacky } 9363199990Srdivacky 9364198092Srdivacky // Add any functions found via argument-dependent lookup. 9365212904Sdim Expr *Args[2] = { First, Second }; 9366212904Sdim unsigned NumArgs = 1 + (Second != 0); 9367198092Srdivacky 9368198092Srdivacky // Create the overloaded operator invocation for unary operators. 9369198092Srdivacky if (NumArgs == 1 || isPostIncDec) { 9370212904Sdim UnaryOperatorKind Opc 9371198092Srdivacky = UnaryOperator::getOverloadedOpcode(Op, isPostIncDec); 9372212904Sdim return SemaRef.CreateOverloadedUnaryOp(OpLoc, Opc, Functions, First); 9373198092Srdivacky } 9374198092Srdivacky 9375224145Sdim if (Op == OO_Subscript) { 9376224145Sdim SourceLocation LBrace; 9377224145Sdim SourceLocation RBrace; 9378198893Srdivacky 9379224145Sdim if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(Callee)) { 9380224145Sdim DeclarationNameLoc &NameLoc = DRE->getNameInfo().getInfo(); 9381224145Sdim LBrace = SourceLocation::getFromRawEncoding( 9382224145Sdim NameLoc.CXXOperatorName.BeginOpNameLoc); 9383224145Sdim RBrace = SourceLocation::getFromRawEncoding( 9384224145Sdim NameLoc.CXXOperatorName.EndOpNameLoc); 9385224145Sdim } else { 9386224145Sdim LBrace = Callee->getLocStart(); 9387224145Sdim RBrace = OpLoc; 9388224145Sdim } 9389224145Sdim 9390224145Sdim return SemaRef.CreateOverloadedArraySubscriptExpr(LBrace, RBrace, 9391224145Sdim First, Second); 9392224145Sdim } 9393224145Sdim 9394198092Srdivacky // Create the overloaded operator invocation for binary operators. 9395212904Sdim BinaryOperatorKind Opc = BinaryOperator::getOverloadedOpcode(Op); 9396212904Sdim ExprResult Result 9397198092Srdivacky = SemaRef.CreateOverloadedBinOp(OpLoc, Opc, Functions, Args[0], Args[1]); 9398198092Srdivacky if (Result.isInvalid()) 9399212904Sdim return ExprError(); 9400198092Srdivacky 9401243830Sdim return Result; 9402198092Srdivacky} 9403198092Srdivacky 9404204643Srdivackytemplate<typename Derived> 9405239462SdimExprResult 9406212904SdimTreeTransform<Derived>::RebuildCXXPseudoDestructorExpr(Expr *Base, 9407204643Srdivacky SourceLocation OperatorLoc, 9408204643Srdivacky bool isArrow, 9409219077Sdim CXXScopeSpec &SS, 9410204643Srdivacky TypeSourceInfo *ScopeType, 9411204643Srdivacky SourceLocation CCLoc, 9412204643Srdivacky SourceLocation TildeLoc, 9413204643Srdivacky PseudoDestructorTypeStorage Destroyed) { 9414212904Sdim QualType BaseType = Base->getType(); 9415212904Sdim if (Base->isTypeDependent() || Destroyed.getIdentifier() || 9416204643Srdivacky (!isArrow && !BaseType->getAs<RecordType>()) || 9417239462Sdim (isArrow && BaseType->getAs<PointerType>() && 9418204643Srdivacky !BaseType->getAs<PointerType>()->getPointeeType() 9419204643Srdivacky ->template getAs<RecordType>())){ 9420204643Srdivacky // This pseudo-destructor expression is still a pseudo-destructor. 9421212904Sdim return SemaRef.BuildPseudoDestructorExpr(Base, OperatorLoc, 9422204643Srdivacky isArrow? tok::arrow : tok::period, 9423204643Srdivacky SS, ScopeType, CCLoc, TildeLoc, 9424204643Srdivacky Destroyed, 9425204643Srdivacky /*FIXME?*/true); 9426204643Srdivacky } 9427212904Sdim 9428204643Srdivacky TypeSourceInfo *DestroyedType = Destroyed.getTypeSourceInfo(); 9429212904Sdim DeclarationName Name(SemaRef.Context.DeclarationNames.getCXXDestructorName( 9430212904Sdim SemaRef.Context.getCanonicalType(DestroyedType->getType()))); 9431212904Sdim DeclarationNameInfo NameInfo(Name, Destroyed.getLocation()); 9432212904Sdim NameInfo.setNamedTypeInfo(DestroyedType); 9433212904Sdim 9434239462Sdim // The scope type is now known to be a valid nested name specifier 9435239462Sdim // component. Tack it on to the end of the nested name specifier. 9436239462Sdim if (ScopeType) 9437239462Sdim SS.Extend(SemaRef.Context, SourceLocation(), 9438239462Sdim ScopeType->getTypeLoc(), CCLoc); 9439212904Sdim 9440234353Sdim SourceLocation TemplateKWLoc; // FIXME: retrieve it from caller. 9441212904Sdim return getSema().BuildMemberReferenceExpr(Base, BaseType, 9442204643Srdivacky OperatorLoc, isArrow, 9443234353Sdim SS, TemplateKWLoc, 9444234353Sdim /*FIXME: FirstQualifier*/ 0, 9445212904Sdim NameInfo, 9446204643Srdivacky /*TemplateArgs*/ 0); 9447204643Srdivacky} 9448204643Srdivacky 9449251662Sdimtemplate<typename Derived> 9450251662SdimStmtResult 9451251662SdimTreeTransform<Derived>::TransformCapturedStmt(CapturedStmt *S) { 9452251662Sdim SourceLocation Loc = S->getLocStart(); 9453251662Sdim unsigned NumParams = S->getCapturedDecl()->getNumParams(); 9454251662Sdim getSema().ActOnCapturedRegionStart(Loc, /*CurScope*/0, 9455251662Sdim S->getCapturedRegionKind(), NumParams); 9456251662Sdim StmtResult Body = getDerived().TransformStmt(S->getCapturedStmt()); 9457251662Sdim 9458251662Sdim if (Body.isInvalid()) { 9459251662Sdim getSema().ActOnCapturedRegionError(); 9460251662Sdim return StmtError(); 9461251662Sdim } 9462251662Sdim 9463251662Sdim return getSema().ActOnCapturedRegionEnd(Body.take()); 9464251662Sdim} 9465251662Sdim 9466198092Srdivacky} // end namespace clang 9467198092Srdivacky 9468198092Srdivacky#endif // LLVM_CLANG_SEMA_TREETRANSFORM_H 9469